flask-smorest
简介
flask-smorest: 基于Flask/Marshmallow的REST API框架
flask-smorest 是一个用于创建于数据库无关的REST API的架库。
它使用Flask作为Web服务器,并使用marsmallow对数据进行序列化和反序列化。(类似于drf)
快速入门
flask-smorest对代码应该如何结构化做了一些设定。应用程序应该在Blueprint中进行拆分。可以使用基本的Flask视图函数,但通常最好使用Flask MethodView。
Marshmallow Schema被用来序列化参数和响应。请求和响应体被序列化为JSON。一个视图函数只有一个成功的响应类型和状态代码。
所以在使用 flask-smorest 前建议先看看 Marshmallow 库
代码示例
首先用Flask应用程序实例化一个Api。
from flask import Flask
from flask.views import MethodView
from marshmallow import Schema, fields, post_load
from flask_smorest import Api, Blueprint, abort
app = Flask(__name__)
api = Api(app) # 注册 flask_smorest
定义一个marshmallow Schema类来输出model
class User:
def __init__(self, name, age):
self.name = name
self.age = age
self.c_time = datetime.datetime.now()
class UserSchema(Schema):
name = fields.String()
age = fields.Integer()
c_time = fields.DateTime()
实例化一个蓝图(Blueprint)
blp = Blueprint('user', 'user', url_prefix='/user')
使用MethodView
类来组织资源(resources),用Blueprint.arguments
和Blueprint.response
来装饰视图方法,指定请求反序列化和响应序列化。
使用abort
返回错误,传递错误处理程序(handle_http_exception
)使用的kwargs来建立错误响应。
def example(self):
if some_condition:
abort(400, message='Invalid request') # 终止请求并返回400错误响应
else:
# 处理请求的逻辑
错误处理的另一种方案
1. 通过Exception定义错误类
class BaseCustomException(Exception):
def __init__(self, msg):
self.msg = msg
def show(self):
return self.msg
class TipResponse(BaseCustomException):
"""
@attention: 提示类响应
"""
def __init__(self, msg, code=400, status=400):
self.code = code
self.status = status
super().__init__(msg)
2. flask 中注册该错误类型
def init_exception(app: Flask):
logger = app.logger
@app.errorhandler(TipResponse)
def tip_handler(error: TipResponse):
"""
@attention: 提示
"""
return BaseResponse(
message=error.msg,
status=error.status,
code=error.code,
).asdict() # 转换成字典返回 dataclass 包的用法
3. 使用
def example(self):
if some_condition:
raise TipResponse("error info")# 终止请求并返回400错误响应
else:
# 处理请求的逻辑
最后,在API中注册蓝图
api.register_blueprint(blp)
使用实例
class UserQuantityView(MethodView):
@blp.doc(tags=[v1.name], description="批量上传用户", summary="批量上传用户")
@blp.arguments(HeaderBaseSchema, location='headers')
@blp.arguments(CreateQuantityUserParserSchema, location="files")
@blp.response(200, BaseResponseSchema)
def post(self, headers: dict, files: dict):
"""批量上传用户"""
data = user_service.bulk_create(files)
return BaseResponse(data=data)
@blp.doc来定义了一些描述信息,包括标签、描述和摘要。
@blp.arguments装饰器用于定义函数参数的验证和转换规则,其中HeaderBaseSchema用于验证和转换headers参数,CreateQuantityUserParserSchema用于验证和转换files参数。
@blp.response装饰器用于定义函数的响应结构,这里返回的是一个HTTP状态码为200的BaseResponseSchema。