]> git.ipfire.org Git - thirdparty/fastapi/fastapi.git/commitdiff
:memo: Add body multiple parameters docs
authorSebastián Ramírez <tiangolo@gmail.com>
Fri, 14 Dec 2018 15:17:17 +0000 (19:17 +0400)
committerSebastián Ramírez <tiangolo@gmail.com>
Fri, 14 Dec 2018 15:17:17 +0000 (19:17 +0400)
docs/tutorial/body-multiple-params.md [new file with mode: 0644]
docs/tutorial/path-params-numeric-validations.md
docs/tutorial/src/body-multiple-params/tutorial001.py [new file with mode: 0644]
docs/tutorial/src/body-multiple-params/tutorial002.py [new file with mode: 0644]
docs/tutorial/src/body-multiple-params/tutorial003.py [new file with mode: 0644]
docs/tutorial/src/body-multiple-params/tutorial004.py [new file with mode: 0644]
docs/tutorial/src/body-multiple-params/tutorial005.py [new file with mode: 0644]
mkdocs.yml

diff --git a/docs/tutorial/body-multiple-params.md b/docs/tutorial/body-multiple-params.md
new file mode 100644 (file)
index 0000000..c95cfca
--- /dev/null
@@ -0,0 +1,167 @@
+Now that we have seen how to use `Path` and `Query`, let's see more advanced uses of request body declarations.
+
+## Mix `Path`, `Query` and body parameters
+
+First, of course, you can mix `Path`, `Query` and request body parameter declarations freely and **FastAPI** will know what to do.
+
+```Python hl_lines="17 18 19"
+{!./tutorial/src/body-multiple-params/tutorial001.py!}
+```
+
+!!! note
+    Notice that, in this case, the `item` that would be taken from the body is optional. As it has a `None` default value.
+
+
+## Multiple body parameters
+
+In the previous example, the endpoint would expect a JSON body with the attributes of an `Item`, like:
+
+```JSON
+{
+    "name": "Foo",
+    "description": "The pretender",
+    "price": 42.0,
+    "tax": 3.2
+}
+```
+
+But you can also declare multiple body parameters, e.g. `item` and `user`:
+
+```Python hl_lines="20"
+{!./tutorial/src/body-multiple-params/tutorial002.py!}
+```
+
+In this case, **FastAPI** will notice that there are more than one body parameter in the function (two parameters that are Pydantic models).
+
+So, it will then use the parameter names as keys (field names) in the body, and expect a body like:
+
+```JSON
+{
+    "item": {
+        "name": "Foo",
+        "description": "The pretender",
+        "price": 42.0,
+        "tax": 3.2
+    },
+    "user": {
+        "username": "dave",
+        "full_name": "Dave Grohl"
+    }
+}
+```
+
+!!! note
+    Notice that even though the `item` was declared the same way as before, it is now expected to be inside of the body with a key `item`.
+
+
+**FastAPI** will do the automatic conversion from the request, so that the parameter `item` receives it's specific content and the same for `user`.
+
+It will perform the validation of the compound data, and will document it like that for the OpenAPI schema and automatic docs.
+
+## Singular values in body
+
+The same way there is a `Query` and `Path` to define extra data for query and path parameters, **FastAPI** provides an equivalent `Body`.
+
+For example, extending the previous model, you could decide that you want to have another key `importance` in the same body, besides the `item` and `user`.
+
+If you declare it as is, because it is a singular value, **FastAPI** will assume that it is a query parameter.
+
+But you can instruct **FastAPI** to treat it as another body key using `Body`:
+
+
+```Python hl_lines="21"
+{!./tutorial/src/body-multiple-params/tutorial003.py!}
+```
+
+In this case, **FastAPI** will expect a body like:
+
+
+```JSON
+{
+    "item": {
+        "name": "Foo",
+        "description": "The pretender",
+        "price": 42.0,
+        "tax": 3.2
+    },
+    "user": {
+        "username": "dave",
+        "full_name": "Dave Grohl"
+    },
+    "importance": 5
+}
+```
+
+Again, it will convert the data types, validate, document, etc.
+
+## Multiple body params and query
+
+Of course, you can also declare additional query parameters whenever you need, additional to any body parameters.
+
+As, by default, singular values are interpreted as query parameters, you don't have to explicitly add a `Query`, you can just do:
+
+```Python
+q: str = None
+```
+
+as in:
+
+```Python hl_lines="25"
+{!./tutorial/src/body-multiple-params/tutorial004.py!}
+```
+
+!!! info
+    `Body` also has all the same extra validation and metadata parameters as `Query`,`Path` and others you will see later.
+
+
+## Embed a single body parameter
+
+Let's say you only have a single `item` body parameter from a Pydantic model `Item`.
+
+By default, **FastAPI** will then expect its body directly.
+
+But if you want it to expect a JSON with a key `item` and inside of it the model contents, as it does when you declare extra body parameters, you can use the special `Body` parameter `embed`:
+
+```Python
+item: Item = Body(..., embed=True)
+```
+
+as in:
+
+```Python hl_lines="15"
+{!./tutorial/src/body-multiple-params/tutorial005.py!}
+```
+
+In this case **FastAPI** will expect a body like:
+
+```JSON hl_lines="2"
+{
+    "item": {
+        "name": "Foo",
+        "description": "The pretender",
+        "price": 42.0,
+        "tax": 3.2
+    }
+}
+```
+
+instead of:
+
+```JSON
+{
+    "name": "Foo",
+    "description": "The pretender",
+    "price": 42.0,
+    "tax": 3.2
+}
+```
+
+## Recap
+
+You can add multiple body parameters to your function endpoint, even though a request can only have a single body.
+
+But **FastAPI** will handle it, give you the correct data in your function, and validate and document the correct schema in the endpoint.
+
+You can also declare singular values to be received as part of the body.
+
+And you can instruct **FastAPI** to embed the body in a key even when there is only a single parameter declared.
index 58ef304da686a0f24e04628c5d1e547bf4e26c88..eade3da020f835357fb361f89d481593486abd5c 100644 (file)
@@ -101,3 +101,8 @@ And you can also declare numeric validations:
 * `ge`: `g`reater than or `e`qual
 * `lt`: `l`ess `t`han
 * `le`: `l`ess than or `e`qual
