I am learning basics of Django following official tutorial and adding some new features to my application. So I added a view that can nullify all votes of particular question
def nullask(request, question_id):
question=get_object_or_404(Question, pk = question_id)
if request.method == "GET":
return render(request, "polls/nullifyask.html", {"question":question})
else:
for i in question.choice_set.all():
i.votes = 0
i.save()
return HttpResponseRedirect(reverse("polls:index"))
So it works fine, but I wanted to practice in writing tests and wanted to write a test that test that votes are really nullified. Here it is
class NullingViewTest(TestCase):
def test_nulling(self):
q=create_question(text="Future", days=-1)
choice=q.choice_set.create(choice_text="1", votes=10)
response=self.client.post(reverse('polls:nullask', args=(q.id,)))
self.assertEqual(choice.votes, 0)
It does't work(votes are not changing from 10 to 0 and AssertionError: 10 != 0
appears. I understand why this happens but cannot make it work like I want. What should I do
here is nullify ask.html:
<!doctype html>
<html lang="en-US">
<head>
<meta charset="utf-8" />
<title>Nullyfying of {{question_id}}</title>
</head>
<body>
<form method="post">
{% csrf_token %}
<legend><h1>Do you want to nullify votes of question {{question.text}}</h1></legend>
<input type="submit" name="Yes" value="Yes!">
</form>
</body>
</html>
Here are models:
class Question(models.Model):
text=models.CharField(max_length=200)
productiondate=models.DateTimeField("date published")
def was_published_recently(self):
return self.productiondate >= timezone.now() - datetime.timedelta(days=1) and self.productiondate<timezone.now()
def __str__(self):
return self.text
class Meta:
permissions=(("can_nullify","User can nullify votes" ),)
class Choice(models.Model):
question = models.ForeignKey(Question, on_delete=models.CASCADE)
choice_text = models.CharField(max_length=200)
votes = models.IntegerField(default=0)
def votesx2(self):
return self.votes*2
def __str__(self):
return self.choice_text
I have tried using question=response.context['question']
in the test but it resulted in an error
In your test, you need to update the choice
Python object to reflect the updated vote count in the database. This can be done by calling refresh_from_db()
on the object in your test after you POST to nullask.
class NullingViewTest(TestCase):
def test_nulling(self):
q=create_question(text="Future", days=-1)
choice=q.choice_set.create(choice_text="1", votes=10)
response=self.client.post(reverse('polls:nullask', args=(q.id,)))
# Update the Python object to reflect changes in the database
choice.refresh_from_db()
self.assertEqual(choice.votes, 0)