mirror of
https://github.com/jesseduffield/lazygit.git
synced 2025-04-21 12:16:54 +02:00
use cached git config
This commit is contained in:
parent
5011cac7ea
commit
b6a5e9d615
@ -4,15 +4,6 @@ import (
|
|||||||
"bufio"
|
"bufio"
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/aybabtme/humanlog"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/config"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/env"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/gui"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/i18n"
|
|
||||||
"github.com/jesseduffield/lazygit/pkg/updates"
|
|
||||||
"github.com/sirupsen/logrus"
|
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"log"
|
"log"
|
||||||
@ -21,6 +12,17 @@ import (
|
|||||||
"regexp"
|
"regexp"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
|
"github.com/aybabtme/humanlog"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/config"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/env"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/gui"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/i18n"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/updates"
|
||||||
|
"github.com/sirupsen/logrus"
|
||||||
)
|
)
|
||||||
|
|
||||||
// App struct
|
// App struct
|
||||||
@ -125,7 +127,7 @@ func NewApp(config config.AppConfigurer, filterPath string) (*App, error) {
|
|||||||
return app, err
|
return app, err
|
||||||
}
|
}
|
||||||
|
|
||||||
app.GitCommand, err = commands.NewGitCommand(app.Log, app.OSCommand, app.Tr, app.Config)
|
app.GitCommand, err = commands.NewGitCommand(app.Log, app.OSCommand, app.Tr, app.Config, git_config.NewStdCachedGitConfig(app.Log))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return app, err
|
return app, err
|
||||||
}
|
}
|
||||||
|
@ -15,12 +15,8 @@ func (c *GitCommand) ConfiguredPager() string {
|
|||||||
if os.Getenv("PAGER") != "" {
|
if os.Getenv("PAGER") != "" {
|
||||||
return os.Getenv("PAGER")
|
return os.Getenv("PAGER")
|
||||||
}
|
}
|
||||||
output, err := c.RunCommandWithOutput("git config --get-all core.pager")
|
output := c.GitConfig.Get("core.pager")
|
||||||
if err != nil {
|
return strings.Split(output, "\n")[0]
|
||||||
return ""
|
|
||||||
}
|
|
||||||
trimmedOutput := strings.TrimSpace(output)
|
|
||||||
return strings.Split(trimmedOutput, "\n")[0]
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *GitCommand) GetPager(width int) string {
|
func (c *GitCommand) GetPager(width int) string {
|
||||||
@ -42,11 +38,6 @@ func (c *GitCommand) colorArg() string {
|
|||||||
return c.Config.GetUserConfig().Git.Paging.ColorArg
|
return c.Config.GetUserConfig().Git.Paging.ColorArg
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *GitCommand) GetConfigValue(key string) string {
|
|
||||||
output, _ := c.getGitConfigValue(key)
|
|
||||||
return output
|
|
||||||
}
|
|
||||||
|
|
||||||
// UsingGpg tells us whether the user has gpg enabled so that we can know
|
// UsingGpg tells us whether the user has gpg enabled so that we can know
|
||||||
// whether we need to run a subprocess to allow them to enter their password
|
// whether we need to run a subprocess to allow them to enter their password
|
||||||
func (c *GitCommand) UsingGpg() bool {
|
func (c *GitCommand) UsingGpg() bool {
|
||||||
@ -55,8 +46,5 @@ func (c *GitCommand) UsingGpg() bool {
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
gpgsign := c.GetConfigValue("commit.gpgsign")
|
return c.GitConfig.GetBool("commit.gpgsign")
|
||||||
value := strings.ToLower(gpgsign)
|
|
||||||
|
|
||||||
return value == "true" || value == "1" || value == "yes" || value == "on"
|
|
||||||
}
|
}
|
||||||
|
@ -1,70 +0,0 @@
|
|||||||
package commands
|
|
||||||
|
|
||||||
import (
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
|
||||||
)
|
|
||||||
|
|
||||||
// TestGitCommandUsingGpg is a function.
|
|
||||||
func TestGitCommandUsingGpg(t *testing.T) {
|
|
||||||
type scenario struct {
|
|
||||||
testName string
|
|
||||||
getGitConfigValue func(string) (string, error)
|
|
||||||
test func(bool)
|
|
||||||
}
|
|
||||||
|
|
||||||
scenarios := []scenario{
|
|
||||||
{
|
|
||||||
"Option global and local config commit.gpgsign is not set",
|
|
||||||
func(string) (string, error) { return "", nil },
|
|
||||||
func(gpgEnabled bool) {
|
|
||||||
assert.False(t, gpgEnabled)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Option commit.gpgsign is true",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "True", nil
|
|
||||||
},
|
|
||||||
func(gpgEnabled bool) {
|
|
||||||
assert.True(t, gpgEnabled)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Option commit.gpgsign is on",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "ON", nil
|
|
||||||
},
|
|
||||||
func(gpgEnabled bool) {
|
|
||||||
assert.True(t, gpgEnabled)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Option commit.gpgsign is yes",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "YeS", nil
|
|
||||||
},
|
|
||||||
func(gpgEnabled bool) {
|
|
||||||
assert.True(t, gpgEnabled)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Option commit.gpgsign is 1",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "1", nil
|
|
||||||
},
|
|
||||||
func(gpgEnabled bool) {
|
|
||||||
assert.True(t, gpgEnabled)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, s := range scenarios {
|
|
||||||
t.Run(s.testName, func(t *testing.T) {
|
|
||||||
gitCmd := NewDummyGitCommand()
|
|
||||||
gitCmd.getGitConfigValue = s.getGitConfigValue
|
|
||||||
s.test(gitCmd.UsingGpg())
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,6 +1,7 @@
|
|||||||
package commands
|
package commands
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
||||||
"github.com/jesseduffield/lazygit/pkg/config"
|
"github.com/jesseduffield/lazygit/pkg/config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/i18n"
|
"github.com/jesseduffield/lazygit/pkg/i18n"
|
||||||
@ -20,6 +21,6 @@ func NewDummyGitCommandWithOSCommand(osCommand *oscommands.OSCommand) *GitComman
|
|||||||
OSCommand: osCommand,
|
OSCommand: osCommand,
|
||||||
Tr: i18n.NewTranslationSet(utils.NewDummyLog(), newAppConfig.GetUserConfig().Gui.Language),
|
Tr: i18n.NewTranslationSet(utils.NewDummyLog(), newAppConfig.GetUserConfig().Gui.Language),
|
||||||
Config: newAppConfig,
|
Config: newAppConfig,
|
||||||
getGitConfigValue: func(string) (string, error) { return "", nil },
|
GitConfig: git_config.NewFakeGitConfig(map[string]string{}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -331,7 +331,7 @@ func (c *GitCommand) EditFileCmdStr(filename string, lineNumber int) (string, er
|
|||||||
editor := c.Config.GetUserConfig().OS.EditCommand
|
editor := c.Config.GetUserConfig().OS.EditCommand
|
||||||
|
|
||||||
if editor == "" {
|
if editor == "" {
|
||||||
editor = c.GetConfigValue("core.editor")
|
editor = c.GitConfig.Get("core.editor")
|
||||||
}
|
}
|
||||||
|
|
||||||
if editor == "" {
|
if editor == "" {
|
||||||
|
@ -6,6 +6,7 @@ import (
|
|||||||
"os/exec"
|
"os/exec"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands/models"
|
"github.com/jesseduffield/lazygit/pkg/commands/models"
|
||||||
"github.com/jesseduffield/lazygit/pkg/secureexec"
|
"github.com/jesseduffield/lazygit/pkg/secureexec"
|
||||||
"github.com/jesseduffield/lazygit/pkg/test"
|
"github.com/jesseduffield/lazygit/pkg/test"
|
||||||
@ -523,11 +524,10 @@ func TestGitCommandApplyPatch(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TestGitCommandDiscardOldFileChanges is a function.
|
|
||||||
func TestGitCommandDiscardOldFileChanges(t *testing.T) {
|
func TestGitCommandDiscardOldFileChanges(t *testing.T) {
|
||||||
type scenario struct {
|
type scenario struct {
|
||||||
testName string
|
testName string
|
||||||
getGitConfigValue func(string) (string, error)
|
gitConfigMockResponses map[string]string
|
||||||
commits []*models.Commit
|
commits []*models.Commit
|
||||||
commitIndex int
|
commitIndex int
|
||||||
fileName string
|
fileName string
|
||||||
@ -538,9 +538,7 @@ func TestGitCommandDiscardOldFileChanges(t *testing.T) {
|
|||||||
scenarios := []scenario{
|
scenarios := []scenario{
|
||||||
{
|
{
|
||||||
"returns error when index outside of range of commits",
|
"returns error when index outside of range of commits",
|
||||||
func(string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
[]*models.Commit{},
|
[]*models.Commit{},
|
||||||
0,
|
0,
|
||||||
"test999.txt",
|
"test999.txt",
|
||||||
@ -551,9 +549,7 @@ func TestGitCommandDiscardOldFileChanges(t *testing.T) {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"returns error when using gpg",
|
"returns error when using gpg",
|
||||||
func(string) (string, error) {
|
map[string]string{"commit.gpgsign": "true"},
|
||||||
return "true", nil
|
|
||||||
},
|
|
||||||
[]*models.Commit{{Name: "commit", Sha: "123456"}},
|
[]*models.Commit{{Name: "commit", Sha: "123456"}},
|
||||||
0,
|
0,
|
||||||
"test999.txt",
|
"test999.txt",
|
||||||
@ -564,9 +560,7 @@ func TestGitCommandDiscardOldFileChanges(t *testing.T) {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"checks out file if it already existed",
|
"checks out file if it already existed",
|
||||||
func(string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
[]*models.Commit{
|
[]*models.Commit{
|
||||||
{Name: "commit", Sha: "123456"},
|
{Name: "commit", Sha: "123456"},
|
||||||
{Name: "commit2", Sha: "abcdef"},
|
{Name: "commit2", Sha: "abcdef"},
|
||||||
@ -608,7 +602,7 @@ func TestGitCommandDiscardOldFileChanges(t *testing.T) {
|
|||||||
for _, s := range scenarios {
|
for _, s := range scenarios {
|
||||||
t.Run(s.testName, func(t *testing.T) {
|
t.Run(s.testName, func(t *testing.T) {
|
||||||
gitCmd.OSCommand.Command = s.command
|
gitCmd.OSCommand.Command = s.command
|
||||||
gitCmd.getGitConfigValue = s.getGitConfigValue
|
gitCmd.GitConfig = git_config.NewFakeGitConfig(s.gitConfigMockResponses)
|
||||||
s.test(gitCmd.DiscardOldFileChanges(s.commits, s.commitIndex, s.fileName))
|
s.test(gitCmd.DiscardOldFileChanges(s.commits, s.commitIndex, s.fileName))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@ -725,7 +719,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
configEditCommandTemplate string
|
configEditCommandTemplate string
|
||||||
command func(string, ...string) *exec.Cmd
|
command func(string, ...string) *exec.Cmd
|
||||||
getenv func(string) string
|
getenv func(string) string
|
||||||
getGitConfigValue func(string) (string, error)
|
gitConfigMockResponses map[string]string
|
||||||
test func(string, error)
|
test func(string, error)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -740,9 +734,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
func(env string) string {
|
func(env string) string {
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.EqualError(t, err, "No editor defined in config file, $GIT_EDITOR, $VISUAL, $EDITOR, or git config")
|
assert.EqualError(t, err, "No editor defined in config file, $GIT_EDITOR, $VISUAL, $EDITOR, or git config")
|
||||||
},
|
},
|
||||||
@ -758,9 +750,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
func(env string) string {
|
func(env string) string {
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, "nano "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
assert.Equal(t, "nano "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
||||||
@ -777,9 +767,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
func(env string) string {
|
func(env string) string {
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
map[string]string{"core.editor": "nano"},
|
||||||
return "nano", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, "nano "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
assert.Equal(t, "nano "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
||||||
@ -800,9 +788,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
|
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
},
|
},
|
||||||
@ -822,9 +808,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
|
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, "emacs "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
assert.Equal(t, "emacs "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
||||||
@ -841,9 +825,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
func(env string) string {
|
func(env string) string {
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, "vi "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
assert.Equal(t, "vi "+gitCmd.OSCommand.Quote("test"), cmdStr)
|
||||||
@ -860,9 +842,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
func(env string) string {
|
func(env string) string {
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, "vi "+gitCmd.OSCommand.Quote("file/with space"), cmdStr)
|
assert.Equal(t, "vi "+gitCmd.OSCommand.Quote("file/with space"), cmdStr)
|
||||||
@ -879,9 +859,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
func(env string) string {
|
func(env string) string {
|
||||||
return ""
|
return ""
|
||||||
},
|
},
|
||||||
func(cf string) (string, error) {
|
nil,
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmdStr string, err error) {
|
func(cmdStr string, err error) {
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Equal(t, "vim +1 "+gitCmd.OSCommand.Quote("open file/at line"), cmdStr)
|
assert.Equal(t, "vim +1 "+gitCmd.OSCommand.Quote("open file/at line"), cmdStr)
|
||||||
@ -894,7 +872,7 @@ func TestEditFileCmdStr(t *testing.T) {
|
|||||||
gitCmd.Config.GetUserConfig().OS.EditCommandTemplate = s.configEditCommandTemplate
|
gitCmd.Config.GetUserConfig().OS.EditCommandTemplate = s.configEditCommandTemplate
|
||||||
gitCmd.OSCommand.Command = s.command
|
gitCmd.OSCommand.Command = s.command
|
||||||
gitCmd.OSCommand.Getenv = s.getenv
|
gitCmd.OSCommand.Getenv = s.getenv
|
||||||
gitCmd.getGitConfigValue = s.getGitConfigValue
|
gitCmd.GitConfig = git_config.NewFakeGitConfig(s.gitConfigMockResponses)
|
||||||
s.test(gitCmd.EditFileCmdStr(s.filename, 1))
|
s.test(gitCmd.EditFileCmdStr(s.filename, 1))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -10,6 +10,7 @@ import (
|
|||||||
"github.com/go-errors/errors"
|
"github.com/go-errors/errors"
|
||||||
|
|
||||||
gogit "github.com/jesseduffield/go-git/v5"
|
gogit "github.com/jesseduffield/go-git/v5"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands/patch"
|
"github.com/jesseduffield/lazygit/pkg/commands/patch"
|
||||||
"github.com/jesseduffield/lazygit/pkg/config"
|
"github.com/jesseduffield/lazygit/pkg/config"
|
||||||
@ -32,32 +33,32 @@ type GitCommand struct {
|
|||||||
Repo *gogit.Repository
|
Repo *gogit.Repository
|
||||||
Tr *i18n.TranslationSet
|
Tr *i18n.TranslationSet
|
||||||
Config config.AppConfigurer
|
Config config.AppConfigurer
|
||||||
getGitConfigValue func(string) (string, error)
|
|
||||||
DotGitDir string
|
DotGitDir string
|
||||||
onSuccessfulContinue func() error
|
onSuccessfulContinue func() error
|
||||||
PatchManager *patch.PatchManager
|
PatchManager *patch.PatchManager
|
||||||
|
GitConfig git_config.IGitConfig
|
||||||
|
|
||||||
// Push to current determines whether the user has configured to push to the remote branch of the same name as the current or not
|
// Push to current determines whether the user has configured to push to the remote branch of the same name as the current or not
|
||||||
PushToCurrent bool
|
PushToCurrent bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// NewGitCommand it runs git commands
|
// NewGitCommand it runs git commands
|
||||||
func NewGitCommand(log *logrus.Entry, osCommand *oscommands.OSCommand, tr *i18n.TranslationSet, config config.AppConfigurer) (*GitCommand, error) {
|
func NewGitCommand(
|
||||||
|
log *logrus.Entry,
|
||||||
|
osCommand *oscommands.OSCommand,
|
||||||
|
tr *i18n.TranslationSet,
|
||||||
|
config config.AppConfigurer,
|
||||||
|
gitConfig git_config.IGitConfig,
|
||||||
|
) (*GitCommand, error) {
|
||||||
var repo *gogit.Repository
|
var repo *gogit.Repository
|
||||||
|
|
||||||
// see what our default push behaviour is
|
pushToCurrent := gitConfig.Get("push.default") == "current"
|
||||||
output, err := osCommand.RunCommandWithOutput("git config --get push.default")
|
|
||||||
pushToCurrent := false
|
|
||||||
if err != nil {
|
|
||||||
log.Errorf("error reading git config: %v", err)
|
|
||||||
} else {
|
|
||||||
pushToCurrent = strings.TrimSpace(output) == "current"
|
|
||||||
}
|
|
||||||
|
|
||||||
if err := navigateToRepoRootDirectory(os.Stat, os.Chdir); err != nil {
|
if err := navigateToRepoRootDirectory(os.Stat, os.Chdir); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var err error
|
||||||
if repo, err = setupRepository(gogit.PlainOpen, tr.GitconfigParseErr); err != nil {
|
if repo, err = setupRepository(gogit.PlainOpen, tr.GitconfigParseErr); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@ -73,9 +74,9 @@ func NewGitCommand(log *logrus.Entry, osCommand *oscommands.OSCommand, tr *i18n.
|
|||||||
Tr: tr,
|
Tr: tr,
|
||||||
Repo: repo,
|
Repo: repo,
|
||||||
Config: config,
|
Config: config,
|
||||||
getGitConfigValue: getGitConfigValue,
|
|
||||||
DotGitDir: dotGitDir,
|
DotGitDir: dotGitDir,
|
||||||
PushToCurrent: pushToCurrent,
|
PushToCurrent: pushToCurrent,
|
||||||
|
GitConfig: gitConfig,
|
||||||
}
|
}
|
||||||
|
|
||||||
gitCommand.PatchManager = patch.NewPatchManager(log, gitCommand.ApplyPatch, gitCommand.ShowFileDiff)
|
gitCommand.PatchManager = patch.NewPatchManager(log, gitCommand.ApplyPatch, gitCommand.ShowFileDiff)
|
||||||
|
59
pkg/commands/git_config/cached_git_config.go
Normal file
59
pkg/commands/git_config/cached_git_config.go
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
package git_config
|
||||||
|
|
||||||
|
import (
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/sirupsen/logrus"
|
||||||
|
)
|
||||||
|
|
||||||
|
type IGitConfig interface {
|
||||||
|
Get(string) string
|
||||||
|
GetBool(string) bool
|
||||||
|
}
|
||||||
|
|
||||||
|
type CachedGitConfig struct {
|
||||||
|
cache map[string]string
|
||||||
|
getKey func(string) (string, error)
|
||||||
|
log *logrus.Entry
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewStdCachedGitConfig(log *logrus.Entry) *CachedGitConfig {
|
||||||
|
return NewCachedGitConfig(getGitConfigValue, log)
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewCachedGitConfig(getKey func(string) (string, error), log *logrus.Entry) *CachedGitConfig {
|
||||||
|
return &CachedGitConfig{
|
||||||
|
cache: make(map[string]string),
|
||||||
|
getKey: getKey,
|
||||||
|
log: log,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (self *CachedGitConfig) Get(key string) string {
|
||||||
|
if value, ok := self.cache[key]; ok {
|
||||||
|
self.log.Debugf("using cache for key " + key)
|
||||||
|
return value
|
||||||
|
}
|
||||||
|
|
||||||
|
value := self.getAux(key)
|
||||||
|
self.cache[key] = value
|
||||||
|
return value
|
||||||
|
}
|
||||||
|
|
||||||
|
func (self *CachedGitConfig) getAux(key string) string {
|
||||||
|
value, err := self.getKey(key)
|
||||||
|
if err != nil {
|
||||||
|
self.log.Debugf("Error getting git config value for key: " + key + ". Error: " + err.Error())
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
return strings.TrimSpace(value)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (self *CachedGitConfig) GetBool(key string) bool {
|
||||||
|
return isTruthy(self.Get(key))
|
||||||
|
}
|
||||||
|
|
||||||
|
func isTruthy(value string) bool {
|
||||||
|
lcValue := strings.ToLower(value)
|
||||||
|
return lcValue == "true" || lcValue == "1" || lcValue == "yes" || lcValue == "on"
|
||||||
|
}
|
116
pkg/commands/git_config/cached_git_config_test.go
Normal file
116
pkg/commands/git_config/cached_git_config_test.go
Normal file
@ -0,0 +1,116 @@
|
|||||||
|
package git_config
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/utils"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestGetBool(t *testing.T) {
|
||||||
|
type scenario struct {
|
||||||
|
testName string
|
||||||
|
mockResponses map[string]string
|
||||||
|
expected bool
|
||||||
|
}
|
||||||
|
|
||||||
|
scenarios := []scenario{
|
||||||
|
{
|
||||||
|
"Option global and local config commit.gpgsign is not set",
|
||||||
|
map[string]string{},
|
||||||
|
false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"Some other random key is set",
|
||||||
|
map[string]string{"blah": "blah"},
|
||||||
|
false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"Option commit.gpgsign is true",
|
||||||
|
map[string]string{"commit.gpgsign": "True"},
|
||||||
|
true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"Option commit.gpgsign is on",
|
||||||
|
map[string]string{"commit.gpgsign": "ON"},
|
||||||
|
true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"Option commit.gpgsign is yes",
|
||||||
|
map[string]string{"commit.gpgsign": "YeS"},
|
||||||
|
true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"Option commit.gpgsign is 1",
|
||||||
|
map[string]string{"commit.gpgsign": "1"},
|
||||||
|
true,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, s := range scenarios {
|
||||||
|
s := s
|
||||||
|
t.Run(s.testName, func(t *testing.T) {
|
||||||
|
fake := NewFakeGitConfig(s.mockResponses)
|
||||||
|
real := NewCachedGitConfig(
|
||||||
|
func(key string) (string, error) {
|
||||||
|
return fake.Get(key), nil
|
||||||
|
},
|
||||||
|
utils.NewDummyLog(),
|
||||||
|
)
|
||||||
|
result := real.GetBool("commit.gpgsign")
|
||||||
|
assert.Equal(t, s.expected, result)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestGet(t *testing.T) {
|
||||||
|
type scenario struct {
|
||||||
|
testName string
|
||||||
|
mockResponses map[string]string
|
||||||
|
expected string
|
||||||
|
}
|
||||||
|
|
||||||
|
scenarios := []scenario{
|
||||||
|
{
|
||||||
|
"not set",
|
||||||
|
map[string]string{},
|
||||||
|
"",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"is set",
|
||||||
|
map[string]string{"commit.gpgsign": "blah"},
|
||||||
|
"blah",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, s := range scenarios {
|
||||||
|
s := s
|
||||||
|
t.Run(s.testName, func(t *testing.T) {
|
||||||
|
fake := NewFakeGitConfig(s.mockResponses)
|
||||||
|
real := NewCachedGitConfig(
|
||||||
|
func(key string) (string, error) {
|
||||||
|
return fake.Get(key), nil
|
||||||
|
},
|
||||||
|
utils.NewDummyLog(),
|
||||||
|
)
|
||||||
|
result := real.Get("commit.gpgsign")
|
||||||
|
assert.Equal(t, s.expected, result)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
// verifying that the cache is used
|
||||||
|
count := 0
|
||||||
|
real := NewCachedGitConfig(
|
||||||
|
func(key string) (string, error) {
|
||||||
|
count++
|
||||||
|
assert.Equal(t, "commit.gpgsign", key)
|
||||||
|
return "blah", nil
|
||||||
|
},
|
||||||
|
utils.NewDummyLog(),
|
||||||
|
)
|
||||||
|
result := real.Get("commit.gpgsign")
|
||||||
|
assert.Equal(t, "blah", result)
|
||||||
|
result = real.Get("commit.gpgsign")
|
||||||
|
assert.Equal(t, "blah", result)
|
||||||
|
assert.Equal(t, 1, count)
|
||||||
|
}
|
22
pkg/commands/git_config/fake_git_config.go
Normal file
22
pkg/commands/git_config/fake_git_config.go
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
package git_config
|
||||||
|
|
||||||
|
type FakeGitConfig struct {
|
||||||
|
mockResponses map[string]string
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewFakeGitConfig(mockResponses map[string]string) *FakeGitConfig {
|
||||||
|
return &FakeGitConfig{
|
||||||
|
mockResponses: mockResponses,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (self *FakeGitConfig) Get(key string) string {
|
||||||
|
if self.mockResponses == nil {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
return self.mockResponses[key]
|
||||||
|
}
|
||||||
|
|
||||||
|
func (self *FakeGitConfig) GetBool(key string) bool {
|
||||||
|
return isTruthy(self.Get(key))
|
||||||
|
}
|
@ -1,4 +1,4 @@
|
|||||||
package commands
|
package git_config
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
@ -8,6 +8,7 @@ import (
|
|||||||
|
|
||||||
"github.com/go-errors/errors"
|
"github.com/go-errors/errors"
|
||||||
gogit "github.com/jesseduffield/go-git/v5"
|
gogit "github.com/jesseduffield/go-git/v5"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
|
||||||
"github.com/jesseduffield/lazygit/pkg/config"
|
"github.com/jesseduffield/lazygit/pkg/config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/i18n"
|
"github.com/jesseduffield/lazygit/pkg/i18n"
|
||||||
@ -210,7 +211,7 @@ func TestNewGitCommand(t *testing.T) {
|
|||||||
t.Run(s.testName, func(t *testing.T) {
|
t.Run(s.testName, func(t *testing.T) {
|
||||||
s.setup()
|
s.setup()
|
||||||
newAppConfig := config.NewDummyAppConfig()
|
newAppConfig := config.NewDummyAppConfig()
|
||||||
s.test(NewGitCommand(utils.NewDummyLog(), oscommands.NewDummyOSCommand(), i18n.NewTranslationSet(utils.NewDummyLog(), newAppConfig.GetUserConfig().Gui.Language), newAppConfig))
|
s.test(NewGitCommand(utils.NewDummyLog(), oscommands.NewDummyOSCommand(), i18n.NewTranslationSet(utils.NewDummyLog(), newAppConfig.GetUserConfig().Gui.Language), newAppConfig, git_config.NewFakeGitConfig(nil)))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -15,7 +15,7 @@ type GetStatusFileOptions struct {
|
|||||||
|
|
||||||
func (c *GitCommand) GetStatusFiles(opts GetStatusFileOptions) []*models.File {
|
func (c *GitCommand) GetStatusFiles(opts GetStatusFileOptions) []*models.File {
|
||||||
// check if config wants us ignoring untracked files
|
// check if config wants us ignoring untracked files
|
||||||
untrackedFilesSetting := c.GetConfigValue("status.showUntrackedFiles")
|
untrackedFilesSetting := c.GitConfig.Get("status.showUntrackedFiles")
|
||||||
|
|
||||||
if untrackedFilesSetting == "" {
|
if untrackedFilesSetting == "" {
|
||||||
untrackedFilesSetting = "all"
|
untrackedFilesSetting = "all"
|
||||||
|
@ -8,6 +8,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/secureexec"
|
"github.com/jesseduffield/lazygit/pkg/secureexec"
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
@ -247,10 +248,7 @@ func TestCreatePullRequest(t *testing.T) {
|
|||||||
"invalid.work.com": "noservice:invalid.work.com",
|
"invalid.work.com": "noservice:invalid.work.com",
|
||||||
"noservice.work.com": "noservice.work.com",
|
"noservice.work.com": "noservice.work.com",
|
||||||
}
|
}
|
||||||
gitCommand.getGitConfigValue = func(path string) (string, error) {
|
gitCommand.GitConfig = git_config.NewFakeGitConfig(map[string]string{"remote.origin.url": s.remoteUrl})
|
||||||
assert.Equal(t, path, "remote.origin.url")
|
|
||||||
return s.remoteUrl, nil
|
|
||||||
}
|
|
||||||
dummyPullRequest := NewPullRequest(gitCommand)
|
dummyPullRequest := NewPullRequest(gitCommand)
|
||||||
s.test(dummyPullRequest.Create(s.from, s.to))
|
s.test(dummyPullRequest.Create(s.from, s.to))
|
||||||
})
|
})
|
||||||
|
@ -8,6 +8,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/secureexec"
|
"github.com/jesseduffield/lazygit/pkg/secureexec"
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
@ -247,10 +248,7 @@ func TestCreatePullRequestOnWindows(t *testing.T) {
|
|||||||
"invalid.work.com": "noservice:invalid.work.com",
|
"invalid.work.com": "noservice:invalid.work.com",
|
||||||
"noservice.work.com": "noservice.work.com",
|
"noservice.work.com": "noservice.work.com",
|
||||||
}
|
}
|
||||||
gitCommand.getGitConfigValue = func(path string) (string, error) {
|
gitCommand.GitConfig = git_config.NewFakeGitConfig(map[string]string{"remote.origin.url": s.remoteUrl})
|
||||||
assert.Equal(t, path, "remote.origin.url")
|
|
||||||
return s.remoteUrl, nil
|
|
||||||
}
|
|
||||||
dummyPullRequest := NewPullRequest(gitCommand)
|
dummyPullRequest := NewPullRequest(gitCommand)
|
||||||
s.test(dummyPullRequest.Create(s.from, s.to))
|
s.test(dummyPullRequest.Create(s.from, s.to))
|
||||||
})
|
})
|
||||||
|
@ -38,5 +38,5 @@ func (c *GitCommand) CheckRemoteBranchExists(branchName string) bool {
|
|||||||
|
|
||||||
// GetRemoteURL returns current repo remote url
|
// GetRemoteURL returns current repo remote url
|
||||||
func (c *GitCommand) GetRemoteURL() string {
|
func (c *GitCommand) GetRemoteURL() string {
|
||||||
return c.GetConfigValue("remote.origin.url")
|
return c.GitConfig.Get("remote.origin.url")
|
||||||
}
|
}
|
||||||
|
@ -18,10 +18,6 @@ type PushOpts struct {
|
|||||||
func (c *GitCommand) Push(opts PushOpts) error {
|
func (c *GitCommand) Push(opts PushOpts) error {
|
||||||
cmdStr := "git push"
|
cmdStr := "git push"
|
||||||
|
|
||||||
if c.GetConfigValue("push.followTags") != "false" {
|
|
||||||
cmdStr += " --follow-tags"
|
|
||||||
}
|
|
||||||
|
|
||||||
if opts.Force {
|
if opts.Force {
|
||||||
cmdStr += " --force-with-lease"
|
cmdStr += " --force-with-lease"
|
||||||
}
|
}
|
||||||
|
@ -12,7 +12,6 @@ import (
|
|||||||
func TestGitCommandPush(t *testing.T) {
|
func TestGitCommandPush(t *testing.T) {
|
||||||
type scenario struct {
|
type scenario struct {
|
||||||
testName string
|
testName string
|
||||||
getGitConfigValue func(string) (string, error)
|
|
||||||
command func(string, ...string) *exec.Cmd
|
command func(string, ...string) *exec.Cmd
|
||||||
opts PushOpts
|
opts PushOpts
|
||||||
test func(error)
|
test func(error)
|
||||||
@ -24,42 +23,7 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
|
|
||||||
scenarios := []scenario{
|
scenarios := []scenario{
|
||||||
{
|
{
|
||||||
"Push with force disabled, follow-tags on",
|
"Push with force disabled",
|
||||||
func(string) (string, error) {
|
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
|
||||||
assert.EqualValues(t, "git", cmd)
|
|
||||||
assert.EqualValues(t, []string{"push", "--follow-tags"}, args)
|
|
||||||
|
|
||||||
return secureexec.Command("echo")
|
|
||||||
},
|
|
||||||
PushOpts{Force: false, PromptUserForCredential: prompt},
|
|
||||||
func(err error) {
|
|
||||||
assert.NoError(t, err)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Push with force enabled, follow-tags on",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
|
||||||
assert.EqualValues(t, "git", cmd)
|
|
||||||
assert.EqualValues(t, []string{"push", "--follow-tags", "--force-with-lease"}, args)
|
|
||||||
|
|
||||||
return secureexec.Command("echo")
|
|
||||||
},
|
|
||||||
PushOpts{Force: true, PromptUserForCredential: prompt},
|
|
||||||
func(err error) {
|
|
||||||
assert.NoError(t, err)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Push with force disabled, follow-tags off",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
assert.EqualValues(t, "git", cmd)
|
assert.EqualValues(t, "git", cmd)
|
||||||
assert.EqualValues(t, []string{"push"}, args)
|
assert.EqualValues(t, []string{"push"}, args)
|
||||||
@ -72,13 +36,23 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"Push with an error occurring, follow-tags on",
|
"Push with force enabled",
|
||||||
func(string) (string, error) {
|
|
||||||
return "", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
assert.EqualValues(t, "git", cmd)
|
assert.EqualValues(t, "git", cmd)
|
||||||
assert.EqualValues(t, []string{"push", "--follow-tags"}, args)
|
assert.EqualValues(t, []string{"push", "--force-with-lease"}, args)
|
||||||
|
|
||||||
|
return secureexec.Command("echo")
|
||||||
|
},
|
||||||
|
PushOpts{Force: true, PromptUserForCredential: prompt},
|
||||||
|
func(err error) {
|
||||||
|
assert.NoError(t, err)
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"Push with an error occurring",
|
||||||
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
|
assert.EqualValues(t, "git", cmd)
|
||||||
|
assert.EqualValues(t, []string{"push"}, args)
|
||||||
return secureexec.Command("test")
|
return secureexec.Command("test")
|
||||||
},
|
},
|
||||||
PushOpts{Force: false, PromptUserForCredential: prompt},
|
PushOpts{Force: false, PromptUserForCredential: prompt},
|
||||||
@ -87,10 +61,7 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"Push with force disabled, follow-tags off, upstream supplied",
|
"Push with force disabled, upstream supplied",
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
assert.EqualValues(t, "git", cmd)
|
assert.EqualValues(t, "git", cmd)
|
||||||
assert.EqualValues(t, []string{"push", "origin", "master"}, args)
|
assert.EqualValues(t, []string{"push", "origin", "master"}, args)
|
||||||
@ -108,10 +79,7 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"Push with force disabled, follow-tags off, setting upstream",
|
"Push with force disabled, setting upstream",
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
assert.EqualValues(t, "git", cmd)
|
assert.EqualValues(t, "git", cmd)
|
||||||
assert.EqualValues(t, []string{"push", "--set-upstream", "origin", "master"}, args)
|
assert.EqualValues(t, []string{"push", "--set-upstream", "origin", "master"}, args)
|
||||||
@ -130,10 +98,7 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"Push with force enabled, follow-tags off, setting upstream",
|
"Push with force enabled, setting upstream",
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
assert.EqualValues(t, "git", cmd)
|
assert.EqualValues(t, "git", cmd)
|
||||||
assert.EqualValues(t, []string{"push", "--force-with-lease", "--set-upstream", "origin", "master"}, args)
|
assert.EqualValues(t, []string{"push", "--force-with-lease", "--set-upstream", "origin", "master"}, args)
|
||||||
@ -153,9 +118,6 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"Push with remote branch but no origin",
|
"Push with remote branch but no origin",
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
return nil
|
return nil
|
||||||
},
|
},
|
||||||
@ -172,10 +134,7 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"Push with force disabled, follow-tags off, upstream supplied",
|
"Push with force disabled, upstream supplied",
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
func(cmd string, args ...string) *exec.Cmd {
|
||||||
assert.EqualValues(t, "git", cmd)
|
assert.EqualValues(t, "git", cmd)
|
||||||
assert.EqualValues(t, []string{"push", "origin", "master"}, args)
|
assert.EqualValues(t, []string{"push", "origin", "master"}, args)
|
||||||
@ -192,57 +151,12 @@ func TestGitCommandPush(t *testing.T) {
|
|||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
|
||||||
"Push with force disabled, follow-tags off, setting upstream",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
|
||||||
assert.EqualValues(t, "git", cmd)
|
|
||||||
assert.EqualValues(t, []string{"push", "--set-upstream", "origin", "master"}, args)
|
|
||||||
|
|
||||||
return secureexec.Command("echo")
|
|
||||||
},
|
|
||||||
PushOpts{
|
|
||||||
Force: false,
|
|
||||||
UpstreamRemote: "origin",
|
|
||||||
UpstreamBranch: "master",
|
|
||||||
PromptUserForCredential: prompt,
|
|
||||||
SetUpstream: true,
|
|
||||||
},
|
|
||||||
func(err error) {
|
|
||||||
assert.NoError(t, err)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"Push with force enabled, follow-tags off, setting upstream",
|
|
||||||
func(string) (string, error) {
|
|
||||||
return "false", nil
|
|
||||||
},
|
|
||||||
func(cmd string, args ...string) *exec.Cmd {
|
|
||||||
assert.EqualValues(t, "git", cmd)
|
|
||||||
assert.EqualValues(t, []string{"push", "--force-with-lease", "--set-upstream", "origin", "master"}, args)
|
|
||||||
|
|
||||||
return secureexec.Command("echo")
|
|
||||||
},
|
|
||||||
PushOpts{
|
|
||||||
Force: true,
|
|
||||||
UpstreamRemote: "origin",
|
|
||||||
UpstreamBranch: "master",
|
|
||||||
PromptUserForCredential: prompt,
|
|
||||||
SetUpstream: true,
|
|
||||||
},
|
|
||||||
func(err error) {
|
|
||||||
assert.NoError(t, err)
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, s := range scenarios {
|
for _, s := range scenarios {
|
||||||
t.Run(s.testName, func(t *testing.T) {
|
t.Run(s.testName, func(t *testing.T) {
|
||||||
gitCmd := NewDummyGitCommand()
|
gitCmd := NewDummyGitCommand()
|
||||||
gitCmd.OSCommand.Command = s.command
|
gitCmd.OSCommand.Command = s.command
|
||||||
gitCmd.getGitConfigValue = s.getGitConfigValue
|
|
||||||
err := gitCmd.Push(s.opts)
|
err := gitCmd.Push(s.opts)
|
||||||
s.test(err)
|
s.test(err)
|
||||||
})
|
})
|
||||||
|
@ -6,6 +6,7 @@ import (
|
|||||||
|
|
||||||
"github.com/jesseduffield/gocui"
|
"github.com/jesseduffield/gocui"
|
||||||
"github.com/jesseduffield/lazygit/pkg/commands"
|
"github.com/jesseduffield/lazygit/pkg/commands"
|
||||||
|
"github.com/jesseduffield/lazygit/pkg/commands/git_config"
|
||||||
"github.com/jesseduffield/lazygit/pkg/env"
|
"github.com/jesseduffield/lazygit/pkg/env"
|
||||||
"github.com/jesseduffield/lazygit/pkg/gui/style"
|
"github.com/jesseduffield/lazygit/pkg/gui/style"
|
||||||
"github.com/jesseduffield/lazygit/pkg/utils"
|
"github.com/jesseduffield/lazygit/pkg/utils"
|
||||||
@ -72,7 +73,7 @@ func (gui *Gui) dispatchSwitchToRepo(path string, reuse bool) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
newGitCommand, err := commands.NewGitCommand(gui.Log, gui.OSCommand, gui.Tr, gui.Config)
|
newGitCommand, err := commands.NewGitCommand(gui.Log, gui.OSCommand, gui.Tr, gui.Config, git_config.NewStdCachedGitConfig(gui.Log))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1 @@
|
|||||||
|
myfile3
|
@ -0,0 +1 @@
|
|||||||
|
d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 branch 'master' of ../actual_remote
|
1
test/integration/pushFollowTags/expected/.git_keep/HEAD
Normal file
1
test/integration/pushFollowTags/expected/.git_keep/HEAD
Normal file
@ -0,0 +1 @@
|
|||||||
|
ref: refs/heads/master
|
18
test/integration/pushFollowTags/expected/.git_keep/config
Normal file
18
test/integration/pushFollowTags/expected/.git_keep/config
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
[core]
|
||||||
|
repositoryformatversion = 0
|
||||||
|
filemode = true
|
||||||
|
bare = false
|
||||||
|
logallrefupdates = true
|
||||||
|
ignorecase = true
|
||||||
|
precomposeunicode = true
|
||||||
|
[user]
|
||||||
|
email = CI@example.com
|
||||||
|
name = CI
|
||||||
|
[remote "origin"]
|
||||||
|
url = ../actual_remote
|
||||||
|
fetch = +refs/heads/*:refs/remotes/origin/*
|
||||||
|
[branch "master"]
|
||||||
|
remote = origin
|
||||||
|
merge = refs/heads/master
|
||||||
|
[push]
|
||||||
|
followTags = true
|
@ -0,0 +1 @@
|
|||||||
|
Unnamed repository; edit this file 'description' to name the repository.
|
BIN
test/integration/pushFollowTags/expected/.git_keep/index
Normal file
BIN
test/integration/pushFollowTags/expected/.git_keep/index
Normal file
Binary file not shown.
@ -0,0 +1,7 @@
|
|||||||
|
# git ls-files --others --exclude-from=.git/info/exclude
|
||||||
|
# Lines that start with '#' are comments.
|
||||||
|
# For a project mostly in C, the following would be a good set of
|
||||||
|
# exclude patterns (uncomment them if you want to use them):
|
||||||
|
# *.[oa]
|
||||||
|
# *~
|
||||||
|
.DS_Store
|
@ -0,0 +1,3 @@
|
|||||||
|
0000000000000000000000000000000000000000 f27af92910b10e6ddf592fae975337355579464b CI <CI@example.com> 1634944096 +1100 commit (initial): myfile1
|
||||||
|
f27af92910b10e6ddf592fae975337355579464b d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 CI <CI@example.com> 1634944096 +1100 commit: myfile2
|
||||||
|
d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 aea6b2960cc3e7a2453ce3490ca09d090d7ce223 CI <CI@example.com> 1634944096 +1100 commit: myfile3
|
@ -0,0 +1,3 @@
|
|||||||
|
0000000000000000000000000000000000000000 f27af92910b10e6ddf592fae975337355579464b CI <CI@example.com> 1634944096 +1100 commit (initial): myfile1
|
||||||
|
f27af92910b10e6ddf592fae975337355579464b d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 CI <CI@example.com> 1634944096 +1100 commit: myfile2
|
||||||
|
d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 aea6b2960cc3e7a2453ce3490ca09d090d7ce223 CI <CI@example.com> 1634944096 +1100 commit: myfile3
|
@ -0,0 +1,2 @@
|
|||||||
|
0000000000000000000000000000000000000000 d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 CI <CI@example.com> 1634944096 +1100 fetch origin: storing head
|
||||||
|
d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 aea6b2960cc3e7a2453ce3490ca09d090d7ce223 CI <CI@example.com> 1634944097 +1100 update by push
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,4 @@
|
|||||||
|
xЌОA
|
||||||
|
В0@QЧ9Eц‚d’ЙДЎ«#if°РШR"иннЬ~ЮвOkks·Аx껈Н) дИкjQ&b-ик‰ЄчЕ©G іе]^ЭЄOYЩ3ёNЁVЌм5§B
|
||||||
|
1ЖДHXL~чзєЫaґ·a|И'·m‘Лґ¶»
|
||||||
|
И€ЋЙћњ3G=¦єьЙMыкј€7?љS9і
|
Binary file not shown.
@ -0,0 +1,2 @@
|
|||||||
|
x█мA
|
||||||
|
┐0@я╝s┼ый▄NгJ\y▄≤L╗Ю░")╢╥в#tШyПS5[к╔М╙─*╘`■eЙ3Ё▓≈Л╘▀T^╦об%╕{ГБ╖╫Йс▐iУМ╫И-U{Iо│┐ю∙я²У°4Щ⌠;Ш∙uSr3m,у
|
@ -0,0 +1 @@
|
|||||||
|
aea6b2960cc3e7a2453ce3490ca09d090d7ce223
|
@ -0,0 +1 @@
|
|||||||
|
aea6b2960cc3e7a2453ce3490ca09d090d7ce223
|
@ -0,0 +1 @@
|
|||||||
|
3410e6811881ccede9ff762c875f9b99a3e6eaef
|
1
test/integration/pushFollowTags/expected/myfile1
Normal file
1
test/integration/pushFollowTags/expected/myfile1
Normal file
@ -0,0 +1 @@
|
|||||||
|
test1
|
1
test/integration/pushFollowTags/expected/myfile2
Normal file
1
test/integration/pushFollowTags/expected/myfile2
Normal file
@ -0,0 +1 @@
|
|||||||
|
test2
|
1
test/integration/pushFollowTags/expected/myfile3
Normal file
1
test/integration/pushFollowTags/expected/myfile3
Normal file
@ -0,0 +1 @@
|
|||||||
|
test3
|
1
test/integration/pushFollowTags/expected_remote/HEAD
Normal file
1
test/integration/pushFollowTags/expected_remote/HEAD
Normal file
@ -0,0 +1 @@
|
|||||||
|
ref: refs/heads/master
|
8
test/integration/pushFollowTags/expected_remote/config
Normal file
8
test/integration/pushFollowTags/expected_remote/config
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
[core]
|
||||||
|
repositoryformatversion = 0
|
||||||
|
filemode = true
|
||||||
|
bare = true
|
||||||
|
ignorecase = true
|
||||||
|
precomposeunicode = true
|
||||||
|
[remote "origin"]
|
||||||
|
url = /Users/jesseduffieldduffield/go/src/github.com/jesseduffield/lazygit/test/integration/pushFollowTags/./actual
|
@ -0,0 +1 @@
|
|||||||
|
Unnamed repository; edit this file 'description' to name the repository.
|
@ -0,0 +1,7 @@
|
|||||||
|
# git ls-files --others --exclude-from=.git/info/exclude
|
||||||
|
# Lines that start with '#' are comments.
|
||||||
|
# For a project mostly in C, the following would be a good set of
|
||||||
|
# exclude patterns (uncomment them if you want to use them):
|
||||||
|
# *.[oa]
|
||||||
|
# *~
|
||||||
|
.DS_Store
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,4 @@
|
|||||||
|
xЌОA
|
||||||
|
В0@QЧ9Eц‚d’ЙДЎ«#if°РШR"иннЬ~ЮвOkks·Аx껈Н) дИкjQ&b-ик‰ЄчЕ©G іе]^ЭЄOYЩ3ёNЁVЌм5§B
|
||||||
|
1ЖДHXL~чзєЫaґ·a|И'·m‘Лґ¶»
|
||||||
|
И€ЋЙћњ3G=¦єьЙMыкј€7?љS9і
|
Binary file not shown.
@ -0,0 +1,2 @@
|
|||||||
|
x█мA
|
||||||
|
┐0@я╝s┼ый▄NгJ\y▄≤L╗Ю░")╢╥в#tШyПS5[к╔М╙─*╘`■eЙ3Ё▓≈Л╘▀T^╦об%╕{ГБ╖╫Йс▐iУМ╫И-U{Iо│┐ю∙я²У°4Щ⌠;Ш∙uSr3m,у
|
@ -0,0 +1,2 @@
|
|||||||
|
# pack-refs with: peeled fully-peeled sorted
|
||||||
|
d0d3bfe09c1a5a9631f3041a184d6b9c6d927c83 refs/heads/master
|
@ -0,0 +1 @@
|
|||||||
|
aea6b2960cc3e7a2453ce3490ca09d090d7ce223
|
@ -0,0 +1 @@
|
|||||||
|
3410e6811881ccede9ff762c875f9b99a3e6eaef
|
1
test/integration/pushFollowTags/recording.json
Normal file
1
test/integration/pushFollowTags/recording.json
Normal file
@ -0,0 +1 @@
|
|||||||
|
{"KeyEvents":[{"Timestamp":682,"Mod":0,"Key":256,"Ch":80},{"Timestamp":1641,"Mod":0,"Key":256,"Ch":113}],"ResizeEvents":[{"Timestamp":0,"Width":272,"Height":74}]}
|
32
test/integration/pushFollowTags/setup.sh
Normal file
32
test/integration/pushFollowTags/setup.sh
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
cd $1
|
||||||
|
|
||||||
|
git init
|
||||||
|
|
||||||
|
git config user.email "CI@example.com"
|
||||||
|
git config user.name "CI"
|
||||||
|
|
||||||
|
echo test1 > myfile1
|
||||||
|
git add .
|
||||||
|
git commit -am "myfile1"
|
||||||
|
echo test2 > myfile2
|
||||||
|
git add .
|
||||||
|
git commit -am "myfile2"
|
||||||
|
|
||||||
|
cd ..
|
||||||
|
git clone --bare ./actual actual_remote
|
||||||
|
|
||||||
|
cd actual
|
||||||
|
|
||||||
|
echo test3 > myfile3
|
||||||
|
git add .
|
||||||
|
git commit -am "myfile3"
|
||||||
|
|
||||||
|
git remote add origin ../actual_remote
|
||||||
|
git fetch origin
|
||||||
|
git branch --set-upstream-to=origin/master master
|
||||||
|
git config push.followTags true
|
||||||
|
git tag -a v1.0 -m "my version 1.0"
|
1
test/integration/pushFollowTags/test.json
Normal file
1
test/integration/pushFollowTags/test.json
Normal file
@ -0,0 +1 @@
|
|||||||
|
{ "description": "push changes to the remote, when --follow-tags is configured", "speed": 10 }
|
@ -0,0 +1 @@
|
|||||||
|
myfile3
|
@ -0,0 +1 @@
|
|||||||
|
8f99b05bf3462e1a797335475bff5fabe3ae9ec5 branch 'master' of ../actual_remote
|
@ -0,0 +1 @@
|
|||||||
|
ref: refs/heads/master
|
16
test/integration/pushNoFollowTags/expected/.git_keep/config
Normal file
16
test/integration/pushNoFollowTags/expected/.git_keep/config
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
[core]
|
||||||
|
repositoryformatversion = 0
|
||||||
|
filemode = true
|
||||||
|
bare = false
|
||||||
|
logallrefupdates = true
|
||||||
|
ignorecase = true
|
||||||
|
precomposeunicode = true
|
||||||
|
[user]
|
||||||
|
email = CI@example.com
|
||||||
|
name = CI
|
||||||
|
[remote "origin"]
|
||||||
|
url = ../actual_remote
|
||||||
|
fetch = +refs/heads/*:refs/remotes/origin/*
|
||||||
|
[branch "master"]
|
||||||
|
remote = origin
|
||||||
|
merge = refs/heads/master
|
@ -0,0 +1 @@
|
|||||||
|
Unnamed repository; edit this file 'description' to name the repository.
|
BIN
test/integration/pushNoFollowTags/expected/.git_keep/index
Normal file
BIN
test/integration/pushNoFollowTags/expected/.git_keep/index
Normal file
Binary file not shown.
@ -0,0 +1,7 @@
|
|||||||
|
# git ls-files --others --exclude-from=.git/info/exclude
|
||||||
|
# Lines that start with '#' are comments.
|
||||||
|
# For a project mostly in C, the following would be a good set of
|
||||||
|
# exclude patterns (uncomment them if you want to use them):
|
||||||
|
# *.[oa]
|
||||||
|
# *~
|
||||||
|
.DS_Store
|
@ -0,0 +1,3 @@
|
|||||||
|
0000000000000000000000000000000000000000 fb20b9e96648c61699f9faf3a4383340fefd5f91 CI <CI@example.com> 1634944114 +1100 commit (initial): myfile1
|
||||||
|
fb20b9e96648c61699f9faf3a4383340fefd5f91 8f99b05bf3462e1a797335475bff5fabe3ae9ec5 CI <CI@example.com> 1634944114 +1100 commit: myfile2
|
||||||
|
8f99b05bf3462e1a797335475bff5fabe3ae9ec5 03009ca2af4be2a9bb49206974ce9c97eaa2da23 CI <CI@example.com> 1634944114 +1100 commit: myfile3
|
@ -0,0 +1,3 @@
|
|||||||
|
0000000000000000000000000000000000000000 fb20b9e96648c61699f9faf3a4383340fefd5f91 CI <CI@example.com> 1634944114 +1100 commit (initial): myfile1
|
||||||
|
fb20b9e96648c61699f9faf3a4383340fefd5f91 8f99b05bf3462e1a797335475bff5fabe3ae9ec5 CI <CI@example.com> 1634944114 +1100 commit: myfile2
|
||||||
|
8f99b05bf3462e1a797335475bff5fabe3ae9ec5 03009ca2af4be2a9bb49206974ce9c97eaa2da23 CI <CI@example.com> 1634944114 +1100 commit: myfile3
|
@ -0,0 +1,2 @@
|
|||||||
|
0000000000000000000000000000000000000000 8f99b05bf3462e1a797335475bff5fabe3ae9ec5 CI <CI@example.com> 1634944115 +1100 fetch origin: storing head
|
||||||
|
8f99b05bf3462e1a797335475bff5fabe3ae9ec5 03009ca2af4be2a9bb49206974ce9c97eaa2da23 CI <CI@example.com> 1634944115 +1100 update by push
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,3 @@
|
|||||||
|
x�ÎA
|
||||||
|
Â0@Q×9ÅìÉ$Ó±"BW=FÒÌ`¡±¥DÐÛÛ#¸ý¼ÅŸÖZç(tj»*¤k$L�˜/EÕ„EY,sä>0—²·@ÈnK»¾X>‹
|
||||||
|
3õ#‹˜X²˜(ö1’7µÒ™ Kïö\wF¸
ãC?©n‹^¦µÞ9’!œ½wG=¦šþÉ]ýÚ¼hp?Ö::
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,3 @@
|
|||||||
|
x█мA
|
||||||
|
б0Faв9еЛиъ▌сD└╝z▄4≥`║C╓Dпшш#╦}|ПR5[│ЕтvUР*╘Ь(к0jхл┼ 9═▀(/эgАс╣sЯщ·u╖i╕ш4?ТМ╣И%U╩╓Г▒`:ч╩ё⌠╕rgъ╡n
|
||||||
|
В0┬,ц
|
@ -0,0 +1 @@
|
|||||||
|
03009ca2af4be2a9bb49206974ce9c97eaa2da23
|
@ -0,0 +1 @@
|
|||||||
|
03009ca2af4be2a9bb49206974ce9c97eaa2da23
|
@ -0,0 +1 @@
|
|||||||
|
e19bd88e6b3a0d7e4ffc1de39b34d5a312fb9b77
|
1
test/integration/pushNoFollowTags/expected/myfile1
Normal file
1
test/integration/pushNoFollowTags/expected/myfile1
Normal file
@ -0,0 +1 @@
|
|||||||
|
test1
|
1
test/integration/pushNoFollowTags/expected/myfile2
Normal file
1
test/integration/pushNoFollowTags/expected/myfile2
Normal file
@ -0,0 +1 @@
|
|||||||
|
test2
|
1
test/integration/pushNoFollowTags/expected/myfile3
Normal file
1
test/integration/pushNoFollowTags/expected/myfile3
Normal file
@ -0,0 +1 @@
|
|||||||
|
test3
|
1
test/integration/pushNoFollowTags/expected_remote/HEAD
Normal file
1
test/integration/pushNoFollowTags/expected_remote/HEAD
Normal file
@ -0,0 +1 @@
|
|||||||
|
ref: refs/heads/master
|
8
test/integration/pushNoFollowTags/expected_remote/config
Normal file
8
test/integration/pushNoFollowTags/expected_remote/config
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
[core]
|
||||||
|
repositoryformatversion = 0
|
||||||
|
filemode = true
|
||||||
|
bare = true
|
||||||
|
ignorecase = true
|
||||||
|
precomposeunicode = true
|
||||||
|
[remote "origin"]
|
||||||
|
url = /Users/jesseduffieldduffield/go/src/github.com/jesseduffield/lazygit/test/integration/pushNoFollowTags/./actual
|
@ -0,0 +1 @@
|
|||||||
|
Unnamed repository; edit this file 'description' to name the repository.
|
@ -0,0 +1,7 @@
|
|||||||
|
# git ls-files --others --exclude-from=.git/info/exclude
|
||||||
|
# Lines that start with '#' are comments.
|
||||||
|
# For a project mostly in C, the following would be a good set of
|
||||||
|
# exclude patterns (uncomment them if you want to use them):
|
||||||
|
# *.[oa]
|
||||||
|
# *~
|
||||||
|
.DS_Store
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,3 @@
|
|||||||
|
x�ÎA
|
||||||
|
Â0@Q×9ÅìÉ$Ó±"BW=FÒÌ`¡±¥DÐÛÛ#¸ý¼ÅŸÖZç(tj»*¤k$L�˜/EÕ„EY,sä>0—²·@ÈnK»¾X>‹
|
||||||
|
3õ#‹˜X²˜(ö1’7µÒ™ Kïö\wF¸
ãC?©n‹^¦µÞ9’!œ½wG=¦šþÉ]ýÚ¼hp?Ö::
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user