Python用Flask封装API及调用详解
作者:AI手记叨叨
本文介绍Flask的优势(轻量、灵活、易扩展),对比GET/POST表单/JSON请求方式,涵盖错误处理、开发建议及生产环境部署注意事项
一、Flask的优势
- 轻量级:核心功能简单,易于学习和使用
- 灵活性:可以通过扩展添加所需功能
- 易扩展性:丰富的扩展生态系统(如Flask-RESTful、Flask-JWT等)
- 开发效率高:快速原型开发,适合中小型项目
一、基础设置
先设置基本的Flask应用结构,创建了一个Flask应用实例,并定义了一个简单的业务逻辑函数main(),它接收查询文本和结果数量参数,返回包含这些信息的字典。
from flask import Flask, request, Response, jsonify, abort
import json
app = Flask(__name__)
def main(query, k):
"""业务逻辑处理函数
Args:
query (str): 查询文本
k (int): 返回结果数量
Returns:
dict: 包含查询参数和结果的字典
"""
return {"query": query, "k": k, "status": "success"}
二、GET请求方式
GET请求是最常见的HTTP方法,参数通过URL传递,适合简单的数据查询。
特点
- 参数通过URL传递(查询字符串)
- 有长度限制(不同浏览器限制不同,通常约2048字符)
- 请求可以被缓存、保留在浏览器历史记录中
- 不应用于敏感数据传输
服务端代码
模拟业务逻辑
@app.route('/api/search', methods=['GET'])
def handle_get():
"""处理GET请求
参数通过URL查询字符串传递:
- query: 必需,字符串类型
- k: 可选,整数类型,默认为1
Returns:
Response: JSON格式的响应
"""
# 获取并验证参数
query = request.args.get("query")
if not query:
abort(400, description="query参数不能为空")
try:
k = int(request.args.get("k", 1)) # 默认为1
except ValueError:
abort(400, description="k必须是整数")
# 调用业务逻辑
result = main(query, k)
# 返回JSON响应
return jsonify(result)
客户端调用
import requests
# 构造URL参数
params = {
'query': 'Python Flask',
'k': 3
}
# 发送GET请求
response = requests.get(
url="http://127.0.0.1:8000/api/search",
params=params
)
# 处理响应
if response.status_code == 200:
print(response.json())
else:
print(f"请求失败,状态码: {response.status_code}, 错误: {response.text}")
三、POST表单方式
POST表单方式适合传统的网页表单提交,数据通过HTTP body以application/x-www-form-urlencoded格式传输。
特点
- 数据通过HTTP body传输
- 使用application/x-www-form-urlencoded编码格式
- 没有长度限制
- 不会显示在URL中
- 适合提交敏感数据或大量数据
服务端代码
@app.route('/api/form-submit', methods=['POST'])
def handle_post_form():
"""处理表单POST请求
参数通过表单数据传递:
- query: 必需,字符串类型
- k: 可选,整数类型,默认为1
Returns:
Response: JSON格式的响应
"""
# 获取并验证参数
query = request.form.get("query")
if not query:
abort(400, description="query参数不能为空")
try:
k = int(request.form.get("k", 1)) # 默认为1
except ValueError:
abort(400, description="k必须是整数")
# 调用业务逻辑
result = main(query, k)
# 返回JSON响应
return jsonify(result)
客户端调用
import requests
# 准备表单数据
form_data = {
'query': '表单提交示例',
'k': 2
}
# 发送POST请求
response = requests.post(
url="http://127.0.0.1:8000/api/form-submit",
data=form_data
)
# 处理响应
if response.status_code == 200:
print(response.json())
else:
print(f"请求失败,状态码: {response.status_code}, 错误: {response.text}")
四、POST JSON方式
POST JSON方式是现代API常用的数据交换格式,适合传输结构化数据。
特点
- 数据通过HTTP body传输
- 使用application/json内容类型
- 支持复杂数据结构(嵌套对象、数组等)
- 是现代Web和移动应用的首选方式
- 易于与前端框架(如React、Vue)集成
服务端代码
@app.route('/api/json-submit', methods=['POST'])
def handle_post_json():
"""处理JSON POST请求
参数通过JSON格式传递:
- query: 必需,字符串类型
- k: 可选,整数类型,默认为1
Returns:
Response: JSON格式的响应
"""
# 验证请求内容类型
if not request.is_json:
abort(415, description="请求必须是JSON格式")
# 获取JSON数据
data = request.get_json()
# 验证参数
query = data.get("query")
if not query:
abort(400, description="query参数不能为空")
try:
k = int(data.get("k", 1)) # 默认为1
except ValueError:
abort(400, description="k必须是整数")
# 调用业务逻辑
result = main(query, k)
# 返回JSON响应
return jsonify(result)
客户端调用
import requests
# 准备JSON数据
json_data = {
'query': 'JSON数据示例',
'k': 4
}
# 发送POST请求
response = requests.post(
url="http://127.0.0.1:8000/api/json-submit",
json=json_data, # 自动设置Content-Type为application/json
headers={'Accept': 'application/json'} # 明确要求JSON响应
)
# 处理响应
if response.status_code == 200:
print(response.json())
else:
print(f"请求失败,状态码: {response.status_code}, 错误: {response.text}")
五、错误处理
Flask提供了完善的错误处理机制
@app.errorhandler(400)
def bad_request(error):
return jsonify({
'status': 'error',
'message': error.description
}), 400
@app.errorhandler(404)
def not_found(error):
return jsonify({
'status': 'error',
'message': '资源不存在'
}), 404
@app.errorhandler(415)
def unsupported_media_type(error):
return jsonify({
'status': 'error',
'message': error.description
}), 415
六、对比
| 方式 | 适用场景 | 数据位置 | 客户端调用方法 | 服务端获取方法 |
|---|---|---|---|---|
| GET | 简单查询,参数少 | URL查询字符串 | requests.get() | request.args |
| POST表单 | 传统网页表单提交 | HTTP Body | requests.post(data=) | request.form |
| POST JSON | 现代API,复杂数据结构 | HTTP Body | requests.post(json=) | request.get_json() |
实践建议
- 使用jsonify()代替手动JSON序列化
- 为所有API端点添加前缀(如/api/)
- 实现统一的错误处理
- 为每个端点编写详细的文档字符串
- 在生产环境使用WSGI服务器(如Gunicorn)
- 添加适当的认证和限流机制
七、启动
if __name__ == '__main__':
app.run(host='0.0.0.0', port=8000, debug=True)
注意:生产环境不应使用debug=True,且应通过WSGI服务器运行应用。
八、总结
以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。
