首页
/ Flasgger项目实战:基于Flask的Swagger UI集成指南

Flasgger项目实战:基于Flask的Swagger UI集成指南

2025-07-09 05:01:17作者:幸俭卉

概述

Flasgger是一个强大的Python库,它能够将Swagger UI无缝集成到Flask应用中。本文将通过一个完整的示例应用,深入讲解如何使用Flasgger为Flask API生成美观且功能完善的Swagger文档。

基础配置

首先,我们需要在Flask应用中初始化Flasgger。基本的配置包括:

from flask import Flask
from flasgger import Swagger

app = Flask(__name__)
swag = Swagger(app)

Flasgger支持多版本API文档配置,我们可以通过SWAGGER配置项定义多个API规范:

app.config['SWAGGER'] = {
    "swagger_version": "2.0",
    "title": "Flasgger",
    "specs": [
        {
            "version": "0.0.1",
            "title": "Api v1",
            "endpoint": 'v1_spec',
            "route": '/v1/spec',
            "rule_filter": lambda rule: rule.endpoint.startswith('should_be_v1_only')
        },
        {
            "version": "0.0.2",
            "title": "Api v2",
            "endpoint": 'v2_spec',
            "route": '/v2/spec',
            "rule_filter": lambda rule: rule.endpoint.startswith('should_be_v2_only')
        }
    ]
}

编写API端点

使用MethodView类

Flasgger支持Flask的MethodView类,我们可以为每个HTTP方法添加Swagger文档:

from flask.views import MethodView
from flask import jsonify

class UserAPI(MethodView):
    def get(self, team_id):
        """
        Get a list of users
        ---
        tags:
          - users
        parameters:
          - name: team_id
            in: path
            type: integer
            default: 42
        responses:
          200:
            description: Returns a list of users
            schema:
                type: array
                items:
                    $ref: '#/definitions/User'
        """
        data = {"users": [...]}
        return jsonify(data)

注册路由

注册路由时需要注意端点命名,以便规则过滤器能够正确识别:

view = UserAPI.as_view('users')
app.add_url_rule(
    '/v1/users/<int:team_id>',
    view_func=view,
    methods=['GET'],
    endpoint='should_be_v1_only'  # 匹配v1规则过滤器
)

外部YAML规范文件

Flasgger支持从外部YAML文件加载API规范,有两种方式:

使用装饰器

from flasgger.utils import swag_from

@app.route('/v1/decorated/<username>')
@swag_from('username_specs.yml')
def fromfile_decorated(username):
    return jsonify({'username': username})

在docstring中引用

@app.route('/v1/fileindoc/<username>')
def fromfile_indocstring(username):
    """
    file: username_specs.yml
    """
    return jsonify({'username': username})

数据模型定义

Flasgger提供了多种定义数据模型的方式:

使用装饰器定义简单模型

@swag.definition('Hack', tags=['v2_model'])
def hack(subitems):
    """
    Hack Object
    ---
    properties:
      hack:
        type: string
        description: it's a hack
      subitems:
        type: array
        items:
          $ref: '#/definitions/SubItem'
    """
    return {'hack': "string", 'subitems': [...]}

定义复杂类模型

@swag.definition('SubItem', tags=['v2_model'])
class SubItem(object):
    """
    SubItem Object
    ---
    properties:
      bla:
        type: string
        description: Bla
      blu:
        type: integer
        description: Blu
    """
    def __init__(self, bla, blu):
        self.bla = str(bla)
        self.blu = int(blu)

    def dump(self):
        return dict(vars(self).items())

跨域支持

Flasgger默认支持跨域访问,我们也可以自定义跨域配置:

@app.after_request
def allow_origin(response):
    response.headers['Access-Control-Allow-Origin'] = 'http://example.com'
    response.headers['Access-Control-Allow-Credentials'] = 'true'
    return response

复杂API示例

下面是一个复杂的推荐API示例,展示了请求体、路径参数和嵌套模型的用法:

@app.route("/v2/recommendation/<target_type>/<item_type>", methods=['POST'])
def recommend(target_type, item_type):
    """
    Recommendation
    Get a single item_type as recommendation for the target_type
    ---
    tags:
      - recommendation
    parameters:
      - name: target_type
        in: path
        type: string
        default: candidate
      - name: item_type
        in: path
        type: string
        default: openings
      - in: body
        name: body
        schema:
          id: rec_query
          required:
            - candidate_id
            - context
          properties:
            candidate_id:
              type: integer
              default: 123456
            context:
              type: object
              schema:
                $ref: '#/definitions/rec_query_context'
    responses:
      200:
        description: A single recommendation item
        schema:
          id: rec_response
          properties:
            opening_id:
              type: integer
              default: 123456
    """
    return jsonify({"opening_id": 12312313434})

运行应用

最后,我们可以运行Flask应用并访问Swagger UI:

if __name__ == "__main__":
    app.run(debug=True)

启动后,可以通过以下URL访问不同版本的API文档:

  • /apidocs/index.html?url=/v1/spec - API版本1
  • /apidocs/index.html?url=/v2/spec - API版本2

总结

通过本文的示例,我们学习了如何使用Flasgger为Flask应用添加Swagger UI支持,包括:

  1. 基础配置和多版本API支持
  2. 使用MethodView类组织API端点
  3. 从外部YAML文件加载API规范
  4. 定义复杂的数据模型
  5. 实现跨域支持
  6. 构建复杂的API端点

Flasgger的强大功能使得API文档的编写和维护变得简单高效,是Flask开发者不可或缺的工具。