package config import ( "os" "testing" ) func TestLoad(t *testing.T) { // Clear environment variables for clean test os.Unsetenv("PORT") os.Unsetenv("HOST") os.Unsetenv("GO_ENV") cfg := Load() // Test default values if cfg.Server.Port != "1999" { t.Errorf("Server.Port = %q, want %q", cfg.Server.Port, "1999") } if cfg.Server.Host != "localhost" { t.Errorf("Server.Host = %q, want %q", cfg.Server.Host, "localhost") } if cfg.Server.ReadTimeout != 15 { t.Errorf("Server.ReadTimeout = %d, want %d", cfg.Server.ReadTimeout, 15) } if cfg.Server.WriteTimeout != 15 { t.Errorf("Server.WriteTimeout = %d, want %d", cfg.Server.WriteTimeout, 15) } if cfg.Template.Dir != "templates" { t.Errorf("Template.Dir = %q, want %q", cfg.Template.Dir, "templates") } if cfg.Data.Dir != "data" { t.Errorf("Data.Dir = %q, want %q", cfg.Data.Dir, "data") } } func TestLoadWithEnvVars(t *testing.T) { // Set custom environment variables os.Setenv("PORT", "8080") os.Setenv("HOST", "0.0.0.0") os.Setenv("READ_TIMEOUT", "30") os.Setenv("WRITE_TIMEOUT", "45") defer func() { os.Unsetenv("PORT") os.Unsetenv("HOST") os.Unsetenv("READ_TIMEOUT") os.Unsetenv("WRITE_TIMEOUT") }() cfg := Load() if cfg.Server.Port != "8080" { t.Errorf("Server.Port = %q, want %q", cfg.Server.Port, "8080") } if cfg.Server.Host != "0.0.0.0" { t.Errorf("Server.Host = %q, want %q", cfg.Server.Host, "0.0.0.0") } if cfg.Server.ReadTimeout != 30 { t.Errorf("Server.ReadTimeout = %d, want %d", cfg.Server.ReadTimeout, 30) } if cfg.Server.WriteTimeout != 45 { t.Errorf("Server.WriteTimeout = %d, want %d", cfg.Server.WriteTimeout, 45) } } func TestAddress(t *testing.T) { os.Unsetenv("PORT") os.Unsetenv("HOST") cfg := Load() addr := cfg.Address() if addr != "localhost:1999" { t.Errorf("Address() = %q, want %q", addr, "localhost:1999") } // Test with custom values os.Setenv("PORT", "3000") os.Setenv("HOST", "127.0.0.1") defer func() { os.Unsetenv("PORT") os.Unsetenv("HOST") }() cfg = Load() addr = cfg.Address() if addr != "127.0.0.1:3000" { t.Errorf("Address() = %q, want %q", addr, "127.0.0.1:3000") } } func TestGetEnv(t *testing.T) { // Test with existing var os.Setenv("TEST_VAR", "test_value") defer os.Unsetenv("TEST_VAR") result := getEnv("TEST_VAR", "default") if result != "test_value" { t.Errorf("getEnv with existing var = %q, want %q", result, "test_value") } // Test with non-existing var result = getEnv("NONEXISTENT_VAR", "default") if result != "default" { t.Errorf("getEnv with non-existing var = %q, want %q", result, "default") } } func TestGetEnvAsInt(t *testing.T) { // Test with valid int os.Setenv("INT_VAR", "42") defer os.Unsetenv("INT_VAR") result := getEnvAsInt("INT_VAR", 10) if result != 42 { t.Errorf("getEnvAsInt with valid int = %d, want %d", result, 42) } // Test with invalid int os.Setenv("INVALID_INT", "not_a_number") defer os.Unsetenv("INVALID_INT") result = getEnvAsInt("INVALID_INT", 10) if result != 10 { t.Errorf("getEnvAsInt with invalid int = %d, want %d", result, 10) } // Test with non-existing var result = getEnvAsInt("NONEXISTENT_INT", 99) if result != 99 { t.Errorf("getEnvAsInt with non-existing var = %d, want %d", result, 99) } } func TestGetEnvAsBool(t *testing.T) { tests := []struct { name string envValue string defaultValue bool expected bool }{ {"True string", "true", false, true}, {"False string", "false", true, false}, {"1 as true", "1", false, true}, {"0 as false", "0", true, false}, {"Invalid returns default true", "invalid", true, true}, {"Invalid returns default false", "invalid", false, false}, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { os.Setenv("BOOL_VAR", tt.envValue) defer os.Unsetenv("BOOL_VAR") result := getEnvAsBool("BOOL_VAR", tt.defaultValue) if result != tt.expected { t.Errorf("getEnvAsBool(%q, %v) = %v, want %v", tt.envValue, tt.defaultValue, result, tt.expected) } }) } // Test non-existing var result := getEnvAsBool("NONEXISTENT_BOOL", true) if result != true { t.Errorf("getEnvAsBool with non-existing var = %v, want %v", result, true) } } func TestIsDevelopment(t *testing.T) { tests := []struct { name string envValue string expected bool }{ {"Development env", "development", true}, {"Dev shorthand", "dev", true}, {"Production env", "production", false}, {"Prod shorthand", "prod", false}, {"Empty (default)", "", true}, // Default is development {"Staging", "staging", false}, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { if tt.envValue == "" { os.Unsetenv("GO_ENV") } else { os.Setenv("GO_ENV", tt.envValue) } defer os.Unsetenv("GO_ENV") result := isDevelopment() if result != tt.expected { t.Errorf("isDevelopment() with GO_ENV=%q = %v, want %v", tt.envValue, result, tt.expected) } }) } } func TestTemplateHotReload(t *testing.T) { // In development, hot reload should be true by default os.Setenv("GO_ENV", "development") os.Unsetenv("TEMPLATE_HOT_RELOAD") defer os.Unsetenv("GO_ENV") cfg := Load() if !cfg.Template.HotReload { t.Error("HotReload should be true in development by default") } // Explicit false should override os.Setenv("TEMPLATE_HOT_RELOAD", "false") defer os.Unsetenv("TEMPLATE_HOT_RELOAD") cfg = Load() if cfg.Template.HotReload { t.Error("HotReload should be false when explicitly set") } // In production, hot reload should be false by default os.Setenv("GO_ENV", "production") os.Unsetenv("TEMPLATE_HOT_RELOAD") cfg = Load() if cfg.Template.HotReload { t.Error("HotReload should be false in production by default") } } func TestEmailConfig(t *testing.T) { os.Unsetenv("SMTP_HOST") os.Unsetenv("SMTP_PORT") os.Unsetenv("SMTP_USER") os.Unsetenv("SMTP_PASSWORD") cfg := Load() // Test defaults if cfg.Email.SMTPHost != "smtp.gmail.com" { t.Errorf("Email.SMTPHost = %q, want %q", cfg.Email.SMTPHost, "smtp.gmail.com") } if cfg.Email.SMTPPort != "587" { t.Errorf("Email.SMTPPort = %q, want %q", cfg.Email.SMTPPort, "587") } // Test custom values os.Setenv("SMTP_HOST", "mail.example.com") os.Setenv("SMTP_PORT", "465") defer func() { os.Unsetenv("SMTP_HOST") os.Unsetenv("SMTP_PORT") }() cfg = Load() if cfg.Email.SMTPHost != "mail.example.com" { t.Errorf("Email.SMTPHost = %q, want %q", cfg.Email.SMTPHost, "mail.example.com") } if cfg.Email.SMTPPort != "465" { t.Errorf("Email.SMTPPort = %q, want %q", cfg.Email.SMTPPort, "465") } }