conf/files_test.go
juancwu c4ebd80669 Add reflective struct-tag config loader
Implements conf.Load to populate tagged structs from a chain of Sources
(env, .env, YAML/JSON/TOML, custom). Supports default values, slice
separators, nested structs, pointer fields, and a Validator hook.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 20:35:51 +00:00

82 lines
1.6 KiB
Go

package conf
import (
"strings"
"testing"
)
func TestYAMLFlatten(t *testing.T) {
src, err := YAMLReader(strings.NewReader(`
bind_addr: ":9000"
session:
idle_ttl: 1h
cookie:
secure: true
list: [a, b, c]
`))
if err != nil {
t.Fatal(err)
}
checks := map[string]string{
"BIND_ADDR": ":9000",
"SESSION_IDLE_TTL": "1h0m0s", // yaml.v3 decodes as time.Duration string? actually it stays string
"SESSION_COOKIE_SECURE": "true",
"LIST": "a,b,c",
}
for k, want := range checks {
got, ok := src.Lookup(k)
if !ok {
t.Errorf("%s missing", k)
continue
}
if k == "SESSION_IDLE_TTL" {
// yaml decodes "1h" as plain string
if got != "1h" && got != want {
t.Errorf("%s = %q", k, got)
}
continue
}
if got != want {
t.Errorf("%s = %q want %q", k, got, want)
}
}
}
func TestJSONFlatten(t *testing.T) {
src, err := JSONReader(strings.NewReader(`{"a":{"b":"c"},"n":7,"arr":[1,2,3]}`))
if err != nil {
t.Fatal(err)
}
if v, _ := src.Lookup("A_B"); v != "c" {
t.Errorf("A_B=%q", v)
}
if v, _ := src.Lookup("N"); v != "7" {
t.Errorf("N=%q", v)
}
if v, _ := src.Lookup("ARR"); v != "1,2,3" {
t.Errorf("ARR=%q", v)
}
}
func TestTOMLFlatten(t *testing.T) {
src, err := TOMLReader(strings.NewReader(`
bind_addr = ":9000"
[session]
idle_ttl = "1h"
[session.cookie]
secure = true
`))
if err != nil {
t.Fatal(err)
}
for k, want := range map[string]string{
"BIND_ADDR": ":9000",
"SESSION_IDLE_TTL": "1h",
"SESSION_COOKIE_SECURE": "true",
} {
got, ok := src.Lookup(k)
if !ok || got != want {
t.Errorf("%s = %q ok=%v want %q", k, got, ok, want)
}
}
}