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
β¨ Add support for adding multiple examples in request bodies and path, query, cookie, and header params #1267
Conversation
Codecov Report
@@ Coverage Diff @@
## master #1267 +/- ##
==========================================
Coverage 100.00% 100.00%
==========================================
Files 243 245 +2
Lines 7419 7539 +120
==========================================
+ Hits 7419 7539 +120
Continue to review full report at Codecov.
|
95ffe99
to
8138ff6
Compare
π Docs preview for commit 8138ff61822a5d944b284e436ecc8a88475e893c at: https://5f52f468e319ee0ebf5d7aad--fastapi.netlify.app |
The docs built for this PR have a screenshot of the new multi-example capabilities here. |
@austinorr The description mentions the need for more coverage but you seem to have added tests - is it ready to be merged perhaps? It would be a really useful feature! π |
@austinorr The goal of my message was to explain one of the possible reasons for what he saw. I didn't mean that we should wait. π
I don't think this is necessary... @tiangolo will eventually see this PR, dw π |
@tiangolo Is there any chance of seeing this merged soon? |
For easier review of the capability this PR enables see the (draft) docs I edited here: https://5f52f468e319ee0ebf5d7aad--fastapi.netlify.app/tutorial/schema-extra-example/#body-with-multiple-examples |
If this isn't the case anymore, maybe it should be removed from the description. :) |
Hey sorry -- we use git comments differently. I will update the original comment to indicate that this has been covered since the commits on Sept 4. The Coverage bot is current (it updates live). |
Coming over from #822 (comment). I tried the implementation in this PR with Pydantic models as described in #822 (comment) and it did not seem to work. That said, there is a good chance I made a mistake somewhere along the way. Maybe this example can be updated/extended and it can be tested that way? I'd be happy to try to submit a PR to this PR with this (but I'm not very familiar with the internals, so I can't promise I'll get it to work). Here is my test (which for me, does not show the dropdown): Code# monkeypatch in this implementation
from fastapi.openapi import utils
def get_openapi_operation_request_body(*, body_field, model_name_map):
if not body_field:
return None
assert isinstance(body_field, utils.ModelField)
# ignore mypy error until enum schemas are released
body_schema, _, _ = utils.field_schema(
body_field, model_name_map=model_name_map, ref_prefix=utils.REF_PREFIX # type: ignore
)
field_info = utils.cast(utils.Body, body_field.field_info)
request_media_type = field_info.media_type
required = body_field.required
request_body_oai= {}
if required:
request_body_oai["required"] = required
request_body_oai["content"] = {request_media_type: {"schema": body_schema}}
examples = body_schema.get("examples")
if examples:
request_body_oai["content"][request_media_type]["examples"] = examples
return request_body_oai
utils.get_openapi_operation_request_body = get_openapi_operation_request_body
# the rest
from typing import Optional
from fastapi import FastAPI, Body
from pydantic import BaseModel
app = FastAPI()
class Item(BaseModel):
name: str
description: Optional[str] = None
price: float
tax: Optional[float] = None
class Config:
schema_extra = {
"examples": {
"Foo": {
"name": "Foo",
"description": "A very nice Item",
"price": 35.4,
"tax": 3.2,
},
"Bar": {
"name": "Bar",
"description": "A Bar Item",
"price": 35.1,
"tax": 3.5,
}
}
}
@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item):
results = {"item_id": item_id, "item": item}
return results However, if I change the function signature from: async def update_item(item_id: int, item: Item): to async def update_item(item_id: int, item: Item = Body(None, examples=Item.Config.schema_extra["examples"])): Then I get a dropdown, as described in this PR. |
Yeah, I see what you mean. The current implementation doesn't work with the You're right to note that my implementation is a bit narrow in that it'll only work as expected if the developer creates a route with only one The |
That makes sense, I think is it pretty sensible to support the simple use case (in terms of implementation and expected behavior, as you point out above). There is certainly a discrepancy between examples-per-route (OpenAPI) and examples-per-model (Pydantic), but that is somehow reconciled within FastAPI, since That said, should also be made to work with |
@adriangb That's right, my understanding is that there's actually nothing we can do with The I'll also admit that I'm way out over my skis here; I just use this fantastic tool, I don't know how it really does some of its magic like the core devs do. Some of this might actually be possible/easier than I thought if we can get this thread reviewed by a dev who knows |
That makes a lot of sense, your explanation is excellent.
That would be cool! But I'm not sure how that fits into the larger OpenAPI picture? Like you I just use this great tool π
Right, and there's not valid way to select the right leaf. I'd imagine there'd need to be some FastAPI specific way for developers to designate the example to use in building the overall examples (it could just be the first one).
Do you want to tag someone here, or would you prefer to open a separate issue? Up to you. |
Looking at this a bit more, it looks like FastAPI does nothing special with So indeed, supporting |
will this support multiple examples for a union type body?
could take body {
"name": "john"
} or [{
"name": "john"
},
{
"name": "jack"
}] currently the example value for union body types is just empty. |
any update on this? is there a plan to merge it? |
β¦ including params to verify that the right overrides are in the right places, from schema_extra, to example, to examples
8138ff6
to
a77098f
Compare
π Docs preview for commit a77098f at: https://6092ddfea9cea100a08ad24c--fastapi.netlify.app |
Thanks for all the effort and work on this @austinorr ! π€ And thanks for all the clarifications and arguments here and in the issue! π π Also thanks for the discussion everyone! β I finally got the time to work on this for several consecutive days (mainly studying the standards) and I refactored it a bit to handle a couple of things. This was quite tricky, as although the description and original change were not too complex, it touches one of the main friction points in the standards, between OpenAPI, JSON Schema, OpenAPI's 3.0.x custom version of JSON Schema, and the recently released (soon to be supported) OpenAPI 3.1.0, based on a recent version of JSON Schema, without the custom parts. π I added internal support for the arguments Boring Technical DetailsThe update/refactor adds Maybe all that sounds super complex π¬ ...it's mainly that the terms are the same here and there, but they refer to slightly different things in one standard and the other which adds to the confusion. Plus, the conflicts also involve older and newer versions, so it sounds dizzy. π₯΄ But in short: this now has "first-class" support, handling all the details, making sure it's future proof, for OpenAPI 3.1.0 (:crossed_fingers: ). :sparkles: And, now it also supports the other parameters, with a bunch of tests for all that to make sure overrides work correctly, etc. π This will be included in the next release, |
Thank you @tiangolo and @austinorr! |
This PR enables multiple examples in a pick-list style dropdown in the OpenApi Docs a la the 'Request Body Examples' here
For more information and discussion see the issue this PR related to #822
Note, this still needs tests to cover the 3 new lines.Docs and full coverage tests added Sept 4 with 8138ff6Edit by @tiangolo π€ π
Added support for arguments
example
andexamples
inBody()
,Path()
,Query()
,Cookie()
,Header()
, handling compatibility (and incompatibilities) between OpenAPI, JSON Schema, and OpenAPI's 3.0.x custom version of JSON Schema π€ͺ π«More details about the standards dizzy mix in a comment below, near the end.