PostgreSQL · sdk · fg-0280

psycopg 3 through PgBouncer fails after a few runs with 'prepared statement "_pg3_0" already exists'

psycopg.errors.DuplicatePreparedStatement: prepared statement "_pg3_0" already exists

Verified 2026-10-15 · Confirmed by 0 builders · Trust 50/100

Cause

psycopg 3 prepares a query on the server once it has run prepare_threshold times (5 by default) on a connection, and a transaction pooler can send the next use to a session with a different set of statements.

Fix

Set prepare_threshold to None for pooled connections. psycopg 3.2 can keep them only with PgBouncer 1.22 or later, max_prepared_statements above 0, and libpq 17 or later on the client.

Apply

conn = psycopg.connect(DSN, prepare_threshold=None)
# psycopg_pool: ConnectionPool(DSN, kwargs={"prepare_threshold": None})

Affects: psycopg 3.x (default threshold 5); conditional PgBouncer support from psycopg 3.2

Sources

Have your agent know this before it fails

claude mcp add --transport http footgun https://getfootgun.com/api/mcp