Integrations: PostgreSQL & Redis
Integrations: PostgreSQL & Redis
Most Go backends in 2026 rely on this “boring” but powerful trio: Go + Postgres + Redis.
PostgreSQL: pgx
Don’t use lib/pq. It is in maintenance mode. Use jackc/pgx. It is faster, safer, and supports more features (COPY, Listen/Notify).
Connection Pooling
Always use pgxpool, not a single connection.
import "github.com/jackc/pgx/v5/pgxpool"
func NewDB(ctx context.Context, connString string) (*pgxpool.Pool, error) {
config, err := pgxpool.ParseConfig(connString)
// Tuning
config.MaxConns = 25
config.MinConns = 5
config.MaxConnLifetime = 1 * time.Hour
return pgxpool.NewWithConfig(ctx, config)
}Type-Safe SQL: sqlc
Don’t write ORM code (GORM) unless you love runtime crashes and slow queries. Use sqlc. You write SQL, it generates type-safe Go structs and interfaces. (See Chapter 59 “Code Generation” for details).
Redis: go-redis
Use github.com/redis/go-redis/v9.
Patterns
Caching (Look-aside):
go val, err := rdb.Get(ctx, key).Result() if err == redis.Nil { // Miss: Fetch DB, Set Redis val = fetchFromDB() rdb.Set(ctx, key, val, 10*time.Minute) } else if err != nil { return err // Real error } // Hit: use valRate Limiting: Redis is atomic.
INCRandEXPIREare perfect for API limits.Queues: Redis Streams or simple Lists (
LPUSH/BRPOP) make for excellent lightweight worker queues before you upgrade to Kafka or NATS.
Context Awareness
Both pgx and go-redis require context.Context in every method call. Always pass the context. This allows your database queries to automatically timeout if the user cancels the HTTP request, preventing zombie queries from eating your database CPU.
// Good
row := db.QueryRow(ctx, "SELECT ...")
// Bad (cancelling request won't stop query)
row := db.QueryRow(context.Background(), "SELECT ...")