v0.145.1
 1from os import environ
 2
 3from plain.runtime.secret import Secret
 4
 5# DATABASE_URL is the widely-used convention for Postgres connection strings;
 6# honor it as a fallback so most hosting setups work unmodified.
 7POSTGRES_URL: Secret[str]
 8if _env_url := environ.get("DATABASE_URL"):
 9    POSTGRES_URL = _env_url
10
11# Optional second URL for management operations (migrations, convergence,
12# schema changes). When set, management commands connect via this URL
13# instead of POSTGRES_URL. Common uses: bypassing a transaction-mode
14# pgbouncer that can't handle DDL, or connecting as a DDL-capable role.
15# Falls back to POSTGRES_URL when empty.
16POSTGRES_MANAGEMENT_URL: Secret[str] = ""
17
18# Connection pool options forwarded to psycopg_pool.ConnectionPool.
19# Defaults match psycopg_pool's own defaults (max_size mirrors min_size when
20# left alone).
21POSTGRES_POOL_MIN_SIZE: int = 4
22POSTGRES_POOL_MAX_SIZE: int = 20
23POSTGRES_POOL_MAX_LIFETIME: float = 3600.0
24POSTGRES_POOL_TIMEOUT: float = 30.0
25
26# DDL timeouts. Applied per-statement via SET LOCAL before every framework-
27# issued DDL in migrations and convergence. Values are Postgres interval
28# strings ("3s", "500ms", "1min"). These do NOT affect application queries.
29#
30# lock_timeout: how long to wait for a lock before failing with
31#   LockNotAvailable. Prevents the lock-queue cascade where a waiting
32#   ACCESS EXCLUSIVE blocks every new query on the table.
33#
34# statement_timeout: how long a statement can run once it has its lock.
35#   Only applied to statements that hold ACCESS EXCLUSIVE. Non-blocking
36#   operations (CREATE INDEX CONCURRENTLY, VALIDATE CONSTRAINT) run
37#   without a statement_timeout — the lock doesn't cascade, so letting
38#   them run to completion on large tables is safe.
39POSTGRES_MIGRATION_LOCK_TIMEOUT: str = "3s"
40POSTGRES_MIGRATION_STATEMENT_TIMEOUT: str = "3s"
41POSTGRES_CONVERGENCE_LOCK_TIMEOUT: str = "3s"
42POSTGRES_CONVERGENCE_STATEMENT_TIMEOUT: str = "3s"