package api import ( "encoding/json" "testing" "crypto-miner-server/internal/db" "crypto-miner-server/internal/strategy" ) func TestAuthResponseIncludesAdaptiveStrategy(t *testing.T) { database, err := db.New(t.TempDir()) if err != nil { t.Fatal(err) } t.Cleanup(func() { _ = database.Close() }) hub := NewWSHub(database) hub.SetFleetSecret("test-secret") hub.SetAdaptiveEngine(strategy.NewAdaptiveEngine(database, true)) conn, _ := dialAgentWS(t, hub) resp := authAgentConn(t, conn, map[string]interface{}{ "agent_id": "agent-strategy-1", "fleet_secret": "test-secret", "wallet": "4" + repeatChar('A', 94), "hostname": "win-docker", "platform": "windows", "version": "test", }) if resp.Type != "auth_response" { t.Fatalf("expected auth_response, got %q", resp.Type) } var payload map[string]interface{} if err := json.Unmarshal(resp.Payload, &payload); err != nil { t.Fatal(err) } if payload["success"] != true { t.Fatalf("auth failed: %v", payload["error"]) } raw, ok := payload["adaptive_strategy"] if !ok { t.Fatal("expected adaptive_strategy in auth_response") } data, _ := json.Marshal(raw) var adaptive struct { TierOrder []string `json:"tier_order"` Reasoning []struct{ Fact, Inference, Action string } `json:"reasoning"` Confidence float64 `json:"confidence"` } if err := json.Unmarshal(data, &adaptive); err != nil { t.Fatal(err) } if len(adaptive.TierOrder) == 0 || len(adaptive.Reasoning) == 0 || adaptive.Confidence <= 0 { t.Fatalf("invalid adaptive_strategy: %+v", adaptive) } } func TestAuthResponseOmitsAdaptiveStrategyWhenAIControlEnabled(t *testing.T) { database, err := db.New(t.TempDir()) if err != nil { t.Fatal(err) } t.Cleanup(func() { _ = database.Close() }) hub := NewWSHub(database) hub.SetFleetSecret("test-secret") hub.SetAdaptiveEngine(strategy.NewAdaptiveEngine(database, true)) hub.SetServerPolicy(ServerPolicy{AIControlEnabled: true}) conn, _ := dialAgentWS(t, hub) resp := authAgentConn(t, conn, map[string]interface{}{ "agent_id": "agent-ai-1", "fleet_secret": "test-secret", "wallet": "4" + repeatChar('B', 94), "hostname": "win-docker", "platform": "windows", "version": "test", }) if resp.Type != "auth_response" { t.Fatalf("expected auth_response, got %q", resp.Type) } var payload map[string]interface{} if err := json.Unmarshal(resp.Payload, &payload); err != nil { t.Fatal(err) } if payload["success"] != true { t.Fatalf("auth failed: %v", payload["error"]) } if _, ok := payload["adaptive_strategy"]; ok { t.Fatal("adaptive_strategy must be omitted when ai_control_enabled is true") } raw, ok := payload["spread_temperament"] if !ok { t.Fatal("expected spread_temperament in auth_response when ai_control_enabled") } data, _ := json.Marshal(raw) var temperament struct { TierOrder []string `json:"tier_order"` } if err := json.Unmarshal(data, &temperament); err != nil { t.Fatal(err) } if len(temperament.TierOrder) == 0 { t.Fatalf("empty spread_temperament: %+v", temperament) } } func repeatChar(c byte, n int) string { buf := make([]byte, n) for i := range buf { buf[i] = c } return string(buf) }