python-restx / flask-restx

Fork of Flask-RESTPlus: Fully featured framework for fast, easy and documented API development with Flask
https://flask-restx.readthedocs.io/en/latest/
Other
2.16k stars 335 forks source link

HTTPStatus in Api.reponse #373

Open alimohammad0816 opened 3 years ago

alimohammad0816 commented 3 years ago

instead of:

from flask_restx import Resource
from http import HTTPStatus
from . import api

class User(Resource):
    @api.doc(
            "user_get",
            responses={
                200: "OK",
                404: "NOT FOUND"
            }
        )
    @api.response(
            200, "user_get", some_marshal
        )
    def get(self, number):
        if number == 1:
            return {"foo": "bar"}, 200
        else:
            return {"foo": "bar"}, 404

I tried to use:

from flask_restx import Resource
from http import HTTPStatus
from . import api

class User(Resource):
    @api.doc(
            "user_get",
            responses={
                HTTPStatus.OK: "OK",
                HTTPStatus.NOT_FOUND: "NOT FOUND"
            }
        )
    @api.response(
            HTTPStatus.OK, "user_get", some_marshal
        )
    def get(self, number):
        if number == 1:
            return {"foo": "bar"}, HTTPStatus.OK
        else:
            return {"foo": "bar"}, HTTPStatus.NOT_FOUND

But there was a problem with the swagger.
also response with status code 200 or 404 was shown as undocumented.

You can see the swagger problem in this image:
github_flask_restx

mahoyen commented 2 years ago

I think this should be relatively simple to fix. There are two places where the operation str(code) is done: https://github.com/python-restx/flask-restx/blob/0dc1c3c966d0394da4b807e491225e90f46b27b8/flask_restx/swagger.py#L554

and

https://github.com/python-restx/flask-restx/blob/41b3b591b4be89d5d27e571dd3a75f849d4455ca/flask_restx/namespace.py#L260

I think by changing str(code) to str(int(code)) it should be possible to fix this. This will work when code is str, int, or HTTPStatus as long as the value is convertable to int.

Anyone knows of any values where this is not the case?

mahoyen commented 2 years ago

After updating it and running the tests, I see that there is a use of "default": https://github.com/python-restx/flask-restx/blob/0dc1c3c966d0394da4b807e491225e90f46b27b8/tests/test_swagger.py#L1199-L1210

So this complicates it a bit. I am not sure the below is good enough:

str(code.value if isinstance(code, IntEnum) else code)

This will handle the default case at least