Add support for Python's http.HTTPStatus in status_code (#1534)

* Normalise IntEnums to ints for route status codes

Closes #1349

* add tests for status code enum support

* add docs for status code enum support

* add endpoint test for enum status code

* 📝 Update note about http.HTTPStatus

Co-authored-by: Sebastián Ramírez <tiangolo@gmail.com>
This commit is contained in:
retnikt 2020-06-13 18:40:10 +01:00 committed by GitHub
parent 6576f724bb
commit c6dd627bdd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 32 additions and 0 deletions

View File

@ -17,6 +17,9 @@ The same way you can specify a response model, you can also declare the HTTP sta
The `status_code` parameter receives a number with the HTTP status code. The `status_code` parameter receives a number with the HTTP status code.
!!! info
`status_code` can alternatively also receive an `IntEnum`, such as Python's <a href="https://docs.python.org/3/library/http.html#http.HTTPStatus" class="external-link" target="_blank">`http.HTTPStatus`</a>.
It will: It will:
* Return that status code in the response. * Return that status code in the response.

View File

@ -1,4 +1,5 @@
import asyncio import asyncio
import enum
import inspect import inspect
import json import json
from typing import Any, Callable, Dict, List, Optional, Sequence, Set, Type, Union from typing import Any, Callable, Dict, List, Optional, Sequence, Set, Type, Union
@ -296,6 +297,9 @@ class APIRoute(routing.Route):
dependency_overrides_provider: Any = None, dependency_overrides_provider: Any = None,
callbacks: Optional[List["APIRoute"]] = None, callbacks: Optional[List["APIRoute"]] = None,
) -> None: ) -> None:
# normalise enums e.g. http.HTTPStatus
if isinstance(status_code, enum.IntEnum):
status_code = int(status_code)
self.path = path self.path = path
self.endpoint = endpoint self.endpoint = endpoint
self.name = get_name(endpoint) if name is None else name self.name = get_name(endpoint) if name is None else name

View File

@ -1,3 +1,5 @@
import http
from fastapi import FastAPI, Path, Query from fastapi import FastAPI, Path, Query
app = FastAPI() app = FastAPI()
@ -184,3 +186,8 @@ def get_query_param_required(query=Query(...)):
@app.get("/query/param-required/int") @app.get("/query/param-required/int")
def get_query_param_required_type(query: int = Query(...)): def get_query_param_required_type(query: int = Query(...)):
return f"foo bar {query}" return f"foo bar {query}"
@app.get("/enum-status-code", status_code=http.HTTPStatus.CREATED)
def get_enum_status_code():
return "foo bar"

View File

@ -1078,6 +1078,18 @@ openapi_schema = {
], ],
} }
}, },
"/enum-status-code": {
"get": {
"responses": {
"201": {
"description": "Successful Response",
"content": {"application/json": {"schema": {}}},
},
},
"summary": "Get Enum Status Code",
"operationId": "get_enum_status_code_enum_status_code_get",
}
},
}, },
"components": { "components": {
"schemas": { "schemas": {
@ -1149,3 +1161,9 @@ def test_redoc():
assert response.status_code == 200, response.text assert response.status_code == 200, response.text
assert response.headers["content-type"] == "text/html; charset=utf-8" assert response.headers["content-type"] == "text/html; charset=utf-8"
assert "redoc@next" in response.text assert "redoc@next" in response.text
def test_enum_status_code_response():
response = client.get("/enum-status-code")
assert response.status_code == 201, response.text
assert response.json() == "foo bar"