first commit

This commit is contained in:
2026-05-13 03:05:24 +03:30
commit 4c7343665a
27 changed files with 2581 additions and 0 deletions

View File

@@ -0,0 +1,130 @@
package config
import (
"log/slog"
"net/netip"
"testing"
"time"
)
func TestLoadUsesProductionDefaults(t *testing.T) {
clearConfigEnv(t)
cfg, err := Load()
if err != nil {
t.Fatalf("load config: %v", err)
}
if cfg.Addr != ":8080" {
t.Fatalf("got addr %q, want %q", cfg.Addr, ":8080")
}
if cfg.TrustProxyHeaders {
t.Fatal("proxy headers should not be trusted by default")
}
wantProxy := netip.MustParsePrefix("127.0.0.1/32")
if len(cfg.TrustedProxyCIDRs) == 0 || cfg.TrustedProxyCIDRs[0] != wantProxy {
t.Fatalf("got trusted proxies %v, want first %v", cfg.TrustedProxyCIDRs, wantProxy)
}
if cfg.ReadHeaderTimeout != 5*time.Second {
t.Fatalf("got read header timeout %s", cfg.ReadHeaderTimeout)
}
if cfg.LogLevel != slog.LevelInfo {
t.Fatalf("got log level %s, want info", cfg.LogLevel)
}
}
func TestLoadParsesEnvironment(t *testing.T) {
clearConfigEnv(t)
t.Setenv("ADDR", "127.0.0.1:9090")
t.Setenv("TRUST_PROXY_HEADERS", "true")
t.Setenv("TRUSTED_PROXY_CIDRS", "10.0.0.0/8,192.0.2.10")
t.Setenv("READ_HEADER_TIMEOUT", "3s")
t.Setenv("READ_TIMEOUT", "4s")
t.Setenv("WRITE_TIMEOUT", "5s")
t.Setenv("IDLE_TIMEOUT", "30s")
t.Setenv("SHUTDOWN_TIMEOUT", "7s")
t.Setenv("MAX_HEADER_BYTES", "8192")
t.Setenv("LOG_LEVEL", "debug")
t.Setenv("LOG_FORMAT", "json")
cfg, err := Load()
if err != nil {
t.Fatalf("load config: %v", err)
}
if cfg.Addr != "127.0.0.1:9090" {
t.Fatalf("got addr %q", cfg.Addr)
}
if !cfg.TrustProxyHeaders {
t.Fatal("expected proxy headers to be trusted")
}
if got, want := cfg.TrustedProxyCIDRs[1], netip.MustParsePrefix("192.0.2.10/32"); got != want {
t.Fatalf("got proxy %v, want %v", got, want)
}
if cfg.ReadTimeout != 4*time.Second || cfg.WriteTimeout != 5*time.Second {
t.Fatalf("got read/write timeouts %s/%s", cfg.ReadTimeout, cfg.WriteTimeout)
}
if cfg.MaxHeaderBytes != 8192 {
t.Fatalf("got max header bytes %d", cfg.MaxHeaderBytes)
}
if cfg.LogLevel != slog.LevelDebug || cfg.LogFormat != "json" {
t.Fatalf("got logging %s/%s", cfg.LogLevel, cfg.LogFormat)
}
}
func TestLoadRejectsInvalidEnvironment(t *testing.T) {
tests := map[string]string{
"TRUST_PROXY_HEADERS": "yes-please",
"TRUSTED_PROXY_CIDRS": "not-a-cidr",
"TRUSTED_PROXY_CIDRS_EMPTY": ",",
"READ_TIMEOUT": "forever",
"MAX_HEADER_BYTES": "0",
"LOG_LEVEL": "verbose",
"LOG_FORMAT": "xml",
}
for name, value := range tests {
t.Run(name, func(t *testing.T) {
clearConfigEnv(t)
envName := name
if name == "TRUSTED_PROXY_CIDRS_EMPTY" {
envName = "TRUSTED_PROXY_CIDRS"
}
t.Setenv(envName, value)
if _, err := Load(); err == nil {
t.Fatal("expected error")
}
})
}
}
func clearConfigEnv(t *testing.T) {
t.Helper()
for _, name := range []string{
"ADDR",
"TRUST_PROXY_HEADERS",
"TRUSTED_PROXY_CIDRS",
"READ_HEADER_TIMEOUT",
"READ_TIMEOUT",
"WRITE_TIMEOUT",
"IDLE_TIMEOUT",
"SHUTDOWN_TIMEOUT",
"MAX_HEADER_BYTES",
"LOG_LEVEL",
"LOG_FORMAT",
} {
t.Setenv(name, "")
}
}