2014-04-15 6 views
16

mam problemy z testowania ViewSet:Django Rest Framework - Jak przetestować ViewSet?

class ViewSetTest(TestCase): 
    def test_view_set(self): 
     factory = APIRequestFactory() 
     view = CatViewSet.as_view() 
     cat = Cat(name="bob") 
     cat.save() 

     request = factory.get(reverse('cat-detail', args=(cat.pk,))) 
     response = view(request) 

Próbuję replikować składni tutaj:

http://www.django-rest-framework.org/api-guide/testing#forcing-authentication

Ale myślę, że ich widok AccountDetail różni się od mojego ViewSet, więc Otrzymuję ten błąd z ostatniej linii:

AttributeError: 'NoneType' object has no attributes 'items' 

Czy istnieje poprawna składnia tutaj lub czy mieszam co ncepts? Moje testy APIClient działają, ale używam tutaj fabryki, ponieważ w końcu chciałbym dodać "request.user = some_user". Z góry dziękuję!

Oh i testy klient działa poprawnie:

def test_client_view(self): 
    response = APIClient().get(reverse('cat-detail', args=(cat.pk,))) 
    self.assertEqual(response.status_code, 200) 

Odpowiedz

3

myślę, że to twoja ostatnia linia. Musisz zadzwonić do CatViewSet as_view(). pójdę z:

response = view(request) 

skoro już zdefiniowane view = CatViewSet.as_view()

EDIT:

można pokazać swoją views.py? Konkretnie, jakiego rodzaju używasz ViewSet? Przeszukuję kod DRF i wygląda na to, że nie masz żadnych akcji mapowanych do twojego zestawu ViewSet, co powoduje błąd.

+0

przykro mi kopiowane ostatnią linię źle, edytowane, aby naprawić ten błąd – WBC

+0

Która linia w kod rzuca błąd? – Alex

+0

ostatnia linia, jestem w stanie przejść do debuggera przed nim, wszystko jest zdefiniowane, ale myślę, że może jest coś specjalnego w przekazywaniu wniosku do ViewSet? – WBC

12

Chyba znalazłem poprawnej składni, ale nie wiem, czy jest to konwencjonalny (wciąż nowe do Django):

def test_view_set(self): 
    request = APIRequestFactory().get("") 
    cat_detail = CatViewSet.as_view({'get': 'retrieve'}) 
    cat = Cat.objects.create(name="bob") 
    response = cat_detail(request, pk=cat.pk) 
    self.assertEqual(response.status_code, 200) 

Więc teraz to przechodzi i mogę przypisać request.user, która pozwala mi dostosować metodę pobierania w CatViewSet, aby rozważyć użytkownika.

7

Miałem ten sam problem i udało mi się znaleźć rozwiązanie.

Patrząc na kod źródłowy, wygląda na to, że widok oczekuje argumentów "działań", które zawierają elementy metody (czyli dyktando).

https://github.com/tomchristie/django-rest-framework/blob/master/rest_framework/viewsets.py#L69

To gdzie błąd dostajesz pochodzi. Będziesz musiał określić działania argumentów za pomocą dyktanda zawierającego dozwolone akcje dla tego zestawu widoków, a następnie będziesz mógł poprawnie przetestować ten zestaw.

Ogólny odwzorowanie idzie:

{ 
    'get': 'retrieve', 
    'put': 'update', 
    'patch': 'partial_update', 
    'delete': 'destroy' 
} 

http://www.django-rest-framework.org/tutorial/6-viewsets-and-routers

W twoim przypadku będziemy chcieli { 'get': 'odzyskać'} tak:

class ViewSetTest(TestCase): 
    def test_view_set(self): 
     factory = APIRequestFactory() 
     view = CatViewSet.as_view(actions={'get': 'retrieve'}) # <-- Changed line 
     cat = Cat(name="bob") 
     cat.save() 

     request = factory.get(reverse('cat-detail', args=(cat.pk,))) 
     response = view(request) 

EDIT: Musisz podać wymagane czynności. Zmieniono kod i komentarze, aby to odzwierciedlić.

3

znalazłem sposób to zrobić bez konieczności ręcznego tworzenia właściwej viewset i nadać jej odwzorowanie Działanie:

from django.core.urlresolvers import reverse, resolve 
... 
url = reverse('cat-list') 
req = factory.get(url) 
view = resolve(url).func 
response = view(req) 
response.render()