API — Flask 文档

来自菜鸟教程
Flask/docs/2.0.x/api
跳转至:导航、​搜索

应用程序接口

这部分文档涵盖了 Flask 的所有接口。 对于 Flask 依赖于外部库的部分,我们在这里记录了最重要的部分,并提供了规范文档的链接。

应用对象

蓝图对象

传入请求数据

flask.request

要访问传入的请求数据,您可以使用全局 request 对象。 Flask 为您解析传入的请求数据,并让您通过该全局对象访问它。 如果您处于多线程环境中,Flask 内部确保您始终获得活动线程的正确数据。

这是一个代理。 有关更多信息,请参阅 代理注意事项

请求对象是一个 Request 的实例。


响应对象

会话

如果您设置了 Flask.secret_key(或从 SECRET_KEY 配置),您可以在 Flask 应用程序中使用会话。 会话可以记住从一个请求到另一个请求的信息。 Flask 执行此操作的方式是使用签名 cookie。 用户可以查看会话内容,但除非他们知道密钥,否则无法修改它,因此请确保将其设置为复杂且不可猜测的内容。

要访问当前会话,您可以使用 session 对象:

class flask.session

session 对象的工作方式与普通的 dict 非常相似,不同之处在于它跟踪修改。

这是一个代理。 有关更多信息,请参阅 代理注意事项

以下属性很有趣:

new

True 如果会话是新的,否则 False

modified

True 如果会话对象检测到修改。 请注意,不会自动获取对可变结构的修改,在这种情况下,您必须自己将属性显式设置为 True。 这里有一个例子:

# this change is not picked up because a mutable object (here
# a list) is changed.
session['objects'].append(42)
# so mark it as modified yourself
session.modified = True
permanent

如果设置为 True,会话将持续 permanent_session_lifetime 秒。 默认值为 31 天。 如果设置为 False(默认值),会话将在用户关闭浏览器时被删除。


会话接口

0.8 版中的新功能。


会话接口提供了一种简单的方法来替换 Flask 正在使用的会话实现。

通知

PERMANENT_SESSION_LIFETIME 配置键也可以是从 Flask 0.8 开始的整数。 要么自己记录下来,要么使用应用程序上的 permanent_session_lifetime 属性,它会自动将结果转换为整数。


测试客户端

测试 CLI 运行程序

应用程序全局变量

要将仅对一个请求有效的数据从一个函数共享到另一个函数,全局变量还不够好,因为它会在线程环境中中断。 Flask 为您提供了一个特殊的对象,以确保它仅对活动请求有效,并且将为每个请求返回不同的值。 简而言之:它做正确的事情,就像它对 requestsession 所做的一样。

flask.g

一个命名空间对象,可以在 应用程序上下文 期间存储数据。 这是Flask.app_ctx_globals_class的实例,默认为ctx._AppCtxGlobals

这是在请求期间存储资源的好地方。 在测试过程中,您可以使用 Faking Resources 和 Context 模式来预先配置此类资源。

这是一个代理。 有关更多信息,请参阅 代理注意事项

在 0.10 版更改: 绑定到应用程序上下文而不是请求上下文。


有用的函数和类

flask.current_app

处理当前请求的应用程序的代理。 这对于无需导入即可访问应用程序或无法导入应用程序非常有用,例如在使用应用程序工厂模式或在蓝图和扩展中时。

这仅在推送 应用程序上下文 时可用。 这会在请求和 CLI 命令期间自动发生。 可通过app_context()手动控制。

这是一个代理。 有关更多信息,请参阅 代理注意事项


消息闪烁

JSON 支持

Flask 使用内置的 json 模块来处理 JSON。 它将使用当前蓝图或应用程序的 JSON 编码器和解码器,以便更轻松地进行定制。 默认情况下,它处理一些额外的数据类型:

  • datetime.datetimedatetime.date 被序列化为 RFC 822 字符串。 这与 HTTP 日期格式相同。
  • uuid.UUID 被序列化为字符串。
  • dataclasses.dataclass 传递给 dataclasses.asdict()
  • Markup(或任何具有 __html__ 方法的对象)将调用 __html__ 方法来获取字符串。

Jinja 的 |tojson 过滤器配置为使用 Flask 的 dumps() 功能。 过滤器自动用 |safe 标记输出。 使用过滤器在 <script> 标签内呈现数据。

<script>
    const names = {{ names|tosjon }};
    renderChart(names, {{ axis_data|tojson }});
</script>

模板渲染

配置

流助手

有用的内部结构

flask._request_ctx_stack

包含 RequestContext 实例的内部 LocalStack。 通常,应该访问 requestsession 代理而不是堆栈。 在扩展代码中访问堆栈可能很有用。

以下属性始终存在于堆栈的每一层上:

应用程序

活动的 Flask 应用程序。

url_适配器

用于匹配请求的 URL 适配器。

要求

当前请求对象。

会议

活动会话对象。

g

具有 flask.g 对象所有属性的对象。

闪烁

闪存消息的内部缓存。

用法示例:

