From e1fba517f4c28c3027feaea73561045264f1f591 Mon Sep 17 00:00:00 2001 From: Gergely Nagy Date: Sun, 21 Jan 2024 18:03:04 +0100 Subject: [PATCH] Don't consider orphan branches as recently pushed When displaying the recently pushed branches banner, don't display branches that have no common history with the default branch. These branches are usually not meant to be merged, so the banner is just noise in this case. Signed-off-by: Gergely Nagy --- routers/web/repo/view.go | 38 +++++++++++++++++- tests/integration/pull_create_test.go | 58 +++++++++++++++++++++++++++ 2 files changed, 95 insertions(+), 1 deletion(-) diff --git a/routers/web/repo/view.go b/routers/web/repo/view.go index 253c6cd4ef..48fcf40695 100644 --- a/routers/web/repo/view.go +++ b/routers/web/repo/view.go @@ -1035,7 +1035,43 @@ func renderCode(ctx *context.Context) { } } - ctx.Data["RecentlyPushedNewBranches"] = branches + // Filter out branches that have no relation to the default branch of + // the repository. + var filteredBranches []*git_model.Branch + for _, branch := range branches { + repo, err := branch.GetRepo(ctx) + if err != nil { + continue + } + gitRepo, err := git.OpenRepository(ctx, repo.RepoPath()) + if err != nil { + continue + } + defer gitRepo.Close() + head, err := gitRepo.GetCommit(branch.CommitID) + if err != nil { + continue + } + defaultBranch, err := gitRepo.GetDefaultBranch() + if err != nil { + continue + } + defaultBranchHead, err := gitRepo.GetCommit(defaultBranch) + if err != nil { + continue + } + + hasMergeBase, err := head.HasPreviousCommit(defaultBranchHead.ID) + if err != nil { + continue + } + + if hasMergeBase { + filteredBranches = append(filteredBranches, branch) + } + } + + ctx.Data["RecentlyPushedNewBranches"] = filteredBranches } PostRecentBranchCheck: diff --git a/tests/integration/pull_create_test.go b/tests/integration/pull_create_test.go index fcdfd029cd..803a7d83ff 100644 --- a/tests/integration/pull_create_test.go +++ b/tests/integration/pull_create_test.go @@ -16,8 +16,13 @@ import ( "code.gitea.io/gitea/models/db" repo_model "code.gitea.io/gitea/models/repo" unit_model "code.gitea.io/gitea/models/unit" + "code.gitea.io/gitea/models/unittest" + user_model "code.gitea.io/gitea/models/user" + "code.gitea.io/gitea/modules/git" + "code.gitea.io/gitea/modules/graceful" "code.gitea.io/gitea/modules/test" repo_service "code.gitea.io/gitea/services/repository" + files_service "code.gitea.io/gitea/services/repository/files" "code.gitea.io/gitea/tests" "github.com/stretchr/testify/assert" @@ -331,5 +336,58 @@ func TestRecentlyPushed(t *testing.T) { // PR link compares against the correct rep, and qualified branch name assert.Equal(t, "/user2/repo1/compare/master...user1/repo1:recent-push", forkPRLink) }) + + t.Run("unrelated branches are not shown", func(t *testing.T) { + defer tests.PrintCurrentTest(t)() + + adminUser := unittest.AssertExistsAndLoadBean(t, &user_model.User{IsAdmin: true}) + + // Create a new branch with no relation to the default branch. + // 1. Create a new Tree object + cmd := git.NewCommand(db.DefaultContext, "write-tree") + treeID, _, gitErr := cmd.RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) + assert.NoError(t, gitErr) + treeID = strings.TrimSpace(treeID) + // 2. Create a new (empty) commit + cmd = git.NewCommand(db.DefaultContext, "commit-tree", "-m", "Initial orphan commit").AddDynamicArguments(treeID) + commitID, _, gitErr := cmd.RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) + assert.NoError(t, gitErr) + commitID = strings.TrimSpace(commitID) + // 3. Create a new ref pointing to the orphaned commit + cmd = git.NewCommand(db.DefaultContext, "update-ref", "refs/heads/orphan1").AddDynamicArguments(commitID) + _, _, gitErr = cmd.RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) + assert.NoError(t, gitErr) + // 4. Sync the git repo to the database + syncErr := repo_service.AddAllRepoBranchesToSyncQueue(graceful.GetManager().ShutdownContext(), adminUser.ID) + assert.NoError(t, syncErr) + // 5. Add a fresh commit, so that FindRecentlyPushedBranches has + // something to find. + owner := unittest.AssertExistsAndLoadBean(t, &user_model.User{Name: "user1"}) + changeResp, err := files_service.ChangeRepoFiles(git.DefaultContext, repo, owner, + &files_service.ChangeRepoFilesOptions{ + Files: []*files_service.ChangeRepoFile{ + { + Operation: "create", + TreePath: "README.md", + ContentReader: strings.NewReader("a readme file"), + }, + }, + Message: "Add README.md", + OldBranch: "orphan1", + NewBranch: "orphan1", + }) + assert.NoError(t, err) + assert.NotEmpty(t, changeResp) + + // Check that we only have 1 message on the main repo, the orphaned + // one is not shown. + req := NewRequest(t, "GET", "/user1/repo1") + resp := session.MakeRequest(t, req, http.StatusOK) + htmlDoc := NewHTMLParser(t, resp.Body) + + htmlDoc.AssertElement(t, ".ui.message", true) + link, _ := htmlDoc.Find(".ui.message a[href*='/src/branch/']").Attr("href") + assert.Equal(t, "/user1/repo1/src/branch/recent-push", link) + }) }) }