Skip to content

Instantly share code, notes, and snippets.

@victorusachev
Created August 12, 2020 20:42
Show Gist options
  • Save victorusachev/676e5b0f9e67475e577724c44761e4d8 to your computer and use it in GitHub Desktop.
Save victorusachev/676e5b0f9e67475e577724c44761e4d8 to your computer and use it in GitHub Desktop.
Application configuration and testability
# tests/helpers.py
from contextlib import contextmanager
from typing import TYPE_CHECKING, Any, Iterator
from defmain.settings import get_settings
if TYPE_CHECKING:
from defmain.settings import Settings
@contextmanager
def override_settings(**overrides: Any) -> Iterator["Settings"]:
try:
settings = get_settings()
for name, value in overrides.items():
if not hasattr(settings, name):
raise AttributeError(
f'The Settings class does not define the "{name}" setting'
)
setattr(settings, name, value)
yield settings
finally:
get_settings.cache_clear()
# defmain/settings.py
from functools import lru_cache
from typing import List
from pydantic import BaseSettings
__all__ = ("Settings", "get_settings")
@lru_cache()
def get_settings() -> "Settings":
return Settings()
class Settings(BaseSettings):
"""Application settings.
The application defines a set of configuration parameters.
The application is configured as follows, in descending order of priority:
- environment variables with the `DEFMAIN_` prefix,
- variables with the `DEFMAIN_` prefix in the` .env` file
in the current working directory (if any),
- default values specified in the code.
"""
debug: bool = False
# CORS middleware
allow_origins: List[str] = ["*"]
allow_methods: List[str] = ["*"]
allow_headers: List[str] = ["*"]
class Config:
env_file = ".env"
env_prefix = "DEFMAIN_"
# tests/instrumental/test_helpers.py
from defmain.settings import get_settings
from tests.helpers import override_settings
def test_override_settings():
original_settings = get_settings()
debug = not original_settings.debug
with override_settings(debug=debug) as settings:
assert settings.debug is debug
assert get_settings().debug is debug
settings = get_settings()
assert settings.debug is not debug
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment