如何统一打印Flask Blueprint路由的请求与响应内容?
全局打印Flask API的请求和响应详情
直接用Flask的全局钩子函数就能一次性搞定,不用改每个路由函数。具体实现如下:
1. 用before_request打印请求信息
这个钩子会在每个请求到达路由之前自动执行,刚好用来打印请求头和请求体:
在app/__init__.py里添加这段代码:
from flask import request, current_app def create_app(config): app = Flask(__name__) app.register_blueprint(foo_route) # 全局打印请求详情 @app.before_request def log_request(): # 打印请求头 print("=== 请求头 ===") for key, value in request.headers.items(): print(f"{key}: {value}") # 打印请求体,按不同格式处理 print("=== 请求体 ===") if request.is_json: print(request.get_json()) elif request.data: print(request.data.decode('utf-8')) elif request.form: print(dict(request.form)) # 原有其他配置... return app
2. 用after_request打印响应信息
这个钩子会在请求处理完成、响应返回给客户端之前执行,用来打印响应头和响应体:
继续在create_app函数中添加:
@app.after_request def log_response(response): # 打印响应头 print("=== 响应头 ===") for key, value in response.headers.items(): print(f"{key}: {value}") # 打印响应体:需先复制一份数据,避免破坏原响应流 response_data = response.get_data().decode('utf-8') print("=== 响应体 ===") print(response_data) # 必须返回原始响应,否则客户端无法正常接收内容 return response
几个注意点
- 如果只想让某个Blueprint下的路由生效,把
@app.before_request改成@foo_route.before_request即可;全局生效就用@app开头的钩子。 - 生产环境建议用Flask的
current_app.logger代替print(),避免日志混乱,比如把print()替换为current_app.logger.info()。 - 遇到大文件上传这类请求时,打印请求体可能占用过多资源,可以加判断逻辑跳过,比如检查
content-length超过阈值就不打印。 - 你原有路由函数
handle_foo_api多传了request参数,Flask路由函数不需要这个参数,需修改为:@foo_route.route("/path/to/foo/API", methods=["POST"]) def handle_foo_api(): result = {"foo1": "foo1", "foo2": "foo2"} return jsonify(result), 200
这样配置完成后,所有API的请求和响应详情都会自动打印,无需在每个路由中重复编写代码。
内容的提问来源于stack exchange,提问作者Paul Chuang
相关产品推荐
相关产品推荐

