1

I am trying to use flasgger to generate both the OpenAPI 2.0 spec and validate my endpoint payloads.

To avoid duplications I want to define the models in the swagger config definitions. The Swagger UI is generated correctly and it appears to be working, but when I post a payload to be validated I am getting the following error: KeyError: 'definitions'.

The project structure is as follows:

.
├── app
│   ├── __init__.py
│   └── blueprints
│       └── accounts
│           └── __init__.py
└── application.py

Contents of application.py:

from app import create_app

application = create_app()

if __name__ == "__main__":
    application.run(host="0.0.0.0", port=5000, debug=True)

Contents of app/__init__.py:

from flasgger import Swagger
from flask import Flask

template = {
    "swagger": "2.0",
    "info": {
        "title": "Test App",
    },
    "basePath": "/api/v1",  # base bash for blueprint registration
    "schemes": ["http", "https"],
}

swagger_config = {
    "headers": [],
    "specs": [
        {
            "endpoint": "apispec",
            "route": "/apispec.json",
        }
    ],
    "static_url_path": "/flasgger_static",
    "swagger_ui": True,
    "specs_route": "/",
    "swagger_ui_bundle_js": "//unpkg.com/swagger-ui-dist@3/swagger-ui-bundle.js",
    "swagger_ui_standalone_preset_js": "//unpkg.com/swagger-ui-dist@3/swagger-ui-standalone-preset.js",
    "jquery_js": "//unpkg.com/jquery@2.2.4/dist/jquery.min.js",
    "swagger_ui_css": "//unpkg.com/swagger-ui-dist@3/swagger-ui.css",
    "definitions": {
        "User": {
            "type": "object",
            "properties": {
                "id": {"type": "integer", "description": "UserId"},
                "email": {
                    "type": "string",
                    "description": "john.doe@abc123.com",
                },
                "first_name": {"type": "string", "description": "John"},
                "last_name": {"type": "string", "description": "Doe"},
            },
        }
    },
}


def create_app():
    app = Flask(__name__)

    Swagger(app, config=swagger_config, template=template)

    from app.blueprints.accounts import accounts_blueprint

    app.register_blueprint(accounts_blueprint, url_prefix="/api/v1/accounts")

    return app

Contents of app/blueprints/__init__.py:

# user, accounts, subscription managment
from flask import Blueprint
from flask import jsonify
from flasgger import swag_from

accounts_blueprint = Blueprint("accounts", __name__)

user_create_swag = {
    "tags": ["Accounts"],
    "parameters": [
        {
            "name": "body",
            "in": "body",
            "required": True,
            "schema": {
                "id": "User",
                "$ref": "#/definitions/User",
                "required": ["email"],
            },
        },
    ],
    "responses": {
        "200": {
            "description": "The user inserted in the database",
            "schema": {"$ref": "#/definitions/User"},
        }
    },
}


@accounts_blueprint.route("/users", methods=["POST"], endpoint="user_post")
@swag_from(user_create_swag, validation=True, endpoint="accounts.user_post")
def create_user():
    # logic goes here
    return jsonify(200)

I am using Python 3.9.2, Flask==2.2.3 and flasgger==0.9.5. I am running the application using flask run and making the request using CURL:

curl -X 'POST' \
  'http://127.0.0.1:5000/api/v1/accounts/users' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "email": "string",
  "first_name": "string",
  "id": 0,
  "last_name": "string"
}'

The error I am getting is the following (full traceback from the console):

[2023-03-22 12:57:46,281] ERROR in app: Exception on /api/v1/accounts/users [POST]
Traceback (most recent call last):
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flask/app.py", line 2528, in wsgi_app
    response = self.full_dispatch_request()
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flask/app.py", line 1825, in full_dispatch_request
    rv = self.handle_user_exception(e)
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flask/app.py", line 1823, in full_dispatch_request
    rv = self.dispatch_request()
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flask/app.py", line 1799, in dispatch_request
    return self.ensure_sync(self.view_functions[rule.endpoint])(**view_args)
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flasgger/utils.py", line 266, in wrapper
    validate(
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flasgger/utils.py", line 438, in validate
    main_def = __replace_ref(main_def, relative_path, swag)
  File "/Users/luisf/flasgger_issue/.venv/lib/python3.9/site-packages/flasgger/utils.py", line 298, in __replace_ref
    content = content[id]
KeyError: 'definitions'

Can you please advise on what might be causing this issue?

luisf
  • 84
  • 4

0 Answers0