Есть ли простой механизм для переопределения настроек Django для модульного теста? У меня есть менеджер на одной из моих моделей, который возвращает определенное количество последних объектов. Количество возвращаемых объектов определяется параметром NUM_LATEST.
Это может привести к тому, что мои тесты не пройдут, если кто-то изменит настройку. Как я могу переопределить настройки setUp()
и впоследствии восстановить их tearDown()
? Если это невозможно, могу ли я как-нибудь исправить метод обезьяны или издеваться над настройками?
РЕДАКТИРОВАТЬ: Вот мой код менеджера:
class LatestManager(models.Manager):
"""
Returns a specific number of the most recent public Articles as defined by
the NEWS_LATEST_MAX setting.
"""
def get_query_set(self):
num_latest = getattr(settings, 'NEWS_NUM_LATEST', 10)
return super(LatestManager, self).get_query_set().filter(is_public=True)[:num_latest]
Менеджер использует settings.NEWS_LATEST_MAX
для нарезки набора запросов. getattr()
Просто используется , чтобы обеспечить значение по умолчанию если параметр не существует.
django
settings
testing
django-managers
Soviut
источник
источник
Ответы:
РЕДАКТИРОВАТЬ: этот ответ применим, если вы хотите изменить настройки для небольшого количества конкретных тестов.
Начиная с Django 1.4, есть способы переопределить настройки во время тестов: https://docs.djangoproject.com/en/dev/topics/testing/tools/#overriding-settings
TestCase будет иметь диспетчер контекста self.settings, а также декоратор @override_settings, который можно применить либо к методу тестирования, либо ко всему подклассу TestCase.
Этих функций еще не было в Django 1.3.
Если вы хотите изменить настройки для всех ваших тестов, вам нужно создать отдельный файл настроек для теста, который может загружать и отменять настройки из вашего основного файла настроек. В других ответах есть несколько хороших подходов к этому; Я видел успешные варианты подходов как hspander, так и dmitrii .
источник
self.settings().wrapped.MEDIA_ROOT
, но это довольно ужасно.@modify_settings(MIDDLEWARE_CLASSES=...
(спасибо за этот ответ)С
UnitTest
подклассом можно делать все, что угодно , включая настройку и чтение свойств экземпляра:Однако, поскольку тестовые примеры django работают в однопоточном режиме, мне любопытно, что еще может изменять значение NUM_LATEST? Если это «что-то еще» вызвано вашей программой тестирования, то я не уверен, что любое количество обезьяньих исправлений спасет тест, не сделав недействительной достоверность самих тестов.
источник
settings.TEMPLATE_LOADERS
... Так что это не общий способ, по крайней мере, настройки или Django не перезагружаются или что-то еще с этим трюком.Хотя переопределение конфигурации настроек во время выполнения может помочь, на мой взгляд, вам следует создать отдельный файл для тестирования. Это экономит много настроек для тестирования и гарантирует, что вы никогда не сделаете что-то необратимое (например, очистите промежуточную базу данных).
Скажем, ваш тестовый файл существует в my_project / test_settings.py, добавьте
в вашем manage.py. Это гарантирует, что при запуске
python manage.py test
вы будете использовать только test_settings. Если вы используете другой клиент тестирования, например pytest, вы можете легко добавить его в pytest.ini.источник
Вы можете передать
--settings
опцию при запуске тестовисточник
Обновление : приведенное ниже решение необходимо только для Django 1.3.x и ранее. Для> 1.4 см . Ответ slinkp .
Если вы часто меняете настройки в своих тестах и используете Python ≥2.5, это также удобно:
Тогда вы сможете:
источник
yield
оператора с последней частью функции, содержащейся вfinally
блоке, так что настройки всегда возвращаются.@override_settings
отлично, если у вас не так много различий между конфигурациями производственной и тестовой среды.В противном случае лучше иметь другие файлы настроек. В этом случае ваш проект будет выглядеть так:
Таким образом, вам нужно сохранить большую часть ваших настроек,
base.py
а затем в других файлах вам нужно импортировать все оттуда и переопределить некоторые параметры. Вот какtest.py
будет выглядеть ваш файл:И затем вам нужно либо указать
--settings
параметр, как в ответе @MicroPyramid, либо указатьDJANGO_SETTINGS_MODULE
переменную среды, а затем вы можете запустить свои тесты:источник
Обнаружил это при попытке исправить некоторые доктесты ... Для полноты картины я хочу упомянуть, что если вы собираетесь изменить настройки при использовании доктестов, вам следует сделать это перед импортом чего-либо еще ...
источник
Для пользователей pytest .
Самая большая проблема:
override_settings
не работает с pytest.TestCase
заставит его работать, но тогда вы не сможете использовать инструменты pytest.Решение состоит в том, чтобы использовать
settings
приспособление, описанное здесь .пример
И если вам нужно обновить несколько полей
источник
Вы можете изменить настройку даже для одной тестовой функции.
или вы можете переопределить настройку для каждой функции в классе.
источник
Я использую pytest.
Мне удалось решить это следующим образом:
источник
Вы можете переопределить настройки в тесте следующим образом:
И если вам нужны эти же настройки в другом файле, вы можете просто импортировать их напрямую
test_settings
.источник
Если у вас есть несколько тестовых файлов, помещенных в подкаталог (пакет python), вы можете переопределить настройки для всех этих файлов на основе условия наличия строки test в sys.argv
__init__.py:
Не лучший подход. Использовал его для изменения брокера Celery с Redis на Memory.
источник
Я создал новый файл settings_test.py, который будет импортировать все из файла settings.py и изменять все, что отличается для целей тестирования. В моем случае я хотел использовать другое ведро облачного хранилища при тестировании.
settings_test.py:
manage.py:
источник