@@ -9,9 +9,12 @@ import (
99 "regexp"
1010 "strings"
1111
12+ "github.com/mgutz/str"
13+
1214 "github.com/fatih/color"
1315 "github.com/go-errors/errors"
1416
17+ "github.com/jesseduffield/lazygit/pkg/config"
1518 "github.com/jesseduffield/lazygit/pkg/i18n"
1619 "github.com/jesseduffield/lazygit/pkg/utils"
1720 "github.com/sirupsen/logrus"
@@ -68,13 +71,14 @@ type GitCommand struct {
6871 Worktree * gogit.Worktree
6972 Repo * gogit.Repository
7073 Tr * i18n.Localizer
74+ Config config.AppConfigurer
7175 getGlobalGitConfig func (string ) (string , error )
7276 getLocalGitConfig func (string ) (string , error )
7377 removeFile func (string ) error
7478}
7579
7680// NewGitCommand it runs git commands
77- func NewGitCommand (log * logrus.Entry , osCommand * OSCommand , tr * i18n.Localizer ) (* GitCommand , error ) {
81+ func NewGitCommand (log * logrus.Entry , osCommand * OSCommand , tr * i18n.Localizer , config config. AppConfigurer ) (* GitCommand , error ) {
7882 var worktree * gogit.Worktree
7983 var repo * gogit.Repository
8084
@@ -104,6 +108,7 @@ func NewGitCommand(log *logrus.Entry, osCommand *OSCommand, tr *i18n.Localizer)
104108 Tr : tr ,
105109 Worktree : worktree ,
106110 Repo : repo ,
111+ Config : config ,
107112 getGlobalGitConfig : gitconfig .Global ,
108113 getLocalGitConfig : gitconfig .Local ,
109114 removeFile : os .RemoveAll ,
@@ -774,3 +779,62 @@ func (c *GitCommand) GenericMerge(commandType string, command string) error {
774779 gitCommand := fmt .Sprintf ("git %s %s --%s" , c .OSCommand .Platform .skipEditorArg , commandType , command )
775780 return c .OSCommand .RunCommand (gitCommand )
776781}
782+
783+ func (c * GitCommand ) InteractiveRebase (commits []* Commit , index int , action string ) (* exec.Cmd , error ) {
784+ ex , err := os .Executable () // get the executable path for git to use
785+ if err != nil {
786+ ex = os .Args [0 ] // fallback to the first call argument if needed
787+ }
788+
789+ // assume for now they won't pick the bottom commit
790+ c .Log .Warn (len (commits ))
791+ c .Log .Warn (index )
792+ if len (commits ) <= index + 1 {
793+ // TODO: support more than say 30 commits and ensure this logic is correct, and i18n
794+ return nil , errors .New ("You cannot interactive rebase onto the first commit" )
795+ }
796+
797+ todo := ""
798+ for i , commit := range commits [0 : index + 1 ] {
799+ a := "pick"
800+ if i == index {
801+ a = action
802+ }
803+ todo += a + " " + commit .Sha + "\n "
804+ }
805+
806+ debug := "FALSE"
807+ if c .OSCommand .Config .GetDebug () == true {
808+ debug = "TRUE"
809+ }
810+
811+ splitCmd := str .ToArgv (fmt .Sprintf ("git rebase --interactive %s" , commits [index + 1 ].Sha ))
812+
813+ cmd := exec .Command (splitCmd [0 ], splitCmd [1 :]... )
814+
815+ cmd .Env = os .Environ ()
816+ cmd .Env = append (
817+ cmd .Env ,
818+ "LAZYGIT_CONTEXT=INTERACTIVE_REBASE" ,
819+ "LAZYGIT_REBASE_TODO=" + todo ,
820+ "DEBUG=" + debug ,
821+ "LANG=en_US.UTF-8" , // Force using EN as language
822+ "LC_ALL=en_US.UTF-8" , // Force using EN as language
823+ "GIT_SEQUENCE_EDITOR=" + ex ,
824+ )
825+
826+ if true {
827+ return cmd , nil
828+ }
829+
830+ out , err := cmd .CombinedOutput ()
831+ outString := string (out )
832+ c .Log .Info (outString )
833+ if err != nil {
834+ if len (outString ) == 0 {
835+ return nil , err
836+ }
837+ return nil , errors .New (outString )
838+ }
839+ return nil , nil
840+ }
0 commit comments