支持Flask快速构建REST API 官方文档:https://flask-restful.readthedocs.io/en/latest/

快速安装
  1. pip3 install flask-restful

使用示例
  1. from flask import Flask, request, Response
  2. from flask_restful import Resource, Api, abort
  3. app = Flask(__name__)
  4. api = Api(app)
  5. todos = {}
  6. """继承资源类Resource,在类中定义方法"""
  7. class TodoSimple(Resource):
  8. """restful 接口"""
  9. def get(self, todo_id):
  10. """get请求-获取数据"""
  11. if not todos.get(todo_id):
  12. # abort(Response("查询失败", 404))
  13. abort(404, message="Todo {} doesn't exist".format(todo_id))
  14. return {todo_id: todos.get(todo_id)}
  15. def put(self, todo_id):
  16. """put请求-更新数据"""
  17. todos[todo_id] = request.form.get("data")
  18. return {todo_id: todos[todo_id]}
  19. def post(self, todo_id):
  20. """post请求-创建数据"""
  21. todos[todo_id] = request.form.get("data")
  22. return {
  23. "status_code": 200,
  24. "msg": "success"
  25. }
  26. def delete(self, todo_id):
  27. """delete请求-删除数据"""
  28. todos[todo_id] = request.form.get("data")
  29. if not todos.get(todo_id):
  30. abort(Response('删除失败', 404))
  31. del todos[todo_id]
  32. return {
  33. "status_code": 200,
  34. "msg": "success"
  35. }
  36. """向 api 添加资源"""
  37. api.add_resource(TodoSimple, '/<string:todo_id>')
  38. # 设置端点
  39. # api.add_resource(TodoSimple, '/<string:todo_id>', endpoint="home")
  40. if __name__ == "__main__":
  41. app.run(debug=True)

参数解析-reqparse
  1. parser = reqparse.RequestParser(bundle_errors=True)
  2. parser.add_argument('data', type=str, help='请求参数必须是字符串', required=True, location='form')
  3. args = self.parser.parse_args(strict=True)

通过flask_restful内置的reqparse,提供对请求数据验证的支持

  1. strict=True: 为强校验,包含解析器未定义的参数则抛出异常
  2. required=True: 可设置参数为必填参数
  3. location:可指定提取值的位置:form、args、headers、cookies、files
  4. bundle_errors=True:将错误捆绑在一起并一次发送回客户端

更多见:https://flask-restful.readthedocs.io/en/latest/reqparse.html#basic-arguments

  1. # 使用实例
  2. from flask_restful import Resource, Api, abort, reqparse
  3. class TodoSimple(Resource):
  4. """restful 接口"""
  5. # 请求参数解析,增加参数验证
  6. parser = reqparse.RequestParser()
  7. parser.add_argument('data', type=str, help='请求参数必须是字符串')
  8. def put(self, todo_id):
  9. """put请求-更新数据"""
  10. # strict=True 为强校验,包含解析器未定义的参数则抛出异常
  11. args = self.parser.parse_args(strict=True)
  12. # todos[todo_id] = request.form.get("data")
  13. todos[todo_id] = args["data"]
  14. return {todo_id: todos[todo_id]}, 201
  15. def post(self, todo_id):
  16. """post请求-创建数据"""
  17. args = self.parser.parse_args(strict=True)
  18. todos[todo_id] = args["data"]
  19. # todos[todo_id] = request.form.get("data")
  20. return {
  21. "status_code": 200,
  22. "msg": "success"
  23. }

输出字段-Fields

控制响应数据的呈现 1.可以在资源中使用任何您想要的对象(ORM 模型/自定义类/等) 2.还可以让您格式化和过滤响应,以防暴露内部数据结构 envelope:指定可选关键字参数包装结果输出 marshal_with装饰器:获取您的数据对象并应用字段过滤 更多见:https://flask-restful.readthedocs.io/en/latest/fields.html

  1. from flask import Flask
  2. from flask_restful import Resource, Api, abort, reqparse, fields, marshal_with
  3. from typing import Optional
  4. app = Flask(__name__)
  5. api = Api(app)
  6. resource_fields = {
  7. 'task': fields.String,
  8. "todo_id": fields.String,
  9. "status": fields.String(default="success")
  10. }
  11. class TodoDao(object):
  12. """响应参数类"""
  13. def __init__(self, todo_id, task, status: Optional[str] = None):
  14. self.todo_id = todo_id
  15. self.task = task
  16. self.status = status
  17. class Todo(Resource):
  18. """数据格式化"""
  19. # envelope指定可选关键字参数包装结果输出
  20. # marshal_with装饰器:获取您的数据对象并应用字段过滤
  21. # @marshal_with(resource_fields)
  22. @marshal_with(resource_fields, envelope='resource')
  23. def get(self, **kwargs):
  24. """get"""
  25. return TodoDao(todo_id="todo2", task='Remember the milk')
  26. """向 api 添加资源"""
  27. api.add_resource(Todo, "/todo_resource")
  28. if __name__ == "__main__":
  29. app.run(debug=True)
  30. """
  31. # 响应示例
  32. {
  33. "resource": {
  34. "task": "Remember the milk",
  35. "todo_id": "todo2",
  36. "status": "success"
  37. }
  38. }
  39. """

项目结构实践
  1. /
  2. /api_resource/ :存放接口资源
  3. /__init.py
  4. /common/ :存放公共配置
  5. /config.py
  6. /__init.py
  7. /static/ :静态文件
  8. /templates/ :模版
  9. /utils/
  10. /__init.py
  11. /app.py flask程序实例&链接mongo
  12. /main.py :向api添加资源,启动flask主程序
  1. # /utils/app.py
  2. from flask_restful import Api
  3. from logzero import logger
  4. from flask_pymongo import PyMongo
  5. from flask import Flask
  6. from common import config
  7. """创建flask程序实例&链接mongo"""
  8. app = Flask(__name__)
  9. api = Api(app)
  10. """链接mongodb"""
  11. app.config["MONGO_URI"] = ''.join([config.mongodb_str, "/", config.MONGODB_DBNAME, "?authSource=admin"])
  12. mongo = PyMongo(app)
  13. DB = mongo.db
  14. logger.info(f"成功链接mongo: {DB}")
  15. # /api_resource/api_test.py
  16. from flask import jsonify
  17. from flask_restful import Resource, abort
  18. from logzero import logger
  19. from utils.app import DB
  20. class TestApi(Resource):
  21. """restful api"""
  22. def get(self):
  23. """get"""
  24. logger.info("restful test")
  25. logger.info(DB.test.find_one({}))
  26. return jsonify(message="success")
  27. # /utils/main.py
  28. """向api添加资源,启动flask主程序"""
  29. from api_resource.api_test import TestApi
  30. from logzero import logger
  31. from app import api, app
  32. api.add_resource(TestApi, "/add_one")
  33. if __name__ == "__main__":
  34. app.run(host="0.0.0.0", debug=True)