Coverage for nexios\openapi\models.py: 99%

1# type: ignore[overide]

2 from __future__ import annotations

3

4 from typing import Any, Dict, List, Mapping, Optional, Union

5

6 from pydantic import ConfigDict, BaseModel, Field

7 from pydantic.networks import AnyUrl

8

9 try:

10 import email_validator # type: ignore # noqa: F401

11 from pydantic import EmailStr

12 except ImportError: # pragma: no cover

13 EmailStr = str # type: ignore

14

15

16 from typing import Annotated, Literal

17

18 ParameterLocations = Literal["header", "path", "query", "cookie"]

19 PathParamStyles = Literal["simple", "label", "matrix"]

20 QueryParamStyles = Literal["form", "spaceDelimited", "pipeDelimited", "deepObject"]

21 HeaderParamStyles = Literal["simple"]

22 CookieParamStyles = Literal["form"]

23 FormDataStyles = QueryParamStyles

24

25 Extension = Union[Dict[str, Any], List[Any], str, int, float, bool, None]

26

27

28 class Contact(BaseModel):

29 name: Optional[str] = None

30 url: Optional[AnyUrl] = None

31 email: Optional[EmailStr] = None

32

33

34 class License(BaseModel):

35 name: str

36 url: Optional[AnyUrl] = None

37

38

39 class Info(BaseModel):

40 title: str

41 version: str

42 description: Optional[str] = None

43 termsOfService: Optional[str] = None

44 contact: Optional[Contact] = None

45 license: Optional[License] = None

46

47 model_config = ConfigDict(extra="allow")

48

49

50# for extensions

51

52

53 class ServerVariable(BaseModel):

54 default: str

55 enum: Optional[List[str]] = None

56 description: Optional[str] = None

57

58

59 class Server(BaseModel):

60 url: Union[AnyUrl, str]

61 description: Optional[str] = None

62 variables: Optional[Dict[str, ServerVariable]] = None

63

64

65 class Reference(BaseModel):

66 ref: Annotated[str, Field(alias="$ref")]

67

68

69 class Discriminator(BaseModel):

70 propertyName: str

71 mapping: Optional[Dict[str, str]] = None

72

73

74 class XML(BaseModel):

75 name: Optional[str] = None

76 namespace: Optional[str] = None

77 prefix: Optional[str] = None

78 attribute: Optional[bool] = None

79 wrapped: Optional[bool] = None

80

81

82 class ExternalDocumentation(BaseModel):

83 url: Optional[AnyUrl] = None

84 description: Optional[str] = None

85

86

87 class Schema(BaseModel):

88 ref: Annotated[Optional[str], Field(alias="$ref")] = None

89 title: Optional[str] = None

90 multipleOf: Optional[float] = None

91 maximum: Optional[float] = None

92 exclusiveMaximum: Optional[float] = None

93 minimum: Optional[float] = None

94 exclusiveMinimum: Optional[float] = None

95 maxLength: Annotated[Optional[int], Field(ge=0)] = None

96 minLength: Annotated[Optional[int], Field(ge=0)] = None

97 pattern: Optional[str] = None

98 maxItems: Annotated[Optional[int], Field(ge=0)] = None

99 minItems: Annotated[Optional[int], Field(ge=0)] = None

100 uniqueItems: Optional[bool] = None

101 maxProperties: Annotated[Optional[int], Field(ge=0)] = None

102 minProperties: Annotated[Optional[int], Field(ge=0)] = None

103 required: Optional[List[str]] = None

104 enum: Optional[List[Any]] = None

105 type: Optional[str] = "object"

106 allOf: Optional[List[Schema]] = None

107 oneOf: Optional[List[Schema]] = None

108 anyOf: Optional[List[Schema]] = None

109 not_: Annotated[Optional[Schema], Field(alias="not")] = None

110 items: Optional[Union[Schema, List[Schema]]] = None

111 properties: Optional[Dict[str, Schema]] = None

112 additionalProperties: Optional[Union[Schema, Reference, bool]] = None

113 description: Optional[str] = None

114 format: Optional[str] = None

115 default: Any = None

116 nullable: Optional[bool] = None

117 discriminator: Optional[Discriminator] = None

118 readOnly: Optional[bool] = None

119 writeOnly: Optional[bool] = None

120 xml: Optional[XML] = None

121 externalDocs: Optional[ExternalDocumentation] = None

122 deprecated: Optional[bool] = None

123 example: Optional[Any] = None

124 examples: Optional[Examples] = None

125

126

127 class Example(BaseModel):

