Coverage for tests / test_tutorial / test_body_nested_models / test_tutorial004.py: 100%
35 statements
« prev ^ index » next coverage.py v7.13.3, created at 2026-02-12 18:15 +0000
« prev ^ index » next coverage.py v7.13.3, created at 2026-02-12 18:15 +0000
1import importlib 1abdc
3import pytest 1abdc
4from dirty_equals import IsList 1abdc
5from fastapi.testclient import TestClient 1abdc
6from inline_snapshot import snapshot 1abdc
8from ...utils import needs_py310 1abdc
11@pytest.fixture( 1abdc
12 name="client",
13 params=[
14 pytest.param("tutorial004_py310", marks=needs_py310),
15 ],
16)
17def get_client(request: pytest.FixtureRequest): 1abdc
18 mod = importlib.import_module(f"docs_src.body_nested_models.{request.param}") 1abc
20 client = TestClient(mod.app) 1abc
21 return client 1abc
24def test_put_all(client: TestClient): 1abdc
25 response = client.put( 1efg
26 "/items/123",
27 json={
28 "name": "Foo",
29 "description": "A very nice Item",
30 "price": 35.4,
31 "tax": 3.2,
32 "tags": ["foo", "bar", "foo"],
33 "image": {"url": "http://example.com/image.png", "name": "example image"},
34 },
35 )
36 assert response.status_code == 200, response.text 1efg
37 assert response.json() == { 1efg
38 "item_id": 123,
39 "item": {
40 "name": "Foo",
41 "description": "A very nice Item",
42 "price": 35.4,
43 "tax": 3.2,
44 "tags": IsList("foo", "bar", check_order=False),
45 "image": {"url": "http://example.com/image.png", "name": "example image"},
46 },
47 }
50def test_put_only_required(client: TestClient): 1abdc
51 response = client.put( 1hij
52 "/items/5",
53 json={"name": "Foo", "price": 35.4},
54 )
55 assert response.status_code == 200, response.text 1hij
56 assert response.json() == { 1hij
57 "item_id": 5,
58 "item": {
59 "name": "Foo",
60 "description": None,
61 "price": 35.4,
62 "tax": None,
63 "tags": [],
64 "image": None,
65 },
66 }
69def test_put_empty_body(client: TestClient): 1abdc
70 response = client.put( 1klm
71 "/items/5",
72 json={},
73 )
74 assert response.status_code == 422, response.text 1klm
75 assert response.json() == { 1klm
76 "detail": [
77 {
78 "loc": ["body", "name"],
79 "input": {},
80 "msg": "Field required",
81 "type": "missing",
82 },
83 {
84 "loc": ["body", "price"],
85 "input": {},
86 "msg": "Field required",
87 "type": "missing",
88 },
89 ]
90 }
93def test_put_missing_required_in_item(client: TestClient): 1abdc
94 response = client.put( 1nop
95 "/items/5",
96 json={"description": "A very nice Item"},
97 )
98 assert response.status_code == 422, response.text 1nop
99 assert response.json() == { 1nop
100 "detail": [
101 {
102 "loc": ["body", "name"],
103 "input": {"description": "A very nice Item"},
104 "msg": "Field required",
105 "type": "missing",
106 },
107 {
108 "loc": ["body", "price"],
109 "input": {"description": "A very nice Item"},
110 "msg": "Field required",
111 "type": "missing",
112 },
113 ]
114 }
117def test_put_missing_required_in_image(client: TestClient): 1abdc
118 response = client.put( 1qrs
119 "/items/5",
120 json={
121 "name": "Foo",
122 "price": 35.4,
123 "image": {"url": "http://example.com/image.png"},
124 },
125 )
126 assert response.status_code == 422, response.text 1qrs
127 assert response.json() == { 1qrs
128 "detail": [
129 {
130 "loc": ["body", "image", "name"],
131 "input": {"url": "http://example.com/image.png"},
132 "msg": "Field required",
133 "type": "missing",
134 },
135 ]
136 }
139def test_openapi_schema(client: TestClient): 1abdc
140 response = client.get("/openapi.json") 1tuv
141 assert response.status_code == 200, response.text 1tuv
142 assert response.json() == snapshot( 1tuv
143 {
144 "openapi": "3.1.0",
145 "info": {"title": "FastAPI", "version": "0.1.0"},
146 "paths": {
147 "/items/{item_id}": {
148 "put": {
149 "parameters": [
150 {
151 "in": "path",
152 "name": "item_id",
153 "required": True,
154 "schema": {
155 "title": "Item Id",
156 "type": "integer",
157 },
158 },
159 ],
160 "responses": {
161 "200": {
162 "description": "Successful Response",
163 "content": {"application/json": {"schema": {}}},
164 },
165 "422": {
166 "description": "Validation Error",
167 "content": {
168 "application/json": {
169 "schema": {
170 "$ref": "#/components/schemas/HTTPValidationError"
171 }
172 }
173 },
174 },
175 },
176 "summary": "Update Item",
177 "operationId": "update_item_items__item_id__put",
178 "requestBody": {
179 "content": {
180 "application/json": {
181 "schema": {
182 "$ref": "#/components/schemas/Item",
183 }
184 }
185 },
186 "required": True,
187 },
188 }
189 }
190 },
191 "components": {
192 "schemas": {
193 "Image": {
194 "properties": {
195 "url": {
196 "title": "Url",
197 "type": "string",
198 },
199 "name": {
200 "title": "Name",
201 "type": "string",
202 },
203 },
204 "required": ["url", "name"],
205 "title": "Image",
206 "type": "object",
207 },
208 "Item": {
209 "properties": {
210 "name": {
211 "title": "Name",
212 "type": "string",
213 },
214 "description": {
215 "title": "Description",
216 "anyOf": [{"type": "string"}, {"type": "null"}],
217 },
218 "price": {
219 "title": "Price",
220 "type": "number",
221 },
222 "tax": {
223 "title": "Tax",
224 "anyOf": [{"type": "number"}, {"type": "null"}],
225 },
226 "tags": {
227 "title": "Tags",
228 "default": [],
229 "type": "array",
230 "items": {"type": "string"},
231 "uniqueItems": True,
232 },
233 "image": {
234 "anyOf": [
235 {"$ref": "#/components/schemas/Image"},
236 {"type": "null"},
237 ],
238 },
239 },
240 "required": [
241 "name",
242 "price",
243 ],
244 "title": "Item",
245 "type": "object",
246 },
247 "ValidationError": {
248 "title": "ValidationError",
249 "required": ["loc", "msg", "type"],
250 "type": "object",
251 "properties": {
252 "loc": {
253 "title": "Location",
254 "type": "array",
255 "items": {
256 "anyOf": [{"type": "string"}, {"type": "integer"}]
257 },
258 },
259 "msg": {"title": "Message", "type": "string"},
260 "type": {"title": "Error Type", "type": "string"},
261 "input": {"title": "Input"},
262 "ctx": {"title": "Context", "type": "object"},
263 },
264 },
265 "HTTPValidationError": {
266 "title": "HTTPValidationError",
267 "type": "object",
268 "properties": {
269 "detail": {
270 "title": "Detail",
271 "type": "array",
272 "items": {
273 "$ref": "#/components/schemas/ValidationError"
274 },
275 }
276 },
277 },
278 }
279 },
280 }
281 )