open-code-review/cmd/opencodereview/scan_helpers_test.go
Zhiming Wang c3e8a46323
fix(cli): stop preview from creating a review session (#784)
runPreview, runScanPreview, and delegate's preview each built a throwaway
agent via agent.New / scan.NewAgent purely to reach Preview. Both
constructors auto-create a session, and session.New opens persistence and
buffers a session_start record, so every preview created a JSONL file
under the OCR home. Preview never runs or finalizes a review, so that
file was left unfinalized and usually empty.

Make the exported entry point a package-level Preview(ctx, args) in both
internal/agent and internal/scan. It builds only what file selection
needs, so there is no session, manifest, or runner to leak. The existing
bodies stay as unexported methods, keeping the in-package tests
(including scan's regression test that Preview must not mutate a.items).

Deleting the file afterwards was rejected: it would still leak on crash
and would keep the wrong abstraction.

Tests assert at the CLI boundary, with a temporary OCR home, that no
session store is created by any of the three preview commands. They also
neutralize global git config, which git resolves via XDG_CONFIG_HOME
independently of HOME.
2026-08-08 20:55:54 +08:00

104 lines
2.7 KiB
Go

// SPDX-License-Identifier: Apache-2.0
// Copyright 2026 alibaba/open-code-review Contributors
package main
import (
"testing"
"github.com/alibaba/open-code-review/internal/config/template"
)
func TestLoadScanResumeState(t *testing.T) {
dir := initTestGitRepo(t)
t.Run("empty resume returns nil", func(t *testing.T) {
state, err := loadScanResumeState(dir, scanOptions{}, nil)
if err != nil || state != nil {
t.Errorf("got state=%v err=%v, want nil,nil", state, err)
}
})
t.Run("missing session load fails", func(t *testing.T) {
_, err := loadScanResumeState(dir, scanOptions{resume: "nope"}, nil)
if err == nil {
t.Fatal("expected error loading nonexistent resume session")
}
})
}
func TestRunScanPreview(t *testing.T) {
dir := initTestGitRepo(t)
gitCommitFile(t, dir, "y.go", "package y\n", "add y")
cc, err := loadCommonContext(dir, "", 0, 0, false)
if err != nil {
t.Fatalf("loadCommonContext: %v", err)
}
scanTpl, err := template.LoadScanDefault()
if err != nil {
t.Fatalf("LoadScanDefault: %v", err)
}
silenceStdout(t, func() {
if err := runScanPreview(cc, scanTpl, nil, "text"); err != nil {
t.Fatalf("runScanPreview error: %v", err)
}
})
}
func TestRunScanPreviewJSONFormat(t *testing.T) {
dir := initTestGitRepo(t)
gitCommitFile(t, dir, "y.go", "package y\n", "add y")
cc, err := loadCommonContext(dir, "", 0, 0, false)
if err != nil {
t.Fatalf("loadCommonContext: %v", err)
}
scanTpl, err := template.LoadScanDefault()
if err != nil {
t.Fatalf("LoadScanDefault: %v", err)
}
out := captureStdout(t, func() {
if err := runScanPreview(cc, scanTpl, nil, "json"); err != nil {
t.Errorf("runScanPreview error: %v", err)
}
})
got := decodeSinglePreviewJSON(t, out)
var found bool
for _, e := range got.Entries {
if e.Path == "y.go" {
found = true
if e.Status != "scan" || !e.WillReview {
t.Errorf("y.go = %+v, want a selected scan entry", e)
}
}
}
if !found {
t.Errorf("y.go missing from scan preview: %+v", got.Entries)
}
}
// TestRunScanPreviewCreatesNoSession mirrors TestRunPreviewCreatesNoSession:
// scan.NewAgent auto-creates a session too, so scan preview leaked the same
// unfinalized JSONL artifact.
func TestRunScanPreviewCreatesNoSession(t *testing.T) {
home := freshOCRHome(t)
dir := initTestGitRepo(t)
gitCommitFile(t, dir, "y.go", "package y\n", "add y")
cc, err := loadCommonContext(dir, "", 0, 0, false)
if err != nil {
t.Fatalf("loadCommonContext: %v", err)
}
scanTpl, err := template.LoadScanDefault()
if err != nil {
t.Fatalf("LoadScanDefault: %v", err)
}
silenceStdout(t, func() {
if err := runScanPreview(cc, scanTpl, nil, "text"); err != nil {
t.Fatalf("runScanPreview error: %v", err)
}
})
assertNoSessionStore(t, home)
}