如何将Flask-RESTful组件应用于构建长尾API?

2026-04-11 08:181阅读0评论SEO问题
  • 内容介绍
  • 文章标签
  • 相关推荐

本文共计2368个文字,预计阅读时间需要10分钟。

如何将Flask-RESTful组件应用于构建长尾API?

目录 + Flask-RESTful + 组件 + 一、简介 + 1. 介绍 + 2. REST 特性 + 3. REST 概念 + 4. 环境配置 + 5. 最小API + 二、请求解析 + 1. 请求解析 + 2. 基本参数 + 3. 必需参数 + 4. 多值参数 + 5. 参数转换 + 6. 参数位置

目录
  • flask-restful 组件
    • 一、 简介
      • 1、 介绍
      • 2、 rest 特性
      • 3、 rest 理念
      • 4、 环境配置
      • 5、 最小的API
    • 二、 请求解析
      • 1、 基本参数
      • 2、 必须参数
      • 3、 多值参数
      • 4、 参数转移
      • 5、 参数位置
      • 6、 多个位置
      • 7、 继承解析
    • 三、 输出字段
      • 1、 基本用法
      • 2、 重命名属性
      • 3、 默认值
      • 4、 自定义字段
      • 5、 url字段
      • 6、 复杂结构
      • 7、 列表字段
    • 四、 扩展知识
      • 1、 响应数据
      • 2、 参数验证
      • 3、 资源方法装饰器
      • 4、 错误处理器
    • 五、 服务案例
      • 1、 环境
      • 2、 模型映射
      • 3、 创建路由
      • 4、 创建restful服务
      • 5、 初始化app

flask-restful 组件 一、 简介 1、 介绍

Flask-restful 是一个 Flask 扩展,它添加了快速构建 REST APIs 的支持。它当然也是一个能够跟你现有的ORM/库协同工作的轻量级的扩展。Flask-RESTful 鼓励以最小设置的最佳实践。如果你熟悉 Flask 的话,Flask-restful 应该很容易上手。

关于flask的使用,参考我之前的博客:blog.csdn.net/qq_62789540/article/details/124781918

关于flask的组件,参考我之前的文章:blog.csdn.net/qq_62789540/article/details/125563241

flask-restful官方文档:flask-restful.readthedocs.io/en/latest/quickstart.html

flask-restful中文文档:www.pythondoc.com/Flask-RESTful/index.html

2、 rest 特性
  • Client-Server:服务器端与客户端分离。
  • Stateless(无状态):每次客户端请求必需包含完整的信息,换句话说,每一次请求都是独立的。
  • Cacheable(可缓存):服务器端必需指定哪些请求是可以缓存的。
  • Layered System(分层结构):服务器端与客户端通讯必需标准化,服务器的变更并不会影响客户端。
  • Uniform Interface(统一接口):客户端与服务器端的通讯方法必需是统一的。
  • Code on demand(按需执行代码?):服务器端可以在上下文中执行代码或者脚本?
3、 rest 理念

REST架构就是为了HTTP协议设计的。RESTful web services的核心概念是管理资源。资源是由URIs来表示,客户端使用HTTP当中的'POST, OPTIONS, GET, PUT, DELETE'等方法发送请求到服务器,改变相应的资源状态。

HTTP请求方法通常也十分合适去描述操作资源的动作:

HTTP方法 动作 例子 GET 获取资源信息 example.com/api/orders(检索订单清单) GET 获取资源信息 example.com/api/orders/123(检索订单 #123) POST 创建一个次的资源 example.com/api/orders(使用带数据的请求,创建一个新的订单) PUT 更新一个资源 example.com/api/orders/123(使用带数据的请求,更新#123订单) DELETE 删除一个资源 example.com/api/orders/123删除订单#123

REST请求并不需要特定的数据格式,通常使用JSON作为请求体,或者URL的查询参数的一部份。

4、 环境配置

安装:

pip install flask pip install flask-restx 5、 最小的API

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "app3.py" __time__ = "2022/7/8 9:30" from flask import Flask, url_for from flask_restx import Resource, Api app = Flask(__name__) api = Api(app) """ 也可以这样 api = Api() app = Flask(__name__) api.init_app(app) """ # 这里可以使用类装饰器,注册路由,其可以做add_resource能做的事情 # @api.route("/", "/index", endpoint="hello") class HelloWorld(Resource): def get(self): # print(url_for("hello")) return { "name": "hello world" } def put(self): pass def post(self): pass def delete(self): pass api.add_resource(HelloWorld, '/', "/hello", endpoint="hello") # 添加路由 if __name__ == '__main__': app.run("0.0.0.0", 5000, debug=True) 二、 请求解析

Flask-RESTful的请求解析接口是模仿argparse接口。它设计成提供简单并且同一的访问Flask中flask.request 对象里的任何变量的入口

1、 基本参数

from flask_restful import reqparse parser = reqparse.RequestParser() # 创建一个参数接收器 parser.add_argument('rate', type=int, help='Rate cannot be converted') # 添加基本参数 parser.add_argument('name', type=str) args = parser.parse_args() # 解析参数

如果你指定了 help 参数的值,在解析的时候当类型错误被触发的时候,它将会被作为错误信息给呈现出来。如果你没有指定 help 信息的话,默认行为是返回类型错误本身的信息。

默认下,arguments 不是 必须的。另外,在请求中提供的参数不属于 RequestParser 的一部分的话将会被忽略。

另请注意:在请求解析中声明的参数如果没有在请求本身设置的话将默认为 None

2、 必须参数

要求一个值传递的参数,只需要添加required=True来调用add_argument()

parser.add_argument('name', type=str, required=True, help="Name cannot be blank!") 3、 多值参数

如果你要接受一个键有多个值的话,你可以传入 action='append'

parser.add_argument('name', type=str, action='append')

这样,查询的话:

curl api.example.com -d "Name=bob" -d "Name=sue" -d "Name=joe" 4、 参数转移

如果由于某些原因,你想要以不同的名称存储你的参数,一旦它被解析的时候,你可以使用dest=arg

parser.add_argument('name', type=str, dest='public_name') args = parser.parse_args() print(args['public_name']) 5、 参数位置

默认下,RequestParser 试着从 flask.Request.values,以及 flask.Request.json 解析值。

add_argument() 中使用 location 参数可以指定解析参数的位置。flask.Request 中任何变量都能被使用。例如:

# Look only in the POST body parser.add_argument('name', type=int, location='form') # Look only in the querystring parser.add_argument('PageSize', type=int, location='args') # From the request headers parser.add_argument('User-Agent', type=str, location='headers') # From /app.db" SQLALCHEMY_DATABASE_URI = DB_URI # 使用sqlachemy SQLALCHEMY_TRACK_MODIFICATIONS = True SWAGGER_TITLE = "API" SWAGGER_DESC = "API接口" # 地址,必须带上端口号 SWAGGER_HOST = "localhost:5000" class Product(): pass 2、 模型映射

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "models.py" __time__ = "2022/7/9 21:32" from . import db class Foo(db.Model): """ 模型,将映射到数据库表中 """ def __init__(self, id, name, age): self.id = id self.name = name self.age = age __tablename__ = 'foo' # 主键ID id = db.Column(db.INTEGER, primary_key=True, autoincrement=True) # 名字 name = db.Column(db.String(100), nullable=False) # 年龄 age = db.Column(db.INTEGER)

然后在终端运行:

flask db init flask db migrate flask db upgrade 3、 创建路由

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "test.py" __time__ = "2022/7/9 21:23" from flask import Blueprint, url_for, redirect from flaskApp.models import Foo from flaskApp import db te = Blueprint("te", __name__) from . import api_te @te.route("/index") def index(): """则,这里只要关注返回页面的请求,返回数据交给restful去处理""" return redirect(url_for("te.operateData")) # 这里就只是进行一个简单的模拟,进行重定向访问,实际开发中可以使用Ajax异步请求 @te.route("/add") def search(): """这里为了方便,我们使用add路由来添加数据""" db.session.add(Foo(1, "李华", 23)) db.session.commit() db.session.remove() return "success" 4、 创建restful服务

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "api_te.py" __time__ = "2022/7/9 21:52" from flask import request, jsonify from .test import te from flask_restful import Api, Resource, fields, marshal_with, reqparse from flaskApp import db from flaskApp.models import Foo from flaskApp.tools import HttpCode api = Api(te) def restful_result(code, message, data): return jsonify({"code": code, "message": message, "data": data or {}}) def success(message="", data=None): """ 正确返回 :return: """ return restful_result(code=HttpCode.ok, message=message, data=data) class FooListApi(Resource): # 定义要返回的字段 resource_fields = { 'id': fields.Integer, 'name': fields.String, 'age': fields.String } # 装饰器,定义返回数据 @marshal_with(resource_fields) def get(self): """ 返回所有记录 :return: """ parser = reqparse.RequestParser() parser.add_argument('name', type=str, location='args', help='必须输入姓名') # 注意,如果添加了parser参数解析,则,返回数据需要是JSON数据 arg = parser.parse_args() print(arg) # 127.0.0.1:5000/api/v1/foo?name=1&a=2 终端输出: {'name': '1'} # 查询数据库 foos = db.session.query(Foo).all() return { "data": foos, "status": HttpCode.ok } def post(self): """ 创建一条记录 :return: """ # 参数 params = request.get_json() name = params.get("name") age = params.get("age") # 构建一个模型 foo = Foo(name=name, age=age) # 加入到数据库 db.session.add(foo) db.session.commit() return success("新增一条记录成功!") # 所有记录 api.add_resource(FooListApi, '/api/v1/foo', endpoint="operateData") # 返回数据 5、 初始化app

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "__init__.py" __time__ = "2022/7/9 21:20" from flask import Flask from . import settings from flask_sqlalchemy import SQLAlchemy db = SQLAlchemy() from .views.test import te # 必须要在db创建后导入 def create_app(): app = Flask(__name__) app.register_blueprint(te) app.config.from_object(settings.Basic) db.init_app(app) return app

完整项目在:github.com/liuzhongkun1/flask_/tree/main/flaskRestful

如何将Flask-RESTful组件应用于构建长尾API?

本文共计2368个文字,预计阅读时间需要10分钟。

如何将Flask-RESTful组件应用于构建长尾API?

目录 + Flask-RESTful + 组件 + 一、简介 + 1. 介绍 + 2. REST 特性 + 3. REST 概念 + 4. 环境配置 + 5. 最小API + 二、请求解析 + 1. 请求解析 + 2. 基本参数 + 3. 必需参数 + 4. 多值参数 + 5. 参数转换 + 6. 参数位置

目录
  • flask-restful 组件
    • 一、 简介
      • 1、 介绍
      • 2、 rest 特性
      • 3、 rest 理念
      • 4、 环境配置
      • 5、 最小的API
    • 二、 请求解析
      • 1、 基本参数
      • 2、 必须参数
      • 3、 多值参数
      • 4、 参数转移
      • 5、 参数位置
      • 6、 多个位置
      • 7、 继承解析
    • 三、 输出字段
      • 1、 基本用法
      • 2、 重命名属性
      • 3、 默认值
      • 4、 自定义字段
      • 5、 url字段
      • 6、 复杂结构
      • 7、 列表字段
    • 四、 扩展知识
      • 1、 响应数据
      • 2、 参数验证
      • 3、 资源方法装饰器
      • 4、 错误处理器
    • 五、 服务案例
      • 1、 环境
      • 2、 模型映射
      • 3、 创建路由
      • 4、 创建restful服务
      • 5、 初始化app

flask-restful 组件 一、 简介 1、 介绍

Flask-restful 是一个 Flask 扩展,它添加了快速构建 REST APIs 的支持。它当然也是一个能够跟你现有的ORM/库协同工作的轻量级的扩展。Flask-RESTful 鼓励以最小设置的最佳实践。如果你熟悉 Flask 的话,Flask-restful 应该很容易上手。

关于flask的使用,参考我之前的博客:blog.csdn.net/qq_62789540/article/details/124781918

关于flask的组件,参考我之前的文章:blog.csdn.net/qq_62789540/article/details/125563241

flask-restful官方文档:flask-restful.readthedocs.io/en/latest/quickstart.html

flask-restful中文文档:www.pythondoc.com/Flask-RESTful/index.html

2、 rest 特性
  • Client-Server:服务器端与客户端分离。
  • Stateless(无状态):每次客户端请求必需包含完整的信息,换句话说,每一次请求都是独立的。
  • Cacheable(可缓存):服务器端必需指定哪些请求是可以缓存的。
  • Layered System(分层结构):服务器端与客户端通讯必需标准化,服务器的变更并不会影响客户端。
  • Uniform Interface(统一接口):客户端与服务器端的通讯方法必需是统一的。
  • Code on demand(按需执行代码?):服务器端可以在上下文中执行代码或者脚本?
3、 rest 理念

REST架构就是为了HTTP协议设计的。RESTful web services的核心概念是管理资源。资源是由URIs来表示,客户端使用HTTP当中的'POST, OPTIONS, GET, PUT, DELETE'等方法发送请求到服务器,改变相应的资源状态。

HTTP请求方法通常也十分合适去描述操作资源的动作:

HTTP方法 动作 例子 GET 获取资源信息 example.com/api/orders(检索订单清单) GET 获取资源信息 example.com/api/orders/123(检索订单 #123) POST 创建一个次的资源 example.com/api/orders(使用带数据的请求,创建一个新的订单) PUT 更新一个资源 example.com/api/orders/123(使用带数据的请求,更新#123订单) DELETE 删除一个资源 example.com/api/orders/123删除订单#123

REST请求并不需要特定的数据格式,通常使用JSON作为请求体,或者URL的查询参数的一部份。

4、 环境配置

安装:

pip install flask pip install flask-restx 5、 最小的API

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "app3.py" __time__ = "2022/7/8 9:30" from flask import Flask, url_for from flask_restx import Resource, Api app = Flask(__name__) api = Api(app) """ 也可以这样 api = Api() app = Flask(__name__) api.init_app(app) """ # 这里可以使用类装饰器,注册路由,其可以做add_resource能做的事情 # @api.route("/", "/index", endpoint="hello") class HelloWorld(Resource): def get(self): # print(url_for("hello")) return { "name": "hello world" } def put(self): pass def post(self): pass def delete(self): pass api.add_resource(HelloWorld, '/', "/hello", endpoint="hello") # 添加路由 if __name__ == '__main__': app.run("0.0.0.0", 5000, debug=True) 二、 请求解析

Flask-RESTful的请求解析接口是模仿argparse接口。它设计成提供简单并且同一的访问Flask中flask.request 对象里的任何变量的入口

1、 基本参数

from flask_restful import reqparse parser = reqparse.RequestParser() # 创建一个参数接收器 parser.add_argument('rate', type=int, help='Rate cannot be converted') # 添加基本参数 parser.add_argument('name', type=str) args = parser.parse_args() # 解析参数

如果你指定了 help 参数的值,在解析的时候当类型错误被触发的时候,它将会被作为错误信息给呈现出来。如果你没有指定 help 信息的话,默认行为是返回类型错误本身的信息。

默认下,arguments 不是 必须的。另外,在请求中提供的参数不属于 RequestParser 的一部分的话将会被忽略。

另请注意:在请求解析中声明的参数如果没有在请求本身设置的话将默认为 None

2、 必须参数

要求一个值传递的参数,只需要添加required=True来调用add_argument()

parser.add_argument('name', type=str, required=True, help="Name cannot be blank!") 3、 多值参数

如果你要接受一个键有多个值的话,你可以传入 action='append'

parser.add_argument('name', type=str, action='append')

这样,查询的话:

curl api.example.com -d "Name=bob" -d "Name=sue" -d "Name=joe" 4、 参数转移

如果由于某些原因,你想要以不同的名称存储你的参数,一旦它被解析的时候,你可以使用dest=arg

parser.add_argument('name', type=str, dest='public_name') args = parser.parse_args() print(args['public_name']) 5、 参数位置

默认下,RequestParser 试着从 flask.Request.values,以及 flask.Request.json 解析值。

add_argument() 中使用 location 参数可以指定解析参数的位置。flask.Request 中任何变量都能被使用。例如:

# Look only in the POST body parser.add_argument('name', type=int, location='form') # Look only in the querystring parser.add_argument('PageSize', type=int, location='args') # From the request headers parser.add_argument('User-Agent', type=str, location='headers') # From /app.db" SQLALCHEMY_DATABASE_URI = DB_URI # 使用sqlachemy SQLALCHEMY_TRACK_MODIFICATIONS = True SWAGGER_TITLE = "API" SWAGGER_DESC = "API接口" # 地址,必须带上端口号 SWAGGER_HOST = "localhost:5000" class Product(): pass 2、 模型映射

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "models.py" __time__ = "2022/7/9 21:32" from . import db class Foo(db.Model): """ 模型,将映射到数据库表中 """ def __init__(self, id, name, age): self.id = id self.name = name self.age = age __tablename__ = 'foo' # 主键ID id = db.Column(db.INTEGER, primary_key=True, autoincrement=True) # 名字 name = db.Column(db.String(100), nullable=False) # 年龄 age = db.Column(db.INTEGER)

然后在终端运行:

flask db init flask db migrate flask db upgrade 3、 创建路由

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "test.py" __time__ = "2022/7/9 21:23" from flask import Blueprint, url_for, redirect from flaskApp.models import Foo from flaskApp import db te = Blueprint("te", __name__) from . import api_te @te.route("/index") def index(): """则,这里只要关注返回页面的请求,返回数据交给restful去处理""" return redirect(url_for("te.operateData")) # 这里就只是进行一个简单的模拟,进行重定向访问,实际开发中可以使用Ajax异步请求 @te.route("/add") def search(): """这里为了方便,我们使用add路由来添加数据""" db.session.add(Foo(1, "李华", 23)) db.session.commit() db.session.remove() return "success" 4、 创建restful服务

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "api_te.py" __time__ = "2022/7/9 21:52" from flask import request, jsonify from .test import te from flask_restful import Api, Resource, fields, marshal_with, reqparse from flaskApp import db from flaskApp.models import Foo from flaskApp.tools import HttpCode api = Api(te) def restful_result(code, message, data): return jsonify({"code": code, "message": message, "data": data or {}}) def success(message="", data=None): """ 正确返回 :return: """ return restful_result(code=HttpCode.ok, message=message, data=data) class FooListApi(Resource): # 定义要返回的字段 resource_fields = { 'id': fields.Integer, 'name': fields.String, 'age': fields.String } # 装饰器,定义返回数据 @marshal_with(resource_fields) def get(self): """ 返回所有记录 :return: """ parser = reqparse.RequestParser() parser.add_argument('name', type=str, location='args', help='必须输入姓名') # 注意,如果添加了parser参数解析,则,返回数据需要是JSON数据 arg = parser.parse_args() print(arg) # 127.0.0.1:5000/api/v1/foo?name=1&a=2 终端输出: {'name': '1'} # 查询数据库 foos = db.session.query(Foo).all() return { "data": foos, "status": HttpCode.ok } def post(self): """ 创建一条记录 :return: """ # 参数 params = request.get_json() name = params.get("name") age = params.get("age") # 构建一个模型 foo = Foo(name=name, age=age) # 加入到数据库 db.session.add(foo) db.session.commit() return success("新增一条记录成功!") # 所有记录 api.add_resource(FooListApi, '/api/v1/foo', endpoint="operateData") # 返回数据 5、 初始化app

# !/usr/bin/python3 # -*- coding: UTF-8 -*- __author__ = "A.L.Kun" __file__ = "__init__.py" __time__ = "2022/7/9 21:20" from flask import Flask from . import settings from flask_sqlalchemy import SQLAlchemy db = SQLAlchemy() from .views.test import te # 必须要在db创建后导入 def create_app(): app = Flask(__name__) app.register_blueprint(te) app.config.from_object(settings.Basic) db.init_app(app) return app

完整项目在:github.com/liuzhongkun1/flask_/tree/main/flaskRestful

如何将Flask-RESTful组件应用于构建长尾API?