Skip to content

Commit e0fdeda

Browse files
committed
Query and use the repository.branch when defined in spec
1 parent ac7ec26 commit e0fdeda

File tree

6 files changed

+158
-18
lines changed

6 files changed

+158
-18
lines changed

cmd/src/campaigns_common.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -232,6 +232,10 @@ func campaignsExecute(ctx context.Context, out *output.Output, svc *campaigns.Se
232232
campaignsCompletePending(pending, "Resolved repositories")
233233
}
234234

235+
for _, r := range repos {
236+
fmt.Printf("Name=%s, BaseRef()=%s, Rev()=%s\n", r.Name, r.BaseRef(), r.Rev())
237+
}
238+
235239
p := newCampaignProgressPrinter(out, *verbose, opts.Parallelism)
236240
specs, err := svc.ExecuteCampaignSpec(ctx, repos, executor, campaignSpec, p.PrintStatuses)
237241
if err != nil {

internal/campaigns/archive_fetcher.go

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -120,12 +120,11 @@ func fetchRepositoryArchive(ctx context.Context, client api.Client, repo *graphq
120120
}
121121

122122
func repositoryZipArchivePath(repo *graphql.Repository) string {
123-
return path.Join("", repo.Name+"@"+repo.DefaultBranch.Name, "-", "raw")
123+
return path.Join("", repo.Name+"@"+repo.BaseRef(), "-", "raw")
124124
}
125125

126126
func localRepositoryZipArchivePath(dir string, repo *graphql.Repository) string {
127-
ref := repo.DefaultBranch.Target.OID
128-
return filepath.Join(dir, fmt.Sprintf("%s-%s.zip", repo.Slug(), ref))
127+
return filepath.Join(dir, fmt.Sprintf("%s-%s.zip", repo.Slug(), repo.Rev()))
129128
}
130129

131130
func unzip(zipFile, dest string) error {

internal/campaigns/archive_fetcher_test.go

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ func TestWorkspaceCreator_Create(t *testing.T) {
3030
repo := &graphql.Repository{
3131
ID: "src-cli",
3232
Name: "github.com/sourcegraph/src-cli",
33-
DefaultBranch: &graphql.Branch{Name: "main", Target: struct{ OID string }{OID: "d34db33f"}},
33+
DefaultBranch: &graphql.Branch{Name: "main", Target: graphql.Target{OID: "d34db33f"}},
3434
}
3535

3636
archive := mockRepoArchive{
@@ -156,6 +156,48 @@ func TestWorkspaceCreator_Create(t *testing.T) {
156156
t.Fatalf("zip file in temp dir was not cleaned up")
157157
}
158158
})
159+
160+
t.Run("non-default branch", func(t *testing.T) {
161+
otherBranchOID := "f00b4r"
162+
repo := &graphql.Repository{
163+
ID: "src-cli-with-non-main-branch",
164+
Name: "github.com/sourcegraph/src-cli",
165+
DefaultBranch: &graphql.Branch{Name: "main", Target: graphql.Target{OID: "d34db33f"}},
166+
Branches: struct {
167+
Nodes []*graphql.Branch
168+
}{
169+
Nodes: []*graphql.Branch{
170+
&graphql.Branch{Name: "other-branch", Target: graphql.Target{OID: otherBranchOID}},
171+
},
172+
},
173+
}
174+
175+
archive := mockRepoArchive{repo: repo, files: map[string]string{}}
176+
177+
ts := httptest.NewServer(newZipArchivesMux(t, nil, archive))
178+
defer ts.Close()
179+
180+
var clientBuffer bytes.Buffer
181+
client := api.NewClient(api.ClientOpts{Endpoint: ts.URL, Out: &clientBuffer})
182+
183+
testTempDir := workspaceTmpDir(t)
184+
185+
creator := &WorkspaceCreator{dir: testTempDir, client: client}
186+
187+
_, err := creator.Create(context.Background(), repo)
188+
if err != nil {
189+
t.Fatalf("unexpected error: %s", err)
190+
}
191+
192+
wantZipFile := "github.1485827954.workers.dev-sourcegraph-src-cli-" + otherBranchOID + ".zip"
193+
ok, err := dirContains(creator.dir, wantZipFile)
194+
if err != nil {
195+
t.Fatal(err)
196+
}
197+
if !ok {
198+
t.Fatalf("temp dir doesnt contain zip file")
199+
}
200+
})
159201
}
160202

161203
func TestMkdirAll(t *testing.T) {

internal/campaigns/executor_test.go

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,14 +37,23 @@ func TestExecutor_Integration(t *testing.T) {
3737
srcCLIRepo := &graphql.Repository{
3838
ID: "src-cli",
3939
Name: "github.com/sourcegraph/src-cli",
40-
DefaultBranch: &graphql.Branch{Name: "main", Target: struct{ OID string }{OID: "d34db33f"}},
40+
DefaultBranch: &graphql.Branch{Name: "main", Target: graphql.Target{OID: "d34db33f"}},
4141
}
4242
sourcegraphRepo := &graphql.Repository{
4343
ID: "sourcegraph",
4444
Name: "github.com/sourcegraph/sourcegraph",
4545
DefaultBranch: &graphql.Branch{
4646
Name: "main",
47-
Target: struct{ OID string }{OID: "f00b4r3r"},
47+
Target: graphql.Target{OID: "f00b4r3r"},
48+
},
49+
50+
Branches: graphql.Branches{
51+
Nodes: []*graphql.Branch{
52+
&graphql.Branch{
53+
Name: "other-branch",
54+
Target: graphql.Target{OID: "0therbr4nch"},
55+
},
56+
},
4857
},
4958
}
5059

@@ -220,7 +229,7 @@ func newZipArchivesMux(t *testing.T, callback http.HandlerFunc, archives ...mock
220229

221230
for _, archive := range archives {
222231
files := archive.files
223-
path := fmt.Sprintf("/%s@%s/-/raw", archive.repo.Name, archive.repo.DefaultBranch.Name)
232+
path := fmt.Sprintf("/%s@%s/-/raw", archive.repo.Name, archive.repo.BaseRef())
224233

225234
downloadName := filepath.Base(archive.repo.Name)
226235
mediaType := mime.FormatMediaType("Attachment", map[string]string{

internal/campaigns/graphql/repository.go

Lines changed: 49 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,26 +22,73 @@ fragment repositoryFields on Repository {
2222
}
2323
`
2424

25+
const RepositoryWithBranchFragment = `
26+
fragment repositoryFieldsWithBranch on Repository {
27+
id
28+
name
29+
url
30+
externalRepository {
31+
serviceType
32+
}
33+
defaultBranch {
34+
name
35+
target {
36+
oid
37+
}
38+
}
39+
branches(query: $branch, first: 1) @include(if:$queryBranch){
40+
nodes {
41+
name
42+
target {
43+
oid
44+
}
45+
}
46+
}
47+
}
48+
`
49+
50+
type Target struct {
51+
OID string
52+
}
53+
2554
type Branch struct {
2655
Name string
27-
Target struct{ OID string }
56+
Target Target
57+
}
58+
59+
type Branches struct {
60+
Nodes []*Branch
2861
}
2962

3063
type Repository struct {
3164
ID string
3265
Name string
3366
URL string
3467
ExternalRepository struct{ ServiceType string }
35-
DefaultBranch *Branch
68+
69+
DefaultBranch *Branch
70+
Branches Branches
3671

3772
FileMatches map[string]bool
3873
}
3974

75+
func (r *Repository) HasBranch() bool {
76+
return r.DefaultBranch != nil || len(r.Branches.Nodes) != 0
77+
}
78+
4079
func (r *Repository) BaseRef() string {
80+
if len(r.Branches.Nodes) != 0 {
81+
return r.Branches.Nodes[0].Name
82+
}
83+
4184
return r.DefaultBranch.Name
4285
}
4386

4487
func (r *Repository) Rev() string {
88+
if len(r.Branches.Nodes) != 0 {
89+
return r.Branches.Nodes[0].Target.OID
90+
}
91+
4592
return r.DefaultBranch.Target.OID
4693
}
4794

internal/campaigns/service.go

Lines changed: 48 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -363,8 +363,7 @@ func (svc *Service) ResolveNamespace(ctx context.Context, namespace string) (str
363363
}
364364

365365
func (svc *Service) ResolveRepositories(ctx context.Context, spec *CampaignSpec) ([]*graphql.Repository, error) {
366-
final := []*graphql.Repository{}
367-
seen := map[string]struct{}{}
366+
seen := map[string]*graphql.Repository{}
368367
unsupported := UnsupportedRepoSet{}
369368

370369
// TODO: this could be trivially parallelised in the future.
@@ -375,11 +374,12 @@ func (svc *Service) ResolveRepositories(ctx context.Context, spec *CampaignSpec)
375374
}
376375

377376
for _, repo := range repos {
378-
if _, ok := seen[repo.ID]; !ok {
379-
if repo.DefaultBranch == nil {
380-
continue
381-
}
382-
seen[repo.ID] = struct{}{}
377+
if !repo.HasBranch() {
378+
continue
379+
}
380+
381+
if other, ok := seen[repo.ID]; !ok {
382+
seen[repo.ID] = repo
383383
switch st := strings.ToLower(repo.ExternalRepository.ServiceType); st {
384384
case "github", "gitlab", "bitbucketserver":
385385
default:
@@ -388,12 +388,19 @@ func (svc *Service) ResolveRepositories(ctx context.Context, spec *CampaignSpec)
388388
continue
389389
}
390390
}
391-
392-
final = append(final, repo)
391+
} else {
392+
// If we've already seen this repository, we overwrite the
393+
// Branches field with the latest value we have
394+
other.Branches = repo.Branches
393395
}
394396
}
395397
}
396398

399+
final := make([]*graphql.Repository, 0, len(seen))
400+
for _, repo := range seen {
401+
final = append(final, repo)
402+
}
403+
397404
if unsupported.hasUnsupported() && !svc.allowUnsupported {
398405
return final, unsupported
399406
}
@@ -404,6 +411,12 @@ func (svc *Service) ResolveRepositories(ctx context.Context, spec *CampaignSpec)
404411
func (svc *Service) ResolveRepositoriesOn(ctx context.Context, on *OnQueryOrRepository) ([]*graphql.Repository, error) {
405412
if on.RepositoriesMatchingQuery != "" {
406413
return svc.resolveRepositorySearch(ctx, on.RepositoriesMatchingQuery)
414+
} else if on.Repository != "" && on.Branch != "" {
415+
repo, err := svc.resolveRepositoryNameAndBranch(ctx, on.Repository, on.Branch)
416+
if err != nil {
417+
return nil, err
418+
}
419+
return []*graphql.Repository{repo}, nil
407420
} else if on.Repository != "" {
408421
repo, err := svc.resolveRepositoryName(ctx, on.Repository)
409422
if err != nil {
@@ -438,6 +451,32 @@ func (svc *Service) resolveRepositoryName(ctx context.Context, name string) (*gr
438451
return result.Repository, nil
439452
}
440453

454+
const repositoryNameAndBranchQuery = `
455+
query Repository($name: String!, $queryBranch: Boolean!, $branch: String!) {
456+
repository(name: $name) {
457+
...repositoryFieldsWithBranch
458+
}
459+
}
460+
` + graphql.RepositoryWithBranchFragment
461+
462+
func (svc *Service) resolveRepositoryNameAndBranch(ctx context.Context, name, branch string) (*graphql.Repository, error) {
463+
var result struct{ Repository *graphql.Repository }
464+
if ok, err := svc.client.NewRequest(repositoryNameAndBranchQuery, map[string]interface{}{
465+
"name": name,
466+
"queryBranch": true,
467+
"branch": branch,
468+
}).Do(ctx, &result); err != nil || !ok {
469+
return nil, err
470+
}
471+
if result.Repository == nil {
472+
return nil, errors.New("no repository found")
473+
}
474+
if len(result.Repository.Branches.Nodes) == 0 {
475+
return nil, fmt.Errorf("no branch matching %q found for repository %s", branch, name)
476+
}
477+
return result.Repository, nil
478+
}
479+
441480
// TODO: search result alerts.
442481
const repositorySearchQuery = `
443482
query ChangesetRepos(

0 commit comments

Comments
 (0)