Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Bug] Decorator doc/openapi not work when using routes of HTTPMethodView under Bluebprint instanc way #233

Closed
hsz1273327 opened this issue May 14, 2021 · 1 comment · Fixed by #234

Comments

@hsz1273327
Copy link

Describe the bug
Decorator doc/openapi not work when using routes of HTTPMethodView under Bluebprint instanc way,

Screenshots
api-2

To Reproduce

  • file1
from sanic import Blueprint
from .userlistsource import UserListSource
from .usersource import UserSource

usernamespace_v1 = Blueprint("user", url_prefix="/user", version=1)
usernamespace_v1.add_route(UserListSource.as_view(), "/")
usernamespace_v1.add_route(UserSource.as_view(), "/<uid:int>")
  • userlistsource.py
from sanic.response import json, HTTPResponse
from sanic.request import Request
from sanic.views import HTTPMethodView
from sanic_openapi import doc
from decorators.checkjsonschema import checkjsonschema
from modules.usermodule import UserDB

post_query_schema = {
    "$schema": "http://json-schema.org/draft-07/schema#",
    "type": "object",
    "additionalProperties": False,
    "required": ["name"],
    "properties": {
        "name": {
            "type": "string",
            "description": "用户注册名"
        }
    }
}


class UserListSource(HTTPMethodView):

    @doc.operation('UserListSource_GET')
    @doc.summary("user接口总览")
    async def get(self, _: Request) -> HTTPResponse:
        cnt = await UserDB.len()
        result = {
            "description": "测试api,User总览",
            "user-count": cnt,
            "links": [
                {
                    "uri": "/user",
                    "method": "POST",
                    "description": "创建一个新用户"
                },
                {
                    "uri": "/user/<int:uid>",
                    "method": "GET",
                    "description": "用户号为<id>的用户信息"
                },
                {
                    "uri": "/user/<int:uid>",
                    "method": "PUT",
                    "description": "更新用户号为<id>用户信息"
                },
                {
                    "uri": "/user/<int:uid>",
                    "method": "DELETE",
                    "description": "删除用户号为<id>用户"
                },
            ]
        }

        return json(result, ensure_ascii=False)

    @doc.operation('UserListSource_POST')
    @doc.summary("创建新用户")
    @checkjsonschema(post_query_schema)
    async def post(self, request: Request) -> HTTPResponse:
        query_json = request.json
        try:
            u = await UserDB.add(query_json.get("name", ""))
        except Exception as e:
            return json({
                "msg": "执行错误",
            }, status=500, ensure_ascii=False)
        else:
            return json({
                "msg": "插入成功",
                "uid": u.ID
            }, ensure_ascii=False)
  • usersource.py
from dataclasses import asdict
from sanic.views import HTTPMethodView
from sanic.request import Request
from sanic.response import json, HTTPResponse
from sanic_openapi import doc
from jsonschema import validate
from decorators.checkjsonschema import checkjsonschema
from modules.usermodule  import UserDB


put_query_schema = {
    "$schema": "http://json-schema.org/draft-07/schema#",
    "type": "object",
    "additionalProperties": False,
    "required": ["name"],
    "properties": {
        "name": {
            "type": "string",
            "description": "用户注册名"
        }
    }
}


class UserSource(HTTPMethodView):

    @doc.operation('UserSource_GET')
    @doc.summary("获取用户信息")
    async def get(self, _: Request, uid: int) -> HTTPResponse:
        try:
            u = await UserDB.find(uid)
        except AttributeError:
            return json({
                "msg": "未找到用户",
            }, status=404, ensure_ascii=False)
        except Exception as e:
            return json({
                "msg": "执行错误",
            }, status=500, ensure_ascii=False)
        else:
            return json(asdict(u), ensure_ascii=False)
    @doc.operation('UserSource_PUT')
    @doc.summary("更新用户信息")
    @checkjsonschema(put_query_schema)
    async def put(self, request: Request, uid: int) -> HTTPResponse:
        query_json = request.json
        try:
            validate(instance=query_json, schema=put_query_schema)
        except Exception as e:
            return json({
                "msg": "参数错误",
                "error": str(e)
            }, status=401, ensure_ascii=False)
        else:
            try:
                await UserDB.update(uid, query_json.get("name", ""))
            except AttributeError:
                return json({
                    "msg": "未找到用户",
                }, status=404, ensure_ascii=False)
            except Exception as e:
                return json({
                    "msg": "执行错误",
                }, status=500, ensure_ascii=False)
            else:
                return json({"msg": "更新成功"}, ensure_ascii=False)
   
    @doc.operation('UserSource_DELETE')
    @doc.summary("删除用户")
    async def delete(self, _: Request, uid: int) -> HTTPResponse:
        try:
            await UserDB.delete(uid)
        except AttributeError:
            return json({
                "msg": "未找到用户",
            }, status=404, ensure_ascii=False)
        except Exception as e:
            return json({
                "msg": "执行错误",
            }, status=500, ensure_ascii=False)
        else:
            return json({"msg": "删除成功"}, ensure_ascii=False)

Expected behavior

there should be summary,and these sections should in user tag

Environment (please complete the following information):

  • OS: win10
  • Browser: chrome
  • Version 21.3.1

Additional context
Add any other context about the problem here. This might be how to fix this bug or some hint to fix it.

@ahopkins
Copy link
Member

I just was looking at this. Sanic supports decorators on methods:

Agreed. This should work, but does not.

class HelloView(HTTPMethodView):
    @openapi.parameter("name", str, location="query")
    async def get(self, request: Request) -> HTTPResponse:
        name = request.args.get("name", "world")
        return text(f"Hello, {name}.")


bp.add_route(HelloView.as_view(), "/")

This does work, but is not always a viable option.

class HelloView(HTTPMethodView):
    decorators = [openapi.parameter("name", str, location="query")]

    async def get(self, request: Request) -> HTTPResponse:
        ...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants