Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions docs-master/Config.md
Original file line number Diff line number Diff line change
Expand Up @@ -321,6 +321,10 @@ gui:
# is already active, go to next tab instead
switchTabsWithPanelJumpKeys: false

# Commit list date source.
# One of 'author' (default) | 'committer'
commitDateSource: author

# Config relating to git
git:
# Array of pagers. Each entry has the following format:
Expand Down
27 changes: 15 additions & 12 deletions pkg/commands/git_commands/commit_loader.go
Original file line number Diff line number Diff line change
Expand Up @@ -190,29 +190,30 @@ func (self *CommitLoader) MergeRebasingCommits(hashPool *utils.StringPool, commi
// example input:
// 8ad01fe32fcc20f07bc6693f87aa4977c327f1e1|10 hours ago|Jesse Duffield| (HEAD -> master, tag: v0.15.2)|refresh commits when adding a tag
func (self *CommitLoader) extractCommitFromLine(hashPool *utils.StringPool, line string, showDivergence bool) *models.Commit {
split := strings.SplitN(line, "\x00", 8)
split := strings.SplitN(line, "\x00", 9)

// Ensure we have the minimum required fields (at least 7 for basic functionality)
if len(split) < 7 {
self.Log.Warnf("Malformed git log line: expected at least 7 fields, got %d. Line: %s", len(split), line)
// Ensure we have the minimum required fields (at least 8 for basic functionality)
if len(split) < 8 {
self.Log.Warnf("Malformed git log line: expected at least 8 fields, got %d. Line: %s", len(split), line)
return nil
}

hash := split[0]
unixTimestamp := split[1]
authorName := split[2]
authorEmail := split[3]
parentHashes := split[4]
committerTimestamp := split[2]
authorName := split[3]
authorEmail := split[4]
parentHashes := split[5]
divergence := models.DivergenceNone
if showDivergence {
divergence = lo.Ternary(split[5] == "<", models.DivergenceLeft, models.DivergenceRight)
divergence = lo.Ternary(split[6] == "<", models.DivergenceLeft, models.DivergenceRight)
}
extraInfo := strings.TrimSpace(split[6])
extraInfo := strings.TrimSpace(split[7])

// message (and the \x00 before it) might not be present if extraInfo is extremely long
message := ""
if len(split) > 7 {
message = split[7]
if len(split) > 8 {
message = split[8]
}

var tags []string
Expand All @@ -232,6 +233,7 @@ func (self *CommitLoader) extractCommitFromLine(hashPool *utils.StringPool, line
}

unitTimestampInt, _ := strconv.Atoi(unixTimestamp)
committerTimestampInt, _ := strconv.Atoi(committerTimestamp)

parents := []string{}
if len(parentHashes) > 0 {
Expand All @@ -244,6 +246,7 @@ func (self *CommitLoader) extractCommitFromLine(hashPool *utils.StringPool, line
Tags: tags,
ExtraInfo: extraInfo,
UnixTimestamp: int64(unitTimestampInt),
CommitterDate: int64(committerTimestampInt),
AuthorName: authorName,
AuthorEmail: authorEmail,
Parents: parents,
Expand Down Expand Up @@ -603,4 +606,4 @@ func (self *CommitLoader) getLogCmd(opts GetCommitsOptions) *oscommands.CmdObj {
return self.cmd.New(cmdArgs).DontLog()
}

const prettyFormat = `--pretty=format:+%H%x00%at%x00%aN%x00%ae%x00%P%x00%m%x00%D%x00%s`
const prettyFormat = `--pretty=format:+%H%x00%at%x00%ct%x00%aN%x00%ae%x00%P%x00%m%x00%D%x00%s`
77 changes: 48 additions & 29 deletions pkg/commands/git_commands/commit_loader_test.go

Large diffs are not rendered by default.

14 changes: 8 additions & 6 deletions pkg/commands/git_commands/reflog_commit_loader.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ func (self *ReflogCommitLoader) GetReflogCommits(hashPool *utils.StringPool, las
cmdArgs := NewGitCmd("log").
Config("log.showSignature=false").
Arg("-g").
Arg("--format=+%H%x00%ct%x00%gs%x00%P").
Arg("--format=+%H%x00%at%x00%ct%x00%gs%x00%P").
ArgIf(filterAuthor != "", "--author="+filterAuthor).
ArgIf(filterPath != "", "--follow", "--name-status", "--", filterPath).
ToArgv()
Expand Down Expand Up @@ -63,27 +63,29 @@ func (self *ReflogCommitLoader) GetReflogCommits(hashPool *utils.StringPool, las
}

func (self *ReflogCommitLoader) sameReflogCommit(a *models.Commit, b *models.Commit) bool {
return a.Hash() == b.Hash() && a.UnixTimestamp == b.UnixTimestamp && a.Name == b.Name
return a.Hash() == b.Hash() && a.UnixTimestamp == b.UnixTimestamp && a.CommitterDate == b.CommitterDate && a.Name == b.Name
}

func (self *ReflogCommitLoader) parseLine(hashPool *utils.StringPool, line string) (*models.Commit, bool) {
fields := strings.SplitN(line, "\x00", 4)
if len(fields) <= 3 {
fields := strings.SplitN(line, "\x00", 5)
if len(fields) <= 4 {
return nil, false
}

unixTimestamp, _ := strconv.Atoi(fields[1])
committerDate, _ := strconv.Atoi(fields[2])

parentHashes := fields[3]
parentHashes := fields[4]
parents := []string{}
if len(parentHashes) > 0 {
parents = strings.Split(parentHashes, " ")
}

return models.NewCommit(hashPool, models.NewCommitOpts{
Hash: fields[0],
Name: fields[2],
Name: fields[3],
UnixTimestamp: int64(unixTimestamp),
CommitterDate: int64(committerDate),
Status: models.StatusReflog,
Parents: parents,
}), true
Expand Down
33 changes: 22 additions & 11 deletions pkg/commands/git_commands/reflog_commit_loader_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,11 @@ import (
"github.com/stretchr/testify/assert"
)

var reflogOutput = strings.ReplaceAll(`+c3c4b66b64c97ffeecde|1643150483|checkout: moving from A to B|51baa8c1
+c3c4b66b64c97ffeecde|1643150483|checkout: moving from B to A|51baa8c1
+c3c4b66b64c97ffeecde|1643150483|checkout: moving from A to B|51baa8c1
+c3c4b66b64c97ffeecde|1643150483|checkout: moving from master to A|51baa8c1
+f4ddf2f0d4be4ccc7efa|1643149435|checkout: moving from A to master|51baa8c1
var reflogOutput = strings.ReplaceAll(`+c3c4b66b64c97ffeecde|1643150483|1643150483|checkout: moving from A to B|51baa8c1
+c3c4b66b64c97ffeecde|1643150483|1643150483|checkout: moving from B to A|51baa8c1
+c3c4b66b64c97ffeecde|1643150483|1643150483|checkout: moving from A to B|51baa8c1
+c3c4b66b64c97ffeecde|1643150483|1643150483|checkout: moving from master to A|51baa8c1
+f4ddf2f0d4be4ccc7efa|1643149435|1643149435|checkout: moving from A to master|51baa8c1
`, "|", "\x00")

func TestGetReflogCommits(t *testing.T) {
Expand All @@ -39,7 +39,7 @@ func TestGetReflogCommits(t *testing.T) {
{
testName: "no reflog entries",
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%ct%x00%gs%x00%P"}, "", nil),
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%at%x00%ct%x00%gs%x00%P"}, "", nil),

lastReflogCommit: nil,
expectedCommitOpts: []models.NewCommitOpts{},
Expand All @@ -49,7 +49,7 @@ func TestGetReflogCommits(t *testing.T) {
{
testName: "some reflog entries",
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%ct%x00%gs%x00%P"}, reflogOutput, nil),
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%at%x00%ct%x00%gs%x00%P"}, reflogOutput, nil),

lastReflogCommit: nil,
expectedCommitOpts: []models.NewCommitOpts{
Expand All @@ -58,34 +58,39 @@ func TestGetReflogCommits(t *testing.T) {
Name: "checkout: moving from A to B",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
{
Hash: "c3c4b66b64c97ffeecde",
Name: "checkout: moving from B to A",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
{
Hash: "c3c4b66b64c97ffeecde",
Name: "checkout: moving from A to B",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
{
Hash: "c3c4b66b64c97ffeecde",
Name: "checkout: moving from master to A",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
{
Hash: "f4ddf2f0d4be4ccc7efa",
Name: "checkout: moving from A to master",
Status: models.StatusReflog,
UnixTimestamp: 1643149435,
CommitterDate: 1643149435,
Parents: []string{"51baa8c1"},
},
},
Expand All @@ -95,13 +100,14 @@ func TestGetReflogCommits(t *testing.T) {
{
testName: "some reflog entries where last commit is given",
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%ct%x00%gs%x00%P"}, reflogOutput, nil),
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%at%x00%ct%x00%gs%x00%P"}, reflogOutput, nil),

lastReflogCommit: models.NewCommit(hashPool, models.NewCommitOpts{
Hash: "c3c4b66b64c97ffeecde",
Name: "checkout: moving from B to A",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
}),
expectedCommitOpts: []models.NewCommitOpts{
Expand All @@ -110,6 +116,7 @@ func TestGetReflogCommits(t *testing.T) {
Name: "checkout: moving from A to B",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
},
Expand All @@ -119,13 +126,14 @@ func TestGetReflogCommits(t *testing.T) {
{
testName: "when passing filterPath",
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%ct%x00%gs%x00%P", "--follow", "--name-status", "--", "path"}, reflogOutput, nil),
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%at%x00%ct%x00%gs%x00%P", "--follow", "--name-status", "--", "path"}, reflogOutput, nil),

lastReflogCommit: models.NewCommit(hashPool, models.NewCommitOpts{
Hash: "c3c4b66b64c97ffeecde",
Name: "checkout: moving from B to A",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
}),
filterPath: "path",
Expand All @@ -135,6 +143,7 @@ func TestGetReflogCommits(t *testing.T) {
Name: "checkout: moving from A to B",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
},
Expand All @@ -144,13 +153,14 @@ func TestGetReflogCommits(t *testing.T) {
{
testName: "when passing filterAuthor",
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%ct%x00%gs%x00%P", "--author=John Doe <john@doe.com>"}, reflogOutput, nil),
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%at%x00%ct%x00%gs%x00%P", "--author=John Doe <john@doe.com>"}, reflogOutput, nil),

lastReflogCommit: models.NewCommit(hashPool, models.NewCommitOpts{
Hash: "c3c4b66b64c97ffeecde",
Name: "checkout: moving from B to A",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
}),
filterAuthor: "John Doe <john@doe.com>",
Expand All @@ -160,6 +170,7 @@ func TestGetReflogCommits(t *testing.T) {
Name: "checkout: moving from A to B",
Status: models.StatusReflog,
UnixTimestamp: 1643150483,
CommitterDate: 1643150483,
Parents: []string{"51baa8c1"},
},
},
Expand All @@ -169,7 +180,7 @@ func TestGetReflogCommits(t *testing.T) {
{
testName: "when command returns error",
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%ct%x00%gs%x00%P"}, "", errors.New("haha")),
ExpectGitArgs([]string{"-c", "log.showSignature=false", "log", "-g", "--format=+%H%x00%at%x00%ct%x00%gs%x00%P"}, "", errors.New("haha")),

lastReflogCommit: nil,
filterPath: "",
Expand Down
3 changes: 3 additions & 0 deletions pkg/commands/models/commit.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ type Commit struct {
AuthorName string // something like 'Jesse Duffield'
AuthorEmail string // something like 'jessedduffield@gmail.com'
UnixTimestamp int64
CommitterDate int64

// Hashes of parent commits (will be multiple if it's a merge commit)
parents []*string
Expand All @@ -73,6 +74,7 @@ type NewCommitOpts struct {
AuthorName string
AuthorEmail string
UnixTimestamp int64
CommitterDate int64
Divergence Divergence
Parents []string
}
Expand All @@ -88,6 +90,7 @@ func NewCommit(hashPool *utils.StringPool, opts NewCommitOpts) *Commit {
AuthorName: opts.AuthorName,
AuthorEmail: opts.AuthorEmail,
UnixTimestamp: opts.UnixTimestamp,
CommitterDate: opts.CommitterDate,
Divergence: opts.Divergence,
parents: lo.Map(opts.Parents, func(s string, _ int) *string { return hashPool.Add(s) }),
}
Expand Down
4 changes: 4 additions & 0 deletions pkg/config/app_config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -599,6 +599,10 @@ gui:
# If true, when using the panel jump keys (default 1 through 5) and target panel is already active, go to next tab instead
switchTabsWithPanelJumpKeys: false

# Commit list date source.
# One of 'author' (default) | 'committer'
commitDateSource: author

# Config relating to git
git:
# See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md
Expand Down
4 changes: 4 additions & 0 deletions pkg/config/user_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,9 @@ type GuiConfig struct {
SwitchToFilesAfterStashApply bool `yaml:"switchToFilesAfterStashApply"`
// If true, when using the panel jump keys (default 1 through 5) and target panel is already active, go to next tab instead
SwitchTabsWithPanelJumpKeys bool `yaml:"switchTabsWithPanelJumpKeys"`
// Commit list date source.
// One of 'author' (default) | 'committer'
CommitDateSource string `yaml:"commitDateSource" jsonschema:"enum=author,enum=committer"`
}

func (c *GuiConfig) UseFuzzySearch() bool {
Expand Down Expand Up @@ -820,6 +823,7 @@ func GetDefaultConfig() *UserConfig {
SwitchToFilesAfterStashPop: true,
SwitchToFilesAfterStashApply: true,
SwitchTabsWithPanelJumpKeys: false,
CommitDateSource: "author",
},
Git: GitConfig{
Commit: CommitConfig{
Expand Down
4 changes: 4 additions & 0 deletions pkg/config/user_config_validation.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,10 @@ import (
)

func (config *UserConfig) Validate() error {
if err := validateEnum("gui.commitDateSource", config.Gui.CommitDateSource,
[]string{"author", "committer"}); err != nil {
return err
}
if err := validateEnum("gui.statusPanelView", config.Gui.StatusPanelView,
[]string{"dashboard", "allBranchesLog"}); err != nil {
return err
Expand Down
10 changes: 9 additions & 1 deletion pkg/gui/presentation/commits.go
Original file line number Diff line number Diff line change
Expand Up @@ -378,8 +378,16 @@ func displayCommit(

descriptionString := ""
if fullDescription {
timestamp := commit.UnixTimestamp
switch common.UserConfig().Gui.CommitDateSource {
case "committer":
timestamp = commit.CommitterDate
case "author":
timestamp = commit.UnixTimestamp
default:
}
descriptionString = style.FgBlue.Sprint(
utils.UnixToDateSmart(now, commit.UnixTimestamp, timeFormat, shortTimeFormat),
utils.UnixToDateSmart(now, timestamp, timeFormat, shortTimeFormat),
)
}

Expand Down
1 change: 1 addition & 0 deletions pkg/gui/services/custom_commands/models.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ type Commit struct {
AuthorName string
AuthorEmail string
UnixTimestamp int64
CommitterDate int64
Divergence models.Divergence
Parents []string
}
Expand Down
1 change: 1 addition & 0 deletions pkg/gui/services/custom_commands/session_state_loader.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ func commitShimFromModelCommit(commit *models.Commit) *Commit {
AuthorName: commit.AuthorName,
AuthorEmail: commit.AuthorEmail,
UnixTimestamp: commit.UnixTimestamp,
CommitterDate: commit.CommitterDate,
Divergence: commit.Divergence,
Parents: commit.Parents(),
}
Expand Down
9 changes: 9 additions & 0 deletions schema-master/config.json
Original file line number Diff line number Diff line change
Expand Up @@ -790,6 +790,15 @@
"type": "boolean",
"description": "If true, when using the panel jump keys (default 1 through 5) and target panel is already active, go to next tab instead",
"default": false
},
"commitDateSource": {
"type": "string",
"enum": [
"author",
"committer"
],
"description": "Commit list date source.\nOne of 'author' (default) | 'committer'",
"default": "author"
}
},
"additionalProperties": false,
Expand Down
Loading