Come faccio a importare l'eccezione Django DoesNotExist?


122

Sto cercando di creare un UnitTest per verificare che un oggetto sia stato eliminato.

from django.utils import unittest
def test_z_Kallie_can_delete_discussion_response(self):
  ...snip...
  self._driver.get("http://localhost:8000/questions/3/want-a-discussion") 
  self.assertRaises(Answer.DoesNotExist, Answer.objects.get(body__exact = '<p>User can reply to discussion.</p>'))

Continuo a ricevere l'errore:

DoesNotExist: Answer matching query does not exist.

Non correlato alla mia risposta di seguito, la chiamata get () sta eliminando la risposta in questione? Se è così, in realtà dovrebbe essere un DELETE, non un GET.
Steve Jalim

Risposte:


136

Non è necessario importarlo - come hai già scritto correttamente, DoesNotExistè una proprietà del modello stesso, in questo caso Answer.

Il tuo problema è che stai chiamando il getmetodo, che solleva l'eccezione, prima che venga passato a assertRaises. Devi separare gli argomenti dal richiamabile, come descritto nella documentazione unittest :

self.assertRaises(Answer.DoesNotExist, Answer.objects.get, body__exact='<p>User can reply to discussion.</p>')

o meglio:

with self.assertRaises(Answer.DoesNotExist):
    Answer.objects.get(body__exact='<p>User can reply to discussion.</p>')

1
Buona risposta, solo il primo degli snippet di cui sopra sarà considerato come sintassi non valida (almeno da Python 2.7)., Dovrebbe essere self.assertRaises(Answer.DoesNotExist, Answer.objects.get, body__exact = '<p>User can reply to discussion.</p>')- cioè con getgli argomenti di aggiunti come singoli argomenti kw, non all'interno di un file ().
Martin B.

1
Augh, ovviamente! Mi sento come Dorothy qui. Stavo cercando in alto e in basso, solo per scoprire che era con me tutto il tempo!
Nick S

Python 3.6 / Django 2.2 solo la withsoluzione ha funzionato per me.
Theruss

183

Puoi anche importare ObjectDoesNotExistda django.core.exceptions, se desideri un modo generico e indipendente dal modello per catturare l'eccezione:

from django.core.exceptions import ObjectDoesNotExist

try:
    SomeModel.objects.get(pk=1)
except ObjectDoesNotExist:
    print 'Does Not Exist!'

10

DoesNotExistè sempre una proprietà del modello che non esiste. In questo caso lo sarebbe Answer.DoesNotExist.


3

Una cosa a cui prestare attenzione è che il secondo parametro assertRaises deve essere un richiamabile, non solo una proprietà. Ad esempio, ho avuto difficoltà con questa affermazione:

self.assertRaises(AP.DoesNotExist, self.fma.ap)

ma ha funzionato bene:

self.assertRaises(AP.DoesNotExist, lambda: self.fma.ap)

3
self.assertFalse(Answer.objects.filter(body__exact='<p>User...discussion.</p>').exists())

Questo non risponde esattamente alla domanda come richiesto. Ma è comunque una bella soluzione, che offre un approccio diverso per ottenere il risultato desiderato.
Cezar

0

È così che eseguo un test del genere.

from foo.models import Answer

def test_z_Kallie_can_delete_discussion_response(self):

  ...snip...

  self._driver.get("http://localhost:8000/questions/3/want-a-discussion") 
  try:
      answer = Answer.objects.get(body__exact = '<p>User can reply to discussion.</p>'))      
      self.fail("Should not have reached here! Expected no Answer object. Found %s" % answer
  except Answer.DoesNotExist:
      pass # all is as expected
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.