Как получить uri_for с помощью webapp2 в unit test?
Я пытаюсь выполнить unit test обработчик с помощью webapp2 и нахожусь в том, что должно быть просто глупой небольшой ошибкой.
Я бы хотел использовать webapp2.uri_for в тесте, но я не могу этого сделать:
def test_returns_200_on_home_page(self):
response = main.app.get_response(webapp2.uri_for('index'))
self.assertEqual(200, response.status_int)
Если я просто делаю main.app.get_response('/')
, он работает нормально.
Полученное исключение:
Traceback (most recent call last):
File "/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/unittest/case.py", line 318, in run
testMethod()
File "tests.py", line 27, in test_returns_200_on_home_page
webapp2.uri_for('index')
File "/Users/.../webapp2_example/lib/webapp2.py", line 1671, in uri_for
return request.app.router.build(request, _name, args, kwargs)
File "/Users/.../webapp2_example/lib/webapp2_extras/local.py", line 173, in __getattr__
return getattr(self._get_current_object(), name)
File "/Users/.../webapp2_example/lib/webapp2_extras/local.py", line 136, in _get_current_object
raise RuntimeError('no object bound to %s' % self.__name__)
RuntimeError: no object bound to request
Есть ли какая-то глупая настройка, которую мне не хватает?
Ответы
Ответ 1
Я думаю, что единственный вариант - установить фиктивный запрос, чтобы иметь возможность создавать URI для теста:
def test_returns_200_on_home_page(self):
// Set a dummy request just to be able to use uri_for().
req = webapp2.Request.blank('/')
req.app = main.app
main.app.set_globals(app=main.app, request=req)
response = main.app.get_response(webapp2.uri_for('index'))
self.assertEqual(200, response.status_int)
Никогда не используйте set_globals()
вне тестов. Is вызывается приложением WSGI для установки активного приложения и запроса поточно-безопасным способом.
Ответ 2
webapp2.uri_for()
предполагает, что вы находитесь в контексте веб-запроса, и он терпит неудачу, потому что он не может найти объект request
.
Вместо того, чтобы обойти это, вы можете придумать свое приложение как черный ящик и называть его с помощью литералов URI, например '/'
, как вы его упоминаете. В конце концов, вы хотите имитировать обычный веб-запрос, а веб-браузер также будет использовать URI, а не внутренние ярлыки маршрутизации.