Psycopg C-optimized
Psycopg 3 is a modern PostgreSQL database adapter for Python, designed to leverage modern Python (asyncio, static typing) and PostgreSQL features (binary protocol, pipeline mode). `psycopg-c` is an optional component providing C-optimized speedups for the core `psycopg` library, offering performance benefits over the pure Python implementation. It is actively maintained with frequent updates, currently at version 3.3.3.
Warnings
- breaking Migration from Psycopg 2 to Psycopg 3 involves significant breaking changes. Key areas include connection context managers (now close the connection by default), connection string format (`postgresql+psycopg://`), updated `COPY` API, and a completely redesigned asynchronous API.
- gotcha Direct installation of `psycopg-c` using `pip install psycopg-c` is discouraged and may lead to issues. It should be installed as an extra feature of the main `psycopg` package using `pip install "psycopg[c]"` to ensure version compatibility and correct integration.
- gotcha The `psycopg[c]` installation requires local build tools (a C compiler, Python development headers, and PostgreSQL's `libpq` development headers). If these prerequisites are not met, the installation will fail with compilation errors. `psycopg[binary]` is an alternative that includes pre-compiled C extensions.
- gotcha Asynchronous connections (`psycopg.AsyncConnection`) require careful use of `await`. While `async with` is used, the `connect()` method itself is an `async` factory, leading to the pattern `async with await psycopg.AsyncConnection.connect()` which can be a source of confusion.
- gotcha By default, `psycopg` starts a new transaction with each `execute()` call. Changes are not persisted until `conn.commit()` is explicitly called. If `commit()` is forgotten, changes will be discarded when the connection closes. Use context managers (`with conn:`) for explicit transaction management.
- gotcha Psycopg 3 primarily uses server-side parameter binding, which is more secure but has limitations. It does not work with all SQL statements (e.g., `SET`, `NOTIFY`) or when executing multiple SQL statements in a single `execute()` call if parameters are passed.
Install
-
pip install "psycopg[c]" -
pip install psycopg -
pip install "psycopg[binary]"
Imports
- connect
import psycopg conn = psycopg.connect(...)
- AsyncConnection
from psycopg import AsyncConnection async with await AsyncConnection.connect(...) as aconn:
Quickstart
import psycopg
import os
# Ensure environment variables are set for connection details
DB_HOST = os.environ.get('PG_HOST', 'localhost')
DB_PORT = os.environ.get('PG_PORT', '5432')
DB_NAME = os.environ.get('PG_DATABASE', 'testdb')
DB_USER = os.environ.get('PG_USER', 'user')
DB_PASSWORD = os.environ.get('PG_PASSWORD', 'password')
conninfo = f"host={DB_HOST} port={DB_PORT} dbname={DB_NAME} user={DB_USER} password={DB_PASSWORD}"
try:
with psycopg.connect(conninfo) as conn:
with conn.cursor() as cur:
# Create a table
cur.execute("""
CREATE TABLE IF NOT EXISTS my_data (
id SERIAL PRIMARY KEY,
value TEXT
)
""")
# Insert data
cur.execute("INSERT INTO my_data (value) VALUES (%s)", ("Hello Psycopg C!",))
conn.commit()
# Query data
cur.execute("SELECT id, value FROM my_data ORDER BY id DESC LIMIT 1")
record = cur.fetchone()
print(f"Inserted and retrieved: {record}")
except psycopg.Error as e:
print(f"Database error: {e}")
# In a real application, you might want to rollback on error
# if 'conn' is available and not in autocommit mode.
except Exception as e:
print(f"An unexpected error occurred: {e}")