mirror of
https://github.com/harness/drone.git
synced 2025-05-06 06:41:35 +08:00
Merge branch 'eb/code-225' of _OKE5H2PQKOUfzFFDuD4FA/default/CODE/gitness (#70)
This commit is contained in:
commit
1b04c8f98e
@ -18,6 +18,7 @@ import (
|
||||
"github.com/harness/gitness/gitrpc/enum"
|
||||
"github.com/harness/gitness/gitrpc/internal/tempdir"
|
||||
"github.com/harness/gitness/gitrpc/internal/types"
|
||||
"github.com/rs/zerolog/log"
|
||||
|
||||
"code.gitea.io/gitea/modules/git"
|
||||
)
|
||||
@ -175,7 +176,7 @@ func (g Adapter) CreateTemporaryRepoForPR(
|
||||
func runMergeCommand(
|
||||
ctx context.Context,
|
||||
pr *types.PullRequest,
|
||||
mergeMethod string,
|
||||
mergeMethod enum.MergeMethod,
|
||||
cmd *git.Command,
|
||||
tmpBasePath string,
|
||||
env []string,
|
||||
@ -254,6 +255,7 @@ func (g Adapter) Merge(
|
||||
ctx context.Context,
|
||||
pr *types.PullRequest,
|
||||
mergeMethod enum.MergeMethod,
|
||||
baseBranch string,
|
||||
trackingBranch string,
|
||||
tmpBasePath string,
|
||||
mergeMsg string,
|
||||
@ -268,13 +270,14 @@ func (g Adapter) Merge(
|
||||
mergeMsg = "Merge commit"
|
||||
}
|
||||
|
||||
stagingBranch := "staging"
|
||||
// TODO: sign merge commit
|
||||
signArg := "--no-gpg-sign"
|
||||
|
||||
switch mergeMethod {
|
||||
case enum.MergeMethodMerge:
|
||||
cmd := git.NewCommand(ctx, "merge", "--no-ff", "--no-commit", trackingBranch)
|
||||
if err := runMergeCommand(ctx, pr, string(mergeMethod), cmd, tmpBasePath, env); err != nil {
|
||||
if err := runMergeCommand(ctx, pr, mergeMethod, cmd, tmpBasePath, env); err != nil {
|
||||
return fmt.Errorf("unable to merge tracking into base: %w", err)
|
||||
}
|
||||
|
||||
@ -284,7 +287,7 @@ func (g Adapter) Merge(
|
||||
case enum.MergeMethodSquash:
|
||||
// Merge with squash
|
||||
cmd := git.NewCommand(ctx, "merge", "--squash", trackingBranch)
|
||||
if err := runMergeCommand(ctx, pr, string(mergeMethod), cmd, tmpBasePath, env); err != nil {
|
||||
if err := runMergeCommand(ctx, pr, mergeMethod, cmd, tmpBasePath, env); err != nil {
|
||||
return fmt.Errorf("unable to merge --squash tracking into base: %v", err)
|
||||
}
|
||||
|
||||
@ -311,6 +314,79 @@ func (g Adapter) Merge(
|
||||
pr.HeadBranch, pr.BaseBranch, outbuf.String(), errbuf.String())
|
||||
}
|
||||
}
|
||||
case enum.MergeMethodRebase:
|
||||
// Checkout head branch
|
||||
if err := git.NewCommand(ctx, "checkout", "-b", stagingBranch, trackingBranch).
|
||||
Run(&git.RunOpts{
|
||||
Dir: tmpBasePath,
|
||||
Stdout: &outbuf,
|
||||
Stderr: &errbuf,
|
||||
}); err != nil {
|
||||
return fmt.Errorf("git checkout base prior to merge post staging rebase [%s -> %s]: %v\n%s\n%s", pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
}
|
||||
outbuf.Reset()
|
||||
errbuf.Reset()
|
||||
|
||||
// Rebase before merging
|
||||
if err := git.NewCommand(ctx, "rebase", baseBranch).
|
||||
Run(&git.RunOpts{
|
||||
Dir: tmpBasePath,
|
||||
Stdout: &outbuf,
|
||||
Stderr: &errbuf,
|
||||
}); err != nil {
|
||||
// Rebase will leave a REBASE_HEAD file in .git if there is a conflict
|
||||
if _, statErr := os.Stat(filepath.Join(tmpBasePath, ".git", "REBASE_HEAD")); statErr == nil {
|
||||
var commitSha string
|
||||
// TBD git version we will support
|
||||
// failingCommitPath := filepath.Join(tmpBasePath, ".git", "rebase-apply", "original-commit") // Git < 2.26
|
||||
// if _, statErr := os.Stat(failingCommitPath); statErr != nil {
|
||||
// return fmt.Errorf("git rebase staging on to base [%s -> %s]: %v\n%s\n%s", pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
// }
|
||||
|
||||
failingCommitPath := filepath.Join(tmpBasePath, ".git", "rebase-merge", "stopped-sha") // Git >= 2.26
|
||||
if _, statErr := os.Stat(failingCommitPath); statErr != nil {
|
||||
return fmt.Errorf("git rebase staging on to base [%s -> %s]: %v\n%s\n%s", pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
}
|
||||
|
||||
commitShaBytes, readErr := os.ReadFile(failingCommitPath)
|
||||
if readErr != nil {
|
||||
// Abandon this attempt to handle the error
|
||||
return fmt.Errorf("git rebase staging on to base [%s -> %s]: %v\n%s\n%s", pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
}
|
||||
commitSha = strings.TrimSpace(string(commitShaBytes))
|
||||
|
||||
log.Debug().Msgf("RebaseConflict at %s [%s -> %s]: %v\n%s\n%s", commitSha, pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
return &types.MergeConflictsError{
|
||||
Method: mergeMethod,
|
||||
CommitSHA: commitSha,
|
||||
StdOut: outbuf.String(),
|
||||
StdErr: errbuf.String(),
|
||||
Err: err,
|
||||
}
|
||||
}
|
||||
return fmt.Errorf("git rebase staging on to base [%s -> %s]: %v\n%s\n%s", pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
}
|
||||
outbuf.Reset()
|
||||
errbuf.Reset()
|
||||
|
||||
// Checkout base branch again
|
||||
if err := git.NewCommand(ctx, "checkout", baseBranch).
|
||||
Run(&git.RunOpts{
|
||||
Dir: tmpBasePath,
|
||||
Stdout: &outbuf,
|
||||
Stderr: &errbuf,
|
||||
}); err != nil {
|
||||
return fmt.Errorf("git checkout base prior to merge post staging rebase [%s -> %s]: %v\n%s\n%s", pr.HeadBranch, pr.BaseBranch, err, outbuf.String(), errbuf.String())
|
||||
}
|
||||
outbuf.Reset()
|
||||
errbuf.Reset()
|
||||
|
||||
cmd := git.NewCommand(ctx, "merge", "--ff-only", stagingBranch)
|
||||
|
||||
// Prepare merge with commit
|
||||
if err := runMergeCommand(ctx, pr, mergeMethod, cmd, tmpBasePath, env); err != nil {
|
||||
return err
|
||||
}
|
||||
default:
|
||||
return fmt.Errorf("wrong merge method provided: %s", mergeMethod)
|
||||
}
|
||||
|
@ -46,7 +46,7 @@ type GitAdapter interface {
|
||||
GetRefPath(refName string, refType enum.RefType) (string, error)
|
||||
UpdateRef(ctx context.Context, repoPath, refName string, refType enum.RefType, newValue, oldValue string) error
|
||||
CreateTemporaryRepoForPR(ctx context.Context, reposTempPath string, pr *types.PullRequest) (string, error)
|
||||
Merge(ctx context.Context, pr *types.PullRequest, mergeMethod enum.MergeMethod, trackingBranch string,
|
||||
Merge(ctx context.Context, pr *types.PullRequest, mergeMethod enum.MergeMethod, baseBranch, trackingBranch string,
|
||||
tmpBasePath string, mergeMsg string, env []string, identity *types.Identity) error
|
||||
GetMergeBase(ctx context.Context, repoPath, remote, base, head string) (string, string, error)
|
||||
GetDiffTree(ctx context.Context, repoPath, baseBranch, headBranch string) (string, error)
|
||||
|
@ -169,10 +169,19 @@ func (s MergeService) Merge(
|
||||
mergeMsg += "\n\n" + strings.TrimSpace(request.Message)
|
||||
}
|
||||
|
||||
if err = s.adapter.Merge(ctx, pr, enum.MergeMethodFromRPC(request.Method), trackingBranch, tmpBasePath, mergeMsg, env, &types.Identity{
|
||||
Name: author.Name,
|
||||
Email: author.Email,
|
||||
}); err != nil {
|
||||
if err = s.adapter.Merge(
|
||||
ctx,
|
||||
pr,
|
||||
enum.MergeMethodFromRPC(request.Method),
|
||||
baseBranch,
|
||||
trackingBranch,
|
||||
tmpBasePath,
|
||||
mergeMsg,
|
||||
env,
|
||||
&types.Identity{
|
||||
Name: author.Name,
|
||||
Email: author.Email,
|
||||
}); err != nil {
|
||||
return nil, processGitErrorf(err, "merge failed")
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,8 @@ package types
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
|
||||
"github.com/harness/gitness/gitrpc/enum"
|
||||
)
|
||||
|
||||
var (
|
||||
@ -29,10 +31,11 @@ var (
|
||||
|
||||
// MergeConflictsError represents an error if merging fails with a conflict.
|
||||
type MergeConflictsError struct {
|
||||
Method string
|
||||
StdOut string
|
||||
StdErr string
|
||||
Err error
|
||||
Method enum.MergeMethod
|
||||
CommitSHA string
|
||||
StdOut string
|
||||
StdErr string
|
||||
Err error
|
||||
}
|
||||
|
||||
func IsMergeConflictsError(err error) bool {
|
||||
@ -55,7 +58,7 @@ func (e *MergeConflictsError) Is(target error) bool {
|
||||
|
||||
// MergeUnrelatedHistoriesError represents an error if merging fails due to unrelated histories.
|
||||
type MergeUnrelatedHistoriesError struct {
|
||||
Method string
|
||||
Method enum.MergeMethod
|
||||
StdOut string
|
||||
StdErr string
|
||||
Err error
|
||||
|
@ -88,7 +88,7 @@ export const PullRequestActionsBox: React.FC<PullRequestActionsBoxProps> = ({
|
||||
method: 'rebase',
|
||||
title: getString('pr.mergeOptions.rebaseAndMerge'),
|
||||
desc: getString('pr.mergeOptions.rebaseAndMergeDesc'),
|
||||
disabled: true
|
||||
disabled: false
|
||||
},
|
||||
{
|
||||
method: 'close',
|
||||
|
Loading…
Reference in New Issue
Block a user