opnsense-portal/internal/config/load_test.go
Carsten Abele b47ee11ba4 feat(config): Strict-YAML, Secret-Dateien, Env-Overrides, Dateirechte und Validierung
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01NBHF4R9EAejDJUMdwr6C68
2026-08-14 09:06:43 +02:00

87 lines
2.5 KiB
Go

package config
import (
"strings"
"testing"
"time"
)
const minimalYAML = `
portal:
tls_cert: "/etc/vpnportal/portal.crt"
tls_key: "/etc/vpnportal/portal.key"
opnsense:
url: "https://fw01.firma.local"
api_key: "KEY"
api_secret: "SECRET"
ad:
domain: "firma.local"
servers: ["dc01.firma.local"]
bind_user: "svc@firma.local"
bind_password: "PW"
vpn_group: "VPN-Users"
logging:
audit_log: "/var/log/vpnportal/audit.log"
`
func TestParseAppliesDefaults(t *testing.T) {
cfg, err := Parse(strings.NewReader(minimalYAML))
if err != nil {
t.Fatalf("Parse: %v", err)
}
if cfg.Portal.Listen != "0.0.0.0:8443" {
t.Errorf("Listen = %q, want default 0.0.0.0:8443", cfg.Portal.Listen)
}
if time.Duration(cfg.Portal.SessionTTL) != 10*time.Minute {
t.Errorf("SessionTTL = %v, want 10m", time.Duration(cfg.Portal.SessionTTL))
}
if cfg.AD.Port != 636 {
t.Errorf("AD.Port = %d, want 636", cfg.AD.Port)
}
if cfg.Matching.CNPattern != "{username}" {
t.Errorf("CNPattern = %q, want {username}", cfg.Matching.CNPattern)
}
if cfg.Logging.MaxSizeMB != 50 || cfg.Logging.MaxBackups != 5 || !cfg.Logging.Compress {
t.Errorf("logging defaults wrong: %+v", cfg.Logging)
}
if cfg.Portal.UpdateCheck {
t.Error("UpdateCheck must default to false")
}
}
func TestParseRejectsUnknownField(t *testing.T) {
_, err := Parse(strings.NewReader(minimalYAML + "\nportal_typo:\n listen: \"x\"\n"))
if err == nil {
t.Fatal("unbekanntes Feld muss abgelehnt werden")
}
if !strings.Contains(err.Error(), "portal_typo") {
t.Errorf("Fehler muss das unbekannte Feld nennen, got: %v", err)
}
}
func TestParseRejectsUnknownNestedField(t *testing.T) {
_, err := Parse(strings.NewReader(strings.Replace(minimalYAML,
" vpn_group: \"VPN-Users\"", " vpn_group: \"VPN-Users\"\n vpngroup: \"typo\"", 1)))
if err == nil {
t.Fatal("unbekanntes verschachteltes Feld muss abgelehnt werden")
}
}
func TestParseSessionTTLOverride(t *testing.T) {
cfg, err := Parse(strings.NewReader(strings.Replace(minimalYAML,
"portal:", "portal:\n session_ttl: \"90s\"", 1)))
if err != nil {
t.Fatalf("Parse: %v", err)
}
if time.Duration(cfg.Portal.SessionTTL) != 90*time.Second {
t.Errorf("SessionTTL = %v, want 90s", time.Duration(cfg.Portal.SessionTTL))
}
}
func TestParseRejectsBadDuration(t *testing.T) {
_, err := Parse(strings.NewReader(strings.Replace(minimalYAML,
"portal:", "portal:\n session_ttl: \"zehn Minuten\"", 1)))
if err == nil {
t.Fatal("ungültige Dauer muss abgelehnt werden")
}
}