package domain import ( "net" "path/filepath" "testing" "time" "github.com/valyala/fasttemplate" ) type ( Config struct { Server ConfigServer `envPrefix:"SERVER_"` Database ConfigDatabase `envPrefix:"DATABASE_"` Name string `env:"NAME" envDefault:"IndieAuth"` RunMode string `env:"RUN_MODE" envDefault:"dev"` IndieAuth ConfigIndieAuth `envPrefix:"INDIEAUTH_"` JWT ConfigJWT `envPrefix:"JWT_"` Code ConfigCode `envPrefix:"CODE_"` TicketAuth ConfigTicketAuth `envPrefix:"TICKETAUTH_"` } ConfigServer struct { CertificateFile string `env:"CERT_FILE"` Domain string `env:"DOMAIN" envDefault:"localhost"` Host string `env:"HOST" envDefault:"0.0.0.0"` KeyFile string `env:"KEY_FILE"` Port string `env:"PORT" envDefault:"3000"` Protocol string `env:"PROTOCOL" envDefault:"http"` RootURL string `env:"ROOT_URL" envDefault:"{{protocol}}://{{domain}}:{{port}}/"` } ConfigDatabase struct { Path string `env:"PATH"` Type string `env:"TYPE" envDefault:"memory"` // memory } // Configuration of a one-time code after giving permission to an // application. The client needs to request the server with this code to // exchange it for a token or user information. ConfigCode struct { Expiry time.Duration `env:"EXPIRY" envDefault:"10m"` // 10m Length uint8 `env:"LENGTH" envDefault:"32"` // 32 } ConfigJWT struct { Algorithm string `env:"ALGORITHM" envDefault:"HS256"` Secret string `env:"SECRET"` Expiry time.Duration `env:"EXPIRY" envDefault:"1h"` NonceLength uint8 `env:"NONCE_LENGTH" envDefault:"22"` } ConfigIndieAuth struct { Password string `env:"PASSWORD"` Username string `env:"USERNAME"` Enabled bool `env:"ENABLED" envDefault:"true"` // true } ConfigTicketAuth struct { Expiry time.Duration `env:"EXPIRY" envDefault:"1m"` // 1m Length uint8 `env:"LENGTH" envDefault:"24"` // 24 } ConfigRelMeAuth struct { Providers []ConfigRelMeAuthProvider `envPrefix:"PROVIDERS_"` Enabled bool `env:"ENABLED" envDefault:"true"` // true } ConfigRelMeAuthProvider struct { ID string `env:"ID"` Secret string `env:"SECRET"` Type string `env:"TYPE"` } ) // TestConfig returns a valid config for tests. // //nolint:gomnd // testing domain can contains non-standart values func TestConfig(tb testing.TB) *Config { tb.Helper() return &Config{ Name: "IndieAuth", RunMode: "dev", Server: ConfigServer{ CertificateFile: filepath.Join("https", "cert.pem"), Domain: "localhost", Host: "0.0.0.0", KeyFile: filepath.Join("https", "key.pem"), Port: "3000", Protocol: "http", RootURL: "{{protocol}}://{{domain}}:{{port}}/", }, Database: ConfigDatabase{ Type: "memory", Path: "", }, Code: ConfigCode{ Expiry: 10 * time.Minute, Length: 32, }, JWT: ConfigJWT{ Expiry: time.Hour, NonceLength: 22, Secret: "hackme", Algorithm: "HS256", }, IndieAuth: ConfigIndieAuth{ Enabled: true, Username: "user", Password: "password", }, TicketAuth: ConfigTicketAuth{ Expiry: time.Minute, Length: 24, }, } } // GetAddress return host:port address. func (cs ConfigServer) GetAddress() string { return net.JoinHostPort(cs.Host, cs.Port) } // GetRootURL returns generated root URL from template RootURL. func (cs ConfigServer) GetRootURL() string { return fasttemplate.ExecuteString(cs.RootURL, `{{`, `}}`, map[string]any{ "domain": cs.Domain, "host": cs.Host, "port": cs.Port, "protocol": cs.Protocol, }) }