from flask import _request_ctx_stack

def get_session():
    ctx = _request_ctx_stack.top
    if ctx is not None:
        return ctx.session
flask._app_ctx_stack

包含 AppContext 实例的内部 LocalStack。 通常,应该访问 current_appg 代理而不是堆栈。 扩展可以访问堆栈上的上下文作为命名空间来存储数据。

0.9 版中的新功能。


信号

0.6 版中的新功能。


signals.signals_available
True 如果信号系统可用。 安装了 blinker 时就是这种情况。

Flask 中存在以下信号:

flask.template_rendered

当模板成功渲染时发送此信号。 使用模板实例作为 template 和作为字典的上下文(名为 context)调用信号。

示例订阅者:

def log_template_renders(sender, template, context, **extra):
    sender.logger.debug('Rendering template "%s" with context %s',
                        template.name or 'string template',
                        context)

from flask import template_rendered
template_rendered.connect(log_template_renders, app)
flask.before_render_template

该信号在模板渲染过程之前发送。 使用模板实例作为 template 和作为字典的上下文(名为 context)调用信号。

示例订阅者:

def log_template_renders(sender, template, context, **extra):
    sender.logger.debug('Rendering template "%s" with context %s',
                        template.name or 'string template',
                        context)

from flask import before_render_template
before_render_template.connect(log_template_renders, app)
flask.request_started

这个信号在请求上下文建立时发送,在任何请求处理发生之前。 由于请求上下文已经绑定,订阅者可以使用标准的全局代理(例如 request)访问请求。

示例订阅者:

def log_request(sender, **extra):
    sender.logger.debug('Request context is set up')

from flask import request_started
request_started.connect(log_request, app)
flask.request_finished

该信号在响应发送到客户端之前发送。 传递名为 response 的待发送响应。

示例订阅者:

def log_response(sender, response, **extra):
    sender.logger.debug('Request context is about to close down.  '
                        'Response: %s', response)

from flask import request_finished
request_finished.connect(log_response, app)
flask.got_request_exception

当请求处理期间发生未处理的异常时,包括调试时,将发送此信号。 异常作为 exception 传递给订阅者。

不会为 HTTPException 或其他已注册错误处理程序的异常发送此信号,除非异常是从错误处理程序引发的。

这个例子展示了如果理论上的 SecurityException 被提出,如何做一些额外的日志记录:

from flask import got_request_exception

def log_security_exception(sender, exception, **extra):
    if not isinstance(exception, SecurityException):
        return

    security_logger.exception(
        f"SecurityException at {request.url!r}",
        exc_info=exception,
    )

got_request_exception.connect(log_security_exception, app)
flask.request_tearing_down

当请求拆除时发送此信号。 即使引发异常,也始终会调用此方法。 当前,在常规拆卸处理程序之后调用侦听此信号的函数,但这不是您可以依赖的。

示例订阅者:

def close_db_connection(sender, **extra):
    session.close()

from flask import request_tearing_down
request_tearing_down.connect(close_db_connection, app)

从 Flask 0.9 开始,这也将传递一个 exc 关键字参数,该参数引用导致拆卸的异常(如果有的话)。

flask.appcontext_tearing_down

当应用程序上下文拆除时发送此信号。 即使引发异常,也始终会调用此方法。 当前,在常规拆卸处理程序之后调用侦听此信号的函数,但这不是您可以依赖的。

示例订阅者:

def close_db_connection(sender, **extra):
    session.close()

from flask import appcontext_tearing_down
appcontext_tearing_down.connect(close_db_connection, app)

这也将传递一个 exc 关键字参数,该参数引用导致拆卸的异常(如果有的话)。

flask.appcontext_pushed

当推送应用程序上下文时发送此信号。 发送方是应用程序。 这对于单元测试通常很有用,以便临时挂钩信息。 例如,它可用于将资源提前设置到 g 对象上。

用法示例:

from contextlib import contextmanager
from flask import appcontext_pushed

@contextmanager
def user_set(app, user):
    def handler(sender, **kwargs):
        g.user = user
    with appcontext_pushed.connected_to(handler, app):
        yield

在测试代码中:

def test_user_me(self):
    with user_set(app, 'john'):
        c = app.test_client()
        resp = c.get('/users/me')
        assert resp.data == 'username=john'

0.10 版中的新功能。

flask.appcontext_popped

当弹出应用程序上下文时发送此信号。 发送方是应用程序。 这通常与 appcontext_tearing_down 信号一致。

0.10 版中的新功能。

flask.message_flashed

当应用程序闪烁消息时发送此信号。 消息作为 message 关键字参数发送,类别作为 category。

示例订阅者:

recorded = []
def record(sender, message, category, **extra):
    recorded.append((message, category))

from flask import message_flashed
message_flashed.connect(record, app)

0.10 版中的新功能。

