Files
lazygit/pkg/gui/branchstack/branchstack_test.go
T
Stefan HallerandClaude Opus 5.5 633bedf4fd Pass only the branch name to BranchesBelow
The commits panel will need to call it. All it knows is the name of the
checked-out branch.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-11-08 12:43:36 +01:00

150 lines
4.9 KiB
Go

package branchstack
import (
"testing"
"github.com/jesseduffield/lazygit/pkg/commands/models"
"github.com/jesseduffield/lazygit/pkg/utils"
"github.com/samber/lo"
"github.com/stefanhaller/git-todo-parser/todo"
"github.com/stretchr/testify/assert"
)
func TestBranchesBelow(t *testing.T) {
hashPool := &utils.StringPool{}
commit := func(hash string, status models.CommitStatus, parents ...string) *models.Commit {
return models.NewCommit(hashPool, models.NewCommitOpts{Hash: hash, Status: status, Parents: parents})
}
todoCommit := func(hash string) *models.Commit {
return models.NewCommit(hashPool, models.NewCommitOpts{Hash: hash, Action: todo.Pick, Status: models.StatusRebasing})
}
branch := func(name string, tip string) *models.Branch {
return &models.Branch{Name: name, CommitHash: tip}
}
current := branch("current", "c3")
mainBranches := []string{"master", "main"}
scenarios := []struct {
testName string
commits []*models.Commit
branches []*models.Branch
// The branch to look for branches below; the one called "current" if nil
current *models.Branch
expected []string
}{
{
testName: "stack of branches, closest to the current one first",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed),
commit("c2", models.StatusPushed),
commit("c1", models.StatusUnpushed),
commit("m1", models.StatusMerged),
},
branches: []*models.Branch{current, branch("first", "c1"), branch("second", "c2"), branch("master", "m1")},
expected: []string{"second", "first"},
},
{
testName: "branch pointing at the same commit as the current one",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed),
commit("m1", models.StatusMerged),
},
branches: []*models.Branch{current, branch("twin", "c3")},
expected: []string{"twin"},
},
{
testName: "several branches pointing at one commit keep their order",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed),
commit("c1", models.StatusUnpushed),
},
branches: []*models.Branch{current, branch("one", "c1"), branch("two", "c1")},
expected: []string{"one", "two"},
},
{
testName: "main branches are left out even if their tip isn't merged",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed),
commit("c1", models.StatusUnpushed),
},
branches: []*models.Branch{current, branch("main", "c1")},
expected: []string{},
},
{
testName: "nothing is stacked below a main branch",
commits: []*models.Commit{
commit("m2", models.StatusUnpushed, "m1", "w1"),
commit("w1", models.StatusUnpushed, "m1"),
commit("m1", models.StatusMerged),
},
branches: []*models.Branch{branch("master", "m2"), branch("wip", "w1")},
current: branch("master", "m2"),
expected: []string{},
},
{
testName: "branches merged into a local main branch below the current one are left out",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed, "c2"),
commit("c2", models.StatusUnpushed, "m2"),
commit("m2", models.StatusUnpushed, "m1", "w1"),
commit("w1", models.StatusUnpushed, "m1"),
commit("m1", models.StatusMerged),
},
branches: []*models.Branch{current, branch("first", "c2"), branch("master", "m2"), branch("wip", "w1")},
expected: []string{"first"},
},
{
testName: "branches merged into a local main branch that was merged into the current one are left out",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed, "c2", "m2"),
commit("m2", models.StatusUnpushed, "m1", "w1"),
commit("w1", models.StatusUnpushed, "m1"),
commit("c2", models.StatusUnpushed, "m1"),
commit("m1", models.StatusMerged),
},
branches: []*models.Branch{current, branch("first", "c2"), branch("master", "m2"), branch("wip", "w1")},
expected: []string{"first"},
},
{
testName: "branches whose tip is merged are left out",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed),
commit("m1", models.StatusMerged),
commit("m0", models.StatusMerged),
},
branches: []*models.Branch{current, branch("old", "m0"), branch("master", "m1")},
expected: []string{},
},
{
testName: "branches whose tip is not among the commits are left out",
commits: []*models.Commit{
commit("c3", models.StatusUnpushed),
},
branches: []*models.Branch{current, branch("sibling", "s1")},
expected: []string{},
},
{
testName: "todo commits of a rebase don't count",
commits: []*models.Commit{
todoCommit("t1"),
commit("c3", models.StatusUnpushed),
},
branches: []*models.Branch{current, branch("other", "t1")},
expected: []string{},
},
}
for _, s := range scenarios {
t.Run(s.testName, func(t *testing.T) {
branch := current
if s.current != nil {
branch = s.current
}
result := BranchesBelow(s.commits, s.branches, branch.Name, mainBranches)
names := lo.Map(result, func(b *models.Branch, _ int) string { return b.Name })
assert.Equal(t, s.expected, names)
})
}
}