Files
dbx/.cursorrules
Aleksey Shakhmatov 7d25e1b73e
All checks were successful
CI / test (push) Successful in 51s
Add CI workflow, README, CLAUDE.md, AGENTS.md, and .cursorrules
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-03-23 00:01:27 +03:00

56 lines
2.7 KiB
Plaintext

You are working on `git.codelab.vc/pkg/dbx`, a Go PostgreSQL cluster library built on pgx/v5.
## Architecture
- Cluster manages master + replicas with method-based routing (no SQL parsing)
- Write ops (Exec, Query, QueryRow, Begin, BeginTx, CopyFrom, SendBatch) → master
- Read ops (ReadQuery, ReadQueryRow) → replicas with master fallback
- Retry with exponential backoff + jitter, iterates nodes then backs off
- Round-robin balancer skips unhealthy nodes
- Background health checker pings all nodes on interval
- RunTx — panic-safe transaction wrapper (recover → rollback → re-panic)
- InjectQuerier/ExtractQuerier — context-based Querier for service layers
## Package structure
- `dbx` (root) — Cluster, Node, Balancer, retry, health, errors, tx, config, options
- `dbx.go` — interfaces: Querier, DB, Logger, MetricsHook
- `cluster.go` — Cluster routing and query execution
- `node.go` — Node wrapping pgxpool.Pool with health state
- `balancer.go` — Balancer interface + RoundRobinBalancer
- `retry.go` — retrier with backoff and node fallback
- `health.go` — background health checker goroutine
- `tx.go` — RunTx, RunTxOptions, InjectQuerier, ExtractQuerier
- `errors.go` — IsRetryable, IsConnectionError, IsConstraintViolation, PgErrorCode
- `config.go` — Config, NodeConfig, PoolConfig, RetryConfig, HealthCheckConfig
- `options.go` — functional options (WithLogger, WithMetrics, WithRetry, WithHealthCheck)
- `dbxtest/` — test helpers: NewTestCluster, TestLogger
## Code conventions
- Struct-based Config with defaults() method for zero-value defaults
- Functional options (Option func(*Config)) used via ApplyOptions
- stdlib only testing — no testify, no gomock
- Thread safety with atomic.Bool (Node.healthy, Cluster.closed)
- dbxtest.NewTestCluster skips on unreachable DB, auto-closes via t.Cleanup
- Sentinel errors: ErrNoHealthyNode, ErrClusterClosed, ErrRetryExhausted
- retryError multi-unwrap for errors.Is compatibility
## When writing new code
- New node type → add to Cluster struct, Config, connect in NewCluster, add to `all` for health checking
- New balancer → implement Balancer interface, check IsHealthy(), return nil if no suitable node
- New retry logic → provide RetryConfig.RetryableErrors or extend IsRetryable()
- New metrics hook → add field to MetricsHook, nil-check before calling
- Close() is required — leaking a Cluster leaks goroutines and connections
- No SQL parsing — routing is method-based, Exec with SELECT still goes to master
## Commands
```bash
go build ./... # compile
go test ./... # test
go test -race ./... # test with race detector
go vet ./... # static analysis
```