Support standard libpq environment variables for Auth service (#901)

This commit is contained in:
solidDoWant 2025-04-24 02:38:20 -05:00 committed by GitHub
parent f2294ac97e
commit 5ced62aab3
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 52 additions and 21 deletions

View File

@ -51,7 +51,7 @@ jobs:
wget --retry-connrefused --retry-on-http-error=502 http://localhost:4568/health
hurl --error-format long --variable host=http://localhost:4568 tests/*
env:
POSTGRES_SERVER: localhost
PGHOST: localhost
FIRST_USER_CLAIMS: '{"permissions": ["users.read"]}'
KEIBI_APIKEY_HURL: 1234apikey
KEIBI_APIKEY_HURL_CLAIMS: '{"permissions": ["apikeys.write", "apikeys.read"]}'

View File

@ -20,8 +20,8 @@ IMAGES_PATH=./images
# https://www.postgresql.org/docs/current/libpq-envars.html
PGUSER=kyoo
PGPASSWORD=password
PGDB=kyooDB
PGSERVER=postgres
PGDATABASE=kyooDB
PGHOST=postgres
PGPORT=5432
# PGOPTIONS=-c search_path=kyoo,public
# PGPASSFILE=/my/password # Takes precedence over PGPASSWORD. New line characters are not trimmed.

View File

@ -29,11 +29,24 @@ PUBLIC_URL=http://localhost:8901
# KEIBI_APIKEY_$YOURNAME_CLAIMS='{"permissions": ["users.read"]}'
# Database things
POSTGRES_USER=kyoo
POSTGRES_PASSWORD=password
POSTGRES_DB=kyoo
POSTGRES_SERVER=postgres
POSTGRES_PORT=5432
# It is recommended to use the below PG environment variables when possible.
# POSTGRES_URL=postgres://user:password@hostname:port/dbname?sslmode=verify-full&sslrootcert=/path/to/server.crt&sslcert=/path/to/client.crt&sslkey=/path/to/client.key
# The behavior of the below variables match what is documented here:
# https://www.postgresql.org/docs/current/libpq-envars.html
# The "source of truth" for what variables are supported is documented here:
# https://github.com/jackc/pgx/blob/master/pgconn/config.go#L190-L205
PGUSER=kyoo
PGPASSWORD=password
PGDATABASE=kyoo
PGHOST=postgres
PGPORT=5432
# PGPASSFILE=/my/password
# PGSSLMODE=verify-full
# PGSSLROOTCERT=/my/serving.crt
# PGSSLCERT=/my/client.crt
# PGSSLKEY=/my/client.key
# Default is keibi, you can specify "disabled" to use the default search_path of the user.
# If this is not "disabled", the schema will be created (if it does not exists) and
# the search_path of the user will be ignored (only the schema specified will be used).

View File

@ -7,7 +7,7 @@ import (
"fmt"
"net/http"
"os"
"strconv"
"os/user"
"strings"
"github.com/zoriya/kyoo/keibi/dbc"
@ -73,23 +73,41 @@ func GetenvOr(env string, def string) string {
func OpenDatabase() (*pgxpool.Pool, error) {
ctx := context.Background()
port, err := strconv.ParseUint(GetenvOr("POSTGRES_PORT", "5432"), 10, 16)
connectionString := GetenvOr("POSTGRES_URL", "")
config, err := pgxpool.ParseConfig(connectionString)
if err != nil {
return nil, errors.New("invalid postgres port specified")
return nil, errors.New("failed to create postgres config from environment variables")
}
config, _ := pgxpool.ParseConfig("")
config.ConnConfig.Host = GetenvOr("POSTGRES_SERVER", "postgres")
config.ConnConfig.Port = uint16(port)
config.ConnConfig.Database = GetenvOr("POSTGRES_DB", "kyoo")
config.ConnConfig.User = GetenvOr("POSTGRES_USER", "kyoo")
config.ConnConfig.Password = GetenvOr("POSTGRES_PASSWORD", "password")
config.ConnConfig.TLSConfig = nil
config.ConnConfig.RuntimeParams = map[string]string{
"application_name": "keibi",
// Set default values
if config.ConnConfig.Host == "" {
config.ConnConfig.Host = "postgres"
}
if config.ConnConfig.Database == "" {
config.ConnConfig.Database = "kyoo"
}
// The pgx library will set the username to the name of the current user if not provided via
// environment variable or connection string. Make a best-effort attempt to see if the user
// was explicitly specified, without implementing full connection string parsing. If not, set
// the username to the default value of "kyoo".
if os.Getenv("PGUSER") == "" {
currentUserName, _ := user.Current()
// If the username matches the current user and it's not in the connection string, then it was set
// by the pgx library. This doesn't cover the case where the system username happens to be in some other part
// of the connection string, but this cannot be checked without full connection string parsing.
if currentUserName.Username == config.ConnConfig.User && !strings.Contains(connectionString, currentUserName.Username) {
config.ConnConfig.User = "kyoo"
}
}
if config.ConnConfig.Password == "" {
config.ConnConfig.Password = "password"
}
if _, ok := config.ConnConfig.RuntimeParams["application_name"]; !ok {
config.ConnConfig.RuntimeParams["application_name"] = "keibi"
}
schema := GetenvOr("POSTGRES_SCHEMA", "keibi")
if schema != "disabled" {
if _, ok := config.ConnConfig.RuntimeParams["search_path"]; !ok {
config.ConnConfig.RuntimeParams["search_path"] = schema
}