128 summary: Optional[str] = None

129 description: Optional[str] = None

130 value: Any = None

131 external_value: Annotated[Optional[str], Field(alias="externalValue")] = None

132

133

134 Examples = Mapping[str, Union[Example, Reference]]

135

136

137 class Encoding(BaseModel):

138 contentType: Optional[str] = None

139 headers: Optional[Dict[str, Union[Header, Reference]]] = None

140 style: Optional[str] = None

141 explode: Optional[bool] = None

142

143

144 class MediaType(BaseModel):

145 schema_: Annotated[Optional[Union[Schema, Reference]], Field(alias="schema")]

146 examples: Optional[Examples] = None

147 encoding: Optional[Dict[str, Encoding]] = None

148

149

150 class ParameterBase(BaseModel):

151 description: Optional[str] = None

152 required: Optional[bool] = None

153 deprecated: Optional[bool] = None

154 # Serialization rules for simple scenarios

155 style: Optional[str] = None

156 explode: Optional[bool] = None

157 schema_: Annotated[Optional[Union[Schema, Reference]], Field(alias="schema")]

158 examples: Optional[Examples] = None

159 # Serialization rules for more complex scenarios

160 content: Optional[Dict[str, MediaType]] = None

161

162

163 class ConcreteParameter(ParameterBase):

164 name: str

165 in_: ParameterLocations = Field(alias="in")

166

167

168 class Header(ConcreteParameter):

169 in_: Literal["header"] = Field(default="header", alias="in")

170 style: HeaderParamStyles = "simple"

171 explode: bool = False

172 schema_: Annotated[Optional[Union[Schema, Reference]], Field(alias="schema")] = (

173 Schema(type="string")

174 )

175

176

177 class Query(ConcreteParameter):

178 in_: Literal["query"] = Field(

179 default="query", # Explicit default

180 alias="in", # Explicit alias for OpenAPI compliance

181 )

182 style: QueryParamStyles = "form"

183 explode: bool = True

184 schema_: Annotated[Optional[Union[Schema, Reference]], Field(alias="schema")] = (

185 Schema(type="string")

186 )

187

188

189 class Path(ConcreteParameter):

190 in_: Literal["path"] = Field(default="path", alias="in") # Explicit default

191 style: PathParamStyles = "simple"

192 explode: bool = False

193 required: Literal[True] = True

194

195

196 class Cookie(ConcreteParameter):

197 in_: Literal["cookie"] = "cookie"

198 style: CookieParamStyles = "form"

199 explode: bool = True

200

201

202 Parameter = Union[Query, Header, Cookie, Path]

203

204

205 class RequestBody(BaseModel):

206 content: Dict[str, MediaType]

207 description: Optional[str] = None

208 required: Optional[bool] = None

209

210

211 class Link(BaseModel):

212 operationRef: Optional[str] = None

213 operationId: Optional[str] = None

214 parameters: Optional[Dict[str, str]] = None

215 requestBody: Optional[str] = None

216 description: Optional[str] = None

217 server: Optional[Server] = None

218

219

220 class ResponseHeader(BaseModel):

221 description: Optional[str] = None

222 deprecated: Optional[bool] = None

223 # Serialization rules for simple scenarios

224 style: HeaderParamStyles = "simple"

225 explode: bool = False

226 schema_: Annotated[Optional[Union[Schema, Reference]], Field(alias="schema")] = None

227 examples: Optional[Examples] = None

228 # Serialization rules for more complex scenarios

229 content: Optional[Dict[str, MediaType]] = None

230

231

232 class Response(BaseModel):

233 description: str

234 headers: Optional[Dict[str, Union[ResponseHeader, Reference]]] = None

235 content: Optional[Dict[str, MediaType]] = None

236 links: Optional[Dict[str, Union[Link, Reference]]] = None

237

238

239 class Operation(BaseModel):

240 responses: Dict[str, Union[Response, Reference]]

241 tags: Optional[List[str]] = None

242 summary: Optional[str] = None

243 description: Optional[str] = None

244 externalDocs: Optional[ExternalDocumentation] = None

245 operationId: Optional[str] = None

246 parameters: Optional[List[Union[ConcreteParameter, Reference]]] = None

247 requestBody: Optional[Union[RequestBody, Reference]] = None

248 # Using Any for Specification Extensions

249 callbacks: Optional[Dict[str, Union[Dict[str, PathItem], Reference]]] = None

250 deprecated: Optional[bool] = None

251 security: Optional[List[Dict[str, List[str]]]] = None

252 servers: Optional[List[Server]] = None

