使用url_for函数为Flask测试客户端生成URL [英] Generate URLs for Flask test client with url_for function
问题描述
我正在尝试使用pytest为Flask应用编写单元测试.我有一个应用程序工厂:
I'm trying to write unit tests for a Flask app using pytest. I have an app factory:
def create_app():
from flask import Flask
app = Flask(__name__)
app.config.from_object('config')
import os
app.secret_key = os.urandom(24)
from models import db
db.init_app(app)
return app
和一个测试班:
class TestViews(object):
@classmethod
def setup_class(cls):
cls.app = create_app()
cls.app.testing = True
cls.client = cls.app.test_client()
@classmethod
def teardown_class(cls):
cls.app_context.pop()
def test_create_user(self):
"""
Tests the creation of a new user.
"""
view = TestViews.client.get(url_for('create_users')).status_code == 200
但是当我运行测试时,出现以下错误:
but when I run my tests I get the following error:
RuntimeError: Attempted to generate a URL without the application context being pushed. This has to be executed when application context is available.
谷歌搜索告诉我(我认为),使用测试客户端应该创建一个自动的应用程序上下文.我想念什么?
Googling this tells me (I think) that using the test client should create an automatic application context. What am I missing?
推荐答案
通过测试客户端发出请求的确确实(间接地)推送了应用上下文.但是,您将 url_for
直观地放在测试请求调用中这一事实与实际上在内部调用它的想法混淆了.首先评估 url_for
调用,然后将结果传递给 client.get
.
Making requests with the test client does indeed push an app context (indirectly). However, you're confusing the fact that url_for
is visually inside the test request call with the idea that it is actually called inside. The url_for
call is evaluated first, the result is passed to client.get
.
url_for
通常用于在应用内 生成URL,单元测试是外部.通常,您只需在请求中准确地编写要尝试测试的URL,而不生成它即可.
url_for
is typically for generating URLs within the app, unit tests are external. Typically, you just write exactly the URL you're trying to test in the request instead of generating it.
self.client.get('/users/create')
如果您确实要在此处使用 url_for
,则必须在应用程序上下文中使用它.请注意,当您处于应用程序上下文而不是请求上下文时,必须设置 SERVER_NAME
配置,还必须传递 _external = False
.但同样,您可能应该只写出您要测试的URL.
If you really want to use url_for
here, you must do it in an app context. Note that when you're in an app context but not a request context, you must set the SERVER_NAME
config and also pass _external=False
. But again, you should probably just write out the URL you're trying to test.
app.config['SERVER_NAME'] = 'localhost'
with self.app.app_context():
url = url_for(..., _external=False)
self.client.get(url, ...)
这篇关于使用url_for函数为Flask测试客户端生成URL的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!