Coverage for fastapi/openapi/models.py: 100%
276 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 enum import Enum 1abcde
2from typing import Any, Callable, Dict, Iterable, List, Optional, Set, Type, Union 1abcde
4from fastapi._compat import ( 1abcde
5 PYDANTIC_V2,
6 CoreSchema,
7 GetJsonSchemaHandler,
8 JsonSchemaValue,
9 _model_rebuild,
10 with_info_plain_validator_function,
11)
12from fastapi.logger import logger 1abcde
13from pydantic import AnyUrl, BaseModel, Field 1abcde
14from typing_extensions import Annotated, Literal, TypedDict 1abcde
15from typing_extensions import deprecated as typing_deprecated 1abcde
17try: 1abcde
18 import email_validator 1abcde
20 assert email_validator # make autoflake ignore the unused import 1abcde
21 from pydantic import EmailStr 1abcde
22except ImportError: # pragma: no cover
24 class EmailStr(str): # type: ignore
25 @classmethod
26 def __get_validators__(cls) -> Iterable[Callable[..., Any]]:
27 yield cls.validate
29 @classmethod
30 def validate(cls, v: Any) -> str:
31 logger.warning(
32 "email-validator not installed, email fields will be treated as str.\n"
33 "To install, run: pip install email-validator"
34 )
35 return str(v)
37 @classmethod
38 def _validate(cls, __input_value: Any, _: Any) -> str:
39 logger.warning(
40 "email-validator not installed, email fields will be treated as str.\n"
41 "To install, run: pip install email-validator"
42 )
43 return str(__input_value)
45 @classmethod
46 def __get_pydantic_json_schema__(
47 cls, core_schema: CoreSchema, handler: GetJsonSchemaHandler
48 ) -> JsonSchemaValue:
49 return {"type": "string", "format": "email"}
51 @classmethod
52 def __get_pydantic_core_schema__(
53 cls, source: Type[Any], handler: Callable[[Any], CoreSchema]
54 ) -> CoreSchema:
55 return with_info_plain_validator_function(cls._validate)
58class BaseModelWithConfig(BaseModel): 1abcde
59 if PYDANTIC_V2: 1abcde
60 model_config = {"extra": "allow"} 1abcde
62 else:
64 class Config: 1abcde
65 extra = "allow" 1abcde
68class Contact(BaseModelWithConfig): 1abcde
69 name: Optional[str] = None 1abcde
70 url: Optional[AnyUrl] = None 1abcde
71 email: Optional[EmailStr] = None 1abcde
74class License(BaseModelWithConfig): 1abcde
75 name: str 1abcde
76 identifier: Optional[str] = None 1abcde
77 url: Optional[AnyUrl] = None 1abcde
80class Info(BaseModelWithConfig): 1abcde
81 title: str 1abcde
82 summary: Optional[str] = None 1abcde
83 description: Optional[str] = None 1abcde
84 termsOfService: Optional[str] = None 1abcde
85 contact: Optional[Contact] = None 1abcde
86 license: Optional[License] = None 1abcde
87 version: str 1abcde
90class ServerVariable(BaseModelWithConfig): 1abcde
91 enum: Annotated[Optional[List[str]], Field(min_length=1)] = None 1abcde
92 default: str 1abcde
93 description: Optional[str] = None 1abcde
96class Server(BaseModelWithConfig): 1abcde
97 url: Union[AnyUrl, str] 1abcde
98 description: Optional[str] = None 1abcde
99 variables: Optional[Dict[str, ServerVariable]] = None 1abcde
102class Reference(BaseModel): 1abcde
103 ref: str = Field(alias="$ref") 1abcde
106class Discriminator(BaseModel): 1abcde
107 propertyName: str 1abcde
108 mapping: Optional[Dict[str, str]] = None 1abcde
111class XML(BaseModelWithConfig): 1abcde
112 name: Optional[str] = None 1abcde
113 namespace: Optional[str] = None 1abcde
114 prefix: Optional[str] = None 1abcde
115 attribute: Optional[bool] = None 1abcde
116 wrapped: Optional[bool] = None 1abcde
119class ExternalDocumentation(BaseModelWithConfig): 1abcde
120 description: Optional[str] = None 1abcde
121 url: AnyUrl 1abcde
124class Schema(BaseModelWithConfig): 1abcde
125 # Ref: JSON Schema 2020-12: https://json-schema.org/draft/2020-12/json-schema-core.html#name-the-json-schema-core-vocabu
126 # Core Vocabulary
127 schema_: Optional[str] = Field(default=None, alias="$schema") 1abcde
128 vocabulary: Optional[str] = Field(default=None, alias="$vocabulary") 1abcde
129 id: Optional[str] = Field(default=None, alias="$id") 1abcde
130 anchor: Optional[str] = Field(default=None, alias="$anchor") 1abcde
131 dynamicAnchor: Optional[str] = Field(default=None, alias="$dynamicAnchor") 1abcde
132 ref: Optional[str] = Field(default=None, alias="$ref") 1abcde
133 dynamicRef: Optional[str] = Field(default=None, alias="$dynamicRef") 1abcde
134 defs: Optional[Dict[str, "SchemaOrBool"]] = Field(default=None, alias="$defs") 1abcde
135 comment: Optional[str] = Field(default=None, alias="$comment") 1abcde
136 # Ref: JSON Schema 2020-12: https://json-schema.org/draft/2020-12/json-schema-core.html#name-a-vocabulary-for-applying-s
137 # A Vocabulary for Applying Subschemas
138 allOf: Optional[List["SchemaOrBool"]] = None 1abcde
139 anyOf: Optional[List["SchemaOrBool"]] = None 1abcde
140 oneOf: Optional[List["SchemaOrBool"]] = None 1abcde
141 not_: Optional["SchemaOrBool"] = Field(default=None, alias="not") 1abcde
142 if_: Optional["SchemaOrBool"] = Field(default=None, alias="if") 1abcde
143 then: Optional["SchemaOrBool"] = None 1abcde
144 else_: Optional["SchemaOrBool"] = Field(default=None, alias="else") 1abcde
145 dependentSchemas: Optional[Dict[str, "SchemaOrBool"]] = None 1abcde
146 prefixItems: Optional[List["SchemaOrBool"]] = None 1abcde
147 # TODO: uncomment and remove below when deprecating Pydantic v1
148 # It generales a list of schemas for tuples, before prefixItems was available
149 # items: Optional["SchemaOrBool"] = None
150 items: Optional[Union["SchemaOrBool", List["SchemaOrBool"]]] = None 1abcde
151 contains: Optional["SchemaOrBool"] = None 1abcde
152 properties: Optional[Dict[str, "SchemaOrBool"]] = None 1abcde
153 patternProperties: Optional[Dict[str, "SchemaOrBool"]] = None 1abcde
154 additionalProperties: Optional["SchemaOrBool"] = None 1abcde
155 propertyNames: Optional["SchemaOrBool"] = None 1abcde
156 unevaluatedItems: Optional["SchemaOrBool"] = None 1abcde
157 unevaluatedProperties: Optional["SchemaOrBool"] = None 1abcde
158 # Ref: JSON Schema Validation 2020-12: https://json-schema.org/draft/2020-12/json-schema-validation.html#name-a-vocabulary-for-structural
159 # A Vocabulary for Structural Validation
160 type: Optional[str] = None 1abcde
161 enum: Optional[List[Any]] = None 1abcde
162 const: Optional[Any] = None 1abcde
163 multipleOf: Optional[float] = Field(default=None, gt=0) 1abcde
164 maximum: Optional[float] = None 1abcde
165 exclusiveMaximum: Optional[float] = None 1abcde
166 minimum: Optional[float] = None 1abcde
167 exclusiveMinimum: Optional[float] = None 1abcde
168 maxLength: Optional[int] = Field(default=None, ge=0) 1abcde
169 minLength: Optional[int] = Field(default=None, ge=0) 1abcde
170 pattern: Optional[str] = None 1abcde
171 maxItems: Optional[int] = Field(default=None, ge=0) 1abcde
172 minItems: Optional[int] = Field(default=None, ge=0) 1abcde
173 uniqueItems: Optional[bool] = None 1abcde
174 maxContains: Optional[int] = Field(default=None, ge=0) 1abcde
175 minContains: Optional[int] = Field(default=None, ge=0) 1abcde
176 maxProperties: Optional[int] = Field(default=None, ge=0) 1abcde
177 minProperties: Optional[int] = Field(default=None, ge=0) 1abcde
178 required: Optional[List[str]] = None 1abcde
179 dependentRequired: Optional[Dict[str, Set[str]]] = None 1abcde
180 # Ref: JSON Schema Validation 2020-12: https://json-schema.org/draft/2020-12/json-schema-validation.html#name-vocabularies-for-semantic-c
181 # Vocabularies for Semantic Content With "format"
182 format: Optional[str] = None 1abcde
183 # Ref: JSON Schema Validation 2020-12: https://json-schema.org/draft/2020-12/json-schema-validation.html#name-a-vocabulary-for-the-conten
184 # A Vocabulary for the Contents of String-Encoded Data
185 contentEncoding: Optional[str] = None 1abcde
186 contentMediaType: Optional[str] = None 1abcde
187 contentSchema: Optional["SchemaOrBool"] = None 1abcde
188 # Ref: JSON Schema Validation 2020-12: https://json-schema.org/draft/2020-12/json-schema-validation.html#name-a-vocabulary-for-basic-meta
189 # A Vocabulary for Basic Meta-Data Annotations
190 title: Optional[str] = None 1abcde
191 description: Optional[str] = None 1abcde
192 default: Optional[Any] = None 1abcde
193 deprecated: Optional[bool] = None 1abcde
194 readOnly: Optional[bool] = None 1abcde
195 writeOnly: Optional[bool] = None 1abcde
196 examples: Optional[List[Any]] = None 1abcde
197 # Ref: OpenAPI 3.1.0: https://github.com/OAI/OpenAPI-Specification/blob/main/versions/3.1.0.md#schema-object
198 # Schema Object
199 discriminator: Optional[Discriminator] = None 1abcde
200 xml: Optional[XML] = None 1abcde
201 externalDocs: Optional[ExternalDocumentation] = None 1abcde
202 example: Annotated[ 1abcde
203 Optional[Any],
204 typing_deprecated(
205 "Deprecated in OpenAPI 3.1.0 that now uses JSON Schema 2020-12, "
206 "although still supported. Use examples instead."
207 ),
208 ] = None
211# Ref: https://json-schema.org/draft/2020-12/json-schema-core.html#name-json-schema-documents
212# A JSON Schema MUST be an object or a boolean.
213SchemaOrBool = Union[Schema, bool] 1abcde
216class Example(TypedDict, total=False): 1abcde
217 summary: Optional[str] 1abcde
218 description: Optional[str] 1abcde
219 value: Optional[Any] 1abcde
220 externalValue: Optional[AnyUrl] 1abcde
222 if PYDANTIC_V2: # type: ignore [misc] 1abcde
223 __pydantic_config__ = {"extra": "allow"} 1abcde
225 else:
227 class Config: 1abcde
228 extra = "allow" 1abcde
231class ParameterInType(Enum): 1abcde
232 query = "query" 1abcde
233 header = "header" 1abcde
234 path = "path" 1abcde
235 cookie = "cookie" 1abcde
238class Encoding(BaseModelWithConfig): 1abcde
239 contentType: Optional[str] = None 1abcde
240 headers: Optional[Dict[str, Union["Header", Reference]]] = None 1abcde
241 style: Optional[str] = None 1abcde
242 explode: Optional[bool] = None 1abcde
243 allowReserved: Optional[bool] = None 1abcde
246class MediaType(BaseModelWithConfig): 1abcde
247 schema_: Optional[Union[Schema, Reference]] = Field(default=None, alias="schema") 1abcde
248 example: Optional[Any] = None 1abcde
249 examples: Optional[Dict[str, Union[Example, Reference]]] = None 1abcde
250 encoding: Optional[Dict[str, Encoding]] = None 1abcde
253class ParameterBase(BaseModelWithConfig): 1abcde
254 description: Optional[str] = None 1abcde
255 required: Optional[bool] = None 1abcde
256 deprecated: Optional[bool] = None 1abcde
257 # Serialization rules for simple scenarios
258 style: Optional[str] = None 1abcde
259 explode: Optional[bool] = None 1abcde
260 allowReserved: Optional[bool] = None 1abcde
261 schema_: Optional[Union[Schema, Reference]] = Field(default=None, alias="schema") 1abcde
262 example: Optional[Any] = None 1abcde
263 examples: Optional[Dict[str, Union[Example, Reference]]] = None 1abcde
264 # Serialization rules for more complex scenarios
265 content: Optional[Dict[str, MediaType]] = None 1abcde
268class Parameter(ParameterBase): 1abcde
269 name: str 1abcde
270 in_: ParameterInType = Field(alias="in") 1abcde
273class Header(ParameterBase): 1abcde
274 pass 1abcde
277class RequestBody(BaseModelWithConfig): 1abcde
278 description: Optional[str] = None 1abcde
279 content: Dict[str, MediaType] 1abcde
280 required: Optional[bool] = None 1abcde
283class Link(BaseModelWithConfig): 1abcde
284 operationRef: Optional[str] = None 1abcde
285 operationId: Optional[str] = None 1abcde
286 parameters: Optional[Dict[str, Union[Any, str]]] = None 1abcde
287 requestBody: Optional[Union[Any, str]] = None 1abcde
288 description: Optional[str] = None 1abcde
289 server: Optional[Server] = None 1abcde
292class Response(BaseModelWithConfig): 1abcde
293 description: str 1abcde
294 headers: Optional[Dict[str, Union[Header, Reference]]] = None 1abcde
295 content: Optional[Dict[str, MediaType]] = None 1abcde
296 links: Optional[Dict[str, Union[Link, Reference]]] = None 1abcde
299class Operation(BaseModelWithConfig): 1abcde
300 tags: Optional[List[str]] = None 1abcde
301 summary: Optional[str] = None 1abcde
302 description: Optional[str] = None 1abcde
303 externalDocs: Optional[ExternalDocumentation] = None 1abcde
304 operationId: Optional[str] = None 1abcde
305 parameters: Optional[List[Union[Parameter, Reference]]] = None 1abcde
306 requestBody: Optional[Union[RequestBody, Reference]] = None 1abcde
307 # Using Any for Specification Extensions
308 responses: Optional[Dict[str, Union[Response, Any]]] = None 1abcde
309 callbacks: Optional[Dict[str, Union[Dict[str, "PathItem"], Reference]]] = None 1abcde
310 deprecated: Optional[bool] = None 1abcde
311 security: Optional[List[Dict[str, List[str]]]] = None 1abcde
312 servers: Optional[List[Server]] = None 1abcde
315class PathItem(BaseModelWithConfig): 1abcde
316 ref: Optional[str] = Field(default=None, alias="$ref") 1abcde
317 summary: Optional[str] = None 1abcde
318 description: Optional[str] = None 1abcde
319 get: Optional[Operation] = None 1abcde
320 put: Optional[Operation] = None 1abcde
321 post: Optional[Operation] = None 1abcde
322 delete: Optional[Operation] = None 1abcde
323 options: Optional[Operation] = None 1abcde
324 head: Optional[Operation] = None 1abcde
325 patch: Optional[Operation] = None 1abcde
326 trace: Optional[Operation] = None 1abcde
327 servers: Optional[List[Server]] = None 1abcde
328 parameters: Optional[List[Union[Parameter, Reference]]] = None 1abcde
331class SecuritySchemeType(Enum): 1abcde
332 apiKey = "apiKey" 1abcde
333 http = "http" 1abcde
334 oauth2 = "oauth2" 1abcde
335 openIdConnect = "openIdConnect" 1abcde
338class SecurityBase(BaseModelWithConfig): 1abcde
339 type_: SecuritySchemeType = Field(alias="type") 1abcde
340 description: Optional[str] = None 1abcde
343class APIKeyIn(Enum): 1abcde
344 query = "query" 1abcde
345 header = "header" 1abcde
346 cookie = "cookie" 1abcde
349class APIKey(SecurityBase): 1abcde
350 type_: SecuritySchemeType = Field(default=SecuritySchemeType.apiKey, alias="type") 1abcde
351 in_: APIKeyIn = Field(alias="in") 1abcde
352 name: str 1abcde
355class HTTPBase(SecurityBase): 1abcde
356 type_: SecuritySchemeType = Field(default=SecuritySchemeType.http, alias="type") 1abcde
357 scheme: str 1abcde
360class HTTPBearer(HTTPBase): 1abcde
361 scheme: Literal["bearer"] = "bearer" 1abcde
362 bearerFormat: Optional[str] = None 1abcde
365class OAuthFlow(BaseModelWithConfig): 1abcde
366 refreshUrl: Optional[str] = None 1abcde
367 scopes: Dict[str, str] = {} 1abcde
370class OAuthFlowImplicit(OAuthFlow): 1abcde
371 authorizationUrl: str 1abcde
374class OAuthFlowPassword(OAuthFlow): 1abcde
375 tokenUrl: str 1abcde
378class OAuthFlowClientCredentials(OAuthFlow): 1abcde
379 tokenUrl: str 1abcde
382class OAuthFlowAuthorizationCode(OAuthFlow): 1abcde
383 authorizationUrl: str 1abcde
384 tokenUrl: str 1abcde
387class OAuthFlows(BaseModelWithConfig): 1abcde
388 implicit: Optional[OAuthFlowImplicit] = None 1abcde
389 password: Optional[OAuthFlowPassword] = None 1abcde
390 clientCredentials: Optional[OAuthFlowClientCredentials] = None 1abcde
391 authorizationCode: Optional[OAuthFlowAuthorizationCode] = None 1abcde
394class OAuth2(SecurityBase): 1abcde
395 type_: SecuritySchemeType = Field(default=SecuritySchemeType.oauth2, alias="type") 1abcde
396 flows: OAuthFlows 1abcde
399class OpenIdConnect(SecurityBase): 1abcde
400 type_: SecuritySchemeType = Field( 1abcde
401 default=SecuritySchemeType.openIdConnect, alias="type"
402 )
403 openIdConnectUrl: str 1abcde
406SecurityScheme = Union[APIKey, HTTPBase, OAuth2, OpenIdConnect, HTTPBearer] 1abcde
409class Components(BaseModelWithConfig): 1abcde
410 schemas: Optional[Dict[str, Union[Schema, Reference]]] = None 1abcde
411 responses: Optional[Dict[str, Union[Response, Reference]]] = None 1abcde
412 parameters: Optional[Dict[str, Union[Parameter, Reference]]] = None 1abcde
413 examples: Optional[Dict[str, Union[Example, Reference]]] = None 1abcde
414 requestBodies: Optional[Dict[str, Union[RequestBody, Reference]]] = None 1abcde
415 headers: Optional[Dict[str, Union[Header, Reference]]] = None 1abcde
416 securitySchemes: Optional[Dict[str, Union[SecurityScheme, Reference]]] = None 1abcde
417 links: Optional[Dict[str, Union[Link, Reference]]] = None 1abcde
418 # Using Any for Specification Extensions
419 callbacks: Optional[Dict[str, Union[Dict[str, PathItem], Reference, Any]]] = None 1abcde
420 pathItems: Optional[Dict[str, Union[PathItem, Reference]]] = None 1abcde
423class Tag(BaseModelWithConfig): 1abcde
424 name: str 1abcde
425 description: Optional[str] = None 1abcde
426 externalDocs: Optional[ExternalDocumentation] = None 1abcde
429class OpenAPI(BaseModelWithConfig): 1abcde
430 openapi: str 1abcde
431 info: Info 1abcde
432 jsonSchemaDialect: Optional[str] = None 1abcde
433 servers: Optional[List[Server]] = None 1abcde
434 # Using Any for Specification Extensions
435 paths: Optional[Dict[str, Union[PathItem, Any]]] = None 1abcde
436 webhooks: Optional[Dict[str, Union[PathItem, Reference]]] = None 1abcde
437 components: Optional[Components] = None 1abcde
438 security: Optional[List[Dict[str, List[str]]]] = None 1abcde
439 tags: Optional[List[Tag]] = None 1abcde
440 externalDocs: Optional[ExternalDocumentation] = None 1abcde
443_model_rebuild(Schema) 1abcde
444_model_rebuild(Operation) 1abcde
445_model_rebuild(Encoding) 1abcde