-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathsight.go
More file actions
148 lines (134 loc) · 5.2 KB
/
Copy pathsight.go
File metadata and controls
148 lines (134 loc) · 5.2 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
// Package sight performs AI-powered code review on diffs. It parses unified diffs,
// enriches them with surrounding code context and git history, then runs parallel
// multi-concern reviews through an LLM provider.
//
// Sight has no CLI and no LLM SDK dependency — it defines a Provider interface
// that consumers (hawk) implement using their own LLM client (eyrie).
//
// Usage:
//
// result, err := sight.Review(ctx, diffText, sight.WithProvider(myProvider), sight.Thorough)
// for _, f := range result.Findings {
// fmt.Printf("[%s] %s:%d — %s\n", f.Severity, f.File, f.Line, f.Message)
// }
//
// For repeated reviews, use the reusable Reviewer:
//
// r := sight.NewReviewer(sight.WithProvider(p), sight.Thorough)
// result1, _ := r.Review(ctx, diff1)
// result2, _ := r.Review(ctx, diff2)
package sight
import (
"context"
"errors"
"time"
)
// Finding represents a single issue detected during review.
type Finding struct {
Concern string `json:"concern"`
Severity Severity `json:"severity"`
File string `json:"file"`
Line int `json:"line"`
EndLine int `json:"end_line,omitempty"`
Message string `json:"message"`
Fix string `json:"fix,omitempty"`
Reasoning string `json:"reasoning,omitempty"`
CWE string `json:"cwe,omitempty"`
// Confidence is a numeric score from 0.0 to 1.0 indicating how certain
// the system is that this finding is a true positive. Values closer to
// 1.0 mean higher confidence.
Confidence float64 `json:"confidence"`
// SASTSource marks findings that originated from static analysis (SAST)
// and were fed into the LLM prompt for validation.
SASTSource bool `json:"sast_source,omitempty"`
}
// InlineComment is a finding mapped to an exact position in a diff, ready for
// posting as a review comment.
type InlineComment struct {
Path string `json:"path"`
StartLine int `json:"start_line"`
EndLine int `json:"end_line,omitempty"`
Body string `json:"body"`
Suggestion string `json:"suggestion,omitempty"`
}
// Stats provides review metrics.
type Stats struct {
FilesReviewed int `json:"files_reviewed"`
HunksAnalyzed int `json:"hunks_analyzed"`
FindingsTotal int `json:"findings_total"`
BySeverity map[Severity]int `json:"by_severity"`
ByConcern map[string]int `json:"by_concern"`
TokensUsed int `json:"tokens_used"`
DurationPerConcern map[string]time.Duration `json:"duration_per_concern"`
// AverageConfidence is the mean confidence score across all findings (0.0-1.0).
AverageConfidence float64 `json:"average_confidence"`
// HighConfidenceCount is the number of findings with confidence >= 0.7.
HighConfidenceCount int `json:"high_confidence_count"`
// LowConfidenceCount is the number of findings with confidence < 0.5.
LowConfidenceCount int `json:"low_confidence_count"`
}
// Result is the complete output of a review operation.
type Result struct {
Findings []Finding `json:"findings"`
Comments []InlineComment `json:"comments"`
Stats Stats `json:"stats"`
Report string `json:"report"`
FailOn Severity `json:"fail_on"`
// SASTFusion tracks which SAST findings the LLM confirmed vs dismissed.
// Only populated when SAST-LLM fusion is active (preAnalysis enabled).
SASTFusion *SASTFusionResult `json:"sast_fusion,omitempty"`
// ConfidenceBreakdown groups findings by confidence band for quick triage.
ConfidenceBreakdown *ConfidenceBreakdown `json:"confidence_breakdown,omitempty"`
}
// ConfidenceBreakdown groups findings into bands for quick triage.
type ConfidenceBreakdown struct {
// High are findings with confidence >= 0.7.
High []Finding `json:"high"`
// Medium are findings with 0.5 <= confidence < 0.7.
Medium []Finding `json:"medium"`
// Low are findings with confidence < 0.5.
Low []Finding `json:"low"`
}
// Failed returns true if any finding meets or exceeds the configured fail threshold.
func (r *Result) Failed() bool {
for _, f := range r.Findings {
if f.Severity.AtLeast(r.FailOn) {
return true
}
}
return false
}
// MaxSeverity returns the highest severity found.
func (r *Result) MaxSeverity() Severity {
max := SeverityInfo
for _, f := range r.Findings {
if f.Severity > max {
max = f.Severity
}
}
return max
}
// FileChange represents a single file's changes for review.
type FileChange struct {
Path string
OldPath string
Diff string
Content string
}
// PRSource identifies a pull request to review.
type PRSource struct {
Owner string
Repo string
Number int
}
// Review performs a one-shot review on a unified diff string.
func Review(ctx context.Context, diff string, opts ...Option) (*Result, error) {
r := NewReviewer(opts...)
return r.Review(ctx, diff)
}
// ErrNoProvider is returned when Review is called without a Provider configured.
var ErrNoProvider = errors.New("sight: no provider configured; use WithProvider()")
// ErrEmptyDiff is returned when the input diff is empty.
var ErrEmptyDiff = errors.New("sight: empty diff; nothing to review")
// ErrContextCancelled is returned when the context is cancelled during review.
var ErrContextCancelled = errors.New("sight: context cancelled")