summaryrefslogtreecommitdiffstats
path: root/pkg
diff options
context:
space:
mode:
authorJesse Duffield <jessedduffield@gmail.com>2018-08-25 11:02:46 +1000
committerJesse Duffield <jessedduffield@gmail.com>2018-08-25 11:02:46 +1000
commitf24c95aedec785985dfcd98ff3997152c193bd3e (patch)
tree9f8ac1a61cf686052f623b767e13d6d1a14e3683 /pkg
parent5628eae502ee3b4d3d72a8e4045713b637f7a764 (diff)
parent93ab892bdd1226f9a519a938c8b28590e71e54f3 (diff)
Merge branch 'master' into feature/auto-updates
Diffstat (limited to 'pkg')
-rw-r--r--pkg/app/app.go7
-rw-r--r--pkg/commands/git.go12
-rw-r--r--pkg/commands/git_test.go2
-rw-r--r--pkg/commands/os.go5
-rw-r--r--pkg/config/app_config.go10
-rw-r--r--pkg/git/branch_list_builder.go2
-rw-r--r--pkg/gui/branches_panel.go21
-rw-r--r--pkg/gui/files_panel.go8
-rw-r--r--pkg/gui/gui.go9
-rw-r--r--pkg/gui/keybindings.go2
-rw-r--r--pkg/gui/view_helpers.go6
-rw-r--r--pkg/i18n/dutch.go8
-rw-r--r--pkg/i18n/english.go8
-rw-r--r--pkg/i18n/i18n.go72
-rw-r--r--pkg/i18n/i18n_test.go81
-rw-r--r--pkg/test/test.go16
-rw-r--r--pkg/updates/updates.go2
-rw-r--r--pkg/utils/utils.go7
-rw-r--r--pkg/utils/utils_test.go33
19 files changed, 233 insertions, 78 deletions
diff --git a/pkg/app/app.go b/pkg/app/app.go
index e1a26e13d..d4219289e 100644
--- a/pkg/app/app.go
+++ b/pkg/app/app.go
@@ -5,7 +5,7 @@ import (
"io/ioutil"
"os"
- "github.com/Sirupsen/logrus"
+ "github.com/sirupsen/logrus"
"github.com/jesseduffield/lazygit/pkg/commands"
"github.com/jesseduffield/lazygit/pkg/config"
"github.com/jesseduffield/lazygit/pkg/gui"
@@ -53,10 +53,7 @@ func NewApp(config config.AppConfigurer) (*App, error) {
return app, err
}
- app.Tr, err = i18n.NewLocalizer(app.Log)
- if err != nil {
- return app, err
- }
+ app.Tr = i18n.NewLocalizer(app.Log)
app.GitCommand, err = commands.NewGitCommand(app.Log, app.OSCommand)
if err != nil {
diff --git a/pkg/commands/git.go b/pkg/commands/git.go
index bf9aa6646..14f3a433a 100644
--- a/pkg/commands/git.go
+++ b/pkg/commands/git.go
@@ -7,7 +7,7 @@ import (
"os/exec"
"strings"
- "github.com/Sirupsen/logrus"
+ "github.com/sirupsen/logrus"
"github.com/jesseduffield/gocui"
"github.com/jesseduffield/lazygit/pkg/utils"
gitconfig "github.com/tcnksm/go-gitconfig"
@@ -223,8 +223,14 @@ func (c *GitCommand) NewBranch(name string) error {
}
// DeleteBranch delete branch
-func (c *GitCommand) DeleteBranch(branch string) error {
- return c.OSCommand.RunCommand("git branch -d " + branch)
+func (c *GitCommand) DeleteBranch(branch string, force bool) error {
+ var command string
+ if force {
+ command = "git branch -D "
+ } else {
+ command = "git branch -d "
+ }
+ return c.OSCommand.RunCommand(command + branch)
}
// ListStash list stash
diff --git a/pkg/commands/git_test.go b/pkg/commands/git_test.go
index 9c2a64330..c930f76eb 100644
--- a/pkg/commands/git_test.go
+++ b/pkg/commands/git_test.go
@@ -5,7 +5,7 @@ import (
"strings"
"testing"
- "github.com/Sirupsen/logrus"
+ "github.com/sirupsen/logrus"
"github.com/jesseduffield/lazygit/pkg/test"
)
diff --git a/pkg/commands/os.go b/pkg/commands/os.go
index 9756d619d..1eef36151 100644
--- a/pkg/commands/os.go
+++ b/pkg/commands/os.go
@@ -11,7 +11,7 @@ import (
"github.com/mgutz/str"
- "github.com/Sirupsen/logrus"
+ "github.com/sirupsen/logrus"
gitconfig "github.com/tcnksm/go-gitconfig"
)
@@ -175,7 +175,8 @@ func (c *OSCommand) Unquote(message string) string {
return message
}
-func (C *OSCommand) AppendLineToFile(filename, line string) error {
+// AppendLineToFile adds a new line in file
+func (c *OSCommand) AppendLineToFile(filename, line string) error {
f, err := os.OpenFile(filename, os.O_APPEND|os.O_WRONLY|os.O_CREATE, 0600)
if err != nil {
return err
diff --git a/pkg/config/app_config.go b/pkg/config/app_config.go
index 9f258d4a6..aa56365e3 100644
--- a/pkg/config/app_config.go
+++ b/pkg/config/app_config.go
@@ -121,10 +121,7 @@ func LoadUserConfigFromFile(v *viper.Viper) error {
folder = configDirs.QueryFolderContainsFile("config.yml")
}
v.AddConfigPath(folder.Path)
- if err := v.MergeInConfig(); err != nil {
- return err
- }
- return nil
+ return v.MergeInConfig()
}
// InsertToUserConfig adds a key/value pair to the user's config and saves it
@@ -139,10 +136,7 @@ func (c *AppConfig) InsertToUserConfig(key, value string) error {
return err
}
v.Set(key, value)
- if err := v.WriteConfig(); err != nil {
- return err
- }
- return nil
+ return v.WriteConfig()
}
func getDefaultConfig() []byte {
diff --git a/pkg/git/branch_list_builder.go b/pkg/git/branch_list_builder.go
index 869e05c98..37421d5b6 100644
--- a/pkg/git/branch_list_builder.go
+++ b/pkg/git/branch_list_builder.go
@@ -7,7 +7,7 @@ import (
"github.com/jesseduffield/lazygit/pkg/commands"
"github.com/jesseduffield/lazygit/pkg/utils"
- "github.com/Sirupsen/logrus"
+ "github.com/sirupsen/logrus"
"gopkg.in/src-d/go-git.v4/plumbing"
)
diff --git a/pkg/gui/branches_panel.go b/pkg/gui/branches_panel.go
index 67e0ceb07..df4dcff78 100644
--- a/pkg/gui/branches_panel.go
+++ b/pkg/gui/branches_panel.go
@@ -62,20 +62,34 @@ func (gui *Gui) handleNewBranch(g *gocui.Gui, v *gocui.View) error {
}
func (gui *Gui) handleDeleteBranch(g *gocui.Gui, v *gocui.View) error {
+ return gui.deleteBranch(g, v, false)
+}
+
+func (gui *Gui) handleForceDeleteBranch(g *gocui.Gui, v *gocui.View) error {
+ return gui.deleteBranch(g, v, true)
+}
+
+func (gui *Gui) deleteBranch(g *gocui.Gui, v *gocui.View, force bool) error {
checkedOutBranch := gui.State.Branches[0]
selectedBranch := gui.getSelectedBranch(v)
if checkedOutBranch.Name == selectedBranch.Name {
return gui.createErrorPanel(g, gui.Tr.SLocalize("CantDeleteCheckOutBranch"))
}
+ title := gui.Tr.SLocalize("DeleteBranch")
+ var messageId string
+ if force {
+ messageId = "ForceDeleteBranchMessage"
+ } else {
+ messageId = "DeleteBranchMessage"
+ }
message := gui.Tr.TemplateLocalize(
- "DeleteBranchMessage",
+ messageId,
Teml{
"selectedBranchName": selectedBranch.Name,
},
)
- title := gui.Tr.SLocalize("DeleteBranch")
return gui.createConfirmationPanel(g, v, title, message, func(g *gocui.Gui, v *gocui.View) error {
- if err := gui.GitCommand.DeleteBranch(selectedBranch.Name); err != nil {
+ if err := gui.GitCommand.DeleteBranch(selectedBranch.Name, force); err != nil {
return gui.createErrorPanel(g, err.Error())
}
return gui.refreshSidePanels(g)
@@ -108,6 +122,7 @@ func (gui *Gui) renderBranchesOptions(g *gocui.Gui) error {
"c": gui.Tr.SLocalize("checkoutByName"),
"n": gui.Tr.SLocalize("newBranch"),
"d": gui.Tr.SLocalize("deleteBranch"),
+ "D": gui.Tr.SLocalize("forceDeleteBranch"),
"← → ↑ ↓": gui.Tr.SLocalize("navigate"),
})
}
diff --git a/pkg/gui/files_panel.go b/pkg/gui/files_panel.go
index 7ddb50811..5791a9d15 100644
--- a/pkg/gui/files_panel.go
+++ b/pkg/gui/files_panel.go
@@ -251,14 +251,6 @@ func (gui *Gui) handleFileEdit(g *gocui.Gui, v *gocui.View) error {
return gui.genericFileOpen(g, v, file.Name, gui.OSCommand.EditFile)
}
-func (gui *Gui) openFile(filename string) error {
- err := gui.OSCommand.OpenFile(filename)
- if err != nil {
- return gui.createErrorPanel(gui.g, err.Error())
- }
- return nil
-}
-
func (gui *Gui) handleFileOpen(g *gocui.Gui, v *gocui.View) error {
file, err := gui.getSelectedFile(g)
if err != nil {
diff --git a/pkg/gui/gui.go b/pkg/gui/gui.go
index baed39056..c00b26b78 100644
--- a/pkg/gui/gui.go
+++ b/pkg/gui/gui.go
@@ -15,13 +15,13 @@ import (
// "strings"
- "github.com/Sirupsen/logrus"
"github.com/golang-collections/collections/stack"
"github.com/jesseduffield/gocui"
"github.com/jesseduffield/lazygit/pkg/commands"
"github.com/jesseduffield/lazygit/pkg/config"
"github.com/jesseduffield/lazygit/pkg/i18n"
"github.com/jesseduffield/lazygit/pkg/updates"
+ "github.com/sirupsen/logrus"
)
// OverlappingEdges determines if panel edges overlap
@@ -152,14 +152,15 @@ func (gui *Gui) setAppStatus(status string) error {
func (gui *Gui) layout(g *gocui.Gui) error {
g.Highlight = true
width, height := g.Size()
+ version := gui.Config.GetVersion()
leftSideWidth := width / 3
statusFilesBoundary := 2
filesBranchesBoundary := 2 * height / 5 // height - 20
commitsBranchesBoundary := 3 * height / 5 // height - 10
commitsStashBoundary := height - 5 // height - 5
+ optionsVersionBoundary := width - max(len(version), 1)
minimumHeight := 16
minimumWidth := 10
- version := gui.Config.GetVersion()
appStatusView, _ := g.View("appStatus")
appStatusOptionsBoundary := -2
@@ -244,7 +245,7 @@ func (gui *Gui) layout(g *gocui.Gui) error {
v.FgColor = gocui.ColorWhite
}
- if v, err := g.SetView("options", appStatusOptionsBoundary-1, optionsTop, width-len(version)-2, optionsTop+2, 0); err != nil {
+ if v, err := g.SetView("options", appStatusOptionsBoundary-1, optionsTop, optionsVersionBoundary-1, optionsTop+2, 0); err != nil {
if err != gocui.ErrUnknownView {
return err
}
@@ -281,7 +282,7 @@ func (gui *Gui) layout(g *gocui.Gui) error {
v.Frame = false
}
- if v, err := g.SetView("version", width-len(version)-1, optionsTop, width, optionsTop+2, 0); err != nil {
+ if v, err := g.SetView("version", optionsVersionBoundary-1, optionsTop, width, optionsTop+2, 0); err != nil {
if err != gocui.ErrUnknownView {
return err
}
diff --git a/pkg/gui/keybindings.go b/pkg/gui/keybindings.go
index 68cccda6b..8041d14ff 100644
--- a/pkg/gui/keybindings.go
+++ b/pkg/gui/keybindings.go
@@ -16,6 +16,7 @@ func (gui *Gui) keybindings(g *gocui.Gui) error {
bindings := []Binding{
{ViewName: "", Key: 'q', Modifier: gocui.ModNone, Handler: gui.quit},
{ViewName: "", Key: gocui.KeyCtrlC, Modifier: gocui.ModNone, Handler: gui.quit},
+ {ViewName: "", Key: gocui.KeyEsc, Modifier: gocui.ModNone, Handler: gui.quit},
{ViewName: "", Key: gocui.KeyPgup, Modifier: gocui.ModNone, Handler: gui.scrollUpMain},
{ViewName: "", Key: gocui.KeyPgdn, Modifier: gocui.ModNone, Handler: gui.scrollDownMain},
{ViewName: "", Key: gocui.KeyCtrlU, Modifier: gocui.ModNone, Handler: gui.scrollUpMain},
@@ -57,6 +58,7 @@ func (gui *Gui) keybindings(g *gocui.Gui) error {
{ViewName: "branches", Key: 'F', Modifier: gocui.ModNone, Handler: gui.handleForceCheckout},
{ViewName: "branches", Key: 'n', Modifier: gocui.ModNone, Handler: gui.handleNewBranch},
{ViewName: "branches", Key: 'd', Modifier: gocui.ModNone, Handler: gui.handleDeleteBranch},
+ {ViewName: "branches", Key: 'D', Modifier: gocui.ModNone, Handler: gui.handleForceDeleteBranch},
{ViewName: "branches", Key: 'm', Modifier: gocui.ModNone, Handler: gui.handleMerge},
{ViewName: "commits", Key: 's', Modifier: gocui.ModNone, Handler: gui.handleCommitSquashDown},
{ViewName: "commits", Key: 'r', Modifier: gocui.ModNone, Handler: gui.handleRenameCommit},
diff --git a/pkg/gui/view_helpers.go b/pkg/gui/view_helpers.go
index cfe985867..91d81b55e 100644
--- a/pkg/gui/view_helpers.go
+++ b/pkg/gui/view_helpers.go
@@ -7,6 +7,8 @@ import (
"time"
"github.com/jesseduffield/gocui"
+ "github.com/jesseduffield/lazygit/pkg/utils"
+ "github.com/spkg/bom"
)
var cyclableViews = []string{"status", "files", "branches", "commits", "stash"}
@@ -224,7 +226,9 @@ func (gui *Gui) renderString(g *gocui.Gui, viewName, s string) error {
gui.Log.Info(s)
}
v.Clear()
- fmt.Fprint(v, s)
+ output := string(bom.Clean([]byte(s)))
+ output = utils.NormalizeLinefeeds(output)
+ fmt.Fprint(v, output)
v.Wrap = true
return nil
})
diff --git a/pkg/i18n/dutch.go b/pkg/i18n/dutch.go
index 60133e662..68e7c82bd 100644
--- a/pkg/i18n/dutch.go
+++ b/pkg/i18n/dutch.go
@@ -132,7 +132,10 @@ func addDutch(i18nObject *i18n.Bundle) error {
Other: "Verwijder branch",
}, &i18n.Message{
ID: "DeleteBranchMessage",
- Other: "Weet je zeker dat je {{.selectedBranchName}} branch wil verwijderen?",
+ Other: "Weet je zeker dat je branch {{.selectedBranchName}} wil verwijderen?",
+ }, &i18n.Message{
+ ID: "ForceDeleteBranchMessage",
+ Other: "Weet je zeker dat je branch {{.selectedBranchName}} geforceerd wil verwijderen?",
}, &i18n.Message{
ID: "CantMergeBranchIntoItself",
Other: "Je kan niet een branch in zichzelf mergen",
@@ -152,6 +155,9 @@ func addDutch(i18nObject *i18n.Bundle) error {
ID: "deleteBranch",
Other: "verwijder branch",
}, &i18n.Message{
+ ID: "forceDeleteBranch",
+ Other: "verwijder branch (forceer)",
+ }, &i18n.Message{
ID: "NoBranchesThisRepo",
Other: "Geen branches voor deze repo",
}, &i18n.Message{
diff --git a/pkg/i18n/english.go b/pkg/i18n/english.go
index c0384136b..38fbac4cb 100644
--- a/pkg/i18n/english.go
+++ b/pkg/i18n/english.go
@@ -140,7 +140,10 @@ func addEnglish(i18nObject *i18n.Bundle) error {
Other: "Delete Branch",
}, &i18n.Message{
ID: "DeleteBranchMessage",
- Other: "Are you sure you want delete the branch {{.selectedBranchName}} ?",
+ Other: "Are you sure you want to delete the branch {{.selectedBranchName}}?",
+ }, &i18n.Message{
+ ID: "ForceDeleteBranchMessage",
+ Other: "Are you sure you want to force delete the branch {{.selectedBranchName}}?",
}, &i18n.Message{
ID: "CantMergeBranchIntoItself",
Other: "You cannot merge a branch into itself",
@@ -160,6 +163,9 @@ func addEnglish(i18nObject *i18n.Bundle) error {
ID: "deleteBranch",
Other: "delete branch",
}, &i18n.Message{
+ ID: "forceDeleteBranch",
+ Other: "delete branch (force)",
+ }, &i18n.Message{
ID: "NoBranchesThisRepo",
Other: "No branches for this repo",
}, &i18n.Message{
diff --git a/pkg/i18n/i18n.go b/pkg/i18n/i18n.go
index e209d55c5..898a13906 100644
--- a/pkg/i18n/i18n.go
+++ b/pkg/i18n/i18n.go
@@ -1,7 +1,7 @@
package i18n
import (
- "github.com/Sirupsen/logrus"
+ "github.com/sirupsen/logrus"
"github.com/cloudfoundry/jibber_jabber"
"github.com/nicksnyder/go-i18n/v2/i18n"
"golang.org/x/text/language"
@@ -18,33 +18,12 @@ type Localizer struct {
}
// NewLocalizer creates a new Localizer
-func NewLocalizer(log *logrus.Logger) (*Localizer, error) {
+func NewLocalizer(log *logrus.Logger) *Localizer {
+ userLang := detectLanguage(jibber_jabber.DetectLanguage)
- // detect the user's language
- userLang, err := jibber_jabber.DetectLanguage()
- if err != nil {
- if err.Error() != "Could not detect Language" {
- return nil, err
- }
- userLang = "C"
- }
log.Info("language: " + userLang)
- // create a i18n bundle that can be used to add translations and other things
- i18nBundle := &i18n.Bundle{DefaultLanguage: language.English}
-
- addBundles(log, i18nBundle)
-
- // return the new localizer that can be used to translate text
- i18nLocalizer := i18n.NewLocalizer(i18nBundle, userLang)
-
- localizer := &Localizer{
- i18nLocalizer: i18nLocalizer,
- language: userLang,
- Log: log,
- }
-
- return localizer, nil
+ return setupLocalizer(log, userLang)
}
// Localize handels the translations
@@ -82,17 +61,42 @@ func (l *Localizer) GetLanguage() string {
// add translation file(s)
func addBundles(log *logrus.Logger, i18nBundle *i18n.Bundle) {
- err := addPolish(i18nBundle)
- if err != nil {
- log.Fatal(err)
+ fs := []func(*i18n.Bundle) error{
+ addPolish,
+ addDutch,
+ addEnglish,
}
- err = addDutch(i18nBundle)
- if err != nil {
- log.Fatal(err)
+
+ for _, f := range fs {
+ if err := f(i18nBundle); err != nil {
+ log.Fatal(err)
+
+ }
}
- err = addEnglish(i18nBundle)
- if err != nil {
- log.Fatal(err)
+}
+
+// detectLanguage extracts user language from environment
+func detectLanguage(langDetector func() (string, error)) string {
+ if userLang, err := langDetector(); err == nil {
+ return userLang
}
+ return "C"
+}
+
+// setupLocalizer creates a new localizer using given userLang
+func setupLocalizer(log *logrus.Logger, userLang string) *Localizer {
+ // create a i18n bundle that can be used to add translations and other things
+ i18nBundle := &i18n.Bundle{DefaultLanguage: language.English}
+
+ addBundles(log, i18nBundle)
+
+ // return the new localizer that can be used to translate text
+ i18nLocalizer := i18n.NewLocalizer(i18nBundle, userLang)
+
+ return &Localizer{
+ i18nLocalizer: i18nLocalizer,
+ language: userLang,
+ Log: log,
+ }
}
diff --git a/pkg/i18n/i18n_test.go b/pkg/i18n/i18n_test.go
new file mode 100644
index 000000000..5eeddb907
--- /dev/null
+++ b/pkg/i18n/i18n_test.go
@@ -0,0 +1,81 @@
+package i18n
+
+import (
+ "fmt"
+ "testing"
+
+ "github.com/nicksnyder/go-i18n/v2/i18n"
+
+ "github.com/sirupsen/logrus"
+ "github.com/stretchr/testify/assert"
+)
+
+func TestNewLocalizer(t *testing.T) {
+ assert.NotNil(t, NewLocalizer(logrus.New()))
+}
+
+func TestDetectLanguage(t *testing.T) {
+ type scenario struct {
+ langDetector func() (string, error)
+ expected string
+ }
+
+ scenarios := []scenario{
+ {
+ func() (string, error) {
+ return "", fmt.Errorf("An error occurred")
+ },
+ "C",
+ },
+ {
+ func() (string, error) {
+ return "en", nil
+ },
+ "en",
+ },
+ }
+
+ for _, s := range scenarios {
+ assert.EqualValues(t, s.expected, detectLanguage(s.langDetector))
+ }
+}
+
+func TestLocalizer(t *testing.T) {
+ type scenario struct {
+ userLang string
+ test func(*Localizer)
+ }
+
+ scenarios := []scenario{
+ {
+ "C",
+ func(l *Localizer) {
+ assert.EqualValues(t, "C", l.GetLanguage())
+ assert.Equal(t, "Diff", l.Localize(&i18n.LocalizeConfig{
+ DefaultMessage: &i18n.Message{
+ ID: "DiffTitle",
+ },
+ }))
+ assert.Equal(t, "Diff", l.SLocalize("DiffTitle"))
+ assert.Equal(t, "Are you sure you want to delete the branch test?", l.TemplateLocalize("DeleteBranchMessage", Teml{"selectedBranchName": "test"}))
+ },
+ },
+ {
+ "nl",
+ func(l *Localizer) {
+ assert.EqualValues(t, "nl", l.GetLanguage())
+ assert.Equal(t, "Diff", l.Localize(&i18n.LocalizeConfig{
+ DefaultMessage: &i18n.Message{
+ ID: "DiffTitle",
+ },
+ }))
+ assert.Equal(t, "Diff", l.SLocalize("DiffTitle"))
+ assert.Equal(t, "Weet je zeker dat je branch test wil verwijderen?", l.TemplateLocalize("DeleteBranchMessage", Teml{"selectedBranchName": "test"}))
+ },
+ },
+ }
+
+ for _, s := range scenarios {
+ s.test(setupLocalizer(logrus.New(), s.userLang))
+ }
+}
diff --git a/pkg/test/test.go b/pkg/test/test.go
index 7bdbd4c10..6346ac556 100644
--- a/pkg/test/test.go
+++ b/pkg/test/test.go
@@ -4,6 +4,7 @@ import (
"errors"
"os"
"os/exec"
+ "path/filepath"
"github.com/jesseduffield/lazygit/pkg/utils"
)
@@ -11,15 +12,20 @@ import (
// GenerateRepo generates a repo from test/repos and changes the directory to be
// inside the newly made repo
func GenerateRepo(filename string) error {
- testPath := utils.GetProjectRoot() + "/test/repos/"
+ reposDir := "/test/repos/"
+ testPath := utils.GetProjectRoot() + reposDir
+
+ // workaround for debian packaging
+ if _, err := os.Stat(testPath); os.IsNotExist(err) {
+ cwd, _ := os.Getwd()
+ testPath = filepath.Dir(filepath.Dir(cwd)) + reposDir
+ }
if err := os.Chdir(testPath); err != nil {
return err
}
if output, err := exec.Command("bash", filename).CombinedOutput(); err != nil {
return errors.New(string(output))
}
- if err := os.Chdir(testPath + "repo"); err != nil {
- return err
- }
- return nil
+
+ return os.Chdir(testPath + "repo")
}
diff --git a/pkg/updates/updates.go b/pkg/updates/updates.go
index dce62bdb4..7e745635c 100644
--- a/pkg/updates/updates.go
+++ b/pkg/updates/updates.go
@@ -13,10 +13,10 @@ import (
"github.com/kardianos/osext"
- "github.com/Sirupsen/logrus"
getter "github.com/jesseduffield/go-getter"
"github.com/jesseduffield/lazygit/pkg/commands"
"github.com/jesseduffield/lazygit/pkg/config"
+ "github.com/sirupsen/logrus"
)
// Update checks for updates and does updates
diff --git a/pkg/utils/utils.go b/pkg/utils/utils.go
index 0333ac45a..511de1af1 100644
--- a/pkg/utils/utils.go
+++ b/pkg/utils/utils.go
@@ -64,6 +64,13 @@ func TrimTrailingNewline(str string) string {
return str
}
+// NormalizeLinefeeds - Removes all Windows and Mac style line feeds
+func NormalizeLinefeeds(str string) string {
+ str = strings.Replace(str, "\r\n", "\n", -1)
+ str = strings.Replace(str, "\r", "", -1)
+ return str
+}
+
// GetProjectRoot returns the path to the root of the project. Only to be used
// in testing contexts, as with binaries it's unlikely this path will exist on
// the machine
diff --git a/pkg/utils/utils_test.go b/pkg/utils/utils_test.go
index 58e78cce9..46b264945 100644
--- a/pkg/utils/utils_test.go
+++ b/pkg/utils/utils_test.go
@@ -81,3 +81,36 @@ func TestTrimTrailingNewline(t *testing.T) {
assert.EqualValues(t, s.expected, TrimTrailingNewline(s.str))
}
}
+
+func TestNormalizeLinefeeds(t *testing.T) {
+ type scenario struct {
+ byteArray []byte
+ expected []byte
+ }
+ var scenarios = []scenario{
+ {
+ // \r\n
+ []byte{97, 115, 100, 102, 13, 10},
+ []byte{97, 115, 100, 102, 10},
+ },
+ {
+ // bash\r\nblah
+ []byte{97, 115, 100, 102, 13, 10, 97, 115, 100, 102},
+ []byte{97, 115, 100, 102, 10, 97, 115, 100, 102},
+ },
+ {
+ // \r
+ []byte{97, 115, 100, 102, 13},
+ []byte{97, 115, 100, 102},
+ },
+ {
+ // \n
+ []byte{97, 115, 100, 102, 10},
+ []byte{97, 115, 100, 102, 10},
+ },
+ }
+
+ for _, s := range scenarios {
+ assert.EqualValues(t, string(s.expected), NormalizeLinefeeds(string(s.byteArray)))
+ }
+}