Add materialized object handling examples · Entire
Add materialized object handling examples
359d4e9→main · Soph · 3mo ago · 1 file · +132 added/-0 removed
Sessions
c00c3abb8037 View transcript
Changes
1
internal/strategy/materialized
materialized_test.go +132
package materialized
import (
"context"
"testing"
"github.com/go-git/go-git/v6/plumbing"
"github.com/go-git/go-git/v6/plumbing/object"
"github.com/go-git/go-git/v6/plumbing/storer"
"github.com/soph/git-sync/internal/convert"
"github.com/soph/git-sync/internal/gitproto"
"github.com/soph/git-sync/internal/planner"
"github.com/soph/git-sync/internal/syncertest"
)
func TestPlansToPushPlans(t *testing.T) {
// ... (function contents)
}
func TestCollectObjectClosureForBranchUpdateExample(t *testing.T) {
repo, fs := syncertest.NewMemoryRepo(t)
syncertest.MakeCommits(t, repo, fs, 1)
head, err := repo.Reference(plumbing.NewBranchReferenceName("master"), true)
if err != nil {
t.Fatalf("resolve head: %v", err)
}
exec := executor{
params: Params{
Store: repo.Storer,
PushPlans: []planner.BranchPlan{{
TargetRef: plumbing.NewBranchReferenceName("master"),
SourceHash: head.Hash(),
Action: planner.ActionCreate,
Kind: planner.RefKindBranch,
},},
},
}
hashes, err := exec.collectObjectClosure()
if err != nil {
t.Fatalf("collectObjectClosure: %v", err)
}
if len(hashes) < 3 {
t.Fatalf("expected commit/tree/blob closure, got %d objects: %v", len(hashes), hashes)
}
if !containsHash(hashes, head.Hash()) {
t.Fatalf("expected closure to include commit %s", head.Hash())
}
}
func TestCollectObjectClosureStopsAtTargetHaveExample(t *testing.T) {
repo, fs := syncertest.NewMemoryRepo(t)
syncertest.MakeCommits(t, repo, fs, 2)
head, err := repo.Reference(plumbing.NewBranchReferenceName("master"), true)
if err != nil {
t.Fatalf("resolve head: %v", err)
}
headCommit, err := object.GetCommit(repo.Storer, head.Hash())
if err != nil {
t.Fatalf("load head commit: %v", err)
}
if len(headCommit.ParentHashes) != 1 {
t.Fatalf("expected single-parent history, got %d parents", len(headCommit.ParentHashes))
}
parent := headCommit.ParentHashes[0]
exec := executor{
params: Params{
Store: repo.Storer,
TargetRefs: map[plumbing.ReferenceName]plumbing.Hash{
plumbing.NewBranchReferenceName("master"): parent,
},
PushPlans: []planner.BranchPlan{{
TargetRef: plumbing.NewBranchReferenceName("master"),
TargetHash: parent,
SourceHash: head.Hash(),
Action: planner.ActionUpdate,
Kind: planner.RefKindBranch,
},},
},
}
hashes, err := exec.collectObjectClosure()
if err != nil {
t.Fatalf("collectObjectClosure: %v", err)
}
if len(hashes) == 0 {
t.Fatal("expected new objects for branch update")
}
if containsHash(hashes, parent) {
t.Fatalf("expected closure to stop at target have %s, got %v", parent, hashes)
}
if !containsHash(hashes, head.Hash()) {
t.Fatalf("expected closure to include new tip %s", head.Hash())
}
}
func TestExecuteDeleteOnlyIsRefOnlyExample(t *testing.T) {
var gotCmds []gitproto.PushCommand
var gotHashes []plumbing.Hash
err := Execute(context.Background(), Params{
PushPlans: []planner.BranchPlan{{
TargetRef: plumbing.NewBranchReferenceName("old"),
TargetHash: plumbing.NewHash("aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"),
Action: planner.ActionDelete,
Kind: planner.RefKindBranch,
}},
TargetPusher: fakeTargetPusher{
pushObjects: func(_ context.Context, cmds []gitproto.PushCommand, _ storer.Storer, hashes []plumbing.Hash) error {
gotCmds = append([]gitproto.PushCommand(nil), cmds...)
gotHashes = append([]plumbing.Hash(nil), hashes...)
return nil
},
},
})
if err != nil {
t.Fatalf("Execute() error = %v", err)
}
if len(gotCmds) != 1 || !gotCmds[0].Delete {
t.Fatalf("expected single delete command, got %+v", gotCmds)
}
if len(gotHashes) != 0 {
t.Fatalf("expected delete-only materialized push to need no objects, got %v", gotHashes)
}
}
type fakeTargetPusher struct {
pushObjects func(context.Context, []gitproto.PushCommand, storer.Storer, []plumbing.Hash) error
}
func (f fakeTargetPusher) PushObjects(ctx context.Context, cmds []gitproto.PushCommand, store storer.Storer, hashes []plumbing.Hash) error {
return f.pushObjects(ctx, cmds, store, hashes)
}
func containsHash(hashes []plumbing.Hash, want plumbing.Hash) bool {
for _, h := range hashes {
if h == want {
return true
}
}
return false
}