fleetanalytics_mcp/pgbouncer/pgbouncer.ini
kiania b58e429c1c infra(pgbouncer): add transaction-pooling front for timescale_db
The DB is at max_connections=100 with ~9 services each holding persistent pools
(several as the postgres superuser, idle for hours), so peaks hit "too many
connections". PgBouncer multiplexes many client connections onto a small fixed
set of backends, bounding DB connections regardless of how many app pools exist.

Adds (stack-wide infra, parked in this repo for now — see README scope note):
- pgbouncer.ini: transaction pooling, auth_query pass-through, bounded pool sizes
- auth_setup.sql: pgbouncer_auth role + SECURITY DEFINER pgbouncer.user_lookup()
  so per-app passwords aren't hand-maintained
- docker-compose.yml: the service (join the existing DB network)
- userlist.txt.example + .gitignore: keep the auth verifier out of git
- README.md: deploy steps, incremental cutover (superuser apps first), and the
  transaction-pooling caveats — including the MCP-specific note (rely on role-level
  GUCs; simplest to leave the minor MCP direct and pool the heavy superuser apps)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-19 23:44:30 +03:00

64 lines
3.5 KiB
INI
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

; pgbouncer.ini — transaction-pooling front for timescale_db (tracksolid_db).
; ─────────────────────────────────────────────────────────────────────────────
; Purpose: the DB runs at max_connections=100 and ~9 stack services each hold a
; persistent pool (several as the postgres superuser, idle for hours), so peaks hit
; "too many connections". PgBouncer multiplexes MANY client connections onto a SMALL
; set of real backend connections, so the DB connection count stays bounded no matter
; how many app pools exist.
;
; Auth uses auth_query (NOT a hand-maintained userlist of every app): PgBouncer logs
; in as `pgbouncer_auth` and looks each user's verifier up via pgbouncer.user_lookup()
; — see auth_setup.sql. Only the pgbouncer_auth verifier lives in userlist.txt.
[databases]
; Apps point their DSN host at pgbouncer:6432 with the SAME dbname/user/password.
; `host` here is the real DB (the timescale_db container hostname on the DB network).
tracksolid_db = host=timescale_db port=5432 dbname=tracksolid_db
[pgbouncer]
listen_addr = 0.0.0.0
listen_port = 6432
; ── Auth (pass-through via auth_query) ──────────────────────────────────────
auth_type = scram-sha-256
auth_file = /etc/pgbouncer/userlist.txt
auth_user = pgbouncer_auth
auth_query = SELECT uname, phash FROM pgbouncer.user_lookup($1)
; ── Pooling ─────────────────────────────────────────────────────────────────
; transaction mode = a server connection is returned to the pool at COMMIT/ROLLBACK,
; so a handful of backends serve hundreds of clients. See README for the feature
; caveats (no session-level prepared statements / SET that persists across txns).
pool_mode = transaction
; Total backend connections PgBouncer will ever open to the DB =
; (number of [databases] entries) × default_pool_size + reserve_pool_size.
; Keep the SUM across all poolers well under the DB's max_connections (100).
; With one database and 20 + 5 reserve = 25 backends max — leaving headroom for
; superuser/admin/background-worker connections that bypass PgBouncer.
default_pool_size = 20
min_pool_size = 0
reserve_pool_size = 5
reserve_pool_timeout = 3
; Clients can be plentiful (cheap) — only backends are scarce.
max_client_conn = 2000
; Recycle idle/old server connections so none linger for hours.
server_idle_timeout = 300
server_lifetime = 3600
; ── Robustness ──────────────────────────────────────────────────────────────
; Apps set per-connection GUCs via the `options` startup param (e.g. the analytics
; MCP sends `-c default_transaction_read_only=on -c statement_timeout=...`). In
; transaction pooling those can't be honored per-shared-backend, so ignore them and
; rely on ROLE-level settings (ALTER ROLE ... SET ...) instead. See README.
ignore_startup_parameters = extra_float_digits,options,search_path
; Admin/stats console (psql -p 6432 pgbouncer) — restricted to the auth role.
admin_users = pgbouncer_auth
stats_users = pgbouncer_auth
; Quiet by default; flip to 1 temporarily when debugging.
log_connections = 0
log_disconnections = 0