Skip to content

Commit 93598e9

Browse files
authored
Merge pull request #31 from modern-python/fix-swagger
fix fastapi swagger
2 parents f4eafa9 + 6fa366f commit 93598e9

File tree

4 files changed

+24
-4
lines changed

4 files changed

+24
-4
lines changed

lite_bootstrap/bootstrappers/fastapi_bootstrapper.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import contextlib
22
import dataclasses
33
import typing
4+
import warnings
45

56
from lite_bootstrap import import_checker
67
from lite_bootstrap.bootstrappers.base import BaseBootstrapper
@@ -35,12 +36,16 @@
3536
class FastAPIConfig(
3637
CorsConfig, HealthChecksConfig, LoggingConfig, OpentelemetryConfig, PrometheusConfig, SentryConfig, SwaggerConfig
3738
):
38-
application: "fastapi.FastAPI" = dataclasses.field(default_factory=lambda: fastapi.FastAPI())
39+
application: "fastapi.FastAPI" = dataclasses.field(default=None) # type: ignore[assignment]
3940
opentelemetry_excluded_urls: list[str] = dataclasses.field(default_factory=list)
4041
prometheus_instrumentator_params: dict[str, typing.Any] = dataclasses.field(default_factory=dict)
4142
prometheus_instrument_params: dict[str, typing.Any] = dataclasses.field(default_factory=dict)
4243
prometheus_expose_params: dict[str, typing.Any] = dataclasses.field(default_factory=dict)
4344

45+
def __post_init__(self) -> None:
46+
if not self.application:
47+
object.__setattr__(self, "application", fastapi.FastAPI(docs_url=self.swagger_path))
48+
4449

4550
@dataclasses.dataclass(kw_only=True, slots=True, frozen=True)
4651
class FastApiCorsInstrument(CorsInstrument):
@@ -139,6 +144,12 @@ class FastApiSwaggerInstrument(SwaggerInstrument):
139144
bootstrap_config: FastAPIConfig
140145

141146
def bootstrap(self) -> None:
147+
if self.bootstrap_config.swagger_path != self.bootstrap_config.application.docs_url:
148+
warnings.warn(
149+
f"swagger_path is differ from docs_url, "
150+
f"{self.bootstrap_config.application.docs_url} will be used for docs path",
151+
stacklevel=2,
152+
)
142153
if self.bootstrap_config.swagger_offline_docs:
143154
enable_offline_docs(
144155
self.bootstrap_config.application, static_path=self.bootstrap_config.swagger_static_path

lite_bootstrap/bootstrappers/litestar_bootstrapper.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ class LitestarConfig(
4949
application_config: "AppConfig" = dataclasses.field(default_factory=lambda: AppConfig())
5050
opentelemetry_excluded_urls: list[str] = dataclasses.field(default_factory=list)
5151
prometheus_additional_params: dict[str, typing.Any] = dataclasses.field(default_factory=dict)
52-
swagger_path: str = "/docs"
52+
swagger_extra_params: dict[str, typing.Any] = dataclasses.field(default_factory=dict)
5353

5454

5555
@dataclasses.dataclass(kw_only=True, slots=True, frozen=True)

lite_bootstrap/instruments/swagger_instrument.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,13 @@
11
import dataclasses
2-
import typing
32

43
from lite_bootstrap.instruments.base import BaseConfig, BaseInstrument
54

65

76
@dataclasses.dataclass(kw_only=True, frozen=True)
87
class SwaggerConfig(BaseConfig):
98
swagger_static_path: str = "/static"
9+
swagger_path: str = "/docs"
1010
swagger_offline_docs: bool = False
11-
swagger_extra_params: dict[str, typing.Any] = dataclasses.field(default_factory=dict)
1211

1312

1413
@dataclasses.dataclass(kw_only=True, slots=True, frozen=True)

tests/test_fastapi_bootstrap.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
import dataclasses
2+
3+
import fastapi
14
import pytest
25
import structlog
36
from opentelemetry.sdk.trace.export import ConsoleSpanExporter
@@ -61,6 +64,13 @@ def test_fastapi_bootstrapper_not_ready() -> None:
6164
FastAPIBootstrapper(bootstrap_config=FastAPIConfig())
6265

6366

67+
def test_fastapi_bootstrapper_docs_url_differ(fastapi_config: FastAPIConfig) -> None:
68+
new_config = dataclasses.replace(fastapi_config, application=fastapi.FastAPI(docs_url="/custom-docs/"))
69+
bootstrapper = FastAPIBootstrapper(bootstrap_config=new_config)
70+
with pytest.warns(UserWarning, match="swagger_path is differ from docs_url"):
71+
bootstrapper.bootstrap()
72+
73+
6474
@pytest.mark.parametrize(
6575
"package_name",
6676
[

0 commit comments

Comments
 (0)