a06f331eb8
CI / benchmark (push) Has been skipped
install-script / posix-syntax (push) Successful in 6m1s
CI / build-onnx (push) Failing after 6m43s
init-smoke / dry-run (push) Failing after 15m57s
security / govulncheck (push) Has been cancelled
security / trivy-fs (push) Has been cancelled
CI / test (1.26, ubuntu-latest) (push) Has been cancelled
Scorecard supply-chain security / Scorecard analysis (push) Has been cancelled
CI / test (1.26, macos-latest) (push) Has been cancelled
CI / build-windows (push) Has been cancelled
CI / lint (push) Has been cancelled
install-script / powershell-syntax (push) Has been cancelled
install-script / install (macos-14) (push) Has been cancelled
install-script / install (ubuntu-latest) (push) Has been cancelled
127 lines
3.7 KiB
Go
127 lines
3.7 KiB
Go
package analysis
|
|
|
|
import (
|
|
"testing"
|
|
|
|
"github.com/zzet/gortex/internal/graph"
|
|
)
|
|
|
|
func groundingLines() map[string][]HunkLine {
|
|
return map[string][]HunkLine{
|
|
"pkg/foo.go": {
|
|
{NewLine: 3, Side: " ", Text: "func Foo() int {"},
|
|
{NewLine: 4, Side: "+", Text: "\tx := compute(a, b)"},
|
|
{NewLine: 5, Side: "+", Text: "\treturn x"},
|
|
{NewLine: 6, Side: " ", Text: "}"},
|
|
{NewLine: 10, Side: "+", Text: "var globalCounter int"},
|
|
},
|
|
}
|
|
}
|
|
|
|
func TestGroundFindingExact(t *testing.T) {
|
|
lg := NewLineGrounder(nil, groundingLines())
|
|
hit, ok := lg.GroundFinding("pkg/foo.go", "", "compute(a, b)")
|
|
if !ok {
|
|
t.Fatal("expected a hit for an exact substring")
|
|
}
|
|
if hit.Line != 4 {
|
|
t.Fatalf("expected line 4, got %d", hit.Line)
|
|
}
|
|
if hit.Confidence != 1.0 {
|
|
t.Fatalf("expected confidence 1.0, got %v", hit.Confidence)
|
|
}
|
|
if hit.File != "pkg/foo.go" {
|
|
t.Fatalf("unexpected file %q", hit.File)
|
|
}
|
|
}
|
|
|
|
func TestGroundFindingWhitespaceVariant(t *testing.T) {
|
|
lg := NewLineGrounder(nil, groundingLines())
|
|
// Different inner spacing than the source ("compute(a, b)" vs "compute(a, b)")
|
|
// — defeats exact match, must hit the whitespace-normalized tier.
|
|
hit, ok := lg.GroundFinding("pkg/foo.go", "", "x := compute(a, b)")
|
|
if !ok {
|
|
t.Fatal("expected a hit for a whitespace variant")
|
|
}
|
|
if hit.Line != 4 {
|
|
t.Fatalf("expected line 4, got %d", hit.Line)
|
|
}
|
|
if hit.Confidence != 0.7 {
|
|
t.Fatalf("expected confidence 0.7, got %v", hit.Confidence)
|
|
}
|
|
}
|
|
|
|
func TestGroundFindingNonexistent(t *testing.T) {
|
|
lg := NewLineGrounder(nil, groundingLines())
|
|
_, ok := lg.GroundFinding("pkg/foo.go", "", "totally unrelated zzzqqq phrase")
|
|
if ok {
|
|
t.Fatal("expected ok=false for a snippet that matches nothing")
|
|
}
|
|
// Unknown file → also ok=false.
|
|
if _, ok := lg.GroundFinding("pkg/nope.go", "", "anything"); ok {
|
|
t.Fatal("expected ok=false for an unknown file")
|
|
}
|
|
}
|
|
|
|
func TestGroundFindingEmptySnippetFirstAdded(t *testing.T) {
|
|
lg := NewLineGrounder(nil, groundingLines())
|
|
hit, ok := lg.GroundFinding("pkg/foo.go", "", "")
|
|
if !ok {
|
|
t.Fatal("expected a hit for an empty snippet")
|
|
}
|
|
// First added line in the file is line 4 (line 3 is context).
|
|
if hit.Line != 4 {
|
|
t.Fatalf("expected first added line 4, got %d", hit.Line)
|
|
}
|
|
}
|
|
|
|
func TestGroundFindingTokenOverlapFallback(t *testing.T) {
|
|
lg := NewLineGrounder(nil, groundingLines())
|
|
// No exact / whitespace match, but shares the token "compute".
|
|
hit, ok := lg.GroundFinding("pkg/foo.go", "", "result of compute step")
|
|
if !ok {
|
|
t.Fatal("expected a token-overlap fallback hit")
|
|
}
|
|
if hit.Line != 4 {
|
|
t.Fatalf("expected fallback to land on line 4, got %d", hit.Line)
|
|
}
|
|
if hit.Confidence >= 0.5 {
|
|
t.Fatalf("fallback confidence must be < 0.5, got %v", hit.Confidence)
|
|
}
|
|
}
|
|
|
|
func TestGroundFindingSymbolScoped(t *testing.T) {
|
|
g := graph.New()
|
|
g.AddNode(&graph.Node{
|
|
ID: "pkg/foo.go::Foo",
|
|
Kind: graph.KindFunction,
|
|
Name: "Foo",
|
|
FilePath: "pkg/foo.go",
|
|
StartLine: 3,
|
|
EndLine: 6,
|
|
Language: "go",
|
|
})
|
|
lg := NewLineGrounder(g, groundingLines())
|
|
|
|
// Empty snippet scoped to Foo (lines 3..6) → first added line in span = 4,
|
|
// NOT the line-10 add outside the symbol.
|
|
hit, ok := lg.GroundFinding("pkg/foo.go", "pkg/foo.go::Foo", "")
|
|
if !ok {
|
|
t.Fatal("expected a hit scoped to Foo")
|
|
}
|
|
if hit.Line != 4 {
|
|
t.Fatalf("expected first added line inside Foo (4), got %d", hit.Line)
|
|
}
|
|
|
|
// A snippet that only exists outside the symbol span still anchors (scope
|
|
// falls back to the whole file when nothing in-span matches), but the
|
|
// in-span content is preferred when present.
|
|
hit, ok = lg.GroundFinding("pkg/foo.go", "pkg/foo.go::Foo", "return x")
|
|
if !ok {
|
|
t.Fatal("expected a hit for in-span snippet")
|
|
}
|
|
if hit.Line != 5 {
|
|
t.Fatalf("expected line 5 for 'return x', got %d", hit.Line)
|
|
}
|
|
}
|