diff options
author | Jesse Duffield <jessedduffield@gmail.com> | 2019-11-04 19:47:25 +1100 |
---|---|---|
committer | Jesse Duffield <jessedduffield@gmail.com> | 2019-11-05 19:22:01 +1100 |
commit | d5e443e8e3609fe38586aed942a3dae3343dbe47 (patch) | |
tree | 6d7465b9abd8df3ae903e6d95898054ac3a6d8b4 /pkg/commands/patch_rebases.go | |
parent | a3c84296bf2fbc8b132d5b2285eedba09813fbee (diff) |
Support building and moving patches
WIP
Diffstat (limited to 'pkg/commands/patch_rebases.go')
-rw-r--r-- | pkg/commands/patch_rebases.go | 153 |
1 files changed, 153 insertions, 0 deletions
diff --git a/pkg/commands/patch_rebases.go b/pkg/commands/patch_rebases.go new file mode 100644 index 000000000..40c3358ac --- /dev/null +++ b/pkg/commands/patch_rebases.go @@ -0,0 +1,153 @@ +package commands + +import "github.com/go-errors/errors" + +// DeletePatchesFromCommit applies a patch in reverse for a commit +func (c *GitCommand) DeletePatchesFromCommit(commits []*Commit, commitIndex int, p *PatchManager) error { + if err := c.BeginInteractiveRebaseForCommit(commits, commitIndex); err != nil { + return err + } + + // apply each patch in reverse + if err := p.ApplyPatches(true); err != nil { + if err := c.GenericMerge("rebase", "abort"); err != nil { + return err + } + return err + } + + // time to amend the selected commit + if _, err := c.AmendHead(); err != nil { + return err + } + + // continue + return c.GenericMerge("rebase", "continue") +} + +func (c *GitCommand) MovePatchToSelectedCommit(commits []*Commit, sourceCommitIdx int, destinationCommitIdx int, p *PatchManager) error { + if sourceCommitIdx < destinationCommitIdx { + if err := c.BeginInteractiveRebaseForCommit(commits, destinationCommitIdx); err != nil { + return err + } + + // apply each patch forward + if err := p.ApplyPatches(false); err != nil { + if err := c.GenericMerge("rebase", "abort"); err != nil { + return err + } + return err + } + + // amend the destination commit + if _, err := c.AmendHead(); err != nil { + return err + } + + // continue + return c.GenericMerge("rebase", "continue") + } + + if len(commits)-1 < sourceCommitIdx { + return errors.New("index outside of range of commits") + } + + // we can make this GPG thing possible it just means we need to do this in two parts: + // one where we handle the possibility of a credential request, and the other + // where we continue the rebase + if c.usingGpg() { + return errors.New(c.Tr.SLocalize("DisabledForGPG")) + } + + baseIndex := sourceCommitIdx + 1 + todo := "" + for i, commit := range commits[0:baseIndex] { + a := "pick" + if i == sourceCommitIdx || i == destinationCommitIdx { + a = "edit" + } + todo = a + " " + commit.Sha + " " + commit.Name + "\n" + todo + } + + cmd, err := c.PrepareInteractiveRebaseCommand(commits[baseIndex].Sha, todo, true) + if err != nil { + return err + } + + if err := c.OSCommand.RunPreparedCommand(cmd); err != nil { + return err + } + + // apply each patch in reverse + if err := p.ApplyPatches(true); err != nil { + if err := c.GenericMerge("rebase", "abort"); err != nil { + return err + } + return err + } + + // amend the source commit + if _, err := c.AmendHead(); err != nil { + return err + } + + if c.onSuccessfulContinue != nil { + return errors.New("You are midway through another rebase operation. Please abort to start again") + } + + c.onSuccessfulContinue = func() error { + // now we should be up to the destination, so let's apply forward these patches to that. + // ideally we would ensure we're on the right commit but I'm not sure if that check is necessary + if err := p.ApplyPatches(false); err != nil { + if err := c.GenericMerge("rebase", "abort"); err != nil { + return err + } + return err + } + + // amend the destination commit + if _, err := c.AmendHead(); err != nil { + return err + } + + return c.GenericMerge("rebase", "continue") + } + + return c.GenericMerge("rebase", "continue") +} + +func (c *GitCommand) PullPatchIntoIndex(commits []*Commit, commitIdx int, p *PatchManager) error { + if err := c.BeginInteractiveRebaseForCommit(commits, commitIdx); err != nil { + return err + } + + if err := p.ApplyPatches(true); err != nil { + if err := c.GenericMerge("rebase", "abort"); err != nil { + return err + } + return err + } + + // amend the commit + if _, err := c.AmendHead(); err != nil { + return err + } + + if c.onSuccessfulContinue != nil { + return errors.New("You are midway through another rebase operation. Please abort to start again") + } + + c.onSuccessfulContinue = func() error { + // add patches to index + if err := p.ApplyPatches(false); err != nil { + if err := c.GenericMerge("rebase", "abort"); err != nil { + return err + } + return err + } + + return nil + } + + return c.GenericMerge("rebase", "continue") +} |