Narzędzia użytkownika

Narzędzia witryny


wiki:django_tests

Testy w Django

Poniżej plik tests.py przygotowany dla aplikacji polls z tutoriala do Django. Działa poprawnie w Django 3.1 oraz 4.0. Jedyna różnica w porównaniu z oryginałem to dodana funkcja fix_votes w modelu Choice:

def fix_votes(self):
    elif self.votes == 0:
      self.votes = 0
      return True
    if self.votes < 0:
      self.votes = 0
      return True
    elif self.votes % (ceil(self.votes)-1) != 1:
      self.votes = ceil(self.votes)-1
      return True

https://docs.djangoproject.com/en/4.0/intro/tutorial01/

import datetime
from django.test import TestCase
from django.utils import timezone
from django.urls import reverse

# Create your tests here.

from .models import Question, Choice

# ---------------------------------------------
# --------- HELPERS ---------------------------
# ---------------------------------------------

def create_question(question_text,days):
  '''
  Create question with with given "question_text"
  and puslished with "days" from now:
  + positive for questions puslished in the past,
  - negative for questions which will be published in the future.
  '''
  time = timezone.now() + datetime.timedelta(days=days)
  return Question.objects.create(question_text=question_text, pub_date=time)

def create_choice(question, choice_text, votes):
  '''
  Create choice for question with id "question"
  with given "answer_text" and "votes" number
  of initial votes.
  '''
  return Choice.objects.create(
           question=question,
           choice_text=choice_text,
           votes=votes,
         )

# ---------------------------------------------
# --------- MODEL TESTS -----------------------
# ---------------------------------------------

class QuestionModelTest(TestCase):

  def test_question_text_attribute(self):
    '''
    Test question_text attribute
    '''
    question = Question(question_text = 'Que?')
    self.assertIs(question.question_text, 'Que?')

  def test_was_published_recently_with_future_question(self):
    '''
    was_published_recently returns False for
    question published in the future
    '''
    time = timezone.now() + datetime.timedelta(days=30)
    future_question = Question(pub_date = time)
    self.assertIs(future_question.was_published_recently(), False)

  def test_was_published_recently_with_old_question(self):
    '''
    was_published_recently() returns False for questions whose pub_date
    is older than 1 day.
    '''
    time = timezone.now() - datetime.timedelta(days=1, seconds=1)
    old_question = Question(pub_date=time)
    self.assertIs(old_question.was_published_recently(), False)

  def test_was_published_recently_with_recent_question(self):
    '''
    was_published_recently() returns True for questions whose pub_date
    is within the last day.
    '''
    time = timezone.now() - datetime.timedelta(hours=23, minutes=59, seconds=59)
    recent_question = Question(pub_date=time)
    self.assertIs(recent_question.was_published_recently(), True)

  def test_too_long_question_over_200_characters(self, toolong='safe'):
    '''
    question_text of lenght over 200 characters should be allowed by Django.
    '''
    try:
      question = Question(question_text='aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa')
    except TypeError:
      pass
    self.assertIs(toolong, 'safe')


class ChoiceModelTest(TestCase):
  
  def test_choice_text_attribute(self):
    '''
    Test question_text attribute
    '''
    choice = Choice(choice_text = 'that')
    self.assertIs(choice.choice_text, 'that')

  def test_votes_attribute(self):
    '''
    Checks Choice vote attribute.
    '''
    votes_above_zero = Choice(votes=5)
    self.assertIs(votes_above_zero.votes, 5)

  def test_fix_votes_with_negative_votes_value(self):
    '''
    fix_votes() should return 0 votes for choice
    instance with -3 votes (which is below zero)
    '''
    votes_below_zero = Choice(votes=-3)
    votes_below_zero.fix_votes()
    self.assertIs(votes_below_zero.votes, 0)

  def test_fix_votes_with_good_votes_value(self):
    '''
    fix_votes() should return 3 votes for choice
    instance with 3 votes
    '''
    votes_below_zero = Choice(votes=3)
    votes_below_zero.fix_votes()
    self.assertIs(votes_below_zero.votes, 3)

  def test_fix_votes_with_zero_votes_value(self):
    '''
    fix_votes() should return 0 votes for choice
    instance with 0 votes
    '''
    votes_below_zero = Choice(votes=0)
    votes_below_zero.fix_votes()
    self.assertIs(votes_below_zero.votes, 0)

  def test_fix_votes_with_float_votes(self):
    '''
    fix_votes() should return 4 votes for choice
    instance with 4.7 votes
    '''
    votes_float = Choice(votes=4.7)
    votes_float.fix_votes()
    self.assertIs(votes_float.votes, 4)

  def test_too_long_choice_over_200_characters(self, toolong='safe'):
    '''
    choice_text of over 200 characters long should not be allowed by Django.
    '''
    try:
      choice = Choice(choice_text='aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa')
    except TypeError:
      pass
    self.assertIs(toolong, 'safe')


# ---------------------------------------------
# --------- VIEW TESTS ------------------------
# ---------------------------------------------

class QuestionIndexTestView(TestCase):

  def test_no_question(self):
    '''
    If no questions exists, view should return appropriate message.
    '''
    response = self.client.get(reverse('polls:index'))
    self.assertEqual(response.status_code, 200)
    self.assertContains(response, "No polls are available")
    self.assertQuerysetEqual(response.context['latest_question_list'], [])
  
  def test_past_question(self):
    '''
    Question with the past publication date have to be displayed on the index page.
    '''
    create_question("Can I have a test?", days=-30)
    response = self.client.get(reverse('polls:index')) 
    self.assertEqual(response.status_code, 200)
    self.assertContains(response, "Can I have a test?")
    self.assertQuerysetEqual(response.context['latest_question_list'],
                          ["<Question: Can I have a test?>"])

  def test_future_question(self):
    '''
    Question with the future publication date should not be listed at index page.
    '''
    create_question("Back from the future?", days=1)
    response = self.client.get(reverse('polls:index'))
    self.assertEqual(response.status_code, 200)
    self.assertContains(response, "No polls are available")
    self.assertQuerysetEqual(response.context['latest_question_list'], [])

  def test_past_and_future_question(self):
    '''
    Only past question should be displayed on the index page.
    '''
    create_question("Can I have a test?", days=-30)
    create_question("Back from the future?", days=1)
    response = self.client.get(reverse('polls:index')) 
    self.assertEqual(response.status_code, 200)
    self.assertContains(response, "Can I have a test?")
    self.assertQuerysetEqual(response.context['latest_question_list'],
                          ["<Question: Can I have a test?>"])

  def test_two_past_questions(self):
    '''
    Both past questions should be
    displayed on the index page.
    '''
    create_question("Can I have a first test?", days=-30)
    create_question("Can I have a second test?", days=-20)
    response = self.client.get(reverse('polls:index')) 
    self.assertEqual(response.status_code, 200)
    self.assertContains(response, "Can I have a first test?")
    self.assertQuerysetEqual(response.context['latest_question_list'],
                          ["<Question: Can I have a second test?>",
                           "<Question: Can I have a first test?>",
                          ])

class QuestionDetailViewTest(TestCase):
  
  def test_future_question_status_code(self):
    '''
    Detail view of question from future should return 404.
    '''
    future_question = create_question(question_text='Future?', days=5)
    url = reverse('polls:detail', args=(future_question.id,))
    response = self.client.get(url)
    self.assertEqual(response.status_code, 404)

  def test_past_question_status_code(self):
    '''
    Detail view of question from the past should return 200.
    '''
    past_question = create_question(question_text='Past?', days=-5)
    url = reverse('polls:detail', args=(past_question.id,))
    response = self.client.get(url)
    self.assertEqual(response.status_code, 200)

  def test_past_question_response(self):
    '''
    Detail view of question from the past should return question_text.
    '''
    past_question = create_question(question_text='Past?', days=-5)
    url = reverse('polls:detail', args=(past_question.id,))
    response = self.client.get(url)
    self.assertContains(response, past_question.question_text)
wiki/django_tests.txt · ostatnio zmienione: 2022/06/04 06:15 przez lukasz