Fix python-fastapi free-form objects mapping and forward ref type hints (#9723)

* map free-form objects to Dict[str, Any]

* support Forward Type References

Forward type references will be supported by default from Python 3.10 on only. Until then (and starting with Python 3.7), we can opt in by a __future__ import, cf. https://docs.python.org/3.9/whatsnew/3.7.html?highlight=forward#pep-563-postponed-evaluation-of-annotations

* re-created pet-store sample

* bump required Python version to 3.7 for generated FastAPI projects

* make pydantic modell classes process forward type references
This commit is contained in:
Christoph Ludwig 2021-06-14 12:05:36 +02:00 committed by GitHub
parent 874d7d4f97
commit f3e3a724fb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
14 changed files with 41 additions and 20 deletions

View File

@ -1,4 +1,4 @@
FROM python:3.6 AS builder
FROM python:3.7 AS builder
WORKDIR /usr/src/app
@ -11,7 +11,7 @@ COPY . .
RUN pip install --no-cache-dir .
FROM python:3.6 AS test_runner
FROM python:3.7 AS test_runner
WORKDIR /tmp
COPY --from=builder /venv /venv
COPY --from=builder /usr/src/app/tests tests
@ -24,7 +24,7 @@ RUN pip install pytest
RUN pytest tests
FROM python:3.6 AS service
FROM python:3.7 AS service
WORKDIR /root/app/site-packages
COPY --from=test_runner /venv /venv
ENV PATH=/venv/bin:$PATH

View File

@ -10,7 +10,7 @@ This Python package is automatically generated by the [OpenAPI Generator](https:
## Requirements.
Python >= 3.6
Python >= 3.7
## Installation & Usage

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
{{#models}}
@ -71,3 +72,5 @@ class {{classname}}(BaseModel):
{{/vars}}
{{/model}}
{{/models}}
{{classname}}.update_forward_refs()

View File

@ -1 +1 @@
{{#isEmail}}EmailStr{{/isEmail}}{{#isUri}}AnyUrl{{/isUri}}{{^isEmail}}{{^isUri}}{{dataType}}{{/isUri}}{{/isEmail}}
{{#isEmail}}EmailStr{{/isEmail}}{{#isUri}}AnyUrl{{/isUri}}{{#isFreeFormObject}}Dict[str, Any]{{/isFreeFormObject}}{{^isEmail}}{{^isUri}}{{^isFreeFormObject}}{{dataType}}{{/isFreeFormObject}}{{/isUri}}{{/isEmail}}

View File

@ -4,11 +4,11 @@ version = {{appVersion}}
description = {{appDescription}}
long_description = file: README.md
keywords = OpenAPI {{appName}}
python_requires = >= 3.6.*
python_requires = >= 3.7.*
classifiers =
Operating System :: OS Independent
Programming Language :: Python :: 3
Programming Language :: Python :: 3.6
Programming Language :: Python :: 3.7
[options]
install_requires =

View File

@ -1,4 +1,4 @@
FROM python:3.6 AS builder
FROM python:3.7 AS builder
WORKDIR /usr/src/app
@ -11,7 +11,7 @@ COPY . .
RUN pip install --no-cache-dir .
FROM python:3.6 AS test_runner
FROM python:3.7 AS test_runner
WORKDIR /tmp
COPY --from=builder /venv /venv
COPY --from=builder /usr/src/app/tests tests
@ -24,7 +24,7 @@ RUN pip install pytest
RUN pytest tests
FROM python:3.6 AS service
FROM python:3.7 AS service
WORKDIR /root/app/site-packages
COPY --from=test_runner /venv /venv
ENV PATH=/venv/bin:$PATH

View File

@ -7,7 +7,7 @@ This Python package is automatically generated by the [OpenAPI Generator](https:
## Requirements.
Python >= 3.6
Python >= 3.7
## Installation & Usage

View File

@ -4,11 +4,11 @@ version = 1.0.0
description = This is a sample server Petstore server. For this sample, you can use the api key `special-key` to test the authorization filters.
long_description = file: README.md
keywords = OpenAPI OpenAPI Petstore
python_requires = >= 3.6.*
python_requires = >= 3.7.*
classifiers =
Operating System :: OS Independent
Programming Language :: Python :: 3
Programming Language :: Python :: 3.6
Programming Language :: Python :: 3.7
[options]
install_requires =

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
@ -23,3 +24,5 @@ class ApiResponse(BaseModel):
code: Optional[int] = None
type: Optional[str] = None
message: Optional[str] = None
ApiResponse.update_forward_refs()

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
@ -26,3 +27,5 @@ class Category(BaseModel):
def name_pattern(cls, value):
assert value is not None and re.match(r"^[a-zA-Z0-9]+[a-zA-Z0-9\.\-_]*[a-zA-Z0-9]+$", value)
return value
Category.update_forward_refs()

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
@ -29,3 +30,5 @@ class Order(BaseModel):
ship_date: Optional[datetime] = None
status: Optional[str] = None
complete: Optional[bool] = None
Order.update_forward_refs()

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
from openapi_server.models.category import Category
@ -31,3 +32,5 @@ class Pet(BaseModel):
photo_urls: List[str]
tags: Optional[List[Tag]] = None
status: Optional[str] = None
Pet.update_forward_refs()

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
@ -21,3 +22,5 @@ class Tag(BaseModel):
id: Optional[int] = None
name: Optional[str] = None
Tag.update_forward_refs()

View File

@ -1,9 +1,10 @@
# coding: utf-8
from __future__ import annotations
from datetime import date, datetime # noqa: F401
import re # noqa: F401
from typing import Dict, List, Optional # noqa: F401
from typing import Any, Dict, List, Optional # noqa: F401
from pydantic import AnyUrl, BaseModel, EmailStr, validator # noqa: F401
@ -33,3 +34,5 @@ class User(BaseModel):
password: Optional[str] = None
phone: Optional[str] = None
user_status: Optional[int] = None
User.update_forward_refs()