Documentation
¶
Overview ¶
Package db owns PostgreSQL connectivity for the openwatch binary.
Day 3: pool helper + goose migration runner + audit_events / idempotency_keys queries. Day 4 onward consumes the pool from the server bootstrap.
Server-version preflight for the migration path.
WHY THIS EXISTS: nothing in the binary checked what PostgreSQL it was talking to. Two versions of that problem showed up during a v0.7.0 install on RHEL 9, which defaults to PostgreSQL 13:
Below the hard floor the schema simply does not build. gen_random_uuid() became a built-in in PostgreSQL 13; three migrations use it as a column DEFAULT. On 12 or older the operator gets "function gen_random_uuid() does not exist" partway through a migration run, which names a function rather than a version and leaves the schema half-applied.
Between the hard floor and the supported floor the schema builds, but the version is old enough to carry behavior the install guide does not account for. PostgreSQL 13 defaults password_encryption to md5 where 14 and later default to scram-sha-256, so a role created by following the guide could not authenticate against the pg_hba.conf rules the same guide supplied.
Those are different failures and deserve different answers, so this reports them separately. Documentation cannot enforce a floor; a released binary can, and says so once, in terms naming the version.
Index ¶
- Constants
- func CheckServerVersion(ctx context.Context, pool *pgxpool.Pool) (advisory string, err error)
- func CountAuditEvents(ctx context.Context, pool *pgxpool.Pool) (int64, error)
- func FormatServerVersion(num int) string
- func NewPool(ctx context.Context, dsn string, maxConns int) (*pgxpool.Pool, error)
- func ServerVersion(ctx context.Context, pool *pgxpool.Pool) (int, error)
- type AuditEvent
- func GetAuditEventByID(ctx context.Context, pool *pgxpool.Pool, id uuid.UUID) (AuditEvent, error)
- func InsertAuditEvent(ctx context.Context, pool *pgxpool.Pool, p InsertAuditEventParams) (AuditEvent, error)
- func ListAuditEvents(ctx context.Context, pool *pgxpool.Pool, p ListAuditEventsParams) ([]AuditEvent, error)
- type InsertAuditEventParams
- type ListAuditEventsParams
- type Queryer
Constants ¶
const ( // MinServerVersionNum is the HARD floor, below which migrations cannot // succeed. 13 is set by gen_random_uuid() as a built-in. Raising this is // a breaking change for existing deployments, so it tracks what the SQL // actually requires, not what the project prefers to support. MinServerVersionNum = 130000 // SupportedServerVersionNum is the lowest version a NEW install should // target. Deliberately higher than the hard floor: PostgreSQL 14 reaches // end of life in November 2026, and a release that ships before then // still runs past it. Below this the binary warns and continues, so an // existing deployment is never bricked by a policy change. SupportedServerVersionNum = 150000 )
Variables ¶
This section is empty.
Functions ¶
func CheckServerVersion ¶ added in v0.8.0
CheckServerVersion enforces the hard floor and reports whether the server is merely below the supported floor.
Returns an error only when the server cannot run the schema at all. The second return is a non-empty advisory when the server is usable but older than a new install should target; callers print it and continue.
func CountAuditEvents ¶
CountAuditEvents returns the total row count. Useful for tests; not recommended for production use against a large table.
func FormatServerVersion ¶ added in v0.8.0
FormatServerVersion renders a version number as major.minor for humans.
func NewPool ¶
NewPool returns a *pgxpool.Pool configured for the OpenWatch backend. The DSN, max-conns, and timeouts come from Config (Day 2).
Caller MUST defer pool.Close().
Validates connectivity with a Ping before returning; an unreachable DB fails fast at startup instead of producing confusing per-query errors.
Types ¶
type AuditEvent ¶
type AuditEvent struct {
ID uuid.UUID
CorrelationID string
ActorType string
ActorID *string
Action string
ResourceType *string
ResourceID *string
Detail json.RawMessage
OccurredAt time.Time
}
AuditEvent mirrors a row of the audit_events table.
func GetAuditEventByID ¶
GetAuditEventByID fetches a single row. Returns pgx.ErrNoRows if missing.
func InsertAuditEvent ¶
func InsertAuditEvent(ctx context.Context, pool *pgxpool.Pool, p InsertAuditEventParams) (AuditEvent, error)
InsertAuditEvent inserts one event and returns the persisted row.
func ListAuditEvents ¶
func ListAuditEvents(ctx context.Context, pool *pgxpool.Pool, p ListAuditEventsParams) ([]AuditEvent, error)
ListAuditEvents returns up to Limit rows ordered newest-first.
type InsertAuditEventParams ¶
type InsertAuditEventParams struct {
ID uuid.UUID
CorrelationID string
ActorType string
ActorID *string
Action string
ResourceType *string
ResourceID *string
Detail json.RawMessage
}
InsertAuditEventParams is the input bundle for InsertAuditEvent.
type ListAuditEventsParams ¶
ListAuditEventsParams is the input bundle for ListAuditEvents. Before is a cursor (rows STRICTLY before this timestamp); nil means "from newest."
type Queryer ¶ added in v0.8.0
type Queryer interface {
Query(ctx context.Context, sql string, args ...any) (pgx.Rows, error)
QueryRow(ctx context.Context, sql string, args ...any) pgx.Row
}
Queryer is the read subset of pgx satisfied by both *pgxpool.Pool and pgx.Tx.
It lives here rather than in each caller because Go matches interface METHODS by exact parameter type. Two packages declaring structurally identical interfaces do not satisfy each other's method signatures, so a service that resolves data for another package's transaction has to name one shared type.
The reason a caller needs this at all: content that will be SIGNED must be read from one snapshot. A helper that quietly used the pool would put part of a signed artifact on a different snapshot from the rest, and nothing in the artifact would record that it happened.
Directories
¶
| Path | Synopsis |
|---|---|
|
Package corpustest seeds host_rule_state rows that are actually IN a host's current corpus.
|
Package corpustest seeds host_rule_state rows that are actually IN a host's current corpus. |
|
Package dbtest gives each test BINARY (i.e.
|
Package dbtest gives each test BINARY (i.e. |
|
Package migrations embeds the SQL migration files and exposes the goose runner that applies them.
|
Package migrations embeds the SQL migration files and exposes the goose runner that applies them. |