♻️ Migrate to DATABASE_URL instead of separate variables (#2184)

Co-authored-by: Sebastián Ramírez <tiangolo@gmail.com>
This commit is contained in:
Patrick Arminio
2026-08-11 18:28:34 +01:00
committed by GitHub
parent cf1548a983
commit 32ab6dd022
6 changed files with 18 additions and 31 deletions
+1 -3
View File
@@ -14,7 +14,5 @@ SMTP_TLS=False
SMTP_PORT=1025
# Postgres
POSTGRES_SERVER=localhost
POSTGRES_DB=app
POSTGRES_USER=postgres
POSTGRES_PASSWORD=changethis
DATABASE_URL=postgresql://postgres:${POSTGRES_PASSWORD}@localhost:5432/app
+1 -1
View File
@@ -31,7 +31,7 @@ target_metadata = SQLModel.metadata
def get_url():
return str(settings.SQLALCHEMY_DATABASE_URI)
return str(settings.DATABASE_URL)
def run_migrations_offline():
+12 -17
View File
@@ -6,6 +6,7 @@ from pydantic import (
HttpUrl,
PostgresDsn,
computed_field,
field_validator,
model_validator,
)
from pydantic_settings import BaseSettings, SettingsConfigDict
@@ -27,23 +28,16 @@ class Settings(BaseSettings):
PROJECT_NAME: str
SENTRY_DSN: HttpUrl | None = None
POSTGRES_SERVER: str
POSTGRES_PORT: int = 5432
POSTGRES_USER: str
POSTGRES_PASSWORD: str = ""
POSTGRES_DB: str = ""
DATABASE_URL: PostgresDsn
@computed_field # type: ignore[prop-decorator]
@property
def SQLALCHEMY_DATABASE_URI(self) -> PostgresDsn:
return PostgresDsn.build(
scheme="postgresql+psycopg",
username=self.POSTGRES_USER,
password=self.POSTGRES_PASSWORD,
host=self.POSTGRES_SERVER,
port=self.POSTGRES_PORT,
path=self.POSTGRES_DB,
)
@field_validator("DATABASE_URL", mode="before")
@classmethod
def _use_psycopg_driver(cls, value: str | PostgresDsn) -> str:
database_url = str(value)
for scheme in ("postgres://", "postgresql://"):
if database_url.startswith(scheme):
return database_url.replace(scheme, "postgresql+psycopg://", 1)
return database_url
SMTP_TLS: bool = True
SMTP_SSL: bool = False
@@ -85,7 +79,8 @@ class Settings(BaseSettings):
@model_validator(mode="after")
def _enforce_non_default_secrets(self) -> Self:
self._check_default_secret("SECRET_KEY", self.SECRET_KEY)
self._check_default_secret("POSTGRES_PASSWORD", self.POSTGRES_PASSWORD)
for host in self.DATABASE_URL.hosts():
self._check_default_secret("DATABASE_URL password", host["password"])
self._check_default_secret(
"FIRST_SUPERUSER_PASSWORD", self.FIRST_SUPERUSER_PASSWORD
)
+1 -1
View File
@@ -4,7 +4,7 @@ from app import crud
from app.core.config import settings
from app.models import User, UserCreate
engine = create_engine(str(settings.SQLALCHEMY_DATABASE_URI))
engine = create_engine(str(settings.DATABASE_URL))
# make sure all SQLModel models are imported (app.models) before initializing DB
+3 -7
View File
@@ -20,7 +20,7 @@ services:
db:
image: postgres:18
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER} -d ${POSTGRES_DB}"]
test: ["CMD-SHELL", "pg_isready -U postgres -d app"]
interval: 10s
retries: 5
start_period: 30s
@@ -29,8 +29,7 @@ services:
- app-db-data:/var/lib/postgresql
environment:
- POSTGRES_PASSWORD=${POSTGRES_PASSWORD:?Variable not set}
- POSTGRES_USER=${POSTGRES_USER:?Variable not set}
- POSTGRES_DB=${POSTGRES_DB:?Variable not set}
- POSTGRES_DB=app
adminer:
image: adminer
@@ -62,10 +61,7 @@ services:
SMTP_USER: ${SMTP_USER:-}
SMTP_PASSWORD: ${SMTP_PASSWORD:-}
EMAILS_FROM_EMAIL: ${EMAILS_FROM_EMAIL}
POSTGRES_SERVER: db
POSTGRES_DB: ${POSTGRES_DB:?Variable not set}
POSTGRES_USER: ${POSTGRES_USER:?Variable not set}
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:?Variable not set}
DATABASE_URL: postgresql://postgres:${POSTGRES_PASSWORD:?Variable not set}@db:5432/app
SENTRY_DSN: ${SENTRY_DSN:-}
healthcheck:
-2
View File
@@ -80,8 +80,6 @@ You can set several other environment variables:
* `SMTP_USER`: The SMTP server user to send emails.
* `SMTP_PASSWORD`: The SMTP server password to send emails.
* `EMAILS_FROM_EMAIL`: The email account to send emails from.
* `POSTGRES_USER`: The Postgres user, you can leave the default.
* `POSTGRES_DB`: The database name to use for this application. You can leave the default of `app`.
* `SENTRY_DSN`: The DSN for Sentry, if you are using it.
## GitHub Actions Environment Variables