Как вы тестируете наборы форм в Django?
Итак, мне нужно провести модульное тестирование представления, более точную форму в представлении. Поэтому я создаю такой юнит-тест.
class ViewTest(TestCase):
fixtures = ['fixture.json']
def setUp(self):
self.client = Client()
def test_company_create(self):
post_data = {
'form-0-user': '',
'form-0-share': '',
'form-TOTAL_FORMS': 1,
'form-INITIAL_FORMS': 0,
'form-MAX_NUM_FORMS': 10
}
resp = self.client.post('/company/create/', post_data)
self.assertFormError (resp, 'shareholder_formset', 'share', 'This field is required.')
self.assertFormError (resp, 'shareholder_formset', 'user', 'This field is required.')
Конечно, я вернул ошибку
AttributeError: у объекта 'ShareholderFormFormSet' нет атрибута 'fields'
Потому что в formset есть формы, а не поля..... Итак, как правильно тестировать formset?
2 ответа
Это функциональный тест (поскольку вы просматриваете представление, возможно, запросите модель, если сохраните ее и т. Д.).
Для форм django-webtest намного проще в использовании; вам не придется беспокоиться об этих деталях: https://pypi.python.org/pypi/django-webtest
Теперь в Django реализована ошибка assertFormsetError.
django-basetestcase имеет функцию, которая позволит вам протестировать formset
отдельно от view
, не требующий response
,
formset = MyFormSet(formset_data)
self.formset_error_test(
formset,
form_index=3,
field='my_field',
message='My error message.'
)
Как вы указали, аргумент имени формы в assertFormError на самом деле является просто ключом в response.context_data. Ключ, который вы используете, возвращает список форм в наборе форм. Итак, как вы обнаружили, он не работает с assertFormError.
Один из вариантов - использовать assertEqual и просто сделать прямое сравнение. Что-то вроде:
self.assertEqual(response.context_data[u'shareholder_formset'][form_index].errors['share'], 'This field is required.')
Я также хотел бы отметить, что моя IDE (PyCharm) очень помогла в этом разобраться. Я работал над аналогичной проблемой. Включение отладчика, установка точки останова после вызова post() и проверка ответа дали решение.