class signals.Namespace
如果闪光灯可用,则为 blinker.base.Namespace 的别名,否则为创建假信号的虚拟类。 此类可用于希望提供与 Flask 本身相同的回退系统的 Flask 扩展。
signal(name, doc=None)
如果 blinker 可用,则为此命名空间创建一个新信号,否则返回一个假信号,该信号具有一个发送方法,该方法将什么都不做,但对于所有其他操作(包括连接)将失败并返回 RuntimeError


基于类的视图

0.7 版中的新功能。


URL 路由注册

路由系统的规则定义一般有以下三种方式:

  1. 您可以使用 flask.Flask.route() 装饰器。
  2. 您可以使用 flask.Flask.add_url_rule() 功能。
  3. 您可以直接访问底层 Werkzeug 路由系统,该系统公开为 flask.Flask.url_map

路径中的可变部分可以用尖括号 (/user/<username>) 指定。 默认情况下,URL 中的变量部分接受任何不带斜杠的字符串,但也可以使用 <converter:name> 指定不同的转换器。

变量部分作为关键字参数传递给视图函数。

以下转换器可用:

细绳 接受任何不带斜杠的文本(默认)
整数 接受整数
漂浮 像 int 但对于浮点值
小路 喜欢默认但也接受斜线
任何 匹配提供的项目之一
用户名 接受 UUID 字符串

可以使用 flask.Flask.url_map 定义自定义转换器。

这里有些例子:

@app.route('/')
def index():
    pass

@app.route('/<username>')
def show_user(username):
    pass

@app.route('/post/<int:post_id>')
def show_post(post_id):
    pass

要记住的一个重要细节是 Flask 如何处理尾部斜杠。 我们的想法是保持每个 URL 的唯一性,以便应用以下规则:

  1. 如果规则以斜杠结尾并且用户请求时没有使用斜杠,则用户会自动重定向到附加斜杠的同一页面。
  2. 如果规则不以斜杠结尾并且用户请求带有斜杠的页面,则会引发 404 not found。

这与 Web 服务器处理静态文件的方式一致。 这也使得可以安全地使用相对链接目标。

您还可以为同一功能定义多个规则。 然而,它们必须是独一无二的。 也可以指定默认值。 例如,这里是接受可选页面的 URL 的定义:

@app.route('/users/', defaults={'page': 1})
@app.route('/users/page/<int:page>')
def show_users(page):
    pass

这指定 /users/ 将是第一页的 URL,而 /users/page/N 将是页面 N 的 URL。

如果 URL 包含默认值,它将通过 301 重定向重定向到其更简单的形式。 在上面的例子中,/users/page/1 将被重定向到 /users/。 如果您的路由处理 GETPOST 请求,请确保默认路由仅处理 GET,因为重定向无法保留表单数据。

@app.route('/region/', defaults={'id': 1})
@app.route('/region/<int:id>', methods=['GET', 'POST'])
def region(id):
   pass

这里是 route()add_url_rule() 接受的参数。 唯一的区别是使用 route 参数,视图函数是用装饰器而不是 view_func 参数定义的。

规则 字符串形式的 URL 规则
端点 已注册 URL 规则的端点。 如果没有明确说明,Flask 本身假设视图函数的名称是端点的名称。
view_func 向提供的端点提供请求时要调用的函数。 如果未提供此功能,则可以稍后通过将其存储在 view_functions 字典中并将端点作为键来指定该函数。
默认值 具有此规则默认值的字典。 有关默认值的工作原理,请参见上面的示例。
子域 如果正在使用子域匹配,则指定子域的规则。 如果未指定,则假定为默认子域。
**选项 要转发到底层 Rule 对象的选项。 Werkzeug 的一个变化是处理方法选项。 方法是此规则应限于的方法列表(GETPOST 等)。 默认情况下,规则只侦听 GET(隐式 HEAD)。 从 Flask 0.6 开始,OPTIONS 被隐式添加并由标准请求处理来处理。 它们必须被指定为关键字参数。


查看功能选项

对于内部使用,视图函数可以附加一些属性来自定义视图函数通常无法控制的行为。 可以选择提供以下属性以覆盖 add_url_rule() 的某些默认值或一般行为:

  • __name__:函数名默认用作端点。 如果明确提供了端点,则使用此值。 此外,默认情况下,这将带有蓝图名称的前缀,无法从函数本身进行自定义。
  • methods:如果添加URL规则时未提供方法,如果存在methods属性,Flask将查看视图函数对象本身。 如果是,它将从那里提取方法的信息。
  • provide_automatic_options:如果设置了这个属性,Flask 将强制启用或禁用 HTTP OPTIONS 响应的自动实现。 这在与想要在每个视图的基础上自定义 OPTIONS 响应的装饰器一起使用时非常有用。
  • required_methods:如果设置了这个属性,Flask 在注册 URL 规则时总是会添加这些方法,即使这些方法在 route() 调用中被显式覆盖。

完整示例:

def index():
    if request.method == 'OPTIONS':
        # custom options handling here
        ...
    return 'Hello World!'
index.provide_automatic_options = False
index.methods = ['GET', 'OPTIONS']

app.add_url_rule('/', index)

0.8 版新功能: 添加了 provide_automatic_options 功能。


命令行界面