Coverage for tests/test_openapi_separate_input_output_schemas.py: 100%
72 statements
« prev ^ index » next coverage.py v7.6.1, created at 2024-08-08 03:53 +0000
« prev ^ index » next coverage.py v7.6.1, created at 2024-08-08 03:53 +0000
1from typing import List, Optional 1abcde
3from fastapi import FastAPI 1abcde
4from fastapi.testclient import TestClient 1abcde
5from pydantic import BaseModel 1abcde
7from .utils import PYDANTIC_V2, needs_pydanticv2 1abcde
10class SubItem(BaseModel): 1abcde
11 subname: str 1abcde
12 sub_description: Optional[str] = None 1abcde
13 tags: List[str] = [] 1abcde
14 if PYDANTIC_V2: 1abcde
15 model_config = {"json_schema_serialization_defaults_required": True} 1abcde
18class Item(BaseModel): 1abcde
19 name: str 1abcde
20 description: Optional[str] = None 1abcde
21 sub: Optional[SubItem] = None 1abcde
22 if PYDANTIC_V2: 1abcde
23 model_config = {"json_schema_serialization_defaults_required": True} 1abcde
26def get_app_client(separate_input_output_schemas: bool = True) -> TestClient: 1abcde
27 app = FastAPI(separate_input_output_schemas=separate_input_output_schemas) 1abcde
29 @app.post("/items/") 1abcde
30 def create_item(item: Item): 1abcde
31 return item 1abcde
33 @app.post("/items-list/") 1abcde
34 def create_item_list(item: List[Item]): 1abcde
35 return item 1abcde
37 @app.get("/items/") 1abcde
38 def read_items() -> List[Item]: 1abcde
39 return [ 1abcde
40 Item(
41 name="Portal Gun",
42 description="Device to travel through the multi-rick-verse",
43 sub=SubItem(subname="subname"),
44 ),
45 Item(name="Plumbus"),
46 ]
48 client = TestClient(app) 1abcde
49 return client 1abcde
52def test_create_item(): 1abcde
53 client = get_app_client() 1abcde
54 client_no = get_app_client(separate_input_output_schemas=False) 1abcde
55 response = client.post("/items/", json={"name": "Plumbus"}) 1abcde
56 response2 = client_no.post("/items/", json={"name": "Plumbus"}) 1abcde
57 assert response.status_code == response2.status_code == 200, response.text 1abcde
58 assert ( 1abcde
59 response.json()
60 == response2.json()
61 == {"name": "Plumbus", "description": None, "sub": None}
62 )
65def test_create_item_with_sub(): 1abcde
66 client = get_app_client() 1abcde
67 client_no = get_app_client(separate_input_output_schemas=False) 1abcde
68 data = { 1abcde
69 "name": "Plumbus",
70 "sub": {"subname": "SubPlumbus", "sub_description": "Sub WTF"},
71 }
72 response = client.post("/items/", json=data) 1abcde
73 response2 = client_no.post("/items/", json=data) 1abcde
74 assert response.status_code == response2.status_code == 200, response.text 1abcde
75 assert ( 1abcde
76 response.json()
77 == response2.json()
78 == {
79 "name": "Plumbus",
80 "description": None,
81 "sub": {"subname": "SubPlumbus", "sub_description": "Sub WTF", "tags": []},
82 }
83 )
86def test_create_item_list(): 1abcde
87 client = get_app_client() 1abcde
88 client_no = get_app_client(separate_input_output_schemas=False) 1abcde
89 data = [ 1abcde
90 {"name": "Plumbus"},
91 {
92 "name": "Portal Gun",
93 "description": "Device to travel through the multi-rick-verse",
94 },
95 ]
96 response = client.post("/items-list/", json=data) 1abcde
97 response2 = client_no.post("/items-list/", json=data) 1abcde
98 assert response.status_code == response2.status_code == 200, response.text 1abcde
99 assert ( 1abcde
100 response.json()
101 == response2.json()
102 == [
103 {"name": "Plumbus", "description": None, "sub": None},
104 {
105 "name": "Portal Gun",
106 "description": "Device to travel through the multi-rick-verse",
107 "sub": None,
108 },
109 ]
110 )
113def test_read_items(): 1abcde
114 client = get_app_client() 1abcde
115 client_no = get_app_client(separate_input_output_schemas=False) 1abcde
116 response = client.get("/items/") 1abcde
117 response2 = client_no.get("/items/") 1abcde
118 assert response.status_code == response2.status_code == 200, response.text 1abcde
119 assert ( 1abcde
120 response.json()
121 == response2.json()
122 == [
123 {
124 "name": "Portal Gun",
125 "description": "Device to travel through the multi-rick-verse",
126 "sub": {"subname": "subname", "sub_description": None, "tags": []},
127 },
128 {"name": "Plumbus", "description": None, "sub": None},
129 ]
130 )
133@needs_pydanticv2 1abcde
134def test_openapi_schema(): 1abcde
135 client = get_app_client() 1abcde
136 response = client.get("/openapi.json") 1abcde
137 assert response.status_code == 200, response.text 1abcde
138 assert response.json() == { 1abcde
139 "openapi": "3.1.0",
140 "info": {"title": "FastAPI", "version": "0.1.0"},
141 "paths": {
142 "/items/": {
143 "get": {
144 "summary": "Read Items",
145 "operationId": "read_items_items__get",
146 "responses": {
147 "200": {
148 "description": "Successful Response",
149 "content": {
150 "application/json": {
151 "schema": {
152 "items": {
153 "$ref": "#/components/schemas/Item-Output"
154 },
155 "type": "array",
156 "title": "Response Read Items Items Get",
157 }
158 }
159 },
160 }
161 },
162 },
163 "post": {
164 "summary": "Create Item",
165 "operationId": "create_item_items__post",
166 "requestBody": {
167 "content": {
168 "application/json": {
169 "schema": {"$ref": "#/components/schemas/Item-Input"}
170 }
171 },
172 "required": True,
173 },
174 "responses": {
175 "200": {
176 "description": "Successful Response",
177 "content": {"application/json": {"schema": {}}},
178 },
179 "422": {
180 "description": "Validation Error",
181 "content": {
182 "application/json": {
183 "schema": {
184 "$ref": "#/components/schemas/HTTPValidationError"
185 }
186 }
187 },
188 },
189 },
190 },
191 },
192 "/items-list/": {
193 "post": {
194 "summary": "Create Item List",
195 "operationId": "create_item_list_items_list__post",
196 "requestBody": {
197 "content": {
198 "application/json": {
199 "schema": {
200 "items": {
201 "$ref": "#/components/schemas/Item-Input"
202 },
203 "type": "array",
204 "title": "Item",
205 }
206 }
207 },
208 "required": True,
209 },
210 "responses": {
211 "200": {
212 "description": "Successful Response",
213 "content": {"application/json": {"schema": {}}},
214 },
215 "422": {
216 "description": "Validation Error",
217 "content": {
218 "application/json": {
219 "schema": {
220 "$ref": "#/components/schemas/HTTPValidationError"
221 }
222 }
223 },
224 },
225 },
226 }
227 },
228 },
229 "components": {
230 "schemas": {
231 "HTTPValidationError": {
232 "properties": {
233 "detail": {
234 "items": {"$ref": "#/components/schemas/ValidationError"},
235 "type": "array",
236 "title": "Detail",
237 }
238 },
239 "type": "object",
240 "title": "HTTPValidationError",
241 },
242 "Item-Input": {
243 "properties": {
244 "name": {"type": "string", "title": "Name"},
245 "description": {
246 "anyOf": [{"type": "string"}, {"type": "null"}],
247 "title": "Description",
248 },
249 "sub": {
250 "anyOf": [
251 {"$ref": "#/components/schemas/SubItem-Input"},
252 {"type": "null"},
253 ]
254 },
255 },
256 "type": "object",
257 "required": ["name"],
258 "title": "Item",
259 },
260 "Item-Output": {
261 "properties": {
262 "name": {"type": "string", "title": "Name"},
263 "description": {
264 "anyOf": [{"type": "string"}, {"type": "null"}],
265 "title": "Description",
266 },
267 "sub": {
268 "anyOf": [
269 {"$ref": "#/components/schemas/SubItem-Output"},
270 {"type": "null"},
271 ]
272 },
273 },
274 "type": "object",
275 "required": ["name", "description", "sub"],
276 "title": "Item",
277 },
278 "SubItem-Input": {
279 "properties": {
280 "subname": {"type": "string", "title": "Subname"},
281 "sub_description": {
282 "anyOf": [{"type": "string"}, {"type": "null"}],
283 "title": "Sub Description",
284 },
285 "tags": {
286 "items": {"type": "string"},
287 "type": "array",
288 "title": "Tags",
289 "default": [],
290 },
291 },
292 "type": "object",
293 "required": ["subname"],
294 "title": "SubItem",
295 },
296 "SubItem-Output": {
297 "properties": {
298 "subname": {"type": "string", "title": "Subname"},
299 "sub_description": {
300 "anyOf": [{"type": "string"}, {"type": "null"}],
301 "title": "Sub Description",
302 },
303 "tags": {
304 "items": {"type": "string"},
305 "type": "array",
306 "title": "Tags",
307 "default": [],
308 },
309 },
310 "type": "object",
311 "required": ["subname", "sub_description", "tags"],
312 "title": "SubItem",
313 },
314 "ValidationError": {
315 "properties": {
316 "loc": {
317 "items": {
318 "anyOf": [{"type": "string"}, {"type": "integer"}]
319 },
320 "type": "array",
321 "title": "Location",
322 },
323 "msg": {"type": "string", "title": "Message"},
324 "type": {"type": "string", "title": "Error Type"},
325 },
326 "type": "object",
327 "required": ["loc", "msg", "type"],
328 "title": "ValidationError",
329 },
330 }
331 },
332 }
335@needs_pydanticv2 1abcde
336def test_openapi_schema_no_separate(): 1abcde
337 client = get_app_client(separate_input_output_schemas=False) 1abcde
338 response = client.get("/openapi.json") 1abcde
339 assert response.status_code == 200, response.text 1abcde
340 assert response.json() == { 1abcde
341 "openapi": "3.1.0",
342 "info": {"title": "FastAPI", "version": "0.1.0"},
343 "paths": {
344 "/items/": {
345 "get": {
346 "summary": "Read Items",
347 "operationId": "read_items_items__get",
348 "responses": {
349 "200": {
350 "description": "Successful Response",
351 "content": {
352 "application/json": {
353 "schema": {
354 "items": {"$ref": "#/components/schemas/Item"},
355 "type": "array",
356 "title": "Response Read Items Items Get",
357 }
358 }
359 },
360 }
361 },
362 },
363 "post": {
364 "summary": "Create Item",
365 "operationId": "create_item_items__post",
366 "requestBody": {
367 "content": {
368 "application/json": {
369 "schema": {"$ref": "#/components/schemas/Item"}
370 }
371 },
372 "required": True,
373 },
374 "responses": {
375 "200": {
376 "description": "Successful Response",
377 "content": {"application/json": {"schema": {}}},
378 },
379 "422": {
380 "description": "Validation Error",
381 "content": {
382 "application/json": {
383 "schema": {
384 "$ref": "#/components/schemas/HTTPValidationError"
385 }
386 }
387 },
388 },
389 },
390 },
391 },
392 "/items-list/": {
393 "post": {
394 "summary": "Create Item List",
395 "operationId": "create_item_list_items_list__post",
396 "requestBody": {
397 "content": {
398 "application/json": {
399 "schema": {
400 "items": {"$ref": "#/components/schemas/Item"},
401 "type": "array",
402 "title": "Item",
403 }
404 }
405 },
406 "required": True,
407 },
408 "responses": {
409 "200": {
410 "description": "Successful Response",
411 "content": {"application/json": {"schema": {}}},
412 },
413 "422": {
414 "description": "Validation Error",
415 "content": {
416 "application/json": {
417 "schema": {
418 "$ref": "#/components/schemas/HTTPValidationError"
419 }
420 }
421 },
422 },
423 },
424 }
425 },
426 },
427 "components": {
428 "schemas": {
429 "HTTPValidationError": {
430 "properties": {
431 "detail": {
432 "items": {"$ref": "#/components/schemas/ValidationError"},
433 "type": "array",
434 "title": "Detail",
435 }
436 },
437 "type": "object",
438 "title": "HTTPValidationError",
439 },
440 "Item": {
441 "properties": {
442 "name": {"type": "string", "title": "Name"},
443 "description": {
444 "anyOf": [{"type": "string"}, {"type": "null"}],
445 "title": "Description",
446 },
447 "sub": {
448 "anyOf": [
449 {"$ref": "#/components/schemas/SubItem"},
450 {"type": "null"},
451 ]
452 },
453 },
454 "type": "object",
455 "required": ["name"],
456 "title": "Item",
457 },
458 "SubItem": {
459 "properties": {
460 "subname": {"type": "string", "title": "Subname"},
461 "sub_description": {
462 "anyOf": [{"type": "string"}, {"type": "null"}],
463 "title": "Sub Description",
464 },
465 "tags": {
466 "items": {"type": "string"},
467 "type": "array",
468 "title": "Tags",
469 "default": [],
470 },
471 },
472 "type": "object",
473 "required": ["subname"],
474 "title": "SubItem",
475 },
476 "ValidationError": {
477 "properties": {
478 "loc": {
479 "items": {
480 "anyOf": [{"type": "string"}, {"type": "integer"}]
481 },
482 "type": "array",
483 "title": "Location",
484 },
485 "msg": {"type": "string", "title": "Message"},
486 "type": {"type": "string", "title": "Error Type"},
487 },
488 "type": "object",
489 "required": ["loc", "msg", "type"],
490 "title": "ValidationError",
491 },
492 }
493 },
494 }