253

254 model_config = ConfigDict(extra="allow")

255

256

257# for extensions

258

259

260 class PathItem(BaseModel):

261 ref: Annotated[Optional[str], Field(alias="$ref")] = None

262 summary: Optional[str] = None

263 description: Optional[str] = None

264 get: Optional[Operation] = None

265 put: Optional[Operation] = None

266 post: Optional[Operation] = None

267 delete: Optional[Operation] = None

268 options: Optional[Operation] = None

269 head: Optional[Operation] = None

270 patch: Optional[Operation] = None

271 trace: Optional[Operation] = None

272 servers: Optional[List[Server]] = None

273 parameters: Optional[List[Union[Parameter, Reference]]] = None

274

275 model_config = ConfigDict(extra="allow")

276

277

278# for extensions

279

280

281 SecuritySchemeName = Literal["apiKey", "http", "oauth2", "openIdConnect"]

282

283

284 class SecurityBase(BaseModel):

285 type: SecuritySchemeName

286 description: Optional[str] = None

287

288

289 APIKeyLocation = Literal["query", "header", "cookie"]

290

291

292 class APIKey(SecurityBase):

293 name: str

294 in_: Annotated[APIKeyLocation, Field(alias="in")]

295 type: Literal["apiKey"] = "apiKey"

296

297

298 class HTTPBase(SecurityBase):

299 scheme: str

300 type: Literal["http"] = "http"

301

302

303 class HTTPBearer(HTTPBase):

304 scheme: Literal["bearer"] = "bearer"

305 bearerFormat: Optional[str] = None

306 type: Literal["http"] = "http"

307

308

309 class OAuthFlow(BaseModel):

310 refreshUrl: Optional[AnyUrl] = None

311 scopes: Annotated[Optional[Mapping[str, str]], Field(default_factory=dict)]

312

313

314 class OAuthFlowImplicit(OAuthFlow):

315 authorizationUrl: str

316

317

318 class OAuthFlowPassword(OAuthFlow):

319 tokenUrl: str

320

321

322 class OAuthFlowClientCredentials(OAuthFlow):

323 tokenUrl: str

324

325

326 class OAuthFlowAuthorizationCode(OAuthFlow):

327 authorizationUrl: str

328 tokenUrl: str

329

330

331 class OAuthFlows(BaseModel):

332 implicit: Optional[OAuthFlowImplicit] = None

333 password: Optional[OAuthFlowPassword] = None

334 clientCredentials: Optional[OAuthFlowClientCredentials] = None

335 authorizationCode: Optional[OAuthFlowAuthorizationCode] = None

336

337

338 class OAuth2(SecurityBase):

339 flows: OAuthFlows

340 type: Literal["oauth2"] = "oauth2"

341

342

343 class OpenIdConnect(SecurityBase):

344 openIdConnectUrl: str

345 type: Literal["openIdConnect"] = "openIdConnect"

346

347

348 SecurityScheme = Union[APIKey, HTTPBase, OAuth2, OpenIdConnect, HTTPBearer]

349

350

351 class Components(BaseModel):

352 schemas: Optional[Dict[str, Union[Schema, Reference]]] = None

353 responses: Optional[Dict[str, Union[Response, Reference]]] = None

354 parameters: Optional[Dict[str, Union[Parameter, Reference]]] = None

355 examples: Optional[Examples] = None

356 requestBodies: Optional[Dict[str, Union[RequestBody, Reference]]] = None

357 headers: Optional[Dict[str, Union[Header, Reference]]] = None

358 securitySchemes: Optional[Dict[str, Union[SecurityScheme, Reference]]] = None

359 links: Optional[Dict[str, Union[Link, Reference]]] = None

360 callbacks: Optional[Dict[str, Union[Dict[str, PathItem], Reference]]] = None

361

362

363 class Tag(BaseModel):

364 name: str

365 description: Optional[str] = None

366 externalDocs: Optional[ExternalDocumentation] = None

367

368

369 class OpenAPI(BaseModel):

370 openapi: str

371 info: Info

372 paths: Annotated[Dict[str, Union[PathItem, Extension]], Field(default_factory=dict)]

373 servers: Optional[List[Server]] = None

374 # Using Any for Specification Extensions

375 components: Optional[Components] = None

376 security: Optional[List[Dict[str, List[str]]]] = None

377 tags: Optional[List[Tag]] = None

378 externalDocs: Optional[ExternalDocumentation] = None

379

380

381 Schema.model_rebuild()

382 Operation.model_rebuild()

383 Encoding.model_rebuild()