Flask学习笔记(4)
Flask-RESTful是用于快速构建REST API的Flask扩展
安装Flask-RESTful
pip install flask-restful
入门Flask-RESTful
from flask import Flask
from flask_restful import Resource, Api
app = Flask(__name__)
api = Api(app)
class HelloWorldResource(Resource):
def get(self):
return {'Hello': 'World'}
def post(self):
return {'msg': 'post hello world'}
api.add_resource(HelloWorldResource,'/')
if __name__ == '__main__':
app.run(debug=True)
关于视图
为路由起别名
通过 endpoint
参数
api.add_resource(HelloWorldResource, '/', endpoint='helloworld')
蓝图中使用
from flask import Flask, Blueprint
from flask_restful import Resource, Api
app = Flask(__name__)
bp = Blueprint('bp', __name__)
api = Api(bp)
class HelloWorldResource(Resource):
def get(self):
return {'Hello': 'World'}
def post(self):
return {'msg': 'post hello world'}
api.add_resource(HelloWorldResource, '/')
app.register_blueprint(bp)
if __name__ == '__main__':
app.run(debug=True)
装饰器
from flask import Flask
from flask_restful import Resource, Api
app = Flask(__name__)
api = Api(app)
def decorator1(func):
def wrapper(*args, **kwargs):
print('decorator1')
return func(*args, **kwargs)
return wrapper
def decorator2(func):
def wrapper(*args, **kwargs):
print('decorator2')
return func(*args, **kwargs)
return wrapper
class HelloWorldResource(Resource):
method_decorators = [decorator1, decorator2]
def get(self):
return {'msg': 'get view'}
def post(self):
return {'msg': 'post hello world'}
api.add_resource(HelloWorldResource, '/')
if __name__ == '__main__':
app.run(debug=True)
注意:先打印decorator2,后打印decorator1
关于请求处理
Flask-RESTful提供了RequestParser类,用来帮助我们检验和转换请求数据。
使用步骤:
- 创建RequestParser对象
- 向RequestParser对象中添加需要检验或转换的参数声明
- 使用parse_args()方法检验处理
- 从检验结果中获取参数时可以按照字典或者对象属性操作
示例:
from flask import Flask
from flask_restful import Resource, Api
from flask_restful.reqparse import RequestParser
app = Flask(__name__)
api = Api(app)
# /hello?a=1&b=2
class HelloWorldResource(Resource):
def get(self):
# 1.创建RequestParser对象
rq = RequestParser()
# 2.声明参数
rq.add_argument('a')
rq.add_argument('b')
# 3.执行检验
req = rq.parse_args()
# 可以将req当作字典或者对象
# a = req['a']
a = req.a
return {'a': a}
api.add_resource(HelloWorldResource, '/hello')
if __name__ == '__main__':
app.run(debug=True)
常用参数说明:
- requeired
描述请求是否必须携带对应参数,默认时False
rq.add_argument('a', required=True)
- help
参数检验错误时返回的错误描述信息
rq.add_argument('a', required=True, help='missing a')
- action
描述对象请求参数中出现多个同名参数时的处理方式
-
action='store' 保留出现的第一个,默认
-
action='append' 以列表形式追加报错所有同名参数的值
rq.add_argument('a', required=True, help='missing a', action='append')
访问后显示如下
- type
描述参数应该匹配的类型,可以使用python的标准数据类型string、int,也可以使用Flask-RESTful提供的检验方法,还可以自己定义。
- 标准类型
rq.add_argument('a', type=int required=True, help='missing a', action='append')
- Flask-RESTful提供
检验类型方法在flask_restful.inputs模块中
url:是否符合url
regex:正则表达式
rq.add_argument('a', type=inputs.regex(r'^\d{2}&'))
natual:自然数0、1、2、3...
positive:正整数1、2、3...
int_range(low, high):整数范围
rq.add_argument('a', type=inputs.int_range(1, 10))
boolean:布尔值
- location
描述参数在请求数据中出现的位置
rq.add_argument('a', type=int, location='form')
rq.add_argument('a', type=int, location='args')
...
关于响应处理
序列化数据
Flask-RESTful提供了marshal工具,用来帮我们把数据序列化为特定格式的字典数据以便作为视图的返回值。
分为装饰器和不使用装饰器两种方式:
from flask import Flask
from flask_restful import Resource, Api, fields, marshal_with, marshal
from flask_restful.reqparse import RequestParser
app = Flask(__name__)
api = Api(app)
class User(object):
def __init__(self,user_id, name, age):
self.user_id = user_id
self.name = name
self.age = age
# 声明需要序列化处理的字段
resource_fields = {
'user_id': fields.Integer,
'name': fields.String
}
# 方式1
class HelloWorldResource1(Resource):
@marshal_with(resource_fields, envelope='data1')
def get(self):
user = User(1, 'xiaoming', 18)
return user
# 方式2
class HelloWorldResource2(Resource):
def get(self):
user = User(1, 'xiaoming', 18)
return marshal(user, resource_fields, envelope='data2')
api.add_resource(HelloWorldResource1, '/hello')
if __name__ == '__main__':
app.run(debug=True)
定制返回的JSON格式
需求:想要接口返回的JSON数据具有以下统一的格式
{"message": "描述信息", "data": {返回的具体数据}}
Flask-RESTful的API对象提供了一个 representation
装饰器,允许定制返回数据的呈现格式。
@api.representation('application/json')
def output_json(data, code, headers=None):
if 'message' not in data:
data = {
'message': 'OK',
'data': data
}