Files
Pulse/internal/api/security_test.go
rcourtman 6eb1a10d9b Refactor: Code cleanup and localStorage consolidation
This commit includes comprehensive codebase cleanup and refactoring:

## Code Cleanup
- Remove dead TypeScript code (types/monitoring.ts - 194 lines duplicate)
- Remove unused Go functions (GetClusterNodes, MigratePassword, GetClusterHealthInfo)
- Clean up commented-out code blocks across multiple files
- Remove unused TypeScript exports (helpTextClass, private tag color helpers)
- Delete obsolete test files and components

## localStorage Consolidation
- Centralize all storage keys into STORAGE_KEYS constant
- Update 5 files to use centralized keys:
  * utils/apiClient.ts (AUTH, LEGACY_TOKEN)
  * components/Dashboard/Dashboard.tsx (GUEST_METADATA)
  * components/Docker/DockerHosts.tsx (DOCKER_METADATA)
  * App.tsx (PLATFORMS_SEEN)
  * stores/updates.ts (UPDATES)
- Benefits: Single source of truth, prevents typos, better maintainability

## Previous Work Committed
- Docker monitoring improvements and disk metrics
- Security enhancements and setup fixes
- API refactoring and cleanup
- Documentation updates
- Build system improvements

## Testing
- All frontend tests pass (29 tests)
- All Go tests pass (15 packages)
- Production build successful
- Zero breaking changes

Total: 186 files changed, 5825 insertions(+), 11602 deletions(-)
2025-11-04 21:50:46 +00:00

84 lines
2.0 KiB
Go

package api
import (
"net/http/httptest"
"sync"
"testing"
)
func resetTrustedProxyConfig() {
trustedProxyCIDRs = nil
trustedProxyOnce = sync.Once{}
}
func TestGetClientIPRejectsSpoofedLoopback(t *testing.T) {
t.Setenv("PULSE_TRUSTED_PROXY_CIDRS", "")
resetTrustedProxyConfig()
req := httptest.NewRequest("GET", "/", nil)
req.RemoteAddr = "198.51.100.42:54321"
req.Header.Set("X-Forwarded-For", "127.0.0.1")
if got := GetClientIP(req); got != "198.51.100.42" {
t.Fatalf("expected remote IP when proxy is untrusted, got %q", got)
}
}
func TestGetClientIPUsesForwardedForTrustedProxy(t *testing.T) {
t.Setenv("PULSE_TRUSTED_PROXY_CIDRS", "127.0.0.1/32")
resetTrustedProxyConfig()
req := httptest.NewRequest("GET", "/", nil)
req.RemoteAddr = "127.0.0.1:54321"
req.Header.Set("X-Forwarded-For", "203.0.113.44")
if got := GetClientIP(req); got != "203.0.113.44" {
t.Fatalf("expected forwarded IP for trusted proxy, got %q", got)
}
}
func TestIsPrivateIP(t *testing.T) {
t.Helper()
cases := []struct {
name string
ip string
want bool
}{
{"public IPv4", "198.51.100.42", false},
{"private IPv4", "10.1.2.3", true},
{"loopback IPv4", "127.0.0.1", true},
{"link-local IPv6", "fe80::1", true},
{"loopback IPv6 with port", "[::1]:8443", true},
}
for _, tc := range cases {
tc := tc
t.Run(tc.name, func(t *testing.T) {
if got := isPrivateIP(tc.ip); got != tc.want {
t.Fatalf("isPrivateIP(%q) = %v, want %v", tc.ip, got, tc.want)
}
})
}
}
func TestIsTrustedNetwork(t *testing.T) {
t.Helper()
if !isTrustedNetwork("10.0.0.5", nil) {
t.Fatal("expected private IP to be trusted when no networks configured")
}
if isTrustedNetwork("198.51.100.42", nil) {
t.Fatal("expected public IP to be untrusted when no networks configured")
}
custom := []string{"203.0.113.0/24"}
if !isTrustedNetwork("203.0.113.44:8080", custom) {
t.Fatal("expected IP within custom CIDR to be trusted")
}
if isTrustedNetwork("198.51.100.42", custom) {
t.Fatal("expected IP outside custom CIDR to be untrusted")
}
}