Feature request: Add an exceptional case for returning a Pydantic model from path operation functions when its type and the type hint for returned value is the same.. #11694
Replies: 2 comments 5 replies
-
|
I also think that this feature would be very useful. For now you can return Response object directly to avoid second validation, as it's described in the documentation: https://fastapi.tiangolo.com/advanced/response-directly/ And, if you are sure that your data is JSON-compatible, you can skip jsonable_encoder part: |
Beta Was this translation helpful? Give feedback.
-
|
My personal opinion on this is that you should stick using @app.get("/", response_model=PersonOutput)
async def index() -> Response:
person = Person(name="foo", age=100)
return personbecause this is how the FastAPI has been thought to be used at the first place (which is usefull to implicitely convert some returned data to a given model). Regarding the typing validation (and make you type checker complain in case of mismatch), in this particular case you are checking the type of the object returned by the endpoint. So you should already have non-regression tests ensuring that your API actually returns what is expected. My point is: endpoint testing is mandatory IMO, so you are safe (of course, detecting problems before running tests would be best). If you really don't want to have a double validation and keep all the typing (and therefore work with explicit over implicit, you can disable the @app.get("/", response_model=None)
async def index() -> PersonOutput:
person = Person(name="foo", age=100)
return PersonOutput(name=person.name, age=person.age) |
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
First Check
Commit to Help
Example Code
Description
In our team, we create a Pydantic model explicitly and return it from the path operation function. The reason is that if we later decide to change one of its fields, the type checker complains about it before runtime.
But here is the problem, FastAPI currently has no idea what the returned object is. It will "re-validate" it using the specified return type, which is obviously unnecessary(by running the above code you'll get
"Validation using PersonOutput."printed two times).A workaround is that I can simply remove the return type (
-> PersonOutput:) but I don't really like it. Ruff (in strict mode) also says: fully annotate your functions. Sometimes I create and return that Pydantic object from an external function so the type hint really helps me ensuring that the object has the correct type. Another workaround is to create and directly return the subclasses ofResponse. It will work but it requires an extra work to do.I tracked down the source code and reached this line:
https://github.com/tiangolo/fastapi/blob/master/fastapi/routing.py#L134
If I provide the return type it will re-validate it for the second time.
I think a simple fix for this is to add additional check like:
If the types are the same it means the validation is already done and we have a valid Pydantic object ready to be serialized. The cost would be an additional comparison but it's beneficial for these cases.
Thanks for reading. I'm ready to help if that made sense to you.
Operating System
macOS
Operating System Details
No response
FastAPI Version
0.108.0
Pydantic Version
2.6.3
Python Version
Python 3.11.5
Additional Context
No response
Beta Was this translation helpful? Give feedback.
All reactions