+
+!!! info
+    `Query`, `Path` and others you will see later are subclasses of a common `Param` class (that you don't need to use).
+    
+    And all of them share the same all these same parameters of additional validation and metadata you have seen.
\ No newline at end of file
diff --git a/docs/tutorial/src/body-multiple-params/tutorial001.py b/docs/tutorial/src/body-multiple-params/tutorial001.py
new file mode 100644 (file)
index 0000000..7918a2f
--- /dev/null
@@ -0,0 +1,26 @@
+from fastapi import FastAPI, Path
+from pydantic import BaseModel
+
+app = FastAPI()
+
+
+class Item(BaseModel):
+    name: str
+    description: str = None
+    price: float
+    tax: float = None
+
+
+@app.put("/items/{item_id}")
+async def update_item(
+    *,
+    item_id: int = Path(..., title="The ID of the item to get", ge=0, le=1000),
+    q: str,
+    item: Item = None,
+):
+    results = {"item_id": item_id}
+    if q:
+        results.update({"q": q})
+    if item:
+        results.update({"item": item})
+    return results
diff --git a/docs/tutorial/src/body-multiple-params/tutorial002.py b/docs/tutorial/src/body-multiple-params/tutorial002.py
new file mode 100644 (file)
index 0000000..5c9e834
--- /dev/null
@@ -0,0 +1,22 @@
+from fastapi import FastAPI
+from pydantic import BaseModel
+
+app = FastAPI()
+
+
+class Item(BaseModel):
+    name: str
+    description: str = None
+    price: float
+    tax: float = None
+
+
+class User(BaseModel):
+    username: str
+    full_name: str = None
+
+
+@app.put("/items/{item_id}")
+async def update_item(*, item_id: int, item: Item, user: User):
+    results = {"item_id": item_id, "item": item, "user": user}
+    return results
diff --git a/docs/tutorial/src/body-multiple-params/tutorial003.py b/docs/tutorial/src/body-multiple-params/tutorial003.py
new file mode 100644 (file)
index 0000000..301f1a8
--- /dev/null
@@ -0,0 +1,24 @@
+from fastapi import Body, FastAPI
+from pydantic import BaseModel
+
+app = FastAPI()
+
+
+class Item(BaseModel):
+    name: str
+    description: str = None
+    price: float
+    tax: float = None
+
+
+class User(BaseModel):
+    username: str
+    full_name: str = None
+
+
+@app.put("/items/{item_id}")
+async def update_item(
+    *, item_id: int, item: Item, user: User, importance: int = Body(...)
+):
+    results = {"item_id": item_id, "item": item, "user": user, "importance": importance}
+    return results
diff --git a/docs/tutorial/src/body-multiple-params/tutorial004.py b/docs/tutorial/src/body-multiple-params/tutorial004.py
new file mode 100644 (file)
index 0000000..359b33c
--- /dev/null
@@ -0,0 +1,31 @@
+from fastapi import Body, FastAPI
+from pydantic import BaseModel
+
+app = FastAPI()
+
+
+class Item(BaseModel):
+    name: str
+    description: str = None
+    price: float
+    tax: float = None
+
+
+class User(BaseModel):
+    username: str
+    full_name: str = None
+
+
+@app.put("/items/{item_id}")
+async def update_item(
+    *,
+    item_id: int,
+    item: Item,
+    user: User,
+    importance: int = Body(..., gt=0),
+    q: str = None
+):
+    results = {"item_id": item_id, "item": item, "user": user, "importance": importance}
+    if q:
+        results.update({"q": q})
+    return results
diff --git a/docs/tutorial/src/body-multiple-params/tutorial005.py b/docs/tutorial/src/body-multiple-params/tutorial005.py
new file mode 100644 (file)
index 0000000..61f1b29
--- /dev/null
@@ -0,0 +1,17 @@
+from fastapi import Body, FastAPI
+from pydantic import BaseModel
+
+app = FastAPI()
+
+
+class Item(BaseModel):
+    name: str
+    description: str = None
+    price: float
+    tax: float = None
+
+
+@app.put("/items/{item_id}")
+async def update_item(*, item_id: int, item: Item = Body(..., embed=True)):
+    results = {"item_id": item_id, "item": item}
+    return results
index a88c6f445f1b30614d72b98e429cbc846c4883a0..855ea596baa30f408405b7490f6007b8b339cc81 100644 (file)
@@ -22,8 +22,9 @@ nav:
         - Path Parameters: 'tutorial/path-params.md'
         - Query Parameters: 'tutorial/query-params.md'
         - Request Body: 'tutorial/body.md'
-        - Query Parameters - string validations: 'tutorial/query-params-str-validations.md'
-        - Path Parameters - numeric validations: 'tutorial/path-params-numeric-validations.md'
+        - Query Parameters - String Validations: 'tutorial/query-params-str-validations.md'
+        - Path Parameters - Numeric Validations: 'tutorial/path-params-numeric-validations.md'
+        - Body - Multiple Parameters: 'tutorial/body-multiple-params.md'
     - Concurrency and async / await: 'async.md'
     - Deployment: 'deployment.md'