Een Wagtail-taalschakelaar testen met Factory Boy

In deze tutorial zullen we een taalschakelaar testen die de gebruiker op dezelfde pagina houdt en in staat is om Wagtail-pagina's en pagina's buiten de Wagtail-boom te verwerken.

15 juli 2020 13:27
Thema's: Meerdere talen Testen

In een eerdere tutorial hebben we zo'n taalschakelaar ontwikkeld. Om hem te testen hebben we een site nodig met enkele pagina's erin. In een andere tutorial hebben we hiervoor een klein raamwerk opgezet met Factory Boy. We hergebruiken dit om onze testgegevens in te stellen in een bestand /tests/test_language.py:

from .factories import HomePageFactory, ArticlePageFactory, ArticleIndexPageFactory
from django.conf import settings
from django.test import TestCase, RequestFactory, Client
from wagtail.core.models import Page, Site
from wagtailtrans.models import Language, TranslatablePage

class TestChangeLanguageViews(TestCase):

    @classmethod
    def setUpTestData(cls):
        cls.client = Client()
        cls.factory = RequestFactory()
        cls.site = Site.objects.create(is_default_site=True, root_page=Page.get_first_root_node())
        cls.homepage = HomePageFactory()
        cls.articleindexpage = ArticleIndexPageFactory(parent=cls.homepage)
        cls.articlepage1 = ArticlePageFactory(parent=cls.articleindexpage)
        cls.foreign_language_code = [code for code, lang in settings.LANGUAGES if code != settings.LANGUAGE_CODE][0]
        # note: Wagtailtrans automatically creates a language tree for every language that is defined
        cls.foreign_language = Language.objects.get_or_create(code=cls.foreign_language_code)[0]
        cls.foreign_articlepage1 = TranslatablePage.objects.get(language=cls.foreign_language,
                                                              canonical_page=cls.articlepage1)

Voor onze tests hebben we de client en de request factory van Django nodig. De Page instanties homepage, articleindexpage en articlepage1 worden op dezelfde manier gemaakt als in de eerdere tutorial. We hebben ook de vreemde-taalcode en de buitenlandse versie van de artikelpagina gezien bij het testen van ons menu. Tijd voor onze eerste test: controleer of de view set_language_from_url ons correct naar de startpagina brengt in de gevraagde taal als er geen vorige pagina is gegeven. We gebruiken de Django-testclient om een response te krijgen vanuit de url van onze view:

from django.urls import reverse

def test_change_language_without_previous_page(self):
    response = self.client.get(
        reverse('set_language_from_url', kwargs={'language_code': self.foreign_language_code}))
    expected_url = '/' + self.foreign_language_code + '/'
    self.assertEquals(response.url, expected_url)

De test wordt als volgt uitgevoerd:

python3 manage.py test cms.tests.test_languages

Als de vorige pagina een url heeft buiten de Wagtail-boom, zoals /accounts/login/, zou de functie set_language_from_url ons naar de vertaalde versie hiervan moeten brengen:

from django.utils import translation

def test_change_language_of_login_url(self):
    # get the url from the get_language_from_url view and make a request object
    url = reverse('set_language_from_url', kwargs={'language_code': self.foreign_language_code})
    request = self.factory.get(url)

    # manually set the HTTP_REFERER value to login url
    request.META['HTTP_REFERER'] = '/' + settings.LANGUAGE_CODE + '/accounts/login/'
    translation.activate(settings.LANGUAGE_CODE)
    response = set_language_from_url(request, self.foreign_language_code)
    expected_url = '/' + self.foreign_language_code + '/accounts/login/'
    self.assertEquals(response.url, expected_url)

We hebben een request object nodig, omdat we de HTTP_REFERER-informatie eraan moeten toevoegen, dus gebruiken we de Django request factory. We simuleren dat de vorige pagina in de standaardtaal is en activeren die taal, en roepen dan onze functie aan. We verwachten dat onze functie de url vertaalt met het voorvoegsel van de vreemde taal. Het uitvoeren van de test vertelt ons of alles werkt zoals verwacht.

Ten slotte testen we of set_language_from_url hetzelfde doet als de verwijzende pagina deel uitmaakt van de Wagtail-boom, namelijk artikelpagina1. De volgorde is hetzelfde: definieer de url en de request, voeg de verwijzende pagina eraan toe, stel de taal in en roep de functie aan om te zien of die de vertaling goed doet:

def test_change_language_from_canonical_page(self):
    # get the url, make a request object and set the HTTP_REFERER
    url = reverse('set_language_from_url', kwargs={'language_code': self.foreign_language_code})
    request = self.factory.get(url)
    request.META['HTTP_REFERER'] = str(self.articlepage1.url)
    translation.activate(settings.LANGUAGE_CODE)
    response = set_language_from_url(request, self.foreign_language_code)
    self.assertEqual(response.url, self.foreign_articlepage1.url)

Bekijk de code-coverage:

coverage run --source=cms manage.py test cms

Onze views.py is voldoende gedekt. Op naar het testen van onze commentaarfunctionaliteit en onze streamforms.

Reageer op dit artikel (log eerst in of bevestig hieronder met naam en email)