alpha
Login
or
Join now
boltless.me
/
zoekt
Star
0
Fork
0
Atom
Configure Feed
Issues
Pull Requests
Commits
Tags
Feed URL
Select the types of activity you want to include in your feed.
fork of https://github.com/sourcegraph/zoekt
Star
0
Fork
0
Atom
Configure Feed
Issues
Pull Requests
Commits
Tags
Feed URL
Select the types of activity you want to include in your feed.
Overview
Issues
Pulls
Pipelines
gitindex: speed up tests (#1031)
author
Keegan Carruthers-Smith
committer
GitHub
date
2 months ago
(Mar 31, 2026, 11:16 AM +0200)
commit
7a3a62ea
7a3a62ea54e4061589d914117d0cdfc3a5678e1b
parent
7d3b9db1
7d3b9db1aaf2181be398959d0da3061bdfa64d18
+221
-100
10 changed files
Expand all
Collapse all
Unified
Split
gitindex
catfile_hardening_test.go
catfile_test.go
clone_test.go
delete_test.go
ignore_test.go
index_test.go
main_test.go
repocache_test.go
submodule_test.go
tree_test.go
+85
-31
gitindex/catfile_hardening_test.go
Reviewed
···
19
19
// TestCatfileReader_DoubleClose verifies that Close is idempotent.
20
20
// Calling Close twice must not deadlock or panic.
21
21
func TestCatfileReader_DoubleClose(t *testing.T) {
22
22
+
t.Parallel()
23
23
+
22
24
repoDir, blobs := createTestRepo(t)
23
25
ids := []plumbing.Hash{blobs["hello.txt"]}
24
26
···
54
56
// multiple goroutines simultaneously does not panic, deadlock, or
55
57
// corrupt state.
56
58
func TestCatfileReader_ConcurrentClose(t *testing.T) {
59
59
+
t.Parallel()
60
60
+
57
61
repoDir, blobs := createTestRepo(t)
58
62
ids := []plumbing.Hash{
59
63
blobs["hello.txt"],
···
103
107
// immediately after creation (without reading any entries) completes
104
108
// without hanging.
105
109
func TestCatfileReader_CloseWithoutReading(t *testing.T) {
110
110
+
t.Parallel()
111
111
+
106
112
repoDir, blobs := createTestRepo(t)
107
113
ids := []plumbing.Hash{
108
114
blobs["hello.txt"],
···
135
141
// termination (e.g., builder.Add error) with many unconsumed blobs.
136
142
// Close should complete promptly — not drain the entire git output.
137
143
func TestCatfileReader_CloseBeforeExhausted_ManyBlobs(t *testing.T) {
138
138
-
// Create a repo with many non-trivial files.
139
139
-
dir := t.TempDir()
140
140
-
repoDir := filepath.Join(dir, "repo")
141
141
-
142
142
-
script := `
143
143
-
set -e
144
144
-
git init -b main repo
145
145
-
cd repo
146
146
-
git config user.email "test@test.com"
147
147
-
git config user.name "Test"
148
148
-
for i in $(seq 1 200); do
149
149
-
dd if=/dev/urandom bs=1024 count=10 of="file_$i.bin" 2>/dev/null
150
150
-
done
151
151
-
git add -A
152
152
-
git commit -m "many files"
153
153
-
`
154
154
-
cmd := exec.Command("/bin/sh", "-c", script)
155
155
-
cmd.Dir = dir
156
156
-
cmd.Stderr = os.Stderr
157
157
-
if err := cmd.Run(); err != nil {
158
158
-
t.Fatalf("create test repo: %v", err)
159
159
-
}
144
144
+
t.Parallel()
160
145
161
161
-
var ids []plumbing.Hash
162
162
-
for i := 1; i <= 200; i++ {
163
163
-
name := fmt.Sprintf("file_%d.bin", i)
164
164
-
out, err := exec.Command("git", "-C", repoDir, "rev-parse", "HEAD:"+name).Output()
165
165
-
if err != nil {
166
166
-
t.Fatalf("rev-parse %s: %v", name, err)
167
167
-
}
168
168
-
ids = append(ids, plumbing.NewHash(string(out[:len(out)-1])))
169
169
-
}
146
146
+
// Create enough blobs to make a draining Close noticeable without spending
147
147
+
// most of the test runtime on shelling out for fixture setup.
148
148
+
repoDir, ids := createManyBlobRepo(t, 128, 4<<10)
170
149
171
150
cr, err := newCatfileReader(repoDir, ids, catfileReaderOptions{})
172
151
if err != nil {
···
199
178
}
200
179
}
201
180
181
181
+
func createManyBlobRepo(t *testing.T, fileCount, fileSize int) (string, []plumbing.Hash) {
182
182
+
t.Helper()
183
183
+
184
184
+
dir := t.TempDir()
185
185
+
repoDir := filepath.Join(dir, "repo")
186
186
+
187
187
+
runGit(t, dir, "init", "-b", "main", "repo")
188
188
+
189
189
+
for i := 0; i < fileCount; i++ {
190
190
+
content := bytes.Repeat([]byte{byte(i)}, fileSize)
191
191
+
name := filepath.Join(repoDir, fmt.Sprintf("file_%03d.bin", i))
192
192
+
if err := os.WriteFile(name, content, 0o644); err != nil {
193
193
+
t.Fatalf("WriteFile(%q): %v", name, err)
194
194
+
}
195
195
+
}
196
196
+
197
197
+
runGit(t, repoDir, "add", ".")
198
198
+
runGit(t, repoDir, "commit", "-m", "many files")
199
199
+
200
200
+
out, err := exec.Command("git", "-C", repoDir, "ls-tree", "-r", "-z", "HEAD").Output()
201
201
+
if err != nil {
202
202
+
t.Fatalf("git ls-tree: %v", err)
203
203
+
}
204
204
+
205
205
+
ids := make([]plumbing.Hash, 0, fileCount)
206
206
+
for _, entry := range bytes.Split(out, []byte{0}) {
207
207
+
if len(entry) == 0 {
208
208
+
continue
209
209
+
}
210
210
+
211
211
+
fields := bytes.Fields(entry)
212
212
+
if len(fields) < 3 {
213
213
+
t.Fatalf("unexpected ls-tree entry %q", entry)
214
214
+
}
215
215
+
216
216
+
ids = append(ids, plumbing.NewHash(string(fields[2])))
217
217
+
}
218
218
+
219
219
+
if len(ids) != fileCount {
220
220
+
t.Fatalf("got %d blob IDs, want %d", len(ids), fileCount)
221
221
+
}
222
222
+
223
223
+
return repoDir, ids
224
224
+
}
225
225
+
202
226
// --- Read edge-case tests ---
203
227
204
228
// TestCatfileReader_ReadWithoutNext verifies that calling Read
205
229
// before calling Next returns io.EOF, not a panic or garbage data.
206
230
func TestCatfileReader_ReadWithoutNext(t *testing.T) {
231
231
+
t.Parallel()
232
232
+
207
233
repoDir, blobs := createTestRepo(t)
208
234
ids := []plumbing.Hash{blobs["hello.txt"]}
209
235
···
224
250
// calls after a blob is fully consumed return io.EOF, not duplicate
225
251
// data or trailing LF bytes.
226
252
func TestCatfileReader_ReadAfterFullConsumption(t *testing.T) {
253
253
+
t.Parallel()
254
254
+
227
255
repoDir, blobs := createTestRepo(t)
228
256
ids := []plumbing.Hash{blobs["hello.txt"]}
229
257
···
253
281
// and verifies the entire content is reconstructed correctly without
254
282
// any trailing LF leaking into user content.
255
283
func TestCatfileReader_SmallBufferReads(t *testing.T) {
284
284
+
t.Parallel()
285
285
+
256
286
repoDir, blobs := createTestRepo(t)
257
287
ids := []plumbing.Hash{blobs["hello.txt"]}
258
288
···
291
321
// content, then advances to the next entry. Verifies that the discard
292
322
// of pending bytes doesn't corrupt the stream.
293
323
func TestCatfileReader_PartialReadThenNext(t *testing.T) {
324
324
+
t.Parallel()
325
325
+
294
326
repoDir, blobs := createTestRepo(t)
295
327
ids := []plumbing.Hash{
296
328
blobs["hello.txt"], // 12 bytes: "hello world\n"
···
337
369
// 1 trailing LF). This stresses the boundary between content and LF
338
370
// in the discard path.
339
371
func TestCatfileReader_PartialReadExactlyOneByteShort(t *testing.T) {
372
372
+
t.Parallel()
373
373
+
340
374
repoDir, blobs := createTestRepo(t)
341
375
ids := []plumbing.Hash{
342
376
blobs["hello.txt"], // 12 bytes
···
384
418
// TestCatfileReader_EmptyIds verifies that an empty id slice produces
385
419
// immediate EOF without errors.
386
420
func TestCatfileReader_EmptyIds(t *testing.T) {
421
421
+
t.Parallel()
422
422
+
387
423
repoDir, _ := createTestRepo(t)
388
424
389
425
cr, err := newCatfileReader(repoDir, nil, catfileReaderOptions{})
···
402
438
// handling for size-0 blobs. Git still outputs a LF after a 0-byte
403
439
// blob body. Repeated empty blobs test the pending=1 discard path.
404
440
func TestCatfileReader_MultipleEmptyBlobs(t *testing.T) {
441
441
+
t.Parallel()
442
442
+
405
443
repoDir, blobs := createTestRepo(t)
406
444
407
445
// Send the empty blob SHA 5 times — git outputs each independently.
···
438
476
// through the io.Reader interface returns 0 bytes and io.EOF, and that
439
477
// the trailing LF is consumed transparently.
440
478
func TestCatfileReader_EmptyBlobRead(t *testing.T) {
479
479
+
t.Parallel()
480
480
+
441
481
repoDir, blobs := createTestRepo(t)
442
482
ids := []plumbing.Hash{
443
483
blobs["empty.txt"], // 0 bytes
···
486
526
// missing objects is handled gracefully — no errors, no panics, just
487
527
// missing=true for each followed by EOF.
488
528
func TestCatfileReader_AllMissing(t *testing.T) {
529
529
+
t.Parallel()
530
530
+
489
531
repoDir, _ := createTestRepo(t)
490
532
491
533
ids := []plumbing.Hash{
···
522
564
// TestCatfileReader_AlternatingMissingPresent interleaves missing and
523
565
// present objects, verifying that stream alignment is maintained.
524
566
func TestCatfileReader_AlternatingMissingPresent(t *testing.T) {
567
567
+
t.Parallel()
568
568
+
525
569
repoDir, blobs := createTestRepo(t)
526
570
527
571
fake1 := plumbing.NewHash("deadbeefdeadbeefdeadbeefdeadbeefdeadbeef")
···
599
643
// the stream. Missing objects have no content body, so there must be
600
644
// no stale pending bytes interfering with the next header read.
601
645
func TestCatfileReader_MissingThenSkip(t *testing.T) {
646
646
+
t.Parallel()
647
647
+
602
648
repoDir, blobs := createTestRepo(t)
603
649
604
650
fake := plumbing.NewHash("deadbeefdeadbeefdeadbeefdeadbeefdeadbeef")
···
649
695
// TestCatfileReader_RepeatedNextAfterEOF verifies that calling Next
650
696
// after EOF keeps returning EOF — not a panic, not a different error.
651
697
func TestCatfileReader_RepeatedNextAfterEOF(t *testing.T) {
698
698
+
t.Parallel()
699
699
+
652
700
repoDir, blobs := createTestRepo(t)
653
701
ids := []plumbing.Hash{blobs["hello.txt"]}
654
702
···
684
732
// is read with byte-exact precision — no off-by-one from trailing LF
685
733
// handling, no truncation, no extra bytes.
686
734
func TestCatfileReader_LargeBlobBytePrecision(t *testing.T) {
735
735
+
t.Parallel()
736
736
+
687
737
repoDir, blobs := createTestRepo(t)
688
738
ids := []plumbing.Hash{blobs["large.bin"]}
689
739
···
732
782
// chunks (a prime number that doesn't align with any power-of-2 buffer)
733
783
// to verify no byte is lost or duplicated across read boundaries.
734
784
func TestCatfileReader_LargeBlobChunkedRead(t *testing.T) {
785
785
+
t.Parallel()
786
786
+
735
787
repoDir, blobs := createTestRepo(t)
736
788
ids := []plumbing.Hash{blobs["large.bin"]}
737
789
···
778
830
// SHA multiple times works — git cat-file --batch outputs the object
779
831
// for each request independently.
780
832
func TestCatfileReader_DuplicateSHAs(t *testing.T) {
833
833
+
t.Parallel()
834
834
+
781
835
repoDir, blobs := createTestRepo(t)
782
836
783
837
sha := blobs["hello.txt"]
+30
-27
gitindex/catfile_test.go
Reviewed
···
1
1
package gitindex
2
2
3
3
import (
4
4
+
"bytes"
4
5
"io"
5
6
"os"
6
7
"os/exec"
7
8
"path/filepath"
9
9
+
"strings"
8
10
"testing"
9
11
10
12
"github.com/go-git/go-git/v5/plumbing"
···
17
19
dir := t.TempDir()
18
20
repoDir := filepath.Join(dir, "repo")
19
21
20
20
-
script := `
21
21
-
set -e
22
22
-
git init -b main repo
23
23
-
cd repo
24
24
-
git config user.email "test@test.com"
25
25
-
git config user.name "Test"
22
22
+
runGit(t, dir, "init", "-b", "main", "repo")
26
23
27
27
-
# Normal text file
28
28
-
echo "hello world" > hello.txt
24
24
+
files := []struct {
25
25
+
name string
26
26
+
content []byte
27
27
+
}{
28
28
+
{name: "hello.txt", content: []byte("hello world\n")},
29
29
+
{name: "empty.txt"},
30
30
+
{name: "binary.bin", content: []byte{0x00, 0x01, 0x02, '\n', 'h', 'e', 'l', 'l', 'o', '\n', 'w', 'o', 'r', 'l', 'd', '\n', 0x03, 0x04}},
31
31
+
{name: "large.bin", content: bytes.Repeat([]byte("0123456789abcdef"), 4096)},
32
32
+
}
29
33
30
30
-
# Empty file
31
31
-
touch empty.txt
34
34
+
for _, file := range files {
35
35
+
if err := os.WriteFile(filepath.Join(repoDir, file.name), file.content, 0o644); err != nil {
36
36
+
t.Fatalf("WriteFile(%q): %v", file.name, err)
37
37
+
}
38
38
+
}
32
39
33
33
-
# Binary file with newlines embedded
34
34
-
printf '\x00\x01\x02\nhello\nworld\n\x03\x04' > binary.bin
35
35
-
36
36
-
# Large-ish file (64KB of data)
37
37
-
dd if=/dev/urandom bs=1024 count=64 of=large.bin 2>/dev/null
38
38
-
39
39
-
git add -A
40
40
-
git commit -m "initial"
41
41
-
`
42
42
-
cmd := exec.Command("/bin/sh", "-c", script)
43
43
-
cmd.Dir = dir
44
44
-
cmd.Stderr = os.Stderr
45
45
-
if err := cmd.Run(); err != nil {
46
46
-
t.Fatalf("create test repo: %v", err)
47
47
-
}
40
40
+
runGit(t, repoDir, "add", ".")
41
41
+
runGit(t, repoDir, "commit", "-m", "initial")
48
42
49
43
// Get blob SHAs for each file.
50
44
blobs := map[string]plumbing.Hash{}
51
51
-
for _, name := range []string{"hello.txt", "empty.txt", "binary.bin", "large.bin"} {
45
45
+
for _, file := range files {
46
46
+
name := file.name
52
47
out, err := exec.Command("git", "-C", repoDir, "rev-parse", "HEAD:"+name).Output()
53
48
if err != nil {
54
49
t.Fatalf("rev-parse %s: %v", name, err)
55
50
}
56
56
-
sha := string(out[:len(out)-1]) // trim newline
51
51
+
sha := strings.TrimSpace(string(out))
57
52
blobs[name] = plumbing.NewHash(sha)
58
53
}
59
54
···
61
56
}
62
57
63
58
func TestCatfileReader(t *testing.T) {
59
59
+
t.Parallel()
60
60
+
64
61
repoDir, blobs := createTestRepo(t)
65
62
66
63
ids := []plumbing.Hash{
···
147
144
}
148
145
149
146
func TestCatfileReader_Skip(t *testing.T) {
147
147
+
t.Parallel()
148
148
+
150
149
repoDir, blobs := createTestRepo(t)
151
150
152
151
ids := []plumbing.Hash{
···
191
190
}
192
191
193
192
func TestCatfileReader_Missing(t *testing.T) {
193
193
+
t.Parallel()
194
194
+
194
195
repoDir, blobs := createTestRepo(t)
195
196
196
197
fakeHash := plumbing.NewHash("deadbeefdeadbeefdeadbeefdeadbeefdeadbeef")
···
242
243
}
243
244
244
245
func TestCatfileReader_Excluded(t *testing.T) {
246
246
+
t.Parallel()
247
247
+
245
248
repoDir, blobs := createTestRepo(t)
246
249
247
250
ids := []plumbing.Hash{
+2
gitindex/clone_test.go
Reviewed
···
22
22
)
23
23
24
24
func TestSetRemote(t *testing.T) {
25
25
+
t.Parallel()
26
26
+
25
27
dir := t.TempDir()
26
28
27
29
script := `mkdir orig
+2
gitindex/delete_test.go
Reviewed
···
8
8
)
9
9
10
10
func TestDeleteRepos(t *testing.T) {
11
11
+
t.Parallel()
12
12
+
11
13
dir := t.TempDir()
12
14
13
15
if err := createSubmoduleRepo(dir); err != nil {
+2
gitindex/ignore_test.go
Reviewed
···
48
48
}
49
49
50
50
func TestIgnore(t *testing.T) {
51
51
+
t.Parallel()
52
52
+
51
53
dir := t.TempDir()
52
54
53
55
if err := createSourcegraphignoreRepo(dir); err != nil {
+53
-42
gitindex/index_test.go
Reviewed
···
18
18
"bytes"
19
19
"context"
20
20
"errors"
21
21
-
"fmt"
22
21
"net/url"
23
22
"os"
24
23
"os/exec"
···
41
40
)
42
41
43
42
func TestIndexEmptyRepo(t *testing.T) {
43
43
+
t.Parallel()
44
44
+
44
45
dir := t.TempDir()
45
46
46
47
cmd := exec.Command("git", "init", "-b", "master", "repo")
···
67
68
}
68
69
69
70
func TestIndexNonexistentRepo(t *testing.T) {
71
71
+
t.Parallel()
72
72
+
70
73
dir := t.TempDir()
71
74
desc := zoekt.Repository{
72
75
Name: "nonexistent",
···
88
91
}
89
92
90
93
func TestIndexTinyRepo(t *testing.T) {
94
94
+
t.Parallel()
95
95
+
91
96
// Create a repo with one file in it.
92
97
dir := t.TempDir()
93
93
-
executeCommand(t, dir, exec.Command("git", "init", "-b", "main", "repo"))
98
98
+
runGit(t, dir, "init", "-b", "main", "repo")
94
99
95
100
repoDir := filepath.Join(dir, "repo")
96
101
if err := os.WriteFile(filepath.Join(repoDir, "file1.go"), []byte("package main\n\nfunc main() {}\n"), 0644); err != nil {
97
102
t.Fatalf("WriteFile: %v", err)
98
103
}
99
99
-
executeCommand(t, repoDir, exec.Command("git", "add", "."))
100
100
-
executeCommand(t, repoDir, exec.Command("git", "commit", "-m", "initial commit"))
104
104
+
runGit(t, repoDir, "add", ".")
105
105
+
runGit(t, repoDir, "commit", "-m", "initial commit")
101
106
102
107
// Test that indexing accepts both the repo directory, and the .git subdirectory.
103
108
for _, testDir := range []string{"repo", "repo/.git"} {
···
133
138
}
134
139
135
140
func TestIndexGitRepo_Worktree(t *testing.T) {
141
141
+
t.Parallel()
142
142
+
136
143
_, worktreeDir := initGitWorktree(t, "file1.go", "package main\n\nfunc main() {}\n")
137
144
indexDir := t.TempDir()
138
145
···
166
173
}
167
174
168
175
func TestOpenRepoVariants(t *testing.T) {
176
176
+
t.Parallel()
177
177
+
169
178
repoDir, worktreeDir := initGitWorktree(t, "file1.go", "package main\n\nfunc main() {}\n")
170
179
bareDir := cloneBareRepo(t, repoDir)
171
180
···
217
226
for _, opener := range openers {
218
227
for _, tc := range paths {
219
228
t.Run(opener.name+"/"+tc.name, func(t *testing.T) {
229
229
+
t.Parallel()
230
230
+
220
231
repo := opener.open(t, tc.path)
221
232
222
233
head, err := repo.Head()
···
269
280
}
270
281
271
282
func TestCatfileFilterSpec(t *testing.T) {
283
283
+
t.Parallel()
284
284
+
272
285
for _, tc := range []struct {
273
286
name string
274
287
opts Options
···
291
304
},
292
305
} {
293
306
t.Run(tc.name, func(t *testing.T) {
307
307
+
t.Parallel()
308
308
+
294
309
if got := catfileFilterSpec(tc.opts); got != tc.want {
295
310
t.Fatalf("catfileFilterSpec() = %q, want %q", got, tc.want)
296
311
}
···
298
313
}
299
314
}
300
315
301
301
-
func executeCommand(t *testing.T, dir string, cmd *exec.Cmd) *exec.Cmd {
302
302
-
cmd.Dir = dir
303
303
-
cmd.Env = []string{
304
304
-
"GIT_CONFIG_GLOBAL=",
305
305
-
"GIT_CONFIG_SYSTEM=",
306
306
-
"GIT_COMMITTER_NAME=Kierkegaard",
307
307
-
"GIT_COMMITTER_EMAIL=soren@apache.com",
308
308
-
"GIT_AUTHOR_NAME=Kierkegaard",
309
309
-
"GIT_AUTHOR_EMAIL=soren@apache.com",
310
310
-
}
311
311
-
if err := cmd.Run(); err != nil {
312
312
-
t.Fatalf("cmd.Run: %v", err)
313
313
-
}
314
314
-
return cmd
315
315
-
}
316
316
-
317
316
func initGitWorktree(t *testing.T, fileName, content string) (string, string) {
318
317
t.Helper()
319
318
320
319
dir := t.TempDir()
321
321
-
executeCommand(t, dir, exec.Command("git", "init", "-b", "main", "repo"))
320
320
+
runGit(t, dir, "init", "-b", "main", "repo")
322
321
323
322
repoDir := filepath.Join(dir, "repo")
324
323
if err := os.WriteFile(filepath.Join(repoDir, fileName), []byte(content), 0o644); err != nil {
325
324
t.Fatalf("WriteFile: %v", err)
326
325
}
327
327
-
executeCommand(t, repoDir, exec.Command("git", "config", "remote.origin.url", "git@github.com:sourcegraph/zoekt.git"))
328
328
-
executeCommand(t, repoDir, exec.Command("git", "add", "."))
329
329
-
executeCommand(t, repoDir, exec.Command("git", "commit", "-m", "initial commit"))
326
326
+
runGit(t, repoDir, "config", "remote.origin.url", "git@github.com:sourcegraph/zoekt.git")
327
327
+
runGit(t, repoDir, "add", ".")
328
328
+
runGit(t, repoDir, "commit", "-m", "initial commit")
330
329
331
330
worktreeDir := filepath.Join(dir, "wt")
332
332
-
executeCommand(t, repoDir, exec.Command("git", "worktree", "add", "-b", "worktree-branch", worktreeDir))
331
331
+
runGit(t, repoDir, "worktree", "add", "-b", "worktree-branch", worktreeDir)
333
332
334
333
return repoDir, worktreeDir
335
334
}
···
338
337
t.Helper()
339
338
340
339
bareDir := filepath.Join(t.TempDir(), "repo.git")
341
341
-
executeCommand(t, filepath.Dir(repoDir), exec.Command("git", "clone", "--bare", repoDir, bareDir))
340
340
+
runGit(t, filepath.Dir(repoDir), "clone", "--bare", repoDir, bareDir)
342
341
343
342
return bareDir
344
343
}
345
344
346
345
func TestIndexDeltaBasic(t *testing.T) {
346
346
+
t.Parallel()
347
347
+
347
348
type branchToDocumentMap map[string][]index.Document
348
349
349
350
type step struct {
···
833
834
repositoryDir := t.TempDir()
834
835
835
836
// setup: initialize the repository and all of its branches
836
836
-
runScript(t, repositoryDir, "git init -b master")
837
837
-
runScript(t, repositoryDir, fmt.Sprintf("git config user.email %q", "you@example.com"))
838
838
-
runScript(t, repositoryDir, fmt.Sprintf("git config user.name %q", "Your Name"))
837
837
+
runGit(t, repositoryDir, "init", "-b", "master")
839
838
840
839
for _, b := range test.branches {
841
841
-
runScript(t, repositoryDir, fmt.Sprintf("git checkout -b %q", b))
842
842
-
runScript(t, repositoryDir, fmt.Sprintf("git commit --allow-empty -m %q", "empty commit"))
840
840
+
runGit(t, repositoryDir, "checkout", "-b", b)
841
841
+
runGit(t, repositoryDir, "commit", "--allow-empty", "-m", "empty commit")
843
842
}
844
843
845
844
for _, step := range test.steps {
···
849
848
850
849
hadChange := false
851
850
852
852
-
runScript(t, repositoryDir, fmt.Sprintf("git checkout %q", b))
851
851
+
runGit(t, repositoryDir, "checkout", b)
853
852
854
853
for _, d := range step.deletedDocuments[b] {
855
854
hadChange = true
···
860
859
if err != nil {
861
860
t.Fatalf("deleting file %q: %s", d.Name, err)
862
861
}
863
863
-
864
864
-
runScript(t, repositoryDir, fmt.Sprintf("git add %q", file))
865
862
}
866
863
867
864
for _, d := range step.addedDocuments[b] {
···
878
875
if err != nil {
879
876
t.Fatalf("writing file %q: %s", d.Name, err)
880
877
}
881
881
-
882
882
-
runScript(t, repositoryDir, fmt.Sprintf("git add %q", file))
883
878
}
884
879
885
880
if !hadChange {
886
881
continue
887
882
}
888
883
889
889
-
runScript(t, repositoryDir, fmt.Sprintf("git commit -m %q", step.name))
884
884
+
runGit(t, repositoryDir, "add", "-A")
885
885
+
runGit(t, repositoryDir, "commit", "-m", step.name)
890
886
}
891
887
892
888
// setup: prepare indexOptions with given overrides
···
1002
998
}
1003
999
}
1004
1000
1005
1005
-
func runScript(t *testing.T, cwd string, script string) {
1001
1001
+
func runGit(t *testing.T, cwd string, args ...string) {
1006
1002
t.Helper()
1007
1003
1008
1004
err := os.MkdirAll(cwd, 0o755)
···
1010
1006
t.Fatalf("ensuring path %q exists: %s", cwd, err)
1011
1007
}
1012
1008
1013
1013
-
cmd := exec.Command("sh", "-euxc", script)
1009
1009
+
cmd := exec.Command("git", args...)
1014
1010
cmd.Dir = cwd
1015
1015
-
cmd.Env = append([]string{"GIT_CONFIG_GLOBAL=", "GIT_CONFIG_SYSTEM="}, os.Environ()...)
1011
1011
+
cmd.Env = append(os.Environ(),
1012
1012
+
"GIT_CONFIG_GLOBAL=",
1013
1013
+
"GIT_CONFIG_SYSTEM=",
1014
1014
+
"GIT_COMMITTER_NAME=Kierkegaard",
1015
1015
+
"GIT_COMMITTER_EMAIL=soren@apache.com",
1016
1016
+
"GIT_AUTHOR_NAME=Kierkegaard",
1017
1017
+
"GIT_AUTHOR_EMAIL=soren@apache.com",
1018
1018
+
)
1016
1019
1017
1020
if out, err := cmd.CombinedOutput(); err != nil {
1018
1021
t.Fatalf("execution error: %v, output %s", err, out)
···
1020
1023
}
1021
1024
1022
1025
func TestSetTemplates_e2e(t *testing.T) {
1026
1026
+
t.Parallel()
1027
1027
+
1023
1028
repositoryDir := t.TempDir()
1024
1029
1025
1030
// setup: initialize the repository and all of its branches
1026
1026
-
runScript(t, repositoryDir, "git init -b master")
1027
1027
-
runScript(t, repositoryDir, "git config remote.origin.url git@github.com:sourcegraph/zoekt.git")
1031
1031
+
runGit(t, repositoryDir, "init", "-b", "master")
1032
1032
+
runGit(t, repositoryDir, "config", "remote.origin.url", "git@github.com:sourcegraph/zoekt.git")
1028
1033
desc := zoekt.Repository{}
1029
1034
if err := setTemplatesFromConfig(&desc, repositoryDir); err != nil {
1030
1035
t.Fatalf("setTemplatesFromConfig: %v", err)
···
1036
1041
}
1037
1042
1038
1043
func TestSetTemplates_Worktree(t *testing.T) {
1044
1044
+
t.Parallel()
1045
1045
+
1039
1046
_, worktreeDir := initGitWorktree(t, "hello.go", "package main\n")
1040
1047
desc := zoekt.Repository{}
1041
1048
···
1049
1056
}
1050
1057
1051
1058
func TestSetTemplates(t *testing.T) {
1059
1059
+
t.Parallel()
1060
1060
+
1052
1061
base := "https://example.com/repo/name"
1053
1062
version := "VERSION"
1054
1063
path := "dir/name.txt"
···
1102
1111
1103
1112
for _, tc := range cases {
1104
1113
t.Run(tc.typ, func(t *testing.T) {
1114
1114
+
t.Parallel()
1115
1115
+
1105
1116
assertOutput := func(templateText string, want string) {
1106
1117
t.Helper()
1107
1118
+19
gitindex/main_test.go
Reviewed
···
1
1
+
package gitindex
2
2
+
3
3
+
import (
4
4
+
"flag"
5
5
+
"io"
6
6
+
"log"
7
7
+
"os"
8
8
+
"testing"
9
9
+
)
10
10
+
11
11
+
func TestMain(m *testing.M) {
12
12
+
flag.Parse()
13
13
+
14
14
+
if !testing.Verbose() {
15
15
+
log.SetOutput(io.Discard)
16
16
+
}
17
17
+
18
18
+
os.Exit(m.Run())
19
19
+
}
+4
gitindex/repocache_test.go
Reviewed
···
22
22
)
23
23
24
24
func TestListReposNonExistent(t *testing.T) {
25
25
+
t.Parallel()
26
26
+
25
27
u, err := url.Parse("https://gerrit.googlesource.com/")
26
28
if err != nil {
27
29
t.Fatalf("url.Parse: %v", err)
···
34
36
}
35
37
36
38
func TestListRepos(t *testing.T) {
39
39
+
t.Parallel()
40
40
+
37
41
dir := t.TempDir()
38
42
39
43
if err := createSubmoduleRepo(dir); err != nil {
+2
gitindex/submodule_test.go
Reviewed
···
20
20
)
21
21
22
22
func TestParseGitModules(t *testing.T) {
23
23
+
t.Parallel()
24
24
+
23
25
cases := []struct {
24
26
data string
25
27
want map[string]*SubmoduleEntry
+22
gitindex/tree_test.go
Reviewed
···
106
106
}
107
107
108
108
func TestFindGitRepos(t *testing.T) {
109
109
+
t.Parallel()
110
110
+
109
111
dir := t.TempDir()
110
112
111
113
if err := createSubmoduleRepo(dir); err != nil {
···
141
143
}
142
144
143
145
func TestCollectFiles(t *testing.T) {
146
146
+
t.Parallel()
147
147
+
144
148
dir := t.TempDir()
145
149
146
150
if err := createSubmoduleRepo(dir); err != nil {
···
195
199
}
196
200
197
201
func TestSubmoduleIndex(t *testing.T) {
202
202
+
t.Parallel()
203
203
+
198
204
dir := t.TempDir()
199
205
200
206
if err := createSubmoduleRepo(dir); err != nil {
···
259
265
}
260
266
261
267
func TestSubmoduleIndexWithoutRepocache(t *testing.T) {
268
268
+
t.Parallel()
269
269
+
262
270
dir := t.TempDir()
263
271
264
272
if err := createSubmoduleRepo(dir); err != nil {
···
363
371
}
364
372
365
373
func TestSearchSymlinkByContent(t *testing.T) {
374
374
+
t.Parallel()
375
375
+
366
376
dir := t.TempDir()
367
377
368
378
if err := createSymlinkRepo(dir); err != nil {
···
420
430
}
421
431
422
432
func TestAllowMissingBranch(t *testing.T) {
433
433
+
t.Parallel()
434
434
+
423
435
dir := t.TempDir()
424
436
425
437
if err := createSubmoduleRepo(dir); err != nil {
···
486
498
}
487
499
488
500
func TestBranchWildcard(t *testing.T) {
501
501
+
t.Parallel()
502
502
+
489
503
dir := t.TempDir()
490
504
491
505
if err := createMultibranchRepo(dir); err != nil {
···
532
546
}
533
547
534
548
func TestSkipSubmodules(t *testing.T) {
549
549
+
t.Parallel()
550
550
+
535
551
dir := t.TempDir()
536
552
537
553
if err := createSubmoduleRepo(dir); err != nil {
···
564
580
}
565
581
566
582
func TestFullAndShortRefNames(t *testing.T) {
583
583
+
t.Parallel()
584
584
+
567
585
dir := t.TempDir()
568
586
569
587
if err := createMultibranchRepo(dir); err != nil {
···
609
627
}
610
628
611
629
func TestUniq(t *testing.T) {
630
630
+
t.Parallel()
631
631
+
612
632
in := []string{"a", "b", "b", "c", "c"}
613
633
want := []string{"a", "b", "c"}
614
634
got := uniq(in)
···
618
638
}
619
639
620
640
func TestLatestCommit(t *testing.T) {
641
641
+
t.Parallel()
642
642
+
621
643
dir := t.TempDir()
622
644
indexDir := t.TempDir()
623
645