Skip to content

Commit 23b8ffe

Browse files
authored
feat: add ability to checkout a repo at a certain commit (#2555)
This is needed for the `update-image` logic -- we plan to checkout the protos repo at the previously generated commit. Towards #2546
1 parent f2a51b6 commit 23b8ffe

File tree

2 files changed

+69
-0
lines changed

2 files changed

+69
-0
lines changed

internal/gitrepo/gitrepo.go

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ type Repository interface {
5454
Restore(paths []string) error
5555
CleanUntracked(paths []string) error
5656
pushRefSpec(refSpec string) error
57+
Checkout(commitHash string) error
5758
}
5859

5960
const RootPath = "."
@@ -651,3 +652,14 @@ func (r *LocalRepository) CleanUntracked(paths []string) error {
651652

652653
return nil
653654
}
655+
656+
// Checkout checks out the local repository at the provided git SHA.
657+
func (r *LocalRepository) Checkout(commitSha string) error {
658+
worktree, err := r.repo.Worktree()
659+
if err != nil {
660+
return err
661+
}
662+
return worktree.Checkout(&git.CheckoutOptions{
663+
Hash: plumbing.NewHash(commitSha),
664+
})
665+
}

system_test.go

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import (
2020
"log/slog"
2121
"os"
2222
"path"
23+
"path/filepath"
2324
"strings"
2425
"testing"
2526
"time"
@@ -438,3 +439,59 @@ func TestCreateRelease(t *testing.T) {
438439
t.Fatalf("release body mismatch (-want + got):\n%s", diff)
439440
}
440441
}
442+
443+
func TestGitCheckout(t *testing.T) {
444+
t.Parallel()
445+
for _, test := range []struct {
446+
name string
447+
sha string
448+
want string
449+
wantErr bool
450+
}{
451+
{
452+
name: "known SHA",
453+
// v0.3.0 release
454+
sha: "2e230f309505db42ce8becb0f3946d608a11a61c",
455+
want: "chore: librarian release pull request: 20250925T070206Z (#2356)",
456+
},
457+
{
458+
name: "unknown SHA",
459+
sha: "should not exist",
460+
wantErr: true,
461+
},
462+
} {
463+
t.Run(test.name, func(t *testing.T) {
464+
t.Parallel()
465+
repo, err := gitrepo.NewRepository(&gitrepo.RepositoryOptions{
466+
Dir: filepath.Join(t.TempDir(), "librarian"),
467+
MaybeClone: true,
468+
RemoteURL: "https://github.com/googleapis/librarian",
469+
RemoteBranch: "main",
470+
})
471+
if err != nil {
472+
t.Fatalf("error cloning repository, %v", err)
473+
}
474+
475+
err = repo.Checkout(test.sha)
476+
477+
if test.wantErr {
478+
if err == nil {
479+
t.Fatal("Checkout() expected to return error")
480+
}
481+
return
482+
}
483+
484+
if err != nil {
485+
t.Fatalf("Checkout() unexpected error: %v", err)
486+
}
487+
488+
headSha, err := repo.HeadHash()
489+
if diff := cmp.Diff(test.sha, headSha); diff != "" {
490+
t.Fatalf("Checkout() mismatch (-want +got):\n%s", diff)
491+
}
492+
if err != nil {
493+
t.Fatalf("Checkout() unexpected error fetching HeadHash: %v", err)
494+
}
495+
})
496+
}
497+
}

0 commit comments

Comments
 (0)