Move the SQLite default constants (max connections, busy timeout) to sqldb/config.go as the single source of truth and export them. Remove the duplicate definitions from lncfg/db.go and reference the sqldb constants instead.
108 lines
4.3 KiB
Go
108 lines
4.3 KiB
Go
package sqldb
|
|
|
|
import (
|
|
"fmt"
|
|
"net/url"
|
|
"time"
|
|
)
|
|
|
|
const (
|
|
// defaultMaxConns is the number of permitted active and idle
|
|
// connections. We want to limit this so it isn't unlimited. We use the
|
|
// same value for the number of idle connections as, this can speed up
|
|
// queries given a new connection doesn't need to be established each
|
|
// time.
|
|
defaultMaxConns = 25
|
|
|
|
// connIdleLifetime is the amount of time a connection can be idle.
|
|
connIdleLifetime = 5 * time.Minute
|
|
)
|
|
|
|
// SqliteConfig holds all the config arguments needed to interact with our
|
|
// sqlite DB.
|
|
//
|
|
//nolint:ll
|
|
type SqliteConfig struct {
|
|
Timeout time.Duration `long:"timeout" description:"The time after which a database query should be timed out."`
|
|
BusyTimeout time.Duration `long:"busytimeout" description:"The maximum amount of time to wait for a database connection to become available for a query."`
|
|
MaxConnections int `long:"maxconnections" description:"The maximum number of open connections to the database. Set to zero for unlimited."`
|
|
PragmaOptions []string `long:"pragmaoptions" description:"A list of pragma options to set on a database connection. For example, 'auto_vacuum=incremental'. Note that the flag must be specified multiple times if multiple options are to be set."`
|
|
SkipMigrations bool `long:"skipmigrations" description:"Skip applying migrations on startup."`
|
|
QueryConfig `group:"query" namespace:"query"`
|
|
}
|
|
|
|
const (
|
|
// DefaultSqliteMaxConns is the default number of maximum open
|
|
// connections for SQLite. SQLite only supports a single writer, so a
|
|
// low default reduces contention on the busy_timeout and limits
|
|
// resource usage, especially on mobile.
|
|
DefaultSqliteMaxConns = 2
|
|
|
|
// DefaultSqliteBusyTimeout is the default busy_timeout value used
|
|
// when no BusyTimeout is configured.
|
|
DefaultSqliteBusyTimeout = 5 * time.Second
|
|
)
|
|
|
|
// busyTimeoutMs returns the busy_timeout value in milliseconds. If
|
|
// BusyTimeout is not set, it returns the default value.
|
|
func (s *SqliteConfig) busyTimeoutMs() int64 {
|
|
if s.BusyTimeout > 0 {
|
|
return s.BusyTimeout.Milliseconds()
|
|
}
|
|
|
|
return DefaultSqliteBusyTimeout.Milliseconds()
|
|
}
|
|
|
|
// MaxConns returns the effective maximum number of open connections. If
|
|
// MaxConnections is not set, it returns a default of 2. This low default is
|
|
// chosen because SQLite only supports a single writer, which helps reduce
|
|
// contention and resource usage.
|
|
func (s *SqliteConfig) MaxConns() int {
|
|
if s.MaxConnections > 0 {
|
|
return s.MaxConnections
|
|
}
|
|
|
|
return DefaultSqliteMaxConns
|
|
}
|
|
|
|
// Validate checks that the SqliteConfig values are valid.
|
|
func (p *SqliteConfig) Validate() error {
|
|
if err := p.QueryConfig.Validate(true); err != nil {
|
|
return fmt.Errorf("invalid query config: %w", err)
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
// PostgresConfig holds the postgres database configuration.
|
|
//
|
|
//nolint:ll
|
|
type PostgresConfig struct {
|
|
Dsn string `long:"dsn" description:"Database connection string."`
|
|
Timeout time.Duration `long:"timeout" description:"Database connection timeout. Set to zero to disable."`
|
|
MaxConnections int `long:"maxconnections" description:"The maximum number of open connections to the database. Set to zero for unlimited."`
|
|
SkipMigrations bool `long:"skipmigrations" description:"Skip applying migrations on startup."`
|
|
ChannelDBWithGlobalLock bool `long:"channeldb-with-global-lock" description:"Use a global lock for channeldb access. This ensures only a single writer at a time but reduces concurrency. This is a temporary workaround until the revocation log is migrated to a native sql schema."`
|
|
WalletDBWithGlobalLock bool `long:"walletdb-with-global-lock" description:"Use a global lock for wallet database access. This ensures only a single writer at a time but reduces concurrency. This is a temporary workaround until the wallet subsystem is upgraded to a native sql schema."`
|
|
QueryConfig `group:"query" namespace:"query"`
|
|
}
|
|
|
|
// Validate checks that the PostgresConfig values are valid.
|
|
func (p *PostgresConfig) Validate() error {
|
|
if p.Dsn == "" {
|
|
return fmt.Errorf("DSN is required")
|
|
}
|
|
|
|
// Parse the DSN as a URL.
|
|
_, err := url.Parse(p.Dsn)
|
|
if err != nil {
|
|
return fmt.Errorf("invalid DSN: %w", err)
|
|
}
|
|
|
|
if err := p.QueryConfig.Validate(false); err != nil {
|
|
return fmt.Errorf("invalid query config: %w", err)
|
|
}
|
|
|
|
return nil
|
|
}
|