[feature] Add db-postgres-connection-string option (#3178)

* handle db-url

* lint and add doc

* add more doc

* fix config test

* return error

* change name from db-url to db-postgres-connection-string
This commit is contained in:
John Winston 2024-08-08 13:00:19 +01:00 committed by GitHub
parent b19cfee7ae
commit 94c615d417
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 70 additions and 13 deletions

View file

@ -44,6 +44,12 @@ grant all privileges on database gotosocial to gotosocial;
GoToSocial makes use of ULIDs (Universally Unique Lexicographically Sortable Identifiers) which will not work in non-English collate environments. For this reason it is important to create the database with `C.UTF-8` locale. To do that on systems which were already initialized with non-C locale, `template0` pristine database template must be used.
If you want to use specific options when connecting to Postgres, you can use `db-postgres-connection-string` to define the connection string. If `db-postgres-connection-string` is defined, all other database related configuration fields will be ignored. For example, we can use `db-postgres-connection-string` to connect to `mySchema`, where the user name is `myUser` and password is `myPass` at `localhost` with the database name of `db`:
```yaml
db-postgres-connection-string: 'postgres://myUser:myPass@localhost/db?search_path=mySchema'
```
## Settings
!!! danger "SQLite cache sizes"
@ -177,6 +183,14 @@ db-sqlite-cache-size: "8MiB"
# Default: "30m"
db-sqlite-busy-timeout: "30m"
# String. Full Database connection string
#
# This connection string is only applicable for Postgres. When this field is defined, all other database related configuration field will be ignored. This field allow you to fine tune connection with Postgres
#
# Examples: ["postgres://user:pass@localhost/db?search_path=gotosocial", "postgres://user:pass@localhost:9999/db"]
# Default: ""
db-postgres-connection-string: ""
cache:
# cache.memory-target sets a target limit that
# the application will try to keep it's caches

View file

@ -248,6 +248,14 @@ db-sqlite-cache-size: "8MiB"
# Default: "30m"
db-sqlite-busy-timeout: "30m"
# String. Full Database connection string
#
# This connection string is only applicable for Postgres. When this field is defined, all other database related configuration field will be ignored. This field allow you to fine tune connection with Postgres
#
# Examples: ["postgres://user:pass@localhost/db?search_path=gotosocial", "postgres://user:pass@localhost:9999/db"]
# Default: ""
db-postgres-connection-string: ""
cache:
# cache.memory-target sets a target limit that
# the application will try to keep it's caches

View file

@ -60,19 +60,20 @@ type Configuration struct {
TrustedProxies []string `name:"trusted-proxies" usage:"Proxies to trust when parsing x-forwarded headers into real IPs."`
SoftwareVersion string `name:"software-version" usage:""`
DbType string `name:"db-type" usage:"Database type: eg., postgres"`
DbAddress string `name:"db-address" usage:"Database ipv4 address, hostname, or filename"`
DbPort int `name:"db-port" usage:"Database port"`
DbUser string `name:"db-user" usage:"Database username"`
DbPassword string `name:"db-password" usage:"Database password"`
DbDatabase string `name:"db-database" usage:"Database name"`
DbTLSMode string `name:"db-tls-mode" usage:"Database tls mode"`
DbTLSCACert string `name:"db-tls-ca-cert" usage:"Path to CA cert for db tls connection"`
DbMaxOpenConnsMultiplier int `name:"db-max-open-conns-multiplier" usage:"Multiplier to use per cpu for max open database connections. 0 or less is normalized to 1."`
DbSqliteJournalMode string `name:"db-sqlite-journal-mode" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_journal_mode"`
DbSqliteSynchronous string `name:"db-sqlite-synchronous" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_synchronous"`
DbSqliteCacheSize bytesize.Size `name:"db-sqlite-cache-size" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_cache_size"`
DbSqliteBusyTimeout time.Duration `name:"db-sqlite-busy-timeout" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_busy_timeout"`
DbType string `name:"db-type" usage:"Database type: eg., postgres"`
DbAddress string `name:"db-address" usage:"Database ipv4 address, hostname, or filename"`
DbPort int `name:"db-port" usage:"Database port"`
DbUser string `name:"db-user" usage:"Database username"`
DbPassword string `name:"db-password" usage:"Database password"`
DbDatabase string `name:"db-database" usage:"Database name"`
DbTLSMode string `name:"db-tls-mode" usage:"Database tls mode"`
DbTLSCACert string `name:"db-tls-ca-cert" usage:"Path to CA cert for db tls connection"`
DbMaxOpenConnsMultiplier int `name:"db-max-open-conns-multiplier" usage:"Multiplier to use per cpu for max open database connections. 0 or less is normalized to 1."`
DbSqliteJournalMode string `name:"db-sqlite-journal-mode" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_journal_mode"`
DbSqliteSynchronous string `name:"db-sqlite-synchronous" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_synchronous"`
DbSqliteCacheSize bytesize.Size `name:"db-sqlite-cache-size" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_cache_size"`
DbSqliteBusyTimeout time.Duration `name:"db-sqlite-busy-timeout" usage:"Sqlite only: see https://www.sqlite.org/pragma.html#pragma_busy_timeout"`
DbPostgresConnectionString string `name:"db-postgres-connection-string" usage:"Full Database URL for connection to postgres"`
WebTemplateBaseDir string `name:"web-template-base-dir" usage:"Basedir for html templating files for rendering pages and composing emails."`
WebAssetBaseDir string `name:"web-asset-base-dir" usage:"Directory to serve static assets from, accessible at example.org/assets/"`

View file

@ -700,6 +700,31 @@ func GetDbSqliteBusyTimeout() time.Duration { return global.GetDbSqliteBusyTimeo
// SetDbSqliteBusyTimeout safely sets the value for global configuration 'DbSqliteBusyTimeout' field
func SetDbSqliteBusyTimeout(v time.Duration) { global.SetDbSqliteBusyTimeout(v) }
// GetDbPostgresConnectionString safely fetches the Configuration value for state's 'DbPostgresConnectionString' field
func (st *ConfigState) GetDbPostgresConnectionString() (v string) {
st.mutex.RLock()
v = st.config.DbPostgresConnectionString
st.mutex.RUnlock()
return
}
// SetDbPostgresConnectionString safely sets the Configuration value for state's 'DbPostgresConnectionString' field
func (st *ConfigState) SetDbPostgresConnectionString(v string) {
st.mutex.Lock()
defer st.mutex.Unlock()
st.config.DbPostgresConnectionString = v
st.reloadToViper()
}
// DbPostgresConnectionStringFlag returns the flag name for the 'DbPostgresConnectionString' field
func DbPostgresConnectionStringFlag() string { return "db-postgres-connection-string" }
// GetDbPostgresConnectionString safely fetches the value for global configuration 'DbPostgresConnectionString' field
func GetDbPostgresConnectionString() string { return global.GetDbPostgresConnectionString() }
// SetDbPostgresConnectionString safely sets the value for global configuration 'DbPostgresConnectionString' field
func SetDbPostgresConnectionString(v string) { global.SetDbPostgresConnectionString(v) }
// GetWebTemplateBaseDir safely fetches the Configuration value for state's 'WebTemplateBaseDir' field
func (st *ConfigState) GetWebTemplateBaseDir() (v string) {
st.mutex.RLock()

View file

@ -396,6 +396,13 @@ func maxOpenConns() int {
// deriveBunDBPGOptions takes an application config and returns either a ready-to-use set of options
// with sensible defaults, or an error if it's not satisfied by the provided config.
func deriveBunDBPGOptions() (*pgx.ConnConfig, error) {
url := config.GetDbPostgresConnectionString()
// if database URL is defined, ignore other DB related configuration fields
if url != "" {
cfg, err := pgx.ParseConfig(url)
return cfg, err
}
// these are all optional, the db adapter figures out defaults
address := config.GetDbAddress()

View file

@ -81,6 +81,7 @@ EXPECT=$(cat << "EOF"
"db-max-open-conns-multiplier": 3,
"db-password": "hunter2",
"db-port": 6969,
"db-postgres-connection-string": "",
"db-sqlite-busy-timeout": 1000000000,
"db-sqlite-cache-size": 0,
"db-sqlite-journal-mode": "DELETE",
@ -212,6 +213,7 @@ GTS_BIND_ADDRESS='127.0.0.1' \
GTS_PORT=6969 \
GTS_TRUSTED_PROXIES='127.0.0.1/32,docker.host.local' \
GTS_DB_TYPE='sqlite' \
GTS_DB_POSTGRES_CONNECTION_STRING='' \
GTS_DB_ADDRESS=':memory:' \
GTS_DB_PORT=6969 \
GTS_DB_USER='sex-haver' \