package codeindex import ( "context" "encoding/json" "testing" "time" "github.com/google/uuid" "github.com/stretchr/testify/require" "github.com/yan1h/agent-coding-workflow/internal/infra/git" "github.com/yan1h/agent-coding-workflow/internal/infra/llm" "github.com/yan1h/agent-coding-workflow/internal/jobs" ) type fakeEnqueuer struct{ count int } func (f *fakeEnqueuer) Enqueue(_ context.Context, typ jobs.JobType, _ json.RawMessage, _ time.Time, _ int32) (*jobs.Job, error) { f.count++ return &jobs.Job{ID: uuid.New(), Type: typ}, nil } func TestService_EnqueueBuild_DisabledEmbedder(t *testing.T) { repo := newFakeRepo() enq := &fakeEnqueuer{} svc := NewService(repo, fakeLocator{}, nil, fakeEmbedSel{err: ErrEmbeddingDisabled}, enq, 50) _, err := svc.EnqueueBuild(context.Background(), uuid.New(), nil, "abc123") require.ErrorIs(t, err, ErrEmbeddingDisabled) require.Equal(t, 0, enq.count) } func TestService_EnqueueBuild_CreatesRunAndEnqueuesOnce(t *testing.T) { dir, sha := tempGitRepo(t) wsID := uuid.New() repo := newFakeRepo() enq := &fakeEnqueuer{} gitr := git.NewDefaultRunner(git.DefaultConfig()) svc := NewService(repo, fakeLocator{dir: dir, wsID: wsID}, gitr, fakeEmbedSel{emb: llm.NewFakeEmbedder()}, enq, 50) run, err := svc.EnqueueBuild(context.Background(), wsID, nil, sha) require.NoError(t, err) require.Equal(t, sha, run.CommitSHA) require.Equal(t, 1, enq.count) require.Len(t, repo.runs, 1) // Re-enqueue at the same commit while pending → no new job, no new run. run2, err := svc.EnqueueBuild(context.Background(), wsID, nil, sha) require.NoError(t, err) require.Equal(t, run.ID, run2.ID) require.Equal(t, 1, enq.count, "idempotent: pending run is reused") require.Len(t, repo.runs, 1) } func TestService_Search_NoCompletedRun(t *testing.T) { repo := newFakeRepo() svc := NewService(repo, fakeLocator{}, nil, fakeEmbedSel{emb: llm.NewFakeEmbedder()}, &fakeEnqueuer{}, 50) _, err := svc.Search(context.Background(), uuid.New(), SearchQuery{Text: "foo"}) require.Error(t, err) // no completed index yet } func TestService_Search_EmptyQuery(t *testing.T) { repo := newFakeRepo() svc := NewService(repo, fakeLocator{}, nil, fakeEmbedSel{emb: llm.NewFakeEmbedder()}, &fakeEnqueuer{}, 50) _, err := svc.Search(context.Background(), uuid.New(), SearchQuery{Text: ""}) require.Error(t, err) }