Documentation
¶
Overview ¶
Package databasecfg selects and builds a database.Client — Postgres, MySQL, or SQLite — and owns the connection strings each of them wants.
That second job is why this package is larger than the other selection seams. ConnectionDetails is parsed from discrete fields or from a URL and rendered as a libpq keyword string, a MySQL DSN, or a SQLite DSN, so the quoting and the SSL-mode handling live in one place rather than in each caller that assembles a connection string by hand.
Postgres is the default provider, applied by EnsureDefaults before validation runs, so an unset provider is a configured deployment rather than a validation failure — and so the provider list this package validates against never has to carry the empty string.
Index ¶
- Constants
- func NewClientConfig(cfg Config) database.ClientConfig
- func NewDatabase(ctx context.Context, cfg *Config, migrator database.Migrator, opts ...Option) (client database.Client, err error)
- func RegisterClientConfig(i do.Injector)
- func RegisterDatabase(i do.Injector)
- type Config
- func (cfg *Config) EnsureDefaults()
- func (cfg *Config) GetConnMaxLifetime() time.Duration
- func (cfg *Config) GetLogQueries() bool
- func (cfg *Config) GetMaxIdleConns() int
- func (cfg *Config) GetMaxOpenConns() int
- func (cfg *Config) GetMaxPingAttempts() uint64
- func (cfg *Config) GetPingWaitPeriod() time.Duration
- func (cfg *Config) GetReadConnectionString() string
- func (cfg *Config) GetWriteConnectionString() string
- func (cfg *Config) LoadConnectionDetailsFromURL(u string) error
- func (cfg *Config) ValidateWithContext(ctx context.Context) error
- type ConnectionDetails
- func (x *ConnectionDetails) LoadFromURL(u string) error
- func (x *ConnectionDetails) MySQLDSN() string
- func (x *ConnectionDetails) SQLiteDSN() string
- func (x *ConnectionDetails) String() string
- func (x *ConnectionDetails) URI() string
- func (x *ConnectionDetails) ValidateWithContext(ctx context.Context) error
- type Option
Constants ¶
const ( ProviderPostgres = "postgres" ProviderMySQL = "mysql" ProviderSQLite = "sqlite" )
Variables ¶
This section is empty.
Functions ¶
func NewClientConfig ¶
func NewClientConfig(cfg Config) database.ClientConfig
NewClientConfig converts Config to database.ClientConfig.
func NewDatabase ¶
func NewDatabase( ctx context.Context, cfg *Config, migrator database.Migrator, opts ...Option, ) (client database.Client, err error)
NewDatabase creates a database client based on the configured provider and optionally runs migrations if RunMigrations is true and a migrator is provided. If metricsProvider is non-nil and cfg.EnableDatabaseMetrics is true, the client will emit db.sql.* metrics (e.g. db_sql_latency_milliseconds). DB metrics are off by default to avoid high cardinality.
func RegisterClientConfig ¶
RegisterClientConfig registers a database.ClientConfig with the injector.
func RegisterDatabase ¶
RegisterDatabase registers a database.Client with the injector. Prerequisite: *Config must be registered in the injector. A database.Migrator is only required when the config's RunMigrations is true.
Types ¶
type Config ¶
type Config struct {
Provider string `` /* 133-byte string literal not displayed */
ReadConnection ConnectionDetails `envPrefix:"READ_CONNECTION_" json:"readConnection,omitzero" yaml:"readConnection,omitempty"`
WriteConnection ConnectionDetails `envPrefix:"WRITE_CONNECTION_" json:"writeConnection,omitzero" yaml:"writeConnection,omitempty"`
PingWaitPeriod time.Duration `` /* 139-byte string literal not displayed */
MaxPingAttempts uint64 `env:"MAX_PING_ATTEMPTS" json:"maxPingAttempts,omitempty" yaml:"maxPingAttempts,omitempty"`
ConnMaxLifetime time.Duration `` /* 140-byte string literal not displayed */
MaxIdleConns uint16 `` /* 137-byte string literal not displayed */
MaxOpenConns uint16 `` /* 137-byte string literal not displayed */
Debug bool `env:"DEBUG" json:"debug,omitempty" yaml:"debug,omitempty"`
LogQueries bool `env:"LOG_QUERIES" json:"logQueries,omitempty" yaml:"logQueries,omitempty"`
RunMigrations bool `env:"RUN_MIGRATIONS" json:"runMigrations,omitempty" yaml:"runMigrations,omitempty"`
EnableDatabaseMetrics bool `env:"ENABLE_DATABASE_METRICS" json:"enableDatabaseMetrics,omitempty" yaml:"enableDatabaseMetrics,omitempty"`
// contains filtered or unexported fields
}
Config represents our database configuration.
func (*Config) EnsureDefaults ¶
func (cfg *Config) EnsureDefaults()
EnsureDefaults sets sensible defaults for zero-valued fields.
func (*Config) GetConnMaxLifetime ¶
GetConnMaxLifetime implements database.ClientConfig. Returns 30m when unset (zero).
func (*Config) GetLogQueries ¶
GetLogQueries reports whether SQL query text should be recorded on database spans. The database client providers consume this via an optional interface assertion; when false (the default), otelsql is configured to suppress the db.statement attribute so raw SQL is not emitted into traces.
func (*Config) GetMaxIdleConns ¶
GetMaxIdleConns implements database.ClientConfig. Returns 5 when unset (zero).
func (*Config) GetMaxOpenConns ¶
GetMaxOpenConns implements database.ClientConfig. Returns 7 when unset (zero).
func (*Config) GetMaxPingAttempts ¶
GetMaxPingAttempts implements database.ClientConfig. Returns 50 when unset (zero) so IsReady retries rather than making a single attempt.
func (*Config) GetPingWaitPeriod ¶
GetPingWaitPeriod implements database.ClientConfig.
func (*Config) GetReadConnectionString ¶
GetReadConnectionString implements database.ClientConfig.
func (*Config) GetWriteConnectionString ¶
GetWriteConnectionString implements database.ClientConfig.
func (*Config) LoadConnectionDetailsFromURL ¶
LoadConnectionDetailsFromURL wraps an inner function.
func (*Config) ValidateWithContext ¶
ValidateWithContext validates a Config. Connection requirements are provider-aware: SQLite only needs a database file path (on either the read or write connection), while Postgres and MySQL require a fully specified read connection. A write connection, when supplied, is validated regardless of provider.
The provider is checked normalized, matching dispatch, and against the same list NewDatabase reads — an unrecognized one used to reach the connection rules, pass them, and be refused only once a client was being built.
type ConnectionDetails ¶
type ConnectionDetails struct {
Username string `env:"USERNAME" json:"username,omitempty" yaml:"username,omitempty"`
Password string `env:"PASSWORD" json:"password,omitempty" yaml:"password,omitempty"`
Database string `env:"DATABASE" json:"database,omitempty" yaml:"database,omitempty"`
Host string `env:"HOST" json:"hostname,omitempty" yaml:"hostname,omitempty"`
Port uint16 `env:"PORT" json:"port,omitempty" yaml:"port,omitempty"`
DisableSSL bool `env:"DISABLE_SSL" json:"disableSSL,omitempty" yaml:"disableSSL,omitempty"`
// contains filtered or unexported fields
}
func (*ConnectionDetails) LoadFromURL ¶
func (x *ConnectionDetails) LoadFromURL(u string) error
LoadFromURL accepts a Postgres connection string and parses it into the ConnectionDetails struct.
func (*ConnectionDetails) MySQLDSN ¶
func (x *ConnectionDetails) MySQLDSN() string
MySQLDSN returns a MySQL DSN connection string. parseTime=true is required so the driver scans DATETIME/TIMESTAMP columns into time.Time rather than []byte, which the null-value helpers (e.g. TimeFromNullTime) depend on. The driver defaults loc to UTC, so times come back in UTC. The DSN is assembled via the driver's own Config so credentials/host values are escaped rather than concatenated.
func (*ConnectionDetails) SQLiteDSN ¶
func (x *ConnectionDetails) SQLiteDSN() string
SQLiteDSN returns the database file path for SQLite.
func (*ConnectionDetails) String ¶
func (x *ConnectionDetails) String() string
func (*ConnectionDetails) URI ¶
func (x *ConnectionDetails) URI() string
func (*ConnectionDetails) ValidateWithContext ¶
func (x *ConnectionDetails) ValidateWithContext(ctx context.Context) error
ValidateWithContext validates an DatabaseSettings struct.
type Option ¶
type Option func(*options)
Option configures how NewDatabase assembles its client.
The observability dependencies are options rather than parameters because every one of them is genuinely optional: an absent logger logs nowhere, an absent tracer provider traces nowhere, and an absent metrics provider records nothing. Requiring them positionally made a caller that wanted none of the three name all three anyway, usually as noops.
func WithLogger ¶
WithLogger attaches a logger. An absent logger logs nowhere.
func WithMetricsProvider ¶
WithMetricsProvider attaches a metrics provider. An absent provider records nothing.
func WithPillars ¶
func WithPillars(p *observability.Pillars) Option
WithPillars attaches a logger, tracer provider, and metrics provider in one go, for the common case where a caller has already built them together. A nil Pillars attaches nothing.
It is applied in order with the individual options, so a caller can hand over its pillars and then override one of them.
func WithTracerProvider ¶
WithTracerProvider attaches a tracer provider, enabling spans on the instrumented operations. An absent tracer provider traces nowhere.