97 lines
1.8 KiB
Go

package config
import (
"net"
"net/url"
"os"
"strconv"
"github.com/joho/godotenv"
)
type Config struct {
Addr string
GinMode string
DB DBConfig
}
type DBConfig struct {
Host string
Port string
User string
Password string
Name string
SSLMode string
MaxConns int32
AppName string
}
func Load() Config {
_ = godotenv.Load()
cfg := Config{
Addr: getenv("ADDR", ":8082"),
GinMode: getenv("GIN_MODE", "release"),
DB: DBConfig{
Host: must("PGHOST"),
Port: must("POSTGRES_PORT"),
User: must("POSTGRES_USER"),
Password: os.Getenv("POSTGRES_PASSWORD"),
Name: must("POSTGRES_DB"),
SSLMode: getenv("PGSSLMODE", "disable"),
AppName: getenv("DB_APP_NAME", "current-api"),
},
}
if n := getenv("DB_MAX_CONNS", ""); n != "" {
if v, err := strconv.Atoi(n); err == nil && v > 0 {
cfg.DB.MaxConns = int32(v)
}
}
return cfg
}
func (d DBConfig) DSN() string {
// DATABASE_URL wins if present
if raw := os.Getenv("DATABASE_URL"); raw != "" {
return raw
}
u := &url.URL{
Scheme: "postgres",
User: url.UserPassword(d.User, d.Password),
Host: net.JoinHostPort(d.Host, d.Port),
Path: "/" + d.Name,
}
q := url.Values{}
q.Set("sslmode", d.SSLMode)
if d.AppName != "" {
q.Set("application_name", d.AppName)
}
u.RawQuery = q.Encode()
return u.String()
}
func RedactDSN(raw string) string {
u, err := url.Parse(raw)
if err != nil || u.User == nil {
return raw
}
if _, ok := u.User.Password(); ok {
u.User = url.UserPassword(u.User.Username(), "*****")
}
return u.String()
}
func getenv(k, def string) string {
if v := os.Getenv(k); v != "" {
return v
}
return def
}
func must(k string) string {
v := os.Getenv(k)
if v == "" {
panic("missing required env: " + k)
}
return v
}