fix bug about can't skip commits base on base branch (#11555)

* fix bug about can't skip commits base on base branch

Signed-off-by: a1012112796 <1012112796@qq.com>

* Update modules/git/commit.go

Co-authored-by: Lauris BH <lauris@nix.lv>

* Update models/issue_comment.go

Co-authored-by: Lauris BH <lauris@nix.lv>

* fix lint

Co-authored-by: Lauris BH <lauris@nix.lv>
This commit is contained in:
赵智超 2020-06-25 03:40:52 +08:00 committed by GitHub
parent 8aef7aefd0
commit ae20de7771
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 98 additions and 12 deletions

View file

@ -1157,12 +1157,11 @@ func getCommitIDsFromRepo(repo *Repository, oldCommitID, newCommitID, baseBranch
return nil, false, err return nil, false, err
} }
oldCommitBranch, err := oldCommit.GetBranchName() if err = oldCommit.LoadBranchName(); err != nil {
if err != nil {
return nil, false, err return nil, false, err
} }
if oldCommitBranch == "" { if len(oldCommit.Branch) == 0 {
commitIDs = make([]string, 2) commitIDs = make([]string, 2)
commitIDs[0] = oldCommitID commitIDs[0] = oldCommitID
commitIDs[1] = newCommitID commitIDs[1] = newCommitID
@ -1175,25 +1174,102 @@ func getCommitIDsFromRepo(repo *Repository, oldCommitID, newCommitID, baseBranch
return nil, false, err return nil, false, err
} }
var commits *list.List var (
commits *list.List
commitChecks map[string]commitBranchCheckItem
)
commits, err = newCommit.CommitsBeforeUntil(oldCommitID) commits, err = newCommit.CommitsBeforeUntil(oldCommitID)
if err != nil { if err != nil {
return nil, false, err return nil, false, err
} }
commitIDs = make([]string, 0, commits.Len()) commitIDs = make([]string, 0, commits.Len())
commitChecks = make(map[string]commitBranchCheckItem)
for e := commits.Back(); e != nil; e = e.Prev() { for e := commits.Front(); e != nil; e = e.Next() {
commit := e.Value.(*git.Commit) commitChecks[e.Value.(*git.Commit).ID.String()] = commitBranchCheckItem{
commitBranch, err := commit.GetBranchName() Commit: e.Value.(*git.Commit),
if err != nil { Checked: false,
return nil, false, err }
} }
if commitBranch != baseBranch { if err = commitBranchCheck(gitRepo, newCommit, oldCommitID, baseBranch, commitChecks); err != nil {
commitIDs = append(commitIDs, commit.ID.String()) return
}
for e := commits.Back(); e != nil; e = e.Prev() {
commitID := e.Value.(*git.Commit).ID.String()
if item, ok := commitChecks[commitID]; ok && item.Checked {
commitIDs = append(commitIDs, commitID)
} }
} }
return return
} }
type commitBranchCheckItem struct {
Commit *git.Commit
Checked bool
}
func commitBranchCheck(gitRepo *git.Repository, startCommit *git.Commit, endCommitID, baseBranch string, commitList map[string]commitBranchCheckItem) (err error) {
var (
item commitBranchCheckItem
ok bool
listItem *list.Element
tmp string
)
if startCommit.ID.String() == endCommitID {
return
}
checkStack := list.New()
checkStack.PushBack(startCommit.ID.String())
listItem = checkStack.Back()
for listItem != nil {
tmp = listItem.Value.(string)
checkStack.Remove(listItem)
if item, ok = commitList[tmp]; !ok {
listItem = checkStack.Back()
continue
}
if item.Commit.ID.String() == endCommitID {
listItem = checkStack.Back()
continue
}
if err = item.Commit.LoadBranchName(); err != nil {
return
}
if item.Commit.Branch == baseBranch {
listItem = checkStack.Back()
continue
}
if item.Checked {
listItem = checkStack.Back()
continue
}
item.Checked = true
commitList[tmp] = item
parentNum := item.Commit.ParentCount()
for i := 0; i < parentNum; i++ {
var parentCommit *git.Commit
parentCommit, err = item.Commit.Parent(i)
if err != nil {
return
}
checkStack.PushBack(parentCommit.ID.String())
}
listItem = checkStack.Back()
}
return nil
}

View file

@ -482,6 +482,16 @@ func (c *Commit) GetBranchName() (string, error) {
return strings.SplitN(strings.TrimSpace(data), "~", 2)[0], nil return strings.SplitN(strings.TrimSpace(data), "~", 2)[0], nil
} }
// LoadBranchName load branch name for commit
func (c *Commit) LoadBranchName() (err error) {
if len(c.Branch) != 0 {
return
}
c.Branch, err = c.GetBranchName()
return
}
// GetTagName gets the current tag name for given commit // GetTagName gets the current tag name for given commit
func (c *Commit) GetTagName() (string, error) { func (c *Commit) GetTagName() (string, error) {
data, err := NewCommand("describe", "--exact-match", "--tags", "--always", c.ID.String()).RunInDir(c.repo.Path) data, err := NewCommand("describe", "--exact-match", "--tags", "--always", c.ID.String()).RunInDir(c.repo.Path)