Skip to content
Merged
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
35 changes: 35 additions & 0 deletions pkg/gui/controllers/basic_commits_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,24 @@ func (self *BasicCommitsController) GetKeybindings(opts types.KeybindingsOpts) [
return bindings
}

func (self *BasicCommitsController) getCommitMessageBody(hash string) string {
commitMessageBody, err := self.c.Git().Commit.GetCommitMessage(hash)
if err != nil {
return ""
}
_, body := self.c.Helpers().Commits.SplitCommitMessageAndDescription(commitMessageBody)
return body
}

func (self *BasicCommitsController) copyCommitAttribute(commit *models.Commit) error {
commitMessageBody := self.getCommitMessageBody(commit.Hash)
var commitMessageBodyDisabled *types.DisabledReason
if commitMessageBody == "" {
commitMessageBodyDisabled = &types.DisabledReason{
Text: self.c.Tr.CommitHasNoMessageBody,
}
}

items := []*types.MenuItem{
{
Label: self.c.Tr.CommitHash,
Expand All @@ -144,6 +161,14 @@ func (self *BasicCommitsController) copyCommitAttribute(commit *models.Commit) e
},
Key: 'm',
},
{
Label: self.c.Tr.CommitMessageBody,
DisabledReason: commitMessageBodyDisabled,
OnPress: func() error {
return self.copyCommitMessageBodyToClipboard(commitMessageBody)
},
Key: 'b',
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

None of the other keys in this menu allow customization, so I felt it was fine to leave this here. I can't think of a different commit attribute that might want to claim the b shortcut one day.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds fine to me.

},
{
Label: self.c.Tr.CommitURL,
OnPress: func() error {
Expand Down Expand Up @@ -259,6 +284,16 @@ func (self *BasicCommitsController) copyCommitMessageToClipboard(commit *models.
return nil
}

func (self *BasicCommitsController) copyCommitMessageBodyToClipboard(commitMessageBody string) error {
self.c.LogAction(self.c.Tr.Actions.CopyCommitMessageBodyToClipboard)
if err := self.c.OS().CopyToClipboard(commitMessageBody); err != nil {
return err
}

self.c.Toast(self.c.Tr.CommitMessageBodyCopiedToClipboard)
return nil
}

func (self *BasicCommitsController) copyCommitSubjectToClipboard(commit *models.Commit) error {
message, err := self.c.Git().Commit.GetCommitSubject(commit.Hash)
if err != nil {
Expand Down
94 changes: 51 additions & 43 deletions pkg/i18n/english.go
Original file line number Diff line number Diff line change
Expand Up @@ -621,6 +621,7 @@ type TranslationSet struct {
PasteCommitMessageFromClipboard string
SurePasteCommitMessage string
CommitMessage string
CommitMessageBody string
CommitSubject string
CommitAuthor string
CommitTags string
Expand Down Expand Up @@ -685,10 +686,12 @@ type TranslationSet struct {
CommitDiffCopiedToClipboard string
CommitURLCopiedToClipboard string
CommitMessageCopiedToClipboard string
CommitMessageBodyCopiedToClipboard string
CommitSubjectCopiedToClipboard string
CommitAuthorCopiedToClipboard string
CommitTagsCopiedToClipboard string
CommitHasNoTags string
CommitHasNoMessageBody string
PatchCopiedToClipboard string
CopiedToClipboard string
ErrCannotEditDirectory string
Expand Down Expand Up @@ -914,6 +917,7 @@ type Actions struct {
MoveCommitUp string
MoveCommitDown string
CopyCommitMessageToClipboard string
CopyCommitMessageBodyToClipboard string
CopyCommitSubjectToClipboard string
CopyCommitDiffToClipboard string
CopyCommitHashToClipboard string
Expand Down Expand Up @@ -1653,7 +1657,8 @@ func EnglishTranslationSet() *TranslationSet {
CopyCommitMessageToClipboard: "Copy commit message to clipboard",
PasteCommitMessageFromClipboard: "Paste commit message from clipboard",
SurePasteCommitMessage: "Pasting will overwrite the current commit message, continue?",
CommitMessage: "Commit message",
CommitMessage: "Commit message (subject and body)",
CommitMessageBody: "Commit message body",
CommitSubject: "Commit subject",
CommitAuthor: "Commit author",
CommitTags: "Commit tags",
Expand Down Expand Up @@ -1717,10 +1722,12 @@ func EnglishTranslationSet() *TranslationSet {
CommitDiffCopiedToClipboard: "Commit diff copied to clipboard",
CommitURLCopiedToClipboard: "Commit URL copied to clipboard",
CommitMessageCopiedToClipboard: "Commit message copied to clipboard",
CommitMessageBodyCopiedToClipboard: "Commit message body copied to clipboard",
CommitSubjectCopiedToClipboard: "Commit subject copied to clipboard",
CommitAuthorCopiedToClipboard: "Commit author copied to clipboard",
CommitTagsCopiedToClipboard: "Commit tags copied to clipboard",
CommitHasNoTags: "Commit has no tags",
CommitHasNoMessageBody: "Commit has no message body",
PatchCopiedToClipboard: "Patch copied to clipboard",
CopiedToClipboard: "copied to clipboard",
ErrCannotEditDirectory: "Cannot edit directories: you can only edit individual files",
Expand Down Expand Up @@ -1873,48 +1880,49 @@ func EnglishTranslationSet() *TranslationSet {

Actions: Actions{
// TODO: combine this with the original keybinding descriptions (those are all in lowercase atm)
CheckoutCommit: "Checkout commit",
CheckoutBranchAtCommit: "Checkout branch '%s'",
CheckoutCommitAsDetachedHead: "Checkout commit %s as detached head",
CheckoutTag: "Checkout tag",
CheckoutBranch: "Checkout branch",
ForceCheckoutBranch: "Force checkout branch",
CheckoutBranchOrCommit: "Checkout branch or commit",
DeleteLocalBranch: "Delete local branch",
Merge: "Merge",
SquashMerge: "Squash merge",
RebaseBranch: "Rebase branch",
RenameBranch: "Rename branch",
CreateBranch: "Create branch",
CherryPick: "(Cherry-pick) paste commits",
CheckoutFile: "Checkout file",
DiscardOldFileChange: "Discard old file change",
SquashCommitDown: "Squash commit down",
FixupCommit: "Fixup commit",
RewordCommit: "Reword commit",
DropCommit: "Drop commit",
EditCommit: "Edit commit",
AmendCommit: "Amend commit",
ResetCommitAuthor: "Reset commit author",
SetCommitAuthor: "Set commit author",
AddCommitCoAuthor: "Add commit co-author",
RevertCommit: "Revert commit",
CreateFixupCommit: "Create fixup commit",
SquashAllAboveFixupCommits: "Squash all above fixup commits",
CreateLightweightTag: "Create lightweight tag",
CreateAnnotatedTag: "Create annotated tag",
CopyCommitMessageToClipboard: "Copy commit message to clipboard",
CopyCommitSubjectToClipboard: "Copy commit subject to clipboard",
CopyCommitTagsToClipboard: "Copy commit tags to clipboard",
CopyCommitDiffToClipboard: "Copy commit diff to clipboard",
CopyCommitHashToClipboard: "Copy full commit hash to clipboard",
CopyCommitURLToClipboard: "Copy commit URL to clipboard",
CopyCommitAuthorToClipboard: "Copy commit author to clipboard",
CopyCommitAttributeToClipboard: "Copy to clipboard",
CopyPatchToClipboard: "Copy patch to clipboard",
MoveCommitUp: "Move commit up",
MoveCommitDown: "Move commit down",
CustomCommand: "Custom command",
CheckoutCommit: "Checkout commit",
CheckoutBranchAtCommit: "Checkout branch '%s'",
CheckoutCommitAsDetachedHead: "Checkout commit %s as detached head",
CheckoutTag: "Checkout tag",
CheckoutBranch: "Checkout branch",
ForceCheckoutBranch: "Force checkout branch",
CheckoutBranchOrCommit: "Checkout branch or commit",
DeleteLocalBranch: "Delete local branch",
Merge: "Merge",
SquashMerge: "Squash merge",
RebaseBranch: "Rebase branch",
RenameBranch: "Rename branch",
CreateBranch: "Create branch",
CherryPick: "(Cherry-pick) paste commits",
CheckoutFile: "Checkout file",
DiscardOldFileChange: "Discard old file change",
SquashCommitDown: "Squash commit down",
FixupCommit: "Fixup commit",
RewordCommit: "Reword commit",
DropCommit: "Drop commit",
EditCommit: "Edit commit",
AmendCommit: "Amend commit",
ResetCommitAuthor: "Reset commit author",
SetCommitAuthor: "Set commit author",
AddCommitCoAuthor: "Add commit co-author",
RevertCommit: "Revert commit",
CreateFixupCommit: "Create fixup commit",
SquashAllAboveFixupCommits: "Squash all above fixup commits",
CreateLightweightTag: "Create lightweight tag",
CreateAnnotatedTag: "Create annotated tag",
CopyCommitMessageToClipboard: "Copy commit message to clipboard",
CopyCommitMessageBodyToClipboard: "Copy commit message body to clipboard",
CopyCommitSubjectToClipboard: "Copy commit subject to clipboard",
CopyCommitTagsToClipboard: "Copy commit tags to clipboard",
CopyCommitDiffToClipboard: "Copy commit diff to clipboard",
CopyCommitHashToClipboard: "Copy full commit hash to clipboard",
CopyCommitURLToClipboard: "Copy commit URL to clipboard",
CopyCommitAuthorToClipboard: "Copy commit author to clipboard",
CopyCommitAttributeToClipboard: "Copy to clipboard",
CopyPatchToClipboard: "Copy patch to clipboard",
MoveCommitUp: "Move commit up",
MoveCommitDown: "Move commit down",
CustomCommand: "Custom command",

// TODO: remove
DiscardAllChangesInDirectory: "Discard all changes in directory",
Expand Down
4 changes: 4 additions & 0 deletions pkg/integration/components/shell.go
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,10 @@ func (self *Shell) EmptyCommit(message string) *Shell {
return self.RunCommand([]string{"git", "commit", "--allow-empty", "-m", message})
}

func (self *Shell) EmptyCommitWithBody(subject string, body string) *Shell {
return self.RunCommand([]string{"git", "commit", "--allow-empty", "-m", subject, "-m", body})
}

func (self *Shell) EmptyCommitDaysAgo(message string, daysAgo int) *Shell {
return self.RunCommand([]string{"git", "commit", "--allow-empty", "--date", fmt.Sprintf("%d days ago", daysAgo), "-m", message})
}
Expand Down
39 changes: 39 additions & 0 deletions pkg/integration/tests/commit/copy_message_body_to_clipboard.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package commit

import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)

// We're emulating the clipboard by writing to a file called clipboard

var CopyMessageBodyToClipboard = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Copy a commit message body to the clipboard",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {
config.GetUserConfig().OS.CopyToClipboardCmd = "printf '%s' {{text}} > clipboard"
},

SetupRepo: func(shell *Shell) {
shell.EmptyCommitWithBody("My Subject", "My awesome commit message body")
},

Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("My Subject").IsSelected(),
).
Press(keys.Commits.CopyCommitAttributeToClipboard)

t.ExpectPopup().Menu().
Title(Equals("Copy to clipboard")).
Select(Contains("Commit message body")).
Confirm()

t.ExpectToast(Equals("Commit message body copied to clipboard"))

t.FileSystem().FileContent("clipboard", Equals("My awesome commit message body"))
},
})
33 changes: 33 additions & 0 deletions pkg/integration/tests/commit/disable_copy_commit_message_body.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
package commit

import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)

var DisableCopyCommitMessageBody = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Disables copy commit message body when there is no body",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {},

SetupRepo: func(shell *Shell) {
shell.EmptyCommit("commit")
},

Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("commit").IsSelected(),
).
Press(keys.Commits.CopyCommitAttributeToClipboard)

t.ExpectPopup().Menu().
Title(Equals("Copy to clipboard")).
Select(Contains("Commit message body")).
Confirm()

t.ExpectToast(Equals("Disabled: Commit has no message body"))
},
})
2 changes: 1 addition & 1 deletion pkg/integration/tests/commit/paste_commit_message.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ var PasteCommitMessage = NewIntegrationTest(NewIntegrationTestArgs{
Press(keys.Commits.CopyCommitAttributeToClipboard)

t.ExpectPopup().Menu().Title(Equals("Copy to clipboard")).
Select(Contains("Commit message")).Confirm()
Select(Contains("Commit message (subject and body)")).Confirm()

t.ExpectToast(Equals("Commit message copied to clipboard"))

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ var PasteCommitMessageOverExisting = NewIntegrationTest(NewIntegrationTestArgs{
Press(keys.Commits.CopyCommitAttributeToClipboard)

t.ExpectPopup().Menu().Title(Equals("Copy to clipboard")).
Select(Contains("Commit message")).Confirm()
Select(Contains("Commit message (subject and body)")).Confirm()

t.ExpectToast(Equals("Commit message copied to clipboard"))

Expand Down
2 changes: 2 additions & 0 deletions pkg/integration/tests/test_list.go
Original file line number Diff line number Diff line change
Expand Up @@ -97,10 +97,12 @@ var tests = []*components.IntegrationTest{
commit.CommitWithNonMatchingBranchName,
commit.CommitWithPrefix,
commit.CopyAuthorToClipboard,
commit.CopyMessageBodyToClipboard,
commit.CopyTagToClipboard,
commit.CreateAmendCommit,
commit.CreateFixupCommitInBranchStack,
commit.CreateTag,
commit.DisableCopyCommitMessageBody,
commit.DiscardOldFileChanges,
commit.FindBaseCommitForFixup,
commit.FindBaseCommitForFixupDisregardMainBranch,
Expand Down