diff --git a/internal/ai/findings_mcp_adapter.go b/internal/ai/findings_tools_adapter.go similarity index 75% rename from internal/ai/findings_mcp_adapter.go rename to internal/ai/findings_tools_adapter.go index 7ec7e3e5d..4d84f6b54 100644 --- a/internal/ai/findings_mcp_adapter.go +++ b/internal/ai/findings_tools_adapter.go @@ -1,7 +1,7 @@ package ai import ( - "github.com/rcourtman/pulse-go-rewrite/internal/ai/mcp" + "github.com/rcourtman/pulse-go-rewrite/internal/ai/tools" ) // FindingsMCPAdapter adapts FindingsStore to MCP FindingsProvider interface @@ -17,18 +17,18 @@ func NewFindingsMCPAdapter(store *FindingsStore) *FindingsMCPAdapter { return &FindingsMCPAdapter{store: store} } -// GetActiveFindings implements mcp.FindingsProvider -func (a *FindingsMCPAdapter) GetActiveFindings() []mcp.Finding { +// GetActiveFindings implements tools.FindingsProvider +func (a *FindingsMCPAdapter) GetActiveFindings() []tools.Finding { if a.store == nil { return nil } // Get all active findings (empty severity means all) internal := a.store.GetActive("") - result := make([]mcp.Finding, 0, len(internal)) + result := make([]tools.Finding, 0, len(internal)) for _, f := range internal { - result = append(result, mcp.Finding{ + result = append(result, tools.Finding{ ID: f.ID, Key: f.Key, Severity: string(f.Severity), @@ -48,17 +48,17 @@ func (a *FindingsMCPAdapter) GetActiveFindings() []mcp.Finding { return result } -// GetDismissedFindings implements mcp.FindingsProvider -func (a *FindingsMCPAdapter) GetDismissedFindings() []mcp.Finding { +// GetDismissedFindings implements tools.FindingsProvider +func (a *FindingsMCPAdapter) GetDismissedFindings() []tools.Finding { if a.store == nil { return nil } internal := a.store.GetDismissedFindings() - result := make([]mcp.Finding, 0, len(internal)) + result := make([]tools.Finding, 0, len(internal)) for _, f := range internal { - result = append(result, mcp.Finding{ + result = append(result, tools.Finding{ ID: f.ID, Key: f.Key, Severity: string(f.Severity), diff --git a/internal/ai/findings_tools_adapter_test.go b/internal/ai/findings_tools_adapter_test.go new file mode 100644 index 000000000..29f1ae0e5 --- /dev/null +++ b/internal/ai/findings_tools_adapter_test.go @@ -0,0 +1,38 @@ +package ai + +import "testing" + +func TestFindingsMCPAdapter(t *testing.T) { + if NewFindingsMCPAdapter(nil) != nil { + t.Fatal("expected nil adapter for nil store") + } + + store := NewFindingsStore() + finding := &Finding{ + ID: "f1", + Key: "k1", + Severity: FindingSeverityWarning, + Category: FindingCategoryPerformance, + ResourceID: "vm-1", + ResourceName: "vm1", + Title: "Issue", + } + store.Add(finding) + store.Dismiss("f1", "not_an_issue", "ok") + + adapter := NewFindingsMCPAdapter(store) + active := adapter.GetActiveFindings() + if len(active) != 0 { + t.Fatalf("expected no active findings, got %d", len(active)) + } + + dismissed := adapter.GetDismissedFindings() + if len(dismissed) != 1 || dismissed[0].ID != "f1" { + t.Fatalf("unexpected dismissed findings: %+v", dismissed) + } + + adapter = &FindingsMCPAdapter{} + if adapter.GetActiveFindings() != nil || adapter.GetDismissedFindings() != nil { + t.Fatal("expected nil results when store missing") + } +} diff --git a/internal/ai/patrol.go b/internal/ai/patrol.go index 1f238007b..b1e062acb 100644 --- a/internal/ai/patrol.go +++ b/internal/ai/patrol.go @@ -335,6 +335,12 @@ func (p *PatrolService) SetOpenCodePatrol(runner OpenCodePatrolRunner, enabled b log.Info().Bool("enabled", enabled).Msg("OpenCode patrol integration configured") } +// SetChatPatrol sets the chat-based patrol runner for delegation +// This is functionally equivalent to SetOpenCodePatrol +func (p *PatrolService) SetChatPatrol(runner OpenCodePatrolRunner, enabled bool) { + p.SetOpenCodePatrol(runner, enabled) +} + // UseOpenCode returns whether OpenCode is configured for patrol func (p *PatrolService) UseOpenCode() bool { p.mu.RLock()