Compare commits

...
Author SHA1 Message Date
Stefan Haller aafe61082e Allow releasing from a branch other than master (#5819)
This is useful for cutting a patch release for the previous version when
master already contains work that shouldn't be released yet.

Scheduled runs are unaffected: with no input provided, the ref is empty
and the checkout falls back to the default branch.
2026-07-15 13:32:02 +02:00
Stefan Haller bd8c06ddc0 Rename version_bump options to be extra clear
I keep getting slightly confused as to which is which, so make this
extra clear.

While at it, change the default to minor, this is the option that is
more often used now that we don't have regular scheduled releases any
more.
2026-07-15 13:23:11 +02:00
Stefan Haller 1d99ba56fc Allow releasing from a branch other than master
This is useful for cutting a patch release for the previous version
when master already contains work that shouldn't be released yet; for
example, v0.63.1 had to be tagged and released by hand from a v0.63.1
branch off the v0.63.0 tag because the workflow could only release
master.

Scheduled runs are unaffected: with no input provided, the ref is
empty and the checkout falls back to the default branch.
2026-07-15 13:23:11 +02:00
Stefan Haller dda0af0f48 Allow having branch and tag with the same name
When creating a patch release from a branch called `v0.63.1`, the new
tag would get the same name and pushing it would fail with `error: src
refspec v0.63.1 matches more than one`.
2026-07-15 13:23:11 +02:00
Stefan Haller a65d468cd3 Determine the latest tag from the checked-out commit's history
The Get Latest Tag step used to pick the most recently created tag in
the entire repo, regardless of whether it is reachable from the commit
being released. In preparation for supporting releases from branches
other than master, use the nearest tag that is an ancestor of the
checked-out commit instead. This way, a patch release cut from an
older release branch bumps that branch's own latest tag even when
master already carries a newer release, and the "changes since last
release" check compares against the release that actually precedes
this one in history.
2026-07-15 10:56:56 +02:00
Stefan Haller 4c78076730 Fix a deadlock on Windows when switching between longer diffs (#5815)
The Windows PTY support that was newly introduced in v0.63.0 had a
potential deadlock problem: when switching between longer diffs, lazygit
could lock up. This should hopefully be fixed with this PR.
2026-07-15 10:32:19 +02:00
Stefan HallerandClaude Fable 5 f116874f0a Fix a deadlock when a Windows pty task is stopped mid-output
winPty.Close could block indefinitely, and it is called while holding
the global PtyMutex and while the task's onDone sync.Once is
executing, so blocking there wedges the task's entire cleanup chain:
the next NewTask call blocks on <-notifyStopped while holding
waitingMutex, every later task for that view queues up behind it, and
onResize blocks on PtyMutex — a full UI freeze. (Reported by a user
via go-deadlock's 30s watchdog; a regression from the ConPTY support
introduced for v0.63.0.)

ClosePseudoConsole is what blocks; before Windows 11 24H2 it can do
so in two ways. It flushes the client's pending output into the out
pipe, but a stopped task's scanner goroutine has already quit
draining, so with a client that's still producing output the flush
never completes; this can also wedge the background waiter's
closeHpc, which runs with the pipes deliberately left open. And it
waits for the console host to exit, but closing only delivers
CTRL_CLOSE_EVENT to the attached client without terminating it, so a
client that keeps running (git still computing an expensive diff, a
pager waiting for input) keeps the host alive arbitrarily long.

Run the teardown on a background goroutine so Close returns
immediately no matter which of these strikes, and within it close our
pipe ends before the pseudoconsole, without taking p.mu: breaking the
pipes fails a pending flush fast, which also unblocks a waiter
already stuck in one.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-15 10:31:11 +02:00
Stefan Haller c2489e1c13 Fix userEvents panic (#5793)
In #5756 we changed the userEvents channel to a fixed 256-slot channel
with a non-blocking send that panicked when the channel was full. It
turns out that this panic can happen in real use:

- Toggling a directory of several hundred files into a custom patch
(reliably): the operation runs on a worker behind a waiting status,
whose spinner enqueues a content-only render on every tick, and over the
long operation these outrun the UI loop and overflow the buffer.
- Editing the config in an editor that suspends lazygit: the editor
subprocess runs on the UI thread, so the loop drains nothing for the
whole editing session, and the full refresh fired on resume fans out
across every scope at once — a burst of updates that overflows before
the just-resumed loop catches up.
- Any time the UI thread blocks for a long time, the periodic refreshes
keep enqueuing and eventually overflow.

The 256-slot buffer was chosen deliberately, with the panic as a "should
never happen" guard, to preserve two properties: FIFO ordering of
same-goroutine Update calls (an earlier goroutine-per-Update design
reordered them), and no self-deadlock (a blocking send from the UI
thread would block against the loop that drains it). But a fixed channel
can only offer those by crashing on overflow.

Replace it with an unbounded, order-preserving queue: a mutex-guarded
slice plus a buffered(1) doorbell channel that wakes the main loop's
select. Enqueuing appends and rings the doorbell; the loop drains the
slice to empty on each wake. This keeps FIFO order and never blocks the
caller, so there is no self-deadlock and no overflow to panic on — under
a stall the queue just grows and then drains.

Fixes #5772.
2026-07-15 10:18:51 +02:00
Stefan HallerandClaude Opus 4.8 f0b139f3ab Log the user-event queue's high-water mark
Now that the queue is unbounded, its depth is a useful signal for
understanding how the event loop behaves under load — and we expect it
to look very different across builds (e.g. master, which carries the
bounce-state-updates-to-ui-thread work, versus the v0.63.0 release this
fix ships in). Track the deepest the queue has ever been and log an Info
line whenever that record is broken, so the numbers show up in the log
for later reasoning. The mark is session-wide and doesn't reset when the
queue drains.

gocui has no logger of its own, so it exposes the new depth through a
handler (matching the existing SetFocusHandler / SetOpenHyperlinkFunc
pattern) that the gui registers to log via its own logger.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:14:05 +02:00
Stefan HallerandClaude Opus 4.8 49eefbcf37 Make the user-event queue unbounded
Update and friends enqueued onto a fixed 256-slot channel with a
non-blocking send that panicked when the channel was full. That guard
was firing in real use:

 - Toggling a directory of several hundred files into a custom patch
   (reliably): the operation runs on a worker behind a waiting status,
   whose spinner enqueues a content-only render on every tick, and over
   the long operation these outrun the UI loop and overflow the buffer.
 - Editing the config in an editor that suspends lazygit: the editor
   subprocess runs on the UI thread, so the loop drains nothing for the
   whole editing session, and the full refresh fired on resume fans out
   across every scope at once — a burst of updates that overflows before
   the just-resumed loop catches up.
 - Any time the UI thread blocks for a long time, the periodic refreshes
   keep enqueuing and eventually overflow.

The 256-slot buffer was chosen deliberately, with the panic as a
"should never happen" guard, to preserve two properties: FIFO ordering
of same-goroutine Update calls (an earlier goroutine-per-Update design
reordered them), and no self-deadlock (a blocking send from the UI
thread would block against the loop that drains it). But a fixed
channel can only offer those by crashing on overflow.

Replace it with an unbounded, order-preserving queue: a mutex-guarded
slice plus a buffered(1) doorbell channel that wakes the main loop's
select. Enqueuing appends and rings the doorbell; the loop drains the
slice to empty on each wake. This keeps FIFO order and never blocks the
caller, so there is no self-deadlock and no overflow to panic on — under
a stall the queue just grows and then drains.

This also removes an inconsistency: updateContentOnly did a plain
blocking send while update panicked, so the two paths disagreed on what
happened when the queue was full. Both now share the same enqueue.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:14:05 +02:00
Stefan Haller 9f51f044fa Improve index.lock retry mechanism (#5788)
In v0.63.0 we made a change to no longer use `GIT_OPTIONAL_LOCKS=0` on
git commands that are part of a "foreground" refresh, meaning the
refresh after a lazygit command or the focus-in refresh. We do this on
purpose to keep git's mod date cache from becoming stale, which could
make lazygit become slower over time. However, this caused a problem for
users who work very fast: staging a file and then immediately pressing
shift-A to amend while the staging's refresh is still running would show
the dreaded index.lock error.

We already had a retry-on-index-lock-error mechanism in place, but it
wasn't used for commands like amend or commit; fix this so that the
retry loop works for these too, and also make the retry window a little
longer, and fix a problem where it wouldn't work in linked worktrees or
submodules.

Closes #5778.
2026-07-15 10:12:51 +02:00
Stefan HallerandClaude Opus 4.8 4052057eee Back off exponentially between lock-error retries
The retry budget was five fixed 50ms waits (250ms total). A foreground
`git status` refresh can hold index.lock for longer than that on a large
repo, so the retries could be exhausted before the lock clears. Wait 20ms
before the first retry and double each time, giving seven attempts over a
bit more than a second — enough to outlast a slow refresh while keeping
the common case (a lock that clears almost immediately) fast. The initial
delay is now a runner field so tests can zero it out instead of sleeping.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:08:44 +02:00
Stefan HallerandClaude Opus 4.8 e3ecb77939 Recognize index.lock contention in worktrees and submodules
The retry check matched the literal ".git/index.lock", which only ever
appears for the main worktree. A linked worktree's lock is at
.git/worktrees/<name>/index.lock and a submodule's is under its own git
dir, so contention there was never retried. Match the bare "index.lock"
fragment instead, which covers all of them.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:08:44 +02:00
Stefan HallerandClaude Opus 4.8 c1cd500fa7 Retry lock errors reported only through the command's error
Have isRetryableError also inspect the returned error, not just the
captured output. Streamed commands (amend, commit, and other operations
run through the gpg helper) don't capture output, so their index.lock
failures were slipping past the retry loop and surfacing to the user as
a hard "Git command failed". Now they retry like every other command.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:08:44 +02:00
Stefan HallerandClaude Opus 4.8 0902c5c058 Demonstrate that a lock error in a streamed command isn't retried
The gpg helper runs commands like amend with StreamOutput, so their
output isn't captured and a failed run returns an empty output string;
the index.lock message is carried by the error instead. isRetryableError
only inspects the output, so the retry loop never fires for these
commands. In practice this means a `shift-A` amend issued while a
foreground `git status` refresh briefly holds index.lock fails outright
instead of retrying.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:08:44 +02:00
Stefan HallerandClaude Opus 4.8 e90daaf812 Unify the git command lock-retry loops
RunWithOutput and RunWithOutputs each carried their own near-identical
copy of the index.lock retry loop. Extract the loop into a single
retryOnLockError helper so the retry policy lives in one place, ahead of
changing that policy. Behavior is unchanged; the added tests characterize
it (success and non-lock errors run once, a lock error in the output is
retried).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 10:08:44 +02:00
Stefan Haller ce5a8b61bd Update docs and schema for release (#5761) 2026-07-04 14:43:54 +02:00
Stefan Haller 440f357319 Update docs and schema for release 2026-07-04 14:40:33 +02:00
Stefan Haller 26dd82d8d4 Update translations from Crowdin (#5760) 2026-07-04 14:39:50 +02:00
Stefan Haller 8e36fba91e Update translations from Crowdin 2026-07-04 14:36:49 +02:00
Stefan Haller 24c6d38983 Show renamed files in the custom patch builder (#5759)
When showing the files of a commit, we used to display renamed files as
a pair of added and deleted files, rather than a single `R` entry. This
is inconvenient when just browsing the commit's files because you can't
see if the rename also has modifications; but it becomes a real problem
when trying to work with the renamed file in a custom patch if it also
had modifications; there was no way to discard them, for example.

The Files panel already shows renamed files as `R` and allows you to
stage/unstage/discard hunks in them, so there's no reason why the patch
building panel shouldn't allow the same; and this PR adds this.

To drop just the modifications of a rename, add the individual hunks to
the custom patch (the side panel shows a `◐` icon); reverting the patch
then only drops the modifications but not the rename. To also drop the
rename, add the entire `R` file to the custom patch from the side panel
(it gets a `●` icon).
2026-07-04 13:07:55 +02:00
Stefan Haller aa46a69f77 Remove unused function ExpectClipboard
This can't be used because it wouldn't work on CI; delete it so that
coding agents aren't tempted to use it.
2026-07-04 13:05:09 +02:00
Stefan HallerandClaude Opus 4.8 f84ada4941 Show renamed files in the custom patch builder
When loading the files of a commit we passed --no-renames, so a rename
showed up as a separate delete and add rather than a single R entry.
That made it impossible to work with a rename that also modifies the
file: the modifications were spread across a full deletion and a full
addition instead of appearing as the handful of lines that actually
changed. The staging view already shows renames and lets you stage
their hunks, so there was no good reason for the patch builder to
differ; the flag was only there because the commit-file parser couldn't
cope with the rename record format.

Switch the commit-file loader and the per-file diff to --find-renames,
teach the parser about the rename record (a status followed by two
paths), and carry the previous path through the patch builder so the
diff for a rename is loaded with both paths, which is what makes git
emit the rename in the first place.

A whole-file selection keeps the rename in the header, so the rename
moves or is discarded together with the file's contents. A partial
selection instead strips the rename metadata and points the header at
the new path, so applying the patch only changes the contents and
leaves the rename in place; the blob index line is kept so that a 3-way
apply can still fall back to a blob merge.

Discarding a renamed file from a commit now discards both the new and
the old path, so the new file is removed and the old one is restored.

Changing the rename similarity threshold refreshes the commit files
panel too, not just the files panel, so that a rename can turn into a
delete and add or back. It is disabled while building a patch, however,
because the patch builder caches each file's diff by path and would
desync if a rename changed into a delete and add underneath it.

Finally, copying a file's diff from the commit files panel now passes
both paths for a rename, so the copied diff shows the rename instead of
a new-file add.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-04 13:05:09 +02:00
54 changed files with 1703 additions and 471 deletions
+12 -6
View File
@@ -13,10 +13,15 @@ on:
description: 'Version bump type'
type: choice
required: true
default: 'patch'
default: 'minor (normal)'
options:
- minor
- patch
- minor (normal)
- patch (hotfix)
branch:
description: 'Branch to release from'
type: string
required: true
default: 'master'
ignore_blocks:
description: 'Ignore blocking PRs/issues'
type: boolean
@@ -49,12 +54,13 @@ jobs:
uses: actions/checkout@v7
with:
repository: jesseduffield/lazygit
ref: ${{ inputs.branch }}
token: ${{ secrets.LAZYGIT_RELEASE_PAT }}
fetch-depth: 0
- name: Get Latest Tag
run: |
latest_tag=$(git describe --tags $(git rev-list --tags --max-count=1) || echo "v0.0.0")
latest_tag=$(git describe --tags --abbrev=0 || echo "v0.0.0")
if ! [[ $latest_tag =~ ^v[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
echo "Error: Tag format is invalid. Expected format: vX.X.X"
@@ -121,7 +127,7 @@ jobs:
IFS='.' read -r major minor patch <<< "$LATEST_TAG"
if [[ "$EVENT_NAME" == "workflow_dispatch" ]]; then
if [[ "$VERSION_BUMP" == "patch" ]]; then
if [[ "$VERSION_BUMP" == "patch (hotfix)" ]]; then
patch=$((patch + 1))
else
minor=$((minor + 1))
@@ -151,7 +157,7 @@ jobs:
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"
git tag "$NEW_TAG" -a -m "Release $NEW_TAG"
git push origin "$NEW_TAG"
git push origin "refs/tags/$NEW_TAG"
- name: Setup Go
uses: actions/setup-go@v6
+61 -61
View File
@@ -10,15 +10,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <pgup>, K, <ctrl+u> (fn+up/shift+k) `` | Scroll naar beneden vanaf hoofdpaneel | |
| `` <pgdown>, J, <ctrl+d> (fn+down/shift+j) `` | Scroll naar beneden vanaf hoofdpaneel | |
| `` @ `` | View command log options | View options for the command log e.g. show/hide the command log and focus the command log. |
| `` P `` | Push | Push the current branch to its upstream branch. If no upstream is configured, you will be prompted to configure an upstream branch. |
| `` p `` | Pull | Pull changes from the remote for the current branch. If no upstream is configured, you will be prompted to configure an upstream branch. |
| `` P `` | Push | Push de huidige branch naar de bijbehorende upstream-branch. Als er geen upstream is geconfigureerd wordt er gevraagd om een upstream-branch te configureren. |
| `` p `` | Pull | Pull wijzigingen van de remote voor de huidige branch. Als er geen upstream is geconfigureerd wordt er gevraagd om een upstream-branch te configureren. |
| `` ) `` | Increase rename similarity threshold | Increase the similarity threshold for a deletion and addition pair to be treated as a rename.<br><br>The default can be changed in the config file with the key 'git.renameSimilarityThreshold'. |
| `` ( `` | Decrease rename similarity threshold | Decrease the similarity threshold for a deletion and addition pair to be treated as a rename.<br><br>The default can be changed in the config file with the key 'git.renameSimilarityThreshold'. |
| `` } `` | Increase diff context size | Increase the amount of the context shown around changes in the diff view.<br><br>The default can be changed in the config file with the key 'git.diffContextSize'. |
| `` { `` | Decrease diff context size | Decrease the amount of the context shown around changes in the diff view.<br><br>The default can be changed in the config file with the key 'git.diffContextSize'. |
| `` : `` | Execute shell command | Bring up a prompt where you can enter a shell command to execute. |
| `` <ctrl+p> `` | Bekijk aangepaste patch opties | |
| `` m `` | Bekijk merge/rebase opties | View options to abort/continue/skip the current merge/rebase. |
| `` m `` | Bekijk merge/rebase opties | Toon abort/continue/skip opties voor huidige merge/rebase. |
| `` R `` | Verversen | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. |
| `` + `` | Volgende scherm modus (normaal/half/groot) | |
| `` _ `` | Vorige scherm modus | |
@@ -28,10 +28,10 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` ? `` | Open menu | |
| `` <ctrl+s> `` | Bekijk scoping opties | View options for filtering the commit log, so that only commits matching the filter are shown. |
| `` W, <ctrl+e> `` | Open diff menu | View options relating to diffing two refs e.g. diffing against selected ref, entering ref to diff against, and reversing the diff direction. |
| `` q, <ctrl+c> `` | Quit | |
| `` <ctrl+z> `` | Suspend the application | |
| `` q, <ctrl+c> `` | Afsluiten | |
| `` <ctrl+z> `` | Pauzeer de applicatie | |
| `` <ctrl+w> `` | Toggle whitespace | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | Verander config bestand | Open file in external editor. |
| `` <alt+shift+c> `` | Verander config bestand | Open bestand in externe editor. |
| `` z `` | Ongedaan maken (via reflog) (experimenteel) | The reflog will be used to determine what git command to run to undo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
| `` Z `` | Redo (via reflog) (experimenteel) | The reflog will be used to determine what git command to run to redo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
@@ -47,8 +47,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <shift+down> `` | Range select down | |
| `` <shift+up> `` | Range select up | |
| `` / `` | Start met zoeken | |
| `` H `` | Scroll left | |
| `` L `` | Scroll right | |
| `` H `` | Scroll naar links | |
| `` L `` | Scroll naar rechts | |
| `` ] `` | Volgende tabblad | |
| `` [ `` | Vorige tabblad | |
@@ -58,15 +58,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer de bestandsnaam naar het klembord | |
| `` <space> `` | Toggle staged | Toggle staged for selected file. |
| `` <ctrl+b> `` | Filter files by status | |
| `` y `` | Copy to clipboard | |
| `` c `` | Commit veranderingen | Commit staged changes. |
| `` <ctrl+b> `` | Filter bestanden op status | |
| `` y `` | Kopieer naar klembord | |
| `` c `` | Commit veranderingen | Commit gestagede wijzigingen. |
| `` w `` | Commit veranderingen zonder pre-commit hook | |
| `` A `` | Wijzig laatste commit | |
| `` C `` | Commit veranderingen met de git editor | |
| `` <ctrl+f> `` | Find base commit for fixup | Find the commit that your current changes are building upon, for the sake of amending/fixing up the commit. This spares you from having to look through your branch's commits one-by-one to see which commit should be amended/fixed up. See docs: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` e `` | Edit | Open file in external editor. |
| `` o `` | Open bestand | Open file in default application. |
| `` <ctrl+f> `` | Find base commit for fixup | Vind de commit waar je huidige wijzigingen bovenop zijn gebouwd met als doel die commit te amenden/fixen. Hierdoor hoef je dit niet met de hand te doen. Zie: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` e `` | Edit | Open bestand in externe editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` i `` | Ignore or exclude file | |
| `` r `` | Refresh bestanden | |
| `` s `` | Stash | Stash all changes. For other variations of stashing, use the view stash options keybinding. |
@@ -75,13 +75,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <enter> `` | Stage individuele hunks/lijnen | If the selected item is a file, focus the staging view so you can stage individual hunks/lines. If the selected item is a directory, collapse/expand it. |
| `` d `` | Bekijk 'veranderingen ongedaan maken' opties | View options for discarding changes to the selected file. |
| `` g `` | Bekijk upstream reset opties | |
| `` D `` | Reset | View reset options for working tree (e.g. nuking the working tree). |
| `` D `` | Resetten | View reset options for working tree (e.g. nuking the working tree). |
| `` ` `` | Toggle bestandsboom weergave | Toggle file view between flat and tree layout. Flat layout shows all file paths in a single list, tree layout groups files by directory.<br><br>The default can be changed in the config file with the key 'gui.showFileTree'. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` M `` | View merge conflict options | View options for resolving merge conflicts. |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` M `` | Bekijk merge conflict opties | Bekijk opties voor het oplossen van mergeconflicten. |
| `` f `` | Fetch | Fetch changes from remote. |
| `` - `` | Collapse all files | Collapse all directories in the files tree |
| `` = `` | Expand all files | Expand all directories in the file tree |
| `` = `` | Vouw alle bestanden uit | Vouw alle mappen in de bestandsstructuur uit |
| `` 0 `` | Focus main view | |
| `` / `` | Filter the current view by text | |
@@ -91,7 +91,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <enter> `` | Bevestig | |
| `` <esc> `` | Sluiten | |
| `` <ctrl+o> `` | Copy to clipboard | |
| `` <ctrl+o> `` | Kopieer naar klembord | |
## Branches
@@ -99,19 +99,19 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer branch name naar klembord | |
| `` i `` | Laat git-flow opties zien | |
| `` <space> `` | Uitchecken | Checkout selected item. |
| `` <space> `` | Uitchecken | Geselecteerd item uitchecken. |
| `` n `` | Nieuwe branch | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` o `` | Maak een pull-request | |
| `` O `` | Bekijk opties voor pull-aanvraag | |
| `` G `` | Open pull request in browser | |
| `` <ctrl+y> `` | Kopieer de URL van het pull-verzoek naar het klembord | |
| `` c `` | Uitchecken bij naam | Checkout by name. In the input box you can enter '-' to switch to the previous branch. |
| `` - `` | Checkout previous branch | |
| `` - `` | Vorige branch uitchecken | |
| `` F `` | Forceer checkout | Force checkout selected branch. This will discard all local changes in your working directory before checking out the selected branch. |
| `` d `` | Delete | View delete options for local/remote branch. |
| `` r `` | Rebase branch | Rebase the checked-out branch onto the selected branch. |
| `` d `` | Verwijderen | View delete options for local/remote branch. |
| `` r `` | Rebase branch | Rebase de uitgecheckte branch bovenop de geselecteerde branch. |
| `` M `` | Merge in met huidige checked out branch | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` f `` | Fast-forward deze branch vanaf zijn upstream | Fast-forward selected branch from its upstream. |
| `` T `` | Creëer tag | |
@@ -119,7 +119,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Bekijk reset opties | |
| `` R `` | Hernoem branch | |
| `` u `` | View upstream options | View options relating to the branch's upstream e.g. setting/unsetting the upstream and resetting to the upstream. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` / `` | Filter the current view by text | |
@@ -136,18 +136,18 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer de bestandsnaam naar het klembord | |
| `` y `` | Copy to clipboard | |
| `` y `` | Kopieer naar klembord | |
| `` c `` | Uitchecken | Bestand uitchecken |
| `` d `` | Bekijk 'veranderingen ongedaan maken' opties | Uitsluit deze commit zijn veranderingen aan dit bestand |
| `` o `` | Open bestand | Open file in default application. |
| `` e `` | Edit | Open file in external editor. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` e `` | Edit | Open bestand in externe editor. |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` <space> `` | Toggle bestand inbegrepen in patch | Toggle whether the file is included in the custom patch. See https://github.com/jesseduffield/lazygit#rebase-magic-custom-patches. |
| `` a `` | Toggle all files | Add/remove all commit's files to custom patch. See https://github.com/jesseduffield/lazygit#rebase-magic-custom-patches. |
| `` <enter> `` | Enter bestand om geselecteerde regels toe te voegen aan de patch | If a file is selected, enter the file so that you can add/remove individual lines to the custom patch. If a directory is selected, toggle the directory. |
| `` ` `` | Toggle bestandsboom weergave | Toggle file view between flat and tree layout. Flat layout shows all file paths in a single list, tree layout groups files by directory.<br><br>The default can be changed in the config file with the key 'gui.showFileTree'. |
| `` - `` | Collapse all files | Collapse all directories in the files tree |
| `` = `` | Expand all files | Expand all directories in the file tree |
| `` = `` | Vouw alle bestanden uit | Vouw alle mappen in de bestandsstructuur uit |
| `` 0 `` | Focus main view | |
| `` / `` | Filter the current view by text | |
@@ -183,11 +183,11 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` y `` | Copy commit attribute to clipboard | Copy commit attribute to clipboard (e.g. hash, URL, diff, message, author). |
| `` o `` | Open commit in browser | |
| `` n `` | Creëer nieuwe branch van commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Kopieer commit (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk gecommite bestanden | |
@@ -219,9 +219,9 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <left>, h `` | Selecteer voorgaand conflict | |
| `` <right>, l `` | Selecteer volgende conflict | |
| `` z `` | Ongedaan maken | Undo last merge conflict resolution. |
| `` e `` | Verander bestand | Open file in external editor. |
| `` o `` | Open bestand | Open file in default application. |
| `` M `` | View merge conflict options | View options for resolving merge conflicts. |
| `` e `` | Verander bestand | Open bestand in externe editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` M `` | Bekijk merge conflict opties | Bekijk opties voor het oplossen van mergeconflicten. |
| `` <esc> `` | Ga terug naar het bestanden paneel | |
## Normaal
@@ -243,8 +243,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` v `` | Toggle drag selecteer | |
| `` a `` | Toggle hunk selection | Toggle line-by-line vs. hunk selection mode. |
| `` <ctrl+o> `` | Copy selected text to clipboard | |
| `` o `` | Open bestand | Open file in default application. |
| `` e `` | Verander bestand | Open file in external editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` e `` | Verander bestand | Open bestand in externe editor. |
| `` <space> `` | Voeg toe/verwijder lijn(en) in patch | |
| `` d `` | Remove lines from commit | Remove the selected lines from this commit. This runs an interactive rebase in the background, so you may get a merge conflict if a later commit also changes these lines. |
| `` <esc> `` | Sluit lijn-bij-lijn modus | |
@@ -259,12 +259,12 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` y `` | Copy commit attribute to clipboard | Copy commit attribute to clipboard (e.g. hash, URL, diff, message, author). |
| `` o `` | Open commit in browser | |
| `` n `` | Creëer nieuwe branch van commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Kopieer commit (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset cherry-picked (gekopieerde) commits selectie | |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
@@ -275,16 +275,16 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer branch name naar klembord | |
| `` <space> `` | Uitchecken | Checkout a new local branch based on the selected remote branch, or the remote branch as a detached head. |
| `` <space> `` | Uitchecken | Geselecteerde remote branch uitchecken als nieuwe locale branch of als detached head. |
| `` n `` | Nieuwe branch | |
| `` w `` | New worktree | |
| `` M `` | Merge in met huidige checked out branch | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` r `` | Rebase branch | Rebase the checked-out branch onto the selected branch. |
| `` d `` | Delete | Delete the remote branch from the remote. |
| `` u `` | Set as upstream | Stel in als upstream van uitgecheckte branch |
| `` r `` | Rebase branch | Rebase de uitgecheckte branch bovenop de geselecteerde branch. |
| `` d `` | Verwijderen | Delete the remote branch from the remote. |
| `` u `` | Instellen als upstream | Stel in als upstream van uitgecheckte branch |
| `` s `` | Sort order | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` / `` | Filter the current view by text | |
@@ -293,9 +293,9 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <enter> `` | View branches | |
| `` <enter> `` | Bekijk branches | |
| `` n `` | Voeg een nieuwe remote toe | |
| `` d `` | Remove | Remove the selected remote. Any local branches tracking a remote branch from the remote will be unaffected. |
| `` d `` | Verwijderen | Remove the selected remote. Any local branches tracking a remote branch from the remote will be unaffected. |
| `` e `` | Edit | Wijzig remote |
| `` f `` | Fetch | Fetch remote |
| `` F `` | Add fork remote | Quickly add a fork remote by replacing the owner in the origin URL and optionally check out a branch from new remote. |
@@ -320,15 +320,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy selected text to clipboard | |
| `` <space> `` | Toggle staged | Toggle lijnen staged / unstaged |
| `` d `` | Verwijdert change (git reset) | When unstaged change is selected, discard the change using `git reset`. When staged change is selected, unstage the change. |
| `` o `` | Open bestand | Open file in default application. |
| `` e `` | Verander bestand | Open file in external editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` e `` | Verander bestand | Open bestand in externe editor. |
| `` <esc> `` | Ga terug naar het bestanden paneel | |
| `` <tab> `` | Ga naar een ander paneel | Switch to other view (staged/unstaged changes). |
| `` E `` | Edit hunk | Edit selected hunk in external editor. |
| `` c `` | Commit veranderingen | Commit staged changes. |
| `` c `` | Commit veranderingen | Commit gestagede wijzigingen. |
| `` w `` | Commit veranderingen zonder pre-commit hook | |
| `` C `` | Commit veranderingen met de git editor | |
| `` <ctrl+f> `` | Find base commit for fixup | Find the commit that your current changes are building upon, for the sake of amending/fixing up the commit. This spares you from having to look through your branch's commits one-by-one to see which commit should be amended/fixed up. See docs: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` <ctrl+f> `` | Find base commit for fixup | Vind de commit waar je huidige wijzigingen bovenop zijn gebouwd met als doel die commit te amenden/fixen. Hierdoor hoef je dit niet met de hand te doen. Zie: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` / `` | Start met zoeken | |
## Stash
@@ -340,7 +340,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` d `` | Laten vallen | Remove the stash entry from the stash list. |
| `` n `` | Nieuwe branch | Create a new branch from the selected stash entry. This works by git checking out the commit that the stash entry was created from, creating a new branch from that commit, then applying the stash entry to the new branch as an additional commit. |
| `` w `` | New worktree | |
| `` r `` | Rename stash | |
| `` r `` | Hernoem stash | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk gecommite bestanden | |
| `` / `` | Filter the current view by text | |
@@ -349,7 +349,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` e `` | Verander config bestand | Open file in external editor. |
| `` e `` | Verander config bestand | Open bestand in externe editor. |
| `` u `` | Check voor updates | |
| `` <enter> `` | Wissel naar een recente repo | |
| `` a `` | Show/cycle all branch logs | |
@@ -365,12 +365,12 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` y `` | Copy commit attribute to clipboard | Copy commit attribute to clipboard (e.g. hash, URL, diff, message, author). |
| `` o `` | Open commit in browser | |
| `` n `` | Creëer nieuwe branch van commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Kopieer commit (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset cherry-picked (gekopieerde) commits selectie | |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk gecommite bestanden | |
@@ -382,7 +382,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer submodule naam naar klembord | |
| `` <enter> `` | Enter | Enter submodule |
| `` d `` | Remove | Remove the selected submodule and its corresponding directory. |
| `` d `` | Verwijderen | Remove the selected submodule and its corresponding directory. |
| `` u `` | Update | Update selected submodule. |
| `` n `` | Voeg nieuwe submodule toe | |
| `` e `` | Update submodule URL | |
@@ -395,13 +395,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <ctrl+o> `` | Copy tag to clipboard | |
| `` <space> `` | Uitchecken | Checkout the selected tag as a detached HEAD. |
| `` <space> `` | Uitchecken | Geselecteerde tag uitchecken als detached HEAD. |
| `` n `` | Creëer tag | Create new tag from current commit. You'll be prompted to enter a tag name and optional description. |
| `` w `` | New worktree | |
| `` d `` | Delete | View delete options for local/remote tag. |
| `` d `` | Verwijderen | View delete options for local/remote tag. |
| `` P `` | Push tag | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` g `` | Resetten | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` / `` | Filter the current view by text | |
@@ -412,6 +412,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` n `` | New worktree | |
| `` <space> `` | Switch | Switch to the selected worktree. |
| `` o `` | Open in editor | |
| `` d `` | Remove | Remove the selected worktree. This will both delete the worktree's directory, as well as metadata about the worktree in the .git directory. |
| `` o `` | Openen in editor | |
| `` d `` | Verwijderen | Remove the selected worktree. This will both delete the worktree's directory, as well as metadata about the worktree in the .git directory. |
| `` / `` | Filter the current view by text | |
+56 -2
View File
@@ -110,6 +110,26 @@ gui:
# is true.
expandedSidePanelWeight: 2
# If true, don't give a side panel more height than it needs to show its
# content; when all panels fit, the leftover height is shared among them so that
# they still fill the screen.
shrinkSidePanelsToContent: false
# The side panels, in the order they appear from top to bottom.
# Each entry is a list of one or more names that share a single panel as tabs
# (cycle through them with the next-tab/previous-tab keys).
# Omit a name to hide it; give a name its own one-element list to promote a tab
# to a top-level panel.
# Valid names are: 'status', 'files', 'worktrees', 'submodules', 'branches',
# 'remotes', 'tags', 'commits', 'reflog', 'stash'. 'files', 'branches', and
# 'commits' must always be included; they can't be hidden.
sidePanels:
- [status]
- [files, worktrees, submodules]
- [branches, remotes, tags]
- [commits, reflog]
- [stash]
# Sometimes the main window is split in two (e.g. when the selected file has
# both staged and unstaged changes). This setting controls how the two sections
# are split.
@@ -342,6 +362,11 @@ gui:
git:
# Array of pagers. Each entry has the following format:
#
# # A name for the pager, shown in the notification when cycling pagers.
# # If not set, the name is derived from the first word of the pager
# # command (or of the external diff command).
# name: ""
#
# # Value of the --color arg in the git diff command. Some pagers want
# # this to be set to 'always' and some want it set to 'never'
# colorArg: "always"
@@ -361,6 +386,9 @@ git:
# # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver.
# useExternalDiffGitConfig: false
#
# 'pager', 'externalDiffCommand', and 'useExternalDiffGitConfig' are mutually
# exclusive; set at most one per entry.
#
# See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md
# for more information.
pagers: []
@@ -406,6 +434,11 @@ git:
# If true, periodically refresh files and submodules
autoRefresh: true
# If true, poll the repo periodically for external ref changes (commits, branch
# updates, checkouts made outside lazygit) and refresh when one is detected.
# Independent of autoRefresh, which only governs the files panel.
autoDetectExternalChanges: true
# If not "none", lazygit will automatically fast-forward local branches to match
# their upstream after fetching. Applies to branches that are not the currently
# checked out branch, and only to those that are strictly behind their upstream
@@ -499,6 +532,15 @@ git:
# to 40 to disable truncation.
truncateCopiedCommitHashesTo: 12
# Config relating to git worktrees
worktree:
# Default parent directory for new worktrees. It is offered as a candidate
# location alongside the parent directories of any worktrees you already have.
# A relative path is resolved against the repository's root directory, so
# "../worktrees" sits beside the repo and ".worktrees" sits inside it.
# A leading "~" is expanded to your home directory, so "~/worktrees" works.
defaultPath: ""
# Periodic update checks
update:
# One of: 'prompt' (default) | 'background' | 'never'
@@ -517,6 +559,11 @@ refresher:
# Auto-fetch can be disabled via option 'git.autoFetch'.
fetchInterval: 60
# Interval in seconds at which lazygit polls for external ref changes (commits,
# branch updates, checkouts made outside lazygit).
# Detection can be disabled via option 'git.autoDetectExternalChanges'.
externalChangeCheckInterval: 2
# If true, show a confirmation popup before quitting Lazygit
confirmOnQuit: false
@@ -648,6 +695,7 @@ keybinding:
confirmInEditor: [<ctrl+enter>, <ctrl+s>]
remove: d
new: "n"
newWorktree: w
edit: e
openFile: o
scrollUpMain: [<pgup>, K, <ctrl+u>]
@@ -667,6 +715,7 @@ keybinding:
nextScreenMode: +
prevScreenMode: _
cyclePagers: '|'
cyclePagersReverse: \
undo: z
redo: Z
filteringMenu: <ctrl+s>
@@ -681,6 +730,7 @@ keybinding:
increaseRenameSimilarityThreshold: )
decreaseRenameSimilarityThreshold: (
openDiffTool: <ctrl+t>
editConfig: <alt+shift+c>
status:
checkForUpdate: u
recentRepos: <enter>
@@ -726,8 +776,6 @@ keybinding:
fetchRemote: f
addForkRemote: F
sortOrder: s
worktrees:
viewWorktreeOptions: w
commits:
squashDown: s
renameCommit: r
@@ -1059,6 +1107,12 @@ keybinding:
edit: <disabled> # disable 'edit file'
```
### Overriding the platform for default keybindings
A few keybindings have different defaults on macOS than on Linux and Windows (e.g. word-wise cursor movement in text inputs uses `alt` on macOS but `ctrl` elsewhere). Lazygit picks these based on the OS it's running on, but you can override that with the `LAZYGIT_KEYBINDING_PLATFORM` environment variable. Set it to `darwin`, `linux`, or `windows`; any other value is ignored and the actual OS is used.
This is useful when running lazygit in a Linux container that you access over ssh from a Mac, where you'd rather use the macOS keybindings.
### Example Keybindings For Colemak Users
```yaml
+2 -29
View File
@@ -2,8 +2,6 @@
Lazygit supports custom pagers, [configured](/docs/Config.md) in the config.yml file (which can be opened by pressing `e` in the Status panel).
Support does not extend to Windows users, because we're making use of a package which doesn't have Windows support. However, see [below](#emulating-custom-pagers-on-windows) for a workaround.
Multiple pagers are supported; you can cycle through them with the `|` key. This can be useful if you usually prefer a particular pager, but want to use a different one for certain kinds of diffs.
Pagers are configured with the `pagers` array in the git section; here's an example for a multi-pager setup (use an empty object `{}` for the default builtin diff display that doesn't use a pager):
@@ -71,7 +69,7 @@ git:
- externalDiffCommand: difft --color=always
```
The `colorArg` and `pager` options are not used in this case.
The `colorArg` option is not used in this case.
You can add whatever extra arguments you prefer for your difftool; for instance
@@ -91,29 +89,4 @@ git:
This can be useful if you also want to use it for diffs on the command line, and it also has the advantage that you can configure it per file type in `.gitattributes`; see https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver.
## Emulating custom pagers on Windows
There is a trick to emulate custom pagers on Windows using a Powershell script configured as an external diff command. It's not perfect, but certainly better than nothing. To do this, save the following script as `lazygit-pager.ps1` at a convenient place on your disk:
```pwsh
#!/usr/bin/env pwsh
$old = $args[1].Replace('\', '/')
$new = $args[4].Replace('\', '/')
$path = $args[0]
git diff --no-index --no-ext-diff $old $new
| %{ $_.Replace($old, $path).Replace($new, $path) }
| delta --width=$env:LAZYGIT_COLUMNS
```
Use the pager of your choice with the arguments you like in the last line of the script. Personally I wouldn't want to use lazygit anymore without delta's `--hyperlinks --hyperlinks-file-link-format="lazygit-edit://{path}:{line}"` args, see [above](#delta).
In your lazygit config, use
```yml
git:
pagers:
- externalDiffCommand: "C:/wherever/lazygit-pager.ps1"
```
The main limitation of this approach compared to a "real" pager is that renames are not displayed correctly; they are shown as if they were modifications of the old file. (This affects only the hunk headers; the diff itself is always correct.)
`pager`, `externalDiffCommand`, and `useExternalDiffGitConfig` are alternative ways of producing the diff, so a pager entry may use at most one of them.
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | Refresh | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. |
| `` + `` | Next screen mode (normal/half/fullscreen) | |
| `` _ `` | Prev screen mode | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | Cancel | |
| `` ? `` | Open keybindings menu | |
| `` <ctrl+s> `` | View filter options | View options for filtering the commit log, so that only commits matching the filter are shown. |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | Quit | |
| `` <ctrl+z> `` | Suspend the application | |
| `` <ctrl+w> `` | Toggle whitespace | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | Edit config file | Open file in external editor. |
| `` z `` | Undo | The reflog will be used to determine what git command to run to undo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
| `` Z `` | Redo | The reflog will be used to determine what git command to run to redo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
@@ -110,13 +112,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Open commit in browser | |
| `` n `` | Create new branch off of commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Copy (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View files | |
| `` w `` | View worktree options | |
| `` / `` | Search the current view by text | |
## Confirmation panel
@@ -176,6 +178,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | Checkout | Checkout selected item. |
| `` n `` | New branch | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` o `` | Create pull request | |
| `` O `` | View create pull request options | |
| `` G `` | Open pull request in browser | |
@@ -195,7 +198,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Main panel (merging)
@@ -203,7 +205,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | Pick hunk | |
| `` b `` | Pick all hunks | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | Previous hunk | |
| `` <down>, j `` | Next hunk | |
| `` <left>, h `` | Previous conflict | |
@@ -280,6 +282,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Open commit in browser | |
| `` n `` | Create new branch off of commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Copy (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset copied (cherry-picked) commits selection | |
@@ -287,7 +290,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Remote branches
@@ -297,6 +299,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy branch name to clipboard | |
| `` <space> `` | Checkout | Checkout a new local branch based on the selected remote branch, or the remote branch as a detached head. |
| `` n `` | New branch | |
| `` w `` | New worktree | |
| `` M `` | Merge | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` r `` | Rebase | Rebase the checked-out branch onto the selected branch. |
| `` d `` | Delete | Delete the remote branch from the remote. |
@@ -306,7 +309,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Remotes
@@ -337,17 +339,16 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Pop | Apply the stash entry to your working directory and remove the stash entry. |
| `` d `` | Drop | Remove the stash entry from the stash list. |
| `` n `` | New branch | Create a new branch from the selected stash entry. This works by git checking out the commit that the stash entry was created from, creating a new branch from that commit, then applying the stash entry to the new branch as an additional commit. |
| `` w `` | New worktree | |
| `` r `` | Rename stash | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View files | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Status
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | Open config file | Open file in default application. |
| `` e `` | Edit config file | Open file in external editor. |
| `` u `` | Check for update | |
| `` <enter> `` | Switch to a recent repo | |
@@ -365,6 +366,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Open commit in browser | |
| `` n `` | Create new branch off of commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Copy (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset copied (cherry-picked) commits selection | |
@@ -372,7 +374,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View files | |
| `` w `` | View worktree options | |
| `` / `` | Search the current view by text | |
## Submodules
@@ -396,13 +397,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy tag to clipboard | |
| `` <space> `` | Checkout | Checkout the selected tag as a detached HEAD. |
| `` n `` | New tag | Create new tag from current commit. You'll be prompted to enter a tag name and optional description. |
| `` w `` | New worktree | |
| `` d `` | Delete | View delete options for local/remote tag. |
| `` P `` | Push tag | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Worktrees
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | 更新 | Gitの状態を更新します(`git status`、`git branch`などをバックグラウンドで実行してパネルの内容を更新します)。これは`git fetch`を実行しません。 |
| `` + `` | 次の画面モード(通常/半分/全画面) | |
| `` _ `` | 前の画面モード | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | キャンセル | |
| `` ? `` | キーバインディングメニューを開く | |
| `` <ctrl+s> `` | フィルターオプションを表示 | コミットログのフィルタリングオプションを表示し、フィルタに一致するコミットのみを表示します。 |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | 終了 | |
| `` <ctrl+z> `` | Suspend the application | |
| `` <ctrl+w> `` | 空白表示の切り替え | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | 設定ファイルを編集 | 外部エディタでファイルを開きます。 |
| `` z `` | 元に戻す | 最後のgitコマンドを元に戻すために実行するgitコマンドを決定するためにreflogが使用されます。これにはワーキングツリーへの変更は含まれません。コミットのみが考慮されます。 |
| `` Z `` | やり直す | 最後のgitコマンドをやり直すために実行するgitコマンドを決定するためにreflogが使用されます。これにはワーキングツリーへの変更は含まれません。コミットのみが考慮されます。 |
@@ -90,13 +92,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | ブラウザでコミットを開く | |
| `` n `` | コミットから新しいブランチを作成 | |
| `` N `` | コミットを新しいブランチに移動 | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | 新しいワークツリー | |
| `` g `` | リセット | 選択した項目へのリセットオプション(ソフト/ミックス/ハード)を表示します。各リセットタイプの詳細は次の通りです:<br>- ソフトリセット:変更を保持し、ステージされた状態にします<br>- ミックスリセット:変更を保持し、ステージされていない状態にします<br>- ハードリセット:すべての変更を破棄します |
| `` C `` | コピー(チェリーピック) | コミットをコピーとしてマークします。ローカルコミットビューで `V` を押すと、コピーしたコミットをチェックアウトしたブランチにペースト(チェリーピック)できます。いつでも `<esc>` を押して選択をキャンセルできます。 |
| `` <ctrl+t> `` | 外部差分ツールを開く(git difftool) | |
| `` * `` | 現在のブランチのコミットを選択 | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | ファイルを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストで検索 | |
## コミットファイル
@@ -136,6 +138,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | ブラウザでコミットを開く | |
| `` n `` | コミットから新しいブランチを作成 | |
| `` N `` | コミットを新しいブランチに移動 | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | 新しいワークツリー | |
| `` g `` | リセット | 選択した項目へのリセットオプション(ソフト/ミックス/ハード)を表示します。各リセットタイプの詳細は次の通りです:<br>- ソフトリセット:変更を保持し、ステージされた状態にします<br>- ミックスリセット:変更を保持し、ステージされていない状態にします<br>- ハードリセット:すべての変更を破棄します |
| `` C `` | コピー(チェリーピック) | コミットをコピーとしてマークします。ローカルコミットビューで `V` を押すと、コピーしたコミットをチェックアウトしたブランチにペースト(チェリーピック)できます。いつでも `<esc>` を押して選択をキャンセルできます。 |
| `` <ctrl+r> `` | コピーされた(チェリーピックされた)コミットの選択をリセット | |
@@ -143,7 +146,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | 現在のブランチのコミットを選択 | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | ファイルを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストで検索 | |
## サブモジュール
@@ -168,17 +170,16 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | ポップ | スタッシュエントリをワーキングディレクトリに適用し、スタッシュエントリを削除します。 |
| `` d `` | 削除 | スタッシュリストからスタッシュエントリを削除します。 |
| `` n `` | 新しいブランチ | 選択したスタッシュエントリから新しいブランチを作成します。これは、スタッシュエントリが作成されたコミットをgitがチェックアウトし、そのコミットから新しいブランチを作成した後、スタッシュエントリを追加のコミットとして新しいブランチに適用することで機能します。 |
| `` w `` | 新しいワークツリー | |
| `` r `` | スタッシュの名前を変更 | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | ファイルを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストでフィルタリング | |
## ステータス
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | 設定ファイルを開く | デフォルトのアプリケーションでファイルを開きます。 |
| `` e `` | 設定ファイルを編集 | 外部エディタでファイルを開きます。 |
| `` u `` | 更新を確認 | |
| `` <enter> `` | 最近のリポジトリをチェックアウト | |
@@ -201,13 +202,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | タグをクリップボードにコピー | |
| `` <space> `` | チェックアウト(ブランチの切り替え) | 選択したタグをデタッチドHEADとしてチェックアウトします。 |
| `` n `` | 新しいタグを作成 | 現在のコミットから新しいタグを作成します。タグ名とオプションの説明を入力するよう促されます。 |
| `` w `` | 新しいワークツリー | |
| `` d `` | 削除 | ローカル/リモートタグの削除オプションを表示します。 |
| `` P `` | タグをプッシュ | 選択したタグをリモートにプッシュします。リモートを選択するよう促されます。 |
| `` g `` | リセット | 選択した項目へのリセットオプション(ソフト/ミックス/ハード)を表示します。各リセットタイプの詳細は次の通りです:<br>- ソフトリセット:変更を保持し、ステージされた状態にします<br>- ミックスリセット:変更を保持し、ステージされていない状態にします<br>- ハードリセット:すべての変更を破棄します |
| `` <ctrl+t> `` | 外部差分ツールを開く(git difftool) | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | コミットを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストでフィルタリング | |
## ファイル
@@ -286,7 +287,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | ハンクを選択 | |
| `` b `` | すべてのハンクを選択 | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | 前のハンク | |
| `` <down>, j `` | 次のハンク | |
| `` <left>, h `` | 前のコンフリクト | |
@@ -325,6 +326,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | ブラウザでコミットを開く | |
| `` n `` | コミットから新しいブランチを作成 | |
| `` N `` | コミットを新しいブランチに移動 | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | 新しいワークツリー | |
| `` g `` | リセット | 選択した項目へのリセットオプション(ソフト/ミックス/ハード)を表示します。各リセットタイプの詳細は次の通りです:<br>- ソフトリセット:変更を保持し、ステージされた状態にします<br>- ミックスリセット:変更を保持し、ステージされていない状態にします<br>- ハードリセット:すべての変更を破棄します |
| `` C `` | コピー(チェリーピック) | コミットをコピーとしてマークします。ローカルコミットビューで `V` を押すと、コピーしたコミットをチェックアウトしたブランチにペースト(チェリーピック)できます。いつでも `<esc>` を押して選択をキャンセルできます。 |
| `` <ctrl+r> `` | コピーされた(チェリーピックされた)コミットの選択をリセット | |
@@ -332,7 +334,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | 現在のブランチのコミットを選択 | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | コミットを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストでフィルタリング | |
## リモート
@@ -354,6 +355,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | ブランチ名をクリップボードにコピー | |
| `` <space> `` | チェックアウト(ブランチの切り替え) | 選択したリモートブランチに基づいて新しいローカルブランチをチェックアウトするか、リモートブランチをデタッチドヘッドとしてチェックアウトします。 |
| `` n `` | 新しいブランチ | |
| `` w `` | 新しいワークツリー | |
| `` M `` | マージ | 選択した項目を現在のブランチにマージするためのオプションを表示します(通常のマージ、スカッシュマージ) |
| `` r `` | リベース | チェックアウトしたブランチを選択したブランチ上にリベースします。 |
| `` d `` | 削除 | リモートからリモートブランチを削除します。 |
@@ -363,7 +365,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | 外部差分ツールを開く(git difftool) | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | コミットを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストでフィルタリング | |
## ローカルブランチ
@@ -375,6 +376,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | チェックアウト(ブランチの切り替え) | 選択した項目をチェックアウトします。 |
| `` n `` | 新しいブランチ | |
| `` N `` | コミットを新しいブランチに移動 | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | 新しいワークツリー | |
| `` o `` | プルリクエストを作成 | |
| `` O `` | プルリクエスト作成オプションを表示 | |
| `` G `` | Open pull request in browser | |
@@ -394,7 +396,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | 外部差分ツールを開く(git difftool) | |
| `` 0 `` | メインビューにフォーカス | |
| `` <enter> `` | コミットを表示 | |
| `` w `` | ワークツリーオプションを表示 | |
| `` / `` | 現在のビューをテキストでフィルタリング | |
## ワークツリー
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | 새로고침 | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. |
| `` + `` | 다음 스크린 모드 (normal/half/fullscreen) | |
| `` _ `` | 이전 스크린 모드 | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | 취소 | |
| `` ? `` | 매뉴 열기 | |
| `` <ctrl+s> `` | View filter-by-path options | View options for filtering the commit log, so that only commits matching the filter are shown. |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | 종료 | |
| `` <ctrl+z> `` | Suspend the application | |
| `` <ctrl+w> `` | 공백문자를 Diff 뷰에서 표시 여부 전환 | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | 설정 파일 수정 | Open file in external editor. |
| `` z `` | 되돌리기 (reflog) (실험적) | The reflog will be used to determine what git command to run to undo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
| `` Z `` | 다시 실행 (reflog) (실험적) | The reflog will be used to determine what git command to run to redo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
@@ -67,6 +69,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 브라우저에서 커밋 열기 | |
| `` n `` | 커밋에서 새 브랜치를 만듭니다. | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | View reset options | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | 커밋을 복사 (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset cherry-picked (copied) commits selection | |
@@ -74,7 +77,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 커밋 보기 | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Secondary
@@ -93,10 +95,10 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Pop | Apply the stash entry to your working directory and remove the stash entry. |
| `` d `` | Drop | Remove the stash entry from the stash list. |
| `` n `` | 새 브랜치 생성 | Create a new branch from the selected stash entry. This works by git checking out the commit that the stash entry was created from, creating a new branch from that commit, then applying the stash entry to the new branch as an additional commit. |
| `` w `` | New worktree | |
| `` r `` | Rename stash | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View selected item's files | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Sub-commits
@@ -109,6 +111,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 브라우저에서 커밋 열기 | |
| `` n `` | 커밋에서 새 브랜치를 만듭니다. | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | View reset options | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | 커밋을 복사 (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset cherry-picked (copied) commits selection | |
@@ -116,7 +119,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View selected item's files | |
| `` w `` | View worktree options | |
| `` / `` | 검색 시작 | |
## Worktrees
@@ -142,7 +144,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | Pick hunk | |
| `` b `` | Pick all hunks | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | 이전 hunk를 선택 | |
| `` <down>, j `` | 다음 hunk를 선택 | |
| `` <left>, h `` | 이전 충돌을 선택 | |
@@ -210,6 +212,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | 체크아웃 | Checkout selected item. |
| `` n `` | 새 브랜치 생성 | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` o `` | 풀 리퀘스트 생성 | |
| `` O `` | 풀 리퀘스트 생성 옵션 | |
| `` G `` | Open pull request in browser | |
@@ -229,14 +232,12 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 커밋 보기 | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## 상태
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | 설정 파일 열기 | Open file in default application. |
| `` e `` | 설정 파일 수정 | Open file in external editor. |
| `` u `` | 업데이트 확인 | |
| `` <enter> `` | 최근에 사용한 저장소로 전환 | |
@@ -277,6 +278,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | 브랜치명을 클립보드에 복사 | |
| `` <space> `` | 체크아웃 | Checkout a new local branch based on the selected remote branch, or the remote branch as a detached head. |
| `` n `` | 새 브랜치 생성 | |
| `` w `` | New worktree | |
| `` M `` | 현재 브랜치에 병합 | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` r `` | 체크아웃된 브랜치를 이 브랜치에 리베이스 | Rebase the checked-out branch onto the selected branch. |
| `` d `` | 삭제 | Delete the remote branch from the remote. |
@@ -286,7 +288,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 커밋 보기 | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## 커밋
@@ -322,13 +323,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 브라우저에서 커밋 열기 | |
| `` n `` | 커밋에서 새 브랜치를 만듭니다. | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | View reset options | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | 커밋을 복사 (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | View selected item's files | |
| `` w `` | View worktree options | |
| `` / `` | 검색 시작 | |
## 커밋 파일
@@ -365,13 +366,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy tag to clipboard | |
| `` <space> `` | 체크아웃 | Checkout the selected tag as a detached HEAD. |
| `` n `` | 태그를 생성 | Create new tag from current commit. You'll be prompted to enter a tag name and optional description. |
| `` w `` | New worktree | |
| `` d `` | 삭제 | View delete options for local/remote tag. |
| `` P `` | 태그를 push | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | 초기화 | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 커밋 보기 | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## 파일
+71 -70
View File
@@ -10,26 +10,28 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <pgup>, K, <ctrl+u> (fn+up/shift+k) `` | Scroll naar beneden vanaf hoofdpaneel | |
| `` <pgdown>, J, <ctrl+d> (fn+down/shift+j) `` | Scroll naar beneden vanaf hoofdpaneel | |
| `` @ `` | View command log options | View options for the command log e.g. show/hide the command log and focus the command log. |
| `` P `` | Push | Push the current branch to its upstream branch. If no upstream is configured, you will be prompted to configure an upstream branch. |
| `` p `` | Pull | Pull changes from the remote for the current branch. If no upstream is configured, you will be prompted to configure an upstream branch. |
| `` P `` | Push | Push de huidige branch naar de bijbehorende upstream-branch. Als er geen upstream is geconfigureerd wordt er gevraagd om een upstream-branch te configureren. |
| `` p `` | Pull | Pull wijzigingen van de remote voor de huidige branch. Als er geen upstream is geconfigureerd wordt er gevraagd om een upstream-branch te configureren. |
| `` ) `` | Increase rename similarity threshold | Increase the similarity threshold for a deletion and addition pair to be treated as a rename.<br><br>The default can be changed in the config file with the key 'git.renameSimilarityThreshold'. |
| `` ( `` | Decrease rename similarity threshold | Decrease the similarity threshold for a deletion and addition pair to be treated as a rename.<br><br>The default can be changed in the config file with the key 'git.renameSimilarityThreshold'. |
| `` } `` | Increase diff context size | Increase the amount of the context shown around changes in the diff view.<br><br>The default can be changed in the config file with the key 'git.diffContextSize'. |
| `` { `` | Decrease diff context size | Decrease the amount of the context shown around changes in the diff view.<br><br>The default can be changed in the config file with the key 'git.diffContextSize'. |
| `` : `` | Execute shell command | Bring up a prompt where you can enter a shell command to execute. |
| `` <ctrl+p> `` | Bekijk aangepaste patch opties | |
| `` m `` | Bekijk merge/rebase opties | View options to abort/continue/skip the current merge/rebase. |
| `` m `` | Bekijk merge/rebase opties | Toon abort/continue/skip opties voor huidige merge/rebase. |
| `` R `` | Verversen | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. |
| `` + `` | Volgende scherm modus (normaal/half/groot) | |
| `` _ `` | Vorige scherm modus | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | Annuleren | |
| `` ? `` | Open menu | |
| `` <ctrl+s> `` | Bekijk scoping opties | View options for filtering the commit log, so that only commits matching the filter are shown. |
| `` W, <ctrl+e> `` | Open diff menu | View options relating to diffing two refs e.g. diffing against selected ref, entering ref to diff against, and reversing the diff direction. |
| `` q, <ctrl+c> `` | Quit | |
| `` <ctrl+z> `` | Suspend the application | |
| `` q, <ctrl+c> `` | Afsluiten | |
| `` <ctrl+z> `` | Pauzeer de applicatie | |
| `` <ctrl+w> `` | Toggle whitespace | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | Verander config bestand | Open bestand in externe editor. |
| `` z `` | Ongedaan maken (via reflog) (experimenteel) | The reflog will be used to determine what git command to run to undo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
| `` Z `` | Redo (via reflog) (experimenteel) | The reflog will be used to determine what git command to run to redo the last git command. This does not include changes to the working tree; only commits are taken into consideration. |
@@ -45,8 +47,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <shift+down> `` | Range select down | |
| `` <shift+up> `` | Range select up | |
| `` / `` | Start met zoeken | |
| `` H `` | Scroll left | |
| `` L `` | Scroll right | |
| `` H `` | Scroll naar links | |
| `` L `` | Scroll naar rechts | |
| `` ] `` | Volgende tabblad | |
| `` [ `` | Vorige tabblad | |
@@ -56,15 +58,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer de bestandsnaam naar het klembord | |
| `` <space> `` | Toggle staged | Toggle staged for selected file. |
| `` <ctrl+b> `` | Filter files by status | |
| `` y `` | Copy to clipboard | |
| `` c `` | Commit veranderingen | Commit staged changes. |
| `` <ctrl+b> `` | Filter bestanden op status | |
| `` y `` | Kopieer naar klembord | |
| `` c `` | Commit veranderingen | Commit gestagede wijzigingen. |
| `` w `` | Commit veranderingen zonder pre-commit hook | |
| `` A `` | Wijzig laatste commit | |
| `` C `` | Commit veranderingen met de git editor | |
| `` <ctrl+f> `` | Find base commit for fixup | Find the commit that your current changes are building upon, for the sake of amending/fixing up the commit. This spares you from having to look through your branch's commits one-by-one to see which commit should be amended/fixed up. See docs: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` e `` | Edit | Open file in external editor. |
| `` o `` | Open bestand | Open file in default application. |
| `` <ctrl+f> `` | Find base commit for fixup | Vind de commit waar je huidige wijzigingen bovenop zijn gebouwd met als doel die commit te amenden/fixen. Hierdoor hoef je dit niet met de hand te doen. Zie: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` e `` | Edit | Open bestand in externe editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` i `` | Ignore or exclude file | |
| `` r `` | Refresh bestanden | |
| `` s `` | Stash | Stash all changes. For other variations of stashing, use the view stash options keybinding. |
@@ -73,13 +75,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <enter> `` | Stage individuele hunks/lijnen | If the selected item is a file, focus the staging view so you can stage individual hunks/lines. If the selected item is a directory, collapse/expand it. |
| `` d `` | Bekijk 'veranderingen ongedaan maken' opties | View options for discarding changes to the selected file. |
| `` g `` | Bekijk upstream reset opties | |
| `` D `` | Reset | View reset options for working tree (e.g. nuking the working tree). |
| `` D `` | Resetten | View reset options for working tree (e.g. nuking the working tree). |
| `` ` `` | Toggle bestandsboom weergave | Toggle file view between flat and tree layout. Flat layout shows all file paths in a single list, tree layout groups files by directory.<br><br>The default can be changed in the config file with the key 'gui.showFileTree'. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` M `` | View merge conflict options | View options for resolving merge conflicts. |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` M `` | Bekijk merge conflict opties | Bekijk opties voor het oplossen van mergeconflicten. |
| `` f `` | Fetch | Fetch changes from remote. |
| `` - `` | Collapse all files | Collapse all directories in the files tree |
| `` = `` | Expand all files | Expand all directories in the file tree |
| `` = `` | Vouw alle bestanden uit | Vouw alle mappen in de bestandsstructuur uit |
| `` 0 `` | Focus main view | |
| `` / `` | Filter the current view by text | |
@@ -89,7 +91,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <enter> `` | Bevestig | |
| `` <esc> `` | Sluiten | |
| `` <ctrl+o> `` | Copy to clipboard | |
| `` <ctrl+o> `` | Kopieer naar klembord | |
## Branches
@@ -97,18 +99,19 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer branch name naar klembord | |
| `` i `` | Laat git-flow opties zien | |
| `` <space> `` | Uitchecken | Checkout selected item. |
| `` <space> `` | Uitchecken | Geselecteerd item uitchecken. |
| `` n `` | Nieuwe branch | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` o `` | Maak een pull-request | |
| `` O `` | Bekijk opties voor pull-aanvraag | |
| `` G `` | Open pull request in browser | |
| `` <ctrl+y> `` | Kopieer de URL van het pull-verzoek naar het klembord | |
| `` c `` | Uitchecken bij naam | Checkout by name. In the input box you can enter '-' to switch to the previous branch. |
| `` - `` | Checkout previous branch | |
| `` - `` | Vorige branch uitchecken | |
| `` F `` | Forceer checkout | Force checkout selected branch. This will discard all local changes in your working directory before checking out the selected branch. |
| `` d `` | Delete | View delete options for local/remote branch. |
| `` r `` | Rebase branch | Rebase the checked-out branch onto the selected branch. |
| `` d `` | Verwijderen | View delete options for local/remote branch. |
| `` r `` | Rebase branch | Rebase de uitgecheckte branch bovenop de geselecteerde branch. |
| `` M `` | Merge in met huidige checked out branch | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` f `` | Fast-forward deze branch vanaf zijn upstream | Fast-forward selected branch from its upstream. |
| `` T `` | Creëer tag | |
@@ -116,10 +119,9 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Bekijk reset opties | |
| `` R `` | Hernoem branch | |
| `` u `` | View upstream options | View options relating to the branch's upstream e.g. setting/unsetting the upstream and resetting to the upstream. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Commit bericht
@@ -134,18 +136,18 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer de bestandsnaam naar het klembord | |
| `` y `` | Copy to clipboard | |
| `` y `` | Kopieer naar klembord | |
| `` c `` | Uitchecken | Bestand uitchecken |
| `` d `` | Bekijk 'veranderingen ongedaan maken' opties | Uitsluit deze commit zijn veranderingen aan dit bestand |
| `` o `` | Open bestand | Open file in default application. |
| `` e `` | Edit | Open file in external editor. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` e `` | Edit | Open bestand in externe editor. |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` <space> `` | Toggle bestand inbegrepen in patch | Toggle whether the file is included in the custom patch. See https://github.com/jesseduffield/lazygit#rebase-magic-custom-patches. |
| `` a `` | Toggle all files | Add/remove all commit's files to custom patch. See https://github.com/jesseduffield/lazygit#rebase-magic-custom-patches. |
| `` <enter> `` | Enter bestand om geselecteerde regels toe te voegen aan de patch | If a file is selected, enter the file so that you can add/remove individual lines to the custom patch. If a directory is selected, toggle the directory. |
| `` ` `` | Toggle bestandsboom weergave | Toggle file view between flat and tree layout. Flat layout shows all file paths in a single list, tree layout groups files by directory.<br><br>The default can be changed in the config file with the key 'gui.showFileTree'. |
| `` - `` | Collapse all files | Collapse all directories in the files tree |
| `` = `` | Expand all files | Expand all directories in the file tree |
| `` = `` | Vouw alle bestanden uit | Vouw alle mappen in de bestandsstructuur uit |
| `` 0 `` | Focus main view | |
| `` / `` | Filter the current view by text | |
@@ -181,14 +183,14 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` y `` | Copy commit attribute to clipboard | Copy commit attribute to clipboard (e.g. hash, URL, diff, message, author). |
| `` o `` | Open commit in browser | |
| `` n `` | Creëer nieuwe branch van commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Kopieer commit (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk gecommite bestanden | |
| `` w `` | View worktree options | |
| `` / `` | Start met zoeken | |
## Input prompt
@@ -211,15 +213,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | Kies stuk | |
| `` b `` | Kies beide stukken | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | Selecteer bovenste hunk | |
| `` <down>, j `` | Selecteer onderste hunk | |
| `` <left>, h `` | Selecteer voorgaand conflict | |
| `` <right>, l `` | Selecteer volgende conflict | |
| `` z `` | Ongedaan maken | Undo last merge conflict resolution. |
| `` e `` | Verander bestand | Open file in external editor. |
| `` o `` | Open bestand | Open file in default application. |
| `` M `` | View merge conflict options | View options for resolving merge conflicts. |
| `` e `` | Verander bestand | Open bestand in externe editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` M `` | Bekijk merge conflict opties | Bekijk opties voor het oplossen van mergeconflicten. |
| `` <esc> `` | Ga terug naar het bestanden paneel | |
## Normaal
@@ -241,8 +243,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` v `` | Toggle drag selecteer | |
| `` a `` | Toggle hunk selection | Toggle line-by-line vs. hunk selection mode. |
| `` <ctrl+o> `` | Copy selected text to clipboard | |
| `` o `` | Open bestand | Open file in default application. |
| `` e `` | Verander bestand | Open file in external editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` e `` | Verander bestand | Open bestand in externe editor. |
| `` <space> `` | Voeg toe/verwijder lijn(en) in patch | |
| `` d `` | Remove lines from commit | Remove the selected lines from this commit. This runs an interactive rebase in the background, so you may get a merge conflict if a later commit also changes these lines. |
| `` <esc> `` | Sluit lijn-bij-lijn modus | |
@@ -257,15 +259,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` y `` | Copy commit attribute to clipboard | Copy commit attribute to clipboard (e.g. hash, URL, diff, message, author). |
| `` o `` | Open commit in browser | |
| `` n `` | Creëer nieuwe branch van commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Kopieer commit (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset cherry-picked (gekopieerde) commits selectie | |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Remote branches
@@ -273,27 +275,27 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer branch name naar klembord | |
| `` <space> `` | Uitchecken | Checkout a new local branch based on the selected remote branch, or the remote branch as a detached head. |
| `` <space> `` | Uitchecken | Geselecteerde remote branch uitchecken als nieuwe locale branch of als detached head. |
| `` n `` | Nieuwe branch | |
| `` w `` | New worktree | |
| `` M `` | Merge in met huidige checked out branch | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` r `` | Rebase branch | Rebase the checked-out branch onto the selected branch. |
| `` d `` | Delete | Delete the remote branch from the remote. |
| `` u `` | Set as upstream | Stel in als upstream van uitgecheckte branch |
| `` r `` | Rebase branch | Rebase de uitgecheckte branch bovenop de geselecteerde branch. |
| `` d `` | Verwijderen | Delete the remote branch from the remote. |
| `` u `` | Instellen als upstream | Stel in als upstream van uitgecheckte branch |
| `` s `` | Sort order | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Remotes
| Key | Action | Info |
|-----|--------|-------------|
| `` <enter> `` | View branches | |
| `` <enter> `` | Bekijk branches | |
| `` n `` | Voeg een nieuwe remote toe | |
| `` d `` | Remove | Remove the selected remote. Any local branches tracking a remote branch from the remote will be unaffected. |
| `` d `` | Verwijderen | Remove the selected remote. Any local branches tracking a remote branch from the remote will be unaffected. |
| `` e `` | Edit | Wijzig remote |
| `` f `` | Fetch | Fetch remote |
| `` F `` | Add fork remote | Quickly add a fork remote by replacing the owner in the origin URL and optionally check out a branch from new remote. |
@@ -318,15 +320,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy selected text to clipboard | |
| `` <space> `` | Toggle staged | Toggle lijnen staged / unstaged |
| `` d `` | Verwijdert change (git reset) | When unstaged change is selected, discard the change using `git reset`. When staged change is selected, unstage the change. |
| `` o `` | Open bestand | Open file in default application. |
| `` e `` | Verander bestand | Open file in external editor. |
| `` o `` | Open bestand | Open bestand in standaardapplicatie. |
| `` e `` | Verander bestand | Open bestand in externe editor. |
| `` <esc> `` | Ga terug naar het bestanden paneel | |
| `` <tab> `` | Ga naar een ander paneel | Switch to other view (staged/unstaged changes). |
| `` E `` | Edit hunk | Edit selected hunk in external editor. |
| `` c `` | Commit veranderingen | Commit staged changes. |
| `` c `` | Commit veranderingen | Commit gestagede wijzigingen. |
| `` w `` | Commit veranderingen zonder pre-commit hook | |
| `` C `` | Commit veranderingen met de git editor | |
| `` <ctrl+f> `` | Find base commit for fixup | Find the commit that your current changes are building upon, for the sake of amending/fixing up the commit. This spares you from having to look through your branch's commits one-by-one to see which commit should be amended/fixed up. See docs: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` <ctrl+f> `` | Find base commit for fixup | Vind de commit waar je huidige wijzigingen bovenop zijn gebouwd met als doel die commit te amenden/fixen. Hierdoor hoef je dit niet met de hand te doen. Zie: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md> |
| `` / `` | Start met zoeken | |
## Stash
@@ -337,18 +339,17 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Pop | Apply the stash entry to your working directory and remove the stash entry. |
| `` d `` | Laten vallen | Remove the stash entry from the stash list. |
| `` n `` | Nieuwe branch | Create a new branch from the selected stash entry. This works by git checking out the commit that the stash entry was created from, creating a new branch from that commit, then applying the stash entry to the new branch as an additional commit. |
| `` r `` | Rename stash | |
| `` w `` | New worktree | |
| `` r `` | Hernoem stash | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk gecommite bestanden | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Status
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | Open config bestand | Open file in default application. |
| `` e `` | Verander config bestand | Open file in external editor. |
| `` e `` | Verander config bestand | Open bestand in externe editor. |
| `` u `` | Check voor updates | |
| `` <enter> `` | Wissel naar een recente repo | |
| `` a `` | Show/cycle all branch logs | |
@@ -364,15 +365,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` y `` | Copy commit attribute to clipboard | Copy commit attribute to clipboard (e.g. hash, URL, diff, message, author). |
| `` o `` | Open commit in browser | |
| `` n `` | Creëer nieuwe branch van commit | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` N `` | Verplaats commits naar nieuwe branch | Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.<br><br>Let op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen). |
| `` w `` | New worktree | |
| `` g `` | Bekijk reset opties | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Kopieer commit (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Reset cherry-picked (gekopieerde) commits selectie | |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk gecommite bestanden | |
| `` w `` | View worktree options | |
| `` / `` | Start met zoeken | |
## Submodules
@@ -381,7 +382,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` <ctrl+o> `` | Kopieer submodule naam naar klembord | |
| `` <enter> `` | Enter | Enter submodule |
| `` d `` | Remove | Remove the selected submodule and its corresponding directory. |
| `` d `` | Verwijderen | Remove the selected submodule and its corresponding directory. |
| `` u `` | Update | Update selected submodule. |
| `` n `` | Voeg nieuwe submodule toe | |
| `` e `` | Update submodule URL | |
@@ -394,15 +395,15 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <ctrl+o> `` | Copy tag to clipboard | |
| `` <space> `` | Uitchecken | Checkout the selected tag as a detached HEAD. |
| `` <space> `` | Uitchecken | Geselecteerde tag uitchecken als detached HEAD. |
| `` n `` | Creëer tag | Create new tag from current commit. You'll be prompted to enter a tag name and optional description. |
| `` d `` | Delete | View delete options for local/remote tag. |
| `` w `` | New worktree | |
| `` d `` | Verwijderen | View delete options for local/remote tag. |
| `` P `` | Push tag | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` g `` | Resetten | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open externe diff applicatie (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Bekijk commits | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Worktrees
@@ -411,6 +412,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
|-----|--------|-------------|
| `` n `` | New worktree | |
| `` <space> `` | Switch | Switch to the selected worktree. |
| `` o `` | Open in editor | |
| `` d `` | Remove | Remove the selected worktree. This will both delete the worktree's directory, as well as metadata about the worktree in the .git directory. |
| `` o `` | Openen in editor | |
| `` d `` | Verwijderen | Remove the selected worktree. This will both delete the worktree's directory, as well as metadata about the worktree in the .git directory. |
| `` / `` | Filter the current view by text | |
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | Odśwież | Odśwież stan git (tj. uruchom `git status`, `git branch`, itp. w tle, aby zaktualizować zawartość paneli). To nie uruchamia `git fetch`. |
| `` + `` | Następny tryb ekranu (normalny/półpełny/pełnoekranowy) | |
| `` _ `` | Poprzedni tryb ekranu | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | Anuluj | |
| `` ? `` | Otwórz menu przypisań klawiszy | |
| `` <ctrl+s> `` | Pokaż opcje filtrowania | Pokaż opcje filtrowania dziennika commitów, tak aby pokazywane były tylko commity pasujące do filtra. |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | Wyjdź | |
| `` <ctrl+z> `` | Suspend the application | |
| `` <ctrl+w> `` | Przełącz białe znaki | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | Edytuj plik konfiguracyjny | Otwórz plik w zewnętrznym edytorze. |
| `` z `` | Cofnij | Dziennik reflog zostanie użyty do określenia, jakie polecenie git należy uruchomić, aby cofnąć ostatnie polecenie git. Nie obejmuje to zmian w drzewie roboczym; brane są pod uwagę tylko commity. |
| `` Z `` | Ponów | Dziennik reflog zostanie użyty do określenia, jakie polecenie git należy uruchomić, aby ponowić ostatnie polecenie git. Nie obejmuje to zmian w drzewie roboczym; brane są pod uwagę tylko commity. |
@@ -83,13 +85,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Otwórz commit w przeglądarce | |
| `` n `` | Utwórz nową gałąź z commita | |
| `` N `` | Przenieś commity do nowej gałęzi | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nowe drzewo pracy | |
| `` g `` | Reset | Wyświetl opcje resetu (miękki/mieszany/twardy) do wybranego elementu. |
| `` C `` | Kopiuj (cherry-pick) | Oznacz commit jako skopiowany. Następnie, w widoku lokalnych commitów, możesz nacisnąć `V`, aby wkleić (cherry-pick) skopiowane commity do sprawdzonej gałęzi. W dowolnym momencie możesz nacisnąć `<esc>`, aby anulować zaznaczenie. |
| `` <ctrl+t> `` | Otwórz zewnętrzne narzędzie różnic (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Wyświetl pliki | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Szukaj w bieżącym widoku po tekście | |
## Dodatkowy
@@ -120,6 +122,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Otwórz commit w przeglądarce | |
| `` n `` | Utwórz nową gałąź z commita | |
| `` N `` | Przenieś commity do nowej gałęzi | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nowe drzewo pracy | |
| `` g `` | Reset | Wyświetl opcje resetu (miękki/mieszany/twardy) do wybranego elementu. |
| `` C `` | Kopiuj (cherry-pick) | Oznacz commit jako skopiowany. Następnie, w widoku lokalnych commitów, możesz nacisnąć `V`, aby wkleić (cherry-pick) skopiowane commity do sprawdzonej gałęzi. W dowolnym momencie możesz nacisnąć `<esc>`, aby anulować zaznaczenie. |
| `` <ctrl+r> `` | Resetuj wybrane (cherry-picked) commity | |
@@ -127,7 +130,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Pokaż commity | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Filtruj bieżący widok po tekście | |
## Główny panel (budowanie łatki)
@@ -162,6 +164,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | Przełącz | Przełącz wybrany element. |
| `` n `` | Nowa gałąź | |
| `` N `` | Przenieś commity do nowej gałęzi | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nowe drzewo pracy | |
| `` o `` | Utwórz żądanie ściągnięcia | |
| `` O `` | Zobacz opcje tworzenia pull requesta | |
| `` G `` | Otwórz żądanie ściągnięcia w przeglądarce | |
@@ -181,7 +184,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Otwórz zewnętrzne narzędzie różnic (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Pokaż commity | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Filtruj bieżący widok po tekście | |
## Menu
@@ -207,7 +209,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | Wybierz fragment | |
| `` b `` | Wybierz wszystkie fragmenty | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | Poprzedni fragment | |
| `` <down>, j `` | Następny fragment | |
| `` <left>, h `` | Poprzedni konflikt | |
@@ -316,17 +318,16 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Wyciągnij | Zastosuj wpis schowka do katalogu roboczego i usuń wpis schowka. |
| `` d `` | Usuń | Usuń wpis schowka z listy schowka. |
| `` n `` | Nowa gałąź | Utwórz nową gałąź z wybranego wpisu schowka. Działa poprzez przełączenie git na commit, na którym wpis schowka został utworzony, tworzenie nowej gałęzi z tego commita, a następnie zastosowanie wpisu schowka do nowej gałęzi jako dodatkowego commita. |
| `` w `` | Nowe drzewo pracy | |
| `` r `` | Zmień nazwę schowka | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Wyświetl pliki | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Filtruj bieżący widok po tekście | |
## Status
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | Otwórz plik konfiguracyjny | Otwórz plik w domyślnej aplikacji. |
| `` e `` | Edytuj plik konfiguracyjny | Otwórz plik w zewnętrznym edytorze. |
| `` u `` | Sprawdź aktualizacje | |
| `` <enter> `` | Przełącz na ostatnie repozytorium | |
@@ -344,6 +345,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Otwórz commit w przeglądarce | |
| `` n `` | Utwórz nową gałąź z commita | |
| `` N `` | Przenieś commity do nowej gałęzi | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nowe drzewo pracy | |
| `` g `` | Reset | Wyświetl opcje resetu (miękki/mieszany/twardy) do wybranego elementu. |
| `` C `` | Kopiuj (cherry-pick) | Oznacz commit jako skopiowany. Następnie, w widoku lokalnych commitów, możesz nacisnąć `V`, aby wkleić (cherry-pick) skopiowane commity do sprawdzonej gałęzi. W dowolnym momencie możesz nacisnąć `<esc>`, aby anulować zaznaczenie. |
| `` <ctrl+r> `` | Resetuj wybrane (cherry-picked) commity | |
@@ -351,7 +353,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Wyświetl pliki | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Szukaj w bieżącym widoku po tekście | |
## Submoduły
@@ -375,13 +376,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Skopiuj tag do schowka | |
| `` <space> `` | Przełącz | Przełącz wybrany tag jako odłączoną głowę (detached HEAD). |
| `` n `` | Nowy tag | Utwórz nowy tag z bieżącego commita. Zostaniesz poproszony o wprowadzenie nazwy tagu i opcjonalnego opisu. |
| `` w `` | Nowe drzewo pracy | |
| `` d `` | Usuń | Wyświetl opcje usuwania lokalnego/odległego tagu. |
| `` P `` | Wyślij tag | Wyślij wybrany tag do zdalnego. Zostaniesz poproszony o wybranie zdalnego. |
| `` g `` | Reset | Wyświetl opcje resetu (miękki/mieszany/twardy) do wybranego elementu. |
| `` <ctrl+t> `` | Otwórz zewnętrzne narzędzie różnic (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Pokaż commity | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Filtruj bieżący widok po tekście | |
## Zdalne
@@ -403,6 +404,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Kopiuj nazwę gałęzi do schowka | |
| `` <space> `` | Przełącz | Przełącz na nową lokalną gałąź na podstawie wybranej gałęzi zdalnej. Nowa gałąź będzie śledzić gałąź zdalną. |
| `` n `` | Nowa gałąź | |
| `` w `` | Nowe drzewo pracy | |
| `` M `` | Scal | Scal wybraną gałąź z aktualnie sprawdzoną gałęzią. |
| `` r `` | Przebazuj | Przebazuj przełączoną gałąź na wybraną gałąź. |
| `` d `` | Usuń | Usuń gałąź zdalną ze zdalnego. |
@@ -412,5 +414,4 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Otwórz zewnętrzne narzędzie różnic (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Pokaż commity | |
| `` w `` | Zobacz opcje drzewa pracy | |
| `` / `` | Filtruj bieżący widok po tekście | |
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | Atualizar | Atualize o estado do git (ou seja, execute `git status`, `git branch`, etc em segundo plano para atualizar o conteúdo de painéis). Isso não executa `git fetch`. |
| `` + `` | Modo de tela seguinte (normal/metade/tela cheia) | |
| `` _ `` | Modo de tela anterior | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | Cancelar | |
| `` ? `` | Abrir o menu de atalhos do teclado | |
| `` <ctrl+s> `` | Ver opções de filtro | View options for filtering the commit log, so that only commits matching the filter are shown. |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | Sair | |
| `` <ctrl+z> `` | Suspender a aplicação | |
| `` <ctrl+w> `` | Toggle whitespace | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | Editar arquivo de configuração | Abrir arquivo no editor externo. |
| `` z `` | Desfazer | O reflog será usado para determinar qual comando git para executar para desfazer o último comando git. Isto não inclui mudanças na árvore de trabalho; apenas compromissos são tidos em consideração. |
| `` Z `` | Refazer | O reflog será usado para determinar qual comando git para executar para refazer o último comando git. Isto não inclui mudanças na árvore de trabalho; apenas compromissos são tidos em consideração. |
@@ -92,6 +94,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | Verificar | Checar item selecionado |
| `` n `` | Nova branch | |
| `` N `` | Mover commits para uma nova branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nova árvore de trabalho | |
| `` o `` | Criar solicitação de pull | |
| `` O `` | View create pull request options | |
| `` G `` | Open pull request in browser | |
@@ -111,7 +114,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Abrir ferramenta de diff externa (git difftool) | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver commits | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Filtrar a visualização atual por texto | |
## Branches remotos
@@ -121,6 +123,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copiar nome da branch para área de transferência | |
| `` <space> `` | Verificar | Checar a nova branch baseada na brach remota selecionada, ou a branch remota como HEAD, desanexado |
| `` n `` | Nova branch | |
| `` w `` | Nova árvore de trabalho | |
| `` M `` | Mesclar | Ver opções para mesclar o item selecionado no branch atual (mesclar regularmente, mesclar squash) |
| `` r `` | Refazer | Refazer a branch checada na branch selecionada |
| `` d `` | Apagar | Excluir o branch remoto do controle remoto. |
@@ -130,7 +133,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Abrir ferramenta de diff externa (git difftool) | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver commits | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Filtrar a visualização atual por texto | |
## Commit arquivos
@@ -186,13 +188,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Abrir commit no navegador | |
| `` n `` | Create new branch off of commit | |
| `` N `` | Mover commits para uma nova branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nova árvore de trabalho | |
| `` g `` | Restaurar | Ver opções de redefinição (soft/mixed/hard) para redefinir para o item selecionado. |
| `` C `` | Copiar (cherry-pick) | Marcar commit como copiado. Então, dentro da visualização local de commits, você pode pressionar `V` para colar (cherry-pick) o(s) commit(s) copiado(s) em seu branch de check-out. A qualquer momento você pode pressionar `<esc>` para cancelar a seleção. |
| `` <ctrl+t> `` | Abrir ferramenta de diff externa (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver arquivos | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Pesquisar na visualização atual por texto | |
## Etiquetas
@@ -202,13 +204,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copiar etiqueta para área de transferência | |
| `` <space> `` | Verificar | Checar a tag selecionada como um HEAD, desanexado |
| `` n `` | Nova etiqueta | Crie uma nova etiqueta a partir do commit atual. Você será solicitado a digitar um nome e uma descrição opcional. |
| `` w `` | Nova árvore de trabalho | |
| `` d `` | Apagar | Ver opções de exclusão para tag local/remoto. |
| `` P `` | Empurrar etiqueta | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | Restaurar | Ver opções de redefinição (soft/mixed/hard) para redefinir para o item selecionado. |
| `` <ctrl+t> `` | Abrir ferramenta de diff externa (git difftool) | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver commits | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Filtrar a visualização atual por texto | |
## Input prompt
@@ -271,7 +273,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | Escolha o local | |
| `` b `` | Pegar todos os pedaços | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | Trecho anterior | |
| `` <down>, j `` | Próximo trecho | |
| `` <left>, h `` | Conflito anterior | |
@@ -308,6 +310,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Abrir commit no navegador | |
| `` n `` | Create new branch off of commit | |
| `` N `` | Mover commits para uma nova branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nova árvore de trabalho | |
| `` g `` | Restaurar | Ver opções de redefinição (soft/mixed/hard) para redefinir para o item selecionado. |
| `` C `` | Copiar (cherry-pick) | Marcar commit como copiado. Então, dentro da visualização local de commits, você pode pressionar `V` para colar (cherry-pick) o(s) commit(s) copiado(s) em seu branch de check-out. A qualquer momento você pode pressionar `<esc>` para cancelar a seleção. |
| `` <ctrl+r> `` | Reset copied (cherry-picked) commits selection | |
@@ -315,7 +318,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver commits | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Filtrar a visualização atual por texto | |
## Remotes
@@ -346,17 +348,16 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Pop | Aplique a entrada de stash no seu diretório de trabalho e remova a entrada de stash. |
| `` d `` | Descartar | Remova a entrada do stash da lista de armazenamento. |
| `` n `` | Nova branch | Criar um novo ramo a partir da entrada de lixo selecionada. Isso funciona verificando o commit do qual a entrada de lixo foi criada, criar um novo branch a partir desse commit e, em seguida, aplicar a entrada de lixo ao novo branch como um commit adicional. |
| `` w `` | Nova árvore de trabalho | |
| `` r `` | Renomear o stash | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver arquivos | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Filtrar a visualização atual por texto | |
## Status
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | Abrir o ficheiro de config | Abrir arquivo no aplicativo padrão. |
| `` e `` | Editar arquivo de configuração | Abrir arquivo no editor externo. |
| `` u `` | Verificar atualização | |
| `` <enter> `` | Mudar para um repositório recente | |
@@ -374,6 +375,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Abrir commit no navegador | |
| `` n `` | Create new branch off of commit | |
| `` N `` | Mover commits para uma nova branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | Nova árvore de trabalho | |
| `` g `` | Restaurar | Ver opções de redefinição (soft/mixed/hard) para redefinir para o item selecionado. |
| `` C `` | Copiar (cherry-pick) | Marcar commit como copiado. Então, dentro da visualização local de commits, você pode pressionar `V` para colar (cherry-pick) o(s) commit(s) copiado(s) em seu branch de check-out. A qualquer momento você pode pressionar `<esc>` para cancelar a seleção. |
| `` <ctrl+r> `` | Reset copied (cherry-picked) commits selection | |
@@ -381,7 +383,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focar visualização principal | |
| `` <enter> `` | Ver arquivos | |
| `` w `` | Ver opções da árvore de trabalho | |
| `` / `` | Pesquisar na visualização atual por texto | |
## Submódulos
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | Обновить | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. |
| `` + `` | Следующий режим экрана (нормальный/полуэкранный/полноэкранный) | |
| `` _ `` | Предыдущий режим экрана | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | Отменить | |
| `` ? `` | Открыть меню | |
| `` <ctrl+s> `` | Просмотреть параметры фильтрации по пути | View options for filtering the commit log, so that only commits matching the filter are shown. |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | Выйти | |
| `` <ctrl+z> `` | Suspend the application | |
| `` <ctrl+w> `` | Переключить отображение изменении пробелов в просмотрщике сравнении | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | Редактировать файл конфигурации | Open file in external editor. |
| `` z `` | Отменить (через reflog) (экспериментальный) | Журнал ссылок (reflog) будет использоваться для определения того, какую команду git запустить, чтобы отменить последнюю команду git. Сюда не входят изменения в рабочем дереве; учитываются только коммиты. |
| `` Z `` | Повторить (через reflog) (экспериментальный) | Журнал ссылок (reflog) будет использоваться для определения того, какую команду git нужно запустить, чтобы повторить последнюю команду git. Сюда не входят изменения в рабочем дереве; учитываются только коммиты. |
@@ -112,7 +114,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | Выбрать эту часть | |
| `` b `` | Выбрать все части | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | Выбрать предыдущую часть | |
| `` <down>, j `` | Выбрать следующую часть | |
| `` <left>, h `` | Выбрать предыдущий конфликт | |
@@ -149,6 +151,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Открыть коммит в браузере | |
| `` n `` | Создать новую ветку с этого коммита | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | Просмотреть параметры сброса | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Скопировать отобранные коммит (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Сбросить отобранную (скопированную \| cherry-picked) выборку коммитов | |
@@ -156,7 +159,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть коммиты | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Коммиты
@@ -192,13 +194,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Открыть коммит в браузере | |
| `` n `` | Создать новую ветку с этого коммита | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | Просмотреть параметры сброса | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Скопировать отобранные коммит (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть файлы выбранного элемента | |
| `` w `` | View worktree options | |
| `` / `` | Найти | |
## Локальные Ветки
@@ -210,6 +212,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | Переключить | Checkout selected item. |
| `` n `` | Новая ветка | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` o `` | Создать запрос на принятие изменений | |
| `` O `` | Создать параметры запроса принятие изменений | |
| `` G `` | Open pull request in browser | |
@@ -229,7 +232,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть коммиты | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Меню
@@ -258,6 +260,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | Открыть коммит в браузере | |
| `` n `` | Создать новую ветку с этого коммита | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | Просмотреть параметры сброса | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | Скопировать отобранные коммит (cherry-pick) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | Сбросить отобранную (скопированную \| cherry-picked) выборку коммитов | |
@@ -265,7 +268,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть файлы выбранного элемента | |
| `` w `` | View worktree options | |
| `` / `` | Найти | |
## Подмодули
@@ -313,7 +315,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | Открыть файл конфигурации | Open file in default application. |
| `` e `` | Редактировать файл конфигурации | Open file in external editor. |
| `` u `` | Проверить обновления | |
| `` <enter> `` | Переключиться на последний репозиторий | |
@@ -328,13 +329,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy tag to clipboard | |
| `` <space> `` | Переключить | Checkout the selected tag as a detached HEAD. |
| `` n `` | Создать тег | Create new tag from current commit. You'll be prompted to enter a tag name and optional description. |
| `` w `` | New worktree | |
| `` d `` | Delete | View delete options for local/remote tag. |
| `` P `` | Отправить тег | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | Reset | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть коммиты | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Удалённые ветки
@@ -344,6 +345,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Скопировать название ветки в буфер обмена | |
| `` <space> `` | Переключить | Checkout a new local branch based on the selected remote branch, or the remote branch as a detached head. |
| `` n `` | Новая ветка | |
| `` w `` | New worktree | |
| `` M `` | Слияние с текущей переключённой веткой | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` r `` | Перебазировать переключённую ветку на эту ветку | Rebase the checked-out branch onto the selected branch. |
| `` d `` | Delete | Delete the remote branch from the remote. |
@@ -353,7 +355,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | Open external diff tool (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть коммиты | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
## Удалённые репозитории
@@ -409,8 +410,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | Применить припрятанные изменения и тут же удалить их из хранилища | Apply the stash entry to your working directory and remove the stash entry. |
| `` d `` | Удалить припрятанные изменения из хранилища | Remove the stash entry from the stash list. |
| `` n `` | Новая ветка | Create a new branch from the selected stash entry. This works by git checking out the commit that the stash entry was created from, creating a new branch from that commit, then applying the stash entry to the new branch as an additional commit. |
| `` w `` | New worktree | |
| `` r `` | Переименовать хранилище | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | Просмотреть файлы выбранного элемента | |
| `` w `` | View worktree options | |
| `` / `` | Filter the current view by text | |
+10 -9
View File
@@ -23,6 +23,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` + `` | 下一屏模式(正常/半屏/全屏) | |
| `` _ `` | 上一屏模式 | |
| `` \| `` | 切换分页器 | 从已配置的分页器列表中选择下一个分页器 |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | 取消 | |
| `` ? `` | 打开菜单 | |
| `` <ctrl+s> `` | 查看按路径过滤选项 | 查看用于过滤提交日志的选项,以便仅显示与过滤器匹配的提交。 |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | 退出 | |
| `` <ctrl+z> `` | 挂起应用程序 | |
| `` <ctrl+w> `` | 切换是否在差异视图中显示空白字符差异 | 切换是否在差异视图中显示空白字符更改。<br><br>默认值可在配置文件中通过键 'git.ignoreWhitespaceInDiffView' 更改。 |
| `` <alt+shift+c> `` | 编辑配置文件 | 使用外部编辑器打开文件 |
| `` z `` | 撤销 | Reflog将用于确定运行哪个git命令来撤消最后一个git命令。这并不包括对工作树的更改,只考虑提交。 |
| `` Z `` | 重做 | Reflog将用于确定运行哪个git命令来重做上一个git命令。这并不包括对工作树的更改,只考虑提交。 |
@@ -60,6 +62,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 在浏览器中打开提交 | |
| `` n `` | 从提交创建新分支 | |
| `` N `` | 移动提交至新分支 | 创建一个新分支,并将当前分支未推送的提交移动到该分支。如果您打算开始新工作但忘记先创建新分支,这会很有用。<br><br>请注意,此操作忽略选择,新分支总是从主分支创建或堆叠在当前分支之上(您可以选择哪种方式)。 |
| `` w `` | 新建工作树 | |
| `` g `` | 查看重置选项 | 查看重置选项 (soft/mixed/hard) 用于重置到选择项 |
| `` C `` | 复制提交(拣选) | 标记提交为已复制。然后,在本地提交视图中,您可以按 `V` (Cherry-Pick) 将已复制的提交粘贴到已检出的分支中。任何时候都可以按 `<esc>` 来取消选择。 |
| `` <ctrl+r> `` | 重置已拣选(复制)的提交 | |
@@ -67,7 +70,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | 选择当前分支的提交 | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交的文件 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 开始搜索 | |
## 子模块
@@ -104,6 +106,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 在浏览器中打开提交 | |
| `` n `` | 从提交创建新分支 | |
| `` N `` | 移动提交至新分支 | 创建一个新分支,并将当前分支未推送的提交移动到该分支。如果您打算开始新工作但忘记先创建新分支,这会很有用。<br><br>请注意,此操作忽略选择,新分支总是从主分支创建或堆叠在当前分支之上(您可以选择哪种方式)。 |
| `` w `` | 新建工作树 | |
| `` g `` | 查看重置选项 | 查看重置选项 (soft/mixed/hard) 用于重置到选择项 |
| `` C `` | 复制提交(拣选) | 标记提交为已复制。然后,在本地提交视图中,您可以按 `V` (Cherry-Pick) 将已复制的提交粘贴到已检出的分支中。任何时候都可以按 `<esc>` 来取消选择。 |
| `` <ctrl+r> `` | 重置已拣选(复制)的提交 | |
@@ -111,7 +114,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | 选择当前分支的提交 | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 通过文本过滤当前视图 | |
## 提交
@@ -147,13 +149,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 在浏览器中打开提交 | |
| `` n `` | 从提交创建新分支 | |
| `` N `` | 移动提交至新分支 | 创建一个新分支,并将当前分支未推送的提交移动到该分支。如果您打算开始新工作但忘记先创建新分支,这会很有用。<br><br>请注意,此操作忽略选择,新分支总是从主分支创建或堆叠在当前分支之上(您可以选择哪种方式)。 |
| `` w `` | 新建工作树 | |
| `` g `` | 查看重置选项 | 查看重置选项 (soft/mixed/hard) 用于重置到选择项 |
| `` C `` | 复制提交(拣选) | 标记提交为已复制。然后,在本地提交视图中,您可以按 `V` (Cherry-Pick) 将已复制的提交粘贴到已检出的分支中。任何时候都可以按 `<esc>` 来取消选择。 |
| `` <ctrl+t> `` | 使用外部差异比较工具(git difftool) | |
| `` * `` | 选择当前分支的提交 | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交的文件 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 开始搜索 | |
## 提交信息
@@ -225,6 +227,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | 检出 | 检出选中的项目 |
| `` n `` | 新分支 | |
| `` N `` | 移动提交至新分支 | 创建一个新分支,并将当前分支未推送的提交移动到该分支。如果您打算开始新工作但忘记先创建新分支,这会很有用。<br><br>请注意,此操作忽略选择,新分支总是从主分支创建或堆叠在当前分支之上(您可以选择哪种方式)。 |
| `` w `` | 新建工作树 | |
| `` o `` | 创建拉取请求 | |
| `` O `` | 创建拉取请求选项 | |
| `` G `` | 在浏览器中打开拉取请求 | |
@@ -244,7 +247,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | 使用外部差异比较工具(git difftool) | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 通过文本过滤当前视图 | |
## 构建补丁中
@@ -270,13 +272,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | 复制标签到剪贴板 | |
| `` <space> `` | 检出 | 检出选择的标签作为分离的HEAD |
| `` n `` | 创建标签 | 基于当前提交创建一个新标签。您将在弹窗中输入标签名称和描述(可选)。 |
| `` w `` | 新建工作树 | |
| `` d `` | 删除 | 查看本地/远程标签的删除选项 |
| `` P `` | 推送标签 | 推送选择的标签到远端。您将在弹窗中选择一个远端。 |
| `` g `` | 重置 | 查看重置选项 (soft/mixed/hard) 用于重置到选择项 |
| `` <ctrl+t> `` | 使用外部差异比较工具(git difftool) | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 通过文本过滤当前视图 | |
## 次要
@@ -292,7 +294,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | 选中区块 | |
| `` b `` | 选中所有区块 | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | 选择顶部块 | |
| `` <down>, j `` | 选择底部块 | |
| `` <left>, h `` | 选择上一个冲突 | |
@@ -339,7 +341,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | 打开配置文件 | 使用默认程序打开该文件 |
| `` e `` | 编辑配置文件 | 使用外部编辑器打开文件 |
| `` u `` | 检查更新 | |
| `` <enter> `` | 切换到最近的仓库 | |
@@ -371,10 +372,10 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | 应用并删除 | 将存储项应用到工作目录并删除存储项。 |
| `` d `` | 删除 | 从贮藏列表中删除该贮藏项 |
| `` n `` | 新分支 | 从选定的贮藏项创建一个新分支。这是通过 git 检查创建贮藏项的提交,从该提交创建一个新分支,然后将贮藏项作为附加提交应用到新分支来实现的。 |
| `` w `` | 新建工作树 | |
| `` r `` | 重命名贮藏 | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交的文件 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 通过文本过滤当前视图 | |
## 输入提示
@@ -403,6 +404,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | 复制分支名称到剪贴板 | |
| `` <space> `` | 检出 | 基于当前选中的远程分支检出一个新的本地分支,或者将远程分支作分离的HEAD。 |
| `` n `` | 新分支 | |
| `` w `` | 新建工作树 | |
| `` M `` | 合并到当前检出的分支 | 查看将选中项合并到当前分支的选项(正常合并,压缩合并) |
| `` r `` | 变基 | 将检出的分支变基到所选的分支上。 |
| `` d `` | 删除 | 从远程删除远程分支。 |
@@ -412,5 +414,4 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | 使用外部差异比较工具(git difftool) | |
| `` 0 `` | 聚焦主视图 | |
| `` <enter> `` | 查看提交 | |
| `` w `` | 查看工作区选项 | |
| `` / `` | 通过文本过滤当前视图 | |
+11 -10
View File
@@ -22,7 +22,8 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` R `` | 重新整理 | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. |
| `` + `` | 下一個螢幕模式(常規/半螢幕/全螢幕) | |
| `` _ `` | 上一個螢幕模式 | |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers |
| `` \| `` | Cycle pagers | Choose the next pager in the list of configured pagers. |
| `` \ `` | Cycle pagers (reverse) | Choose the previous pager in the list of configured pagers. |
| `` <esc> `` | 取消 | |
| `` ? `` | 開啟選單 | |
| `` <ctrl+s> `` | 檢視篩選路徑選項 | View options for filtering the commit log, so that only commits matching the filter are shown. |
@@ -30,6 +31,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` q, <ctrl+c> `` | 結束 | |
| `` <ctrl+z> `` | Suspend the application | |
| `` <ctrl+w> `` | 切換是否在差異檢視中顯示空格變更 | Toggle whether or not whitespace changes are shown in the diff view.<br><br>The default can be changed in the config file with the key 'git.ignoreWhitespaceInDiffView'. |
| `` <alt+shift+c> `` | 編輯設定檔案 | 使用外部編輯器開啟 |
| `` z `` | 復原 | 將使用 reflog 確任 git 指令以復原。這不包括工作區更改;只考慮提交。 |
| `` Z `` | 取消復原 | 將使用 reflog 確任 git 指令以重作。這不包括工作區更改;只考慮提交。 |
@@ -88,7 +90,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` <space> `` | 挑選程式碼片段 | |
| `` b `` | 挑選所有程式碼片段 | |
| `` b `` | Pick both hunks | |
| `` <up>, k `` | 選擇上一段 | |
| `` <down>, j `` | 選擇下一段 | |
| `` <left>, h `` | 選擇上一個衝突 | |
@@ -139,6 +141,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 在瀏覽器中開啟提交 | |
| `` n `` | 從提交建立新分支 | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | 檢視重設選項 | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | 複製提交 (揀選) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | 重設選定的揀選 (複製) 提交 | |
@@ -146,7 +149,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視所選項目的檔案 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
## 子模組
@@ -206,13 +208,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 在瀏覽器中開啟提交 | |
| `` n `` | 從提交建立新分支 | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | 檢視重設選項 | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | 複製提交 (揀選) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+t> `` | 開啟外部差異工具 (git difftool) | |
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視所選項目的檔案 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
## 提交摘要
@@ -250,10 +252,10 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` g `` | 還原 | Apply the stash entry to your working directory and remove the stash entry. |
| `` d `` | 捨棄 | Remove the stash entry from the stash list. |
| `` n `` | 新分支 | Create a new branch from the selected stash entry. This works by git checking out the commit that the stash entry was created from, creating a new branch from that commit, then applying the stash entry to the new branch as an additional commit. |
| `` w `` | New worktree | |
| `` r `` | 重新命名收藏 | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視所選項目的檔案 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
## 日誌
@@ -266,6 +268,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` o `` | 在瀏覽器中開啟提交 | |
| `` n `` | 從提交建立新分支 | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` g `` | 檢視重設選項 | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` C `` | 複製提交 (揀選) | Mark commit as copied. Then, within the local commits view, you can press `V` to paste (cherry-pick) the copied commit(s) into your checked out branch. At any time you can press `<esc>` to cancel the selection. |
| `` <ctrl+r> `` | 重設選定的揀選 (複製) 提交 | |
@@ -273,7 +276,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` * `` | Select commits of current branch | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視提交 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
## 本地分支
@@ -285,6 +287,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <space> `` | 檢出 | 檢出選定的項目。 |
| `` n `` | 新分支 | |
| `` N `` | Move commits to new branch | Create a new branch and move the unpushed commits of the current branch to it. Useful if you meant to start new work and forgot to create a new branch first.<br><br>Note that this disregards the selection, the new branch is always created either from the main branch or stacked on top of the current branch (you get to choose which). |
| `` w `` | New worktree | |
| `` o `` | 建立拉取請求 | |
| `` O `` | 建立拉取請求選項 | |
| `` G `` | Open pull request in browser | |
@@ -304,7 +307,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | 開啟外部差異工具 (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視提交 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
## 標籤
@@ -314,13 +316,13 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | Copy tag to clipboard | |
| `` <space> `` | 檢出 | Checkout the selected tag as a detached HEAD. |
| `` n `` | 建立標籤 | Create new tag from current commit. You'll be prompted to enter a tag name and optional description. |
| `` w `` | New worktree | |
| `` d `` | 刪除 | View delete options for local/remote tag. |
| `` P `` | 推送標籤 | Push the selected tag to a remote. You'll be prompted to select a remote. |
| `` g `` | 重設 | View reset options (soft/mixed/hard) for resetting onto selected item. |
| `` <ctrl+t> `` | 開啟外部差異工具 (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視提交 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
## 檔案
@@ -368,7 +370,6 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| Key | Action | Info |
|-----|--------|-------------|
| `` o `` | 開啟設定檔案 | 使用預設軟體開啟 |
| `` e `` | 編輯設定檔案 | 使用外部編輯器開啟 |
| `` u `` | 檢查更新 | |
| `` <enter> `` | 切換到最近使用的版本庫 | |
@@ -403,6 +404,7 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+o> `` | 複製分支名稱到剪貼簿 | |
| `` <space> `` | 檢出 | Checkout a new local branch based on the selected remote branch, or the remote branch as a detached head. |
| `` n `` | 新分支 | |
| `` w `` | New worktree | |
| `` M `` | 合併到當前檢出的分支 | View options for merging the selected item into the current branch (regular merge, squash merge) |
| `` r `` | 將已檢出的分支變基至此分支 | Rebase the checked-out branch onto the selected branch. |
| `` d `` | 刪除 | Delete the remote branch from the remote. |
@@ -412,5 +414,4 @@ _This file is auto-generated. To update, make the changes in the pkg/i18n direct
| `` <ctrl+t> `` | 開啟外部差異工具 (git difftool) | |
| `` 0 `` | Focus main view | |
| `` <enter> `` | 檢視提交 | |
| `` w `` | 檢視工作目錄選項 | |
| `` / `` | 搜尋 | |
+2 -2
View File
@@ -117,8 +117,8 @@ func NewGitCommandAux(
rebaseCommands := git_commands.NewRebaseCommands(gitCommon, commitCommands, workingTreeCommands)
stashCommands := git_commands.NewStashCommands(gitCommon, fileLoader, workingTreeCommands)
patchBuilder := patch.NewPatchBuilder(cmn.Log,
func(from string, to string, reverse bool, filename string, plain bool) (string, error) {
return workingTreeCommands.ShowFileDiff(from, to, reverse, filename, plain)
func(from string, to string, reverse bool, filename string, previousPath string, plain bool) (string, error) {
return workingTreeCommands.ShowFileDiff(from, to, reverse, filename, previousPath, plain)
})
patchCommands := git_commands.NewPatchCommands(gitCommon, rebaseCommands, commitCommands, statusCommands, stashCommands, patchBuilder)
bisectCommands := git_commands.NewBisectCommands(gitCommon)
+3 -2
View File
@@ -25,8 +25,9 @@ func NewGitCmdObjBuilder(log *logrus.Entry, innerBuilder *oscommands.CmdObjBuild
// the price of having a convenient interface where we can say .New(...).Run() is that our builder now depends on our runner, so when we want to wrap the default builder/runner in new functionality we need to jump through some hoops. We could avoid the use of a decorator function here by just exporting the runner field on the default builder but that would be misleading because we don't want anybody using that to run commands (i.e. we want there to be a single API used across the codebase)
updatedBuilder := innerBuilder.CloneWithNewRunner(func(runner oscommands.ICmdObjRunner) oscommands.ICmdObjRunner {
return &gitCmdObjRunner{
log: log,
innerRunner: runner,
log: log,
innerRunner: runner,
initialRetryDelay: defaultInitialRetryDelay,
}
})
+58 -33
View File
@@ -11,20 +11,42 @@ import (
// here we're wrapping the default command runner in some git-specific stuff e.g. retry logic if we get an error due to the presence of .git/index.lock
const (
WaitTime = 50 * time.Millisecond
RetryCount = 5
// defaultInitialRetryDelay is how long we wait before the first retry of a
// command that failed with a transient lock error. We double it before each
// subsequent retry (see retryOnLockError), so across maxRetries attempts we
// wait for a bit over a second in total. That's long enough to outlast the
// brief window during which another git process holds a lock we need —
// typically our own foreground `git status` refresh, which takes index.lock
// to persist its refreshed stat-cache.
defaultInitialRetryDelay = 20 * time.Millisecond
maxRetries = 7
)
type gitCmdObjRunner struct {
log *logrus.Entry
innerRunner oscommands.ICmdObjRunner
// initialRetryDelay is the wait before the first lock-error retry. It's a
// field rather than the constant directly so tests can set it to zero and
// not actually sleep.
initialRetryDelay time.Duration
}
// isRetryableError returns true if the error output indicates a transient
// lock-related error that may succeed on retry
func isRetryableError(output string) bool {
return strings.Contains(output, ".git/index.lock") ||
strings.Contains(output, "cannot lock ref")
// isRetryableError returns true if a failed command hit a transient
// lock-related condition that may succeed on retry. The lock message can reach
// us either in the command's captured output or, for streamed commands whose
// output we don't capture, only in the returned error, so we check both.
//
// We match the bare "index.lock" fragment rather than a fuller path or message
// so we catch the lock wherever git puts it: the main .git dir, a linked
// worktree's git dir (.git/worktrees/<name>/index.lock), or a submodule's git
// dir.
func isRetryableError(output string, err error) bool {
text := output
if err != nil {
text += "\n" + err.Error()
}
return strings.Contains(text, "index.lock") ||
strings.Contains(text, "cannot lock ref")
}
func (self *gitCmdObjRunner) Run(cmdObj *oscommands.CmdObj) error {
@@ -33,41 +55,44 @@ func (self *gitCmdObjRunner) Run(cmdObj *oscommands.CmdObj) error {
}
func (self *gitCmdObjRunner) RunWithOutput(cmdObj *oscommands.CmdObj) (string, error) {
var output string
var err error
for range RetryCount {
newCmdObj := cmdObj.Clone()
output, err = self.innerRunner.RunWithOutput(newCmdObj)
if err == nil || !isRetryableError(output) {
return output, err
}
// if we have an error based on a lock, we should wait a bit and then retry
self.log.Warn("lock error prevented command from running. Retrying command after a small wait")
time.Sleep(WaitTime)
}
return output, err
return self.retryOnLockError(func() (string, error) {
return self.innerRunner.RunWithOutput(cmdObj.Clone())
})
}
func (self *gitCmdObjRunner) RunWithOutputs(cmdObj *oscommands.CmdObj) (string, string, error) {
var stdout, stderr string
var err error
for range RetryCount {
newCmdObj := cmdObj.Clone()
stdout, stderr, err = self.innerRunner.RunWithOutputs(newCmdObj)
_, err := self.retryOnLockError(func() (string, error) {
var runErr error
stdout, stderr, runErr = self.innerRunner.RunWithOutputs(cmdObj.Clone())
return stdout + stderr, runErr
})
return stdout, stderr, err
}
if err == nil || !isRetryableError(stdout+stderr) {
return stdout, stderr, err
// retryOnLockError runs the given function, retrying if it fails with a
// transient lock error (see isRetryableError). The string returned by run is
// the command output we inspect to classify the failure. We clone the command
// for each attempt (inside run) because an *exec.Cmd can only be run once.
func (self *gitCmdObjRunner) retryOnLockError(run func() (string, error)) (string, error) {
delay := self.initialRetryDelay
var output string
var err error
for attempt := range maxRetries {
output, err = run()
if err == nil || !isRetryableError(output, err) {
break
}
// if we have an error based on a lock, we should wait a bit and then retry
self.log.Warn("lock error prevented command from running. Retrying command after a small wait")
time.Sleep(WaitTime)
if attempt < maxRetries-1 {
self.log.Warnf("lock error prevented command from running; retrying in %s", delay)
time.Sleep(delay)
delay *= 2
}
}
return stdout, stderr, err
return output, err
}
// Retry logic not implemented here, but these commands typically don't need to obtain a lock.
+137
View File
@@ -0,0 +1,137 @@
package commands
import (
"errors"
"testing"
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
"github.com/jesseduffield/lazygit/pkg/utils"
"github.com/stretchr/testify/assert"
)
type runnerResult struct {
output string
err error
}
// scriptedRunner is an ICmdObjRunner stub that returns a preconfigured result
// for each successive call, letting us drive the retry loop deterministically.
// It counts calls so tests can assert whether a command was retried.
type scriptedRunner struct {
results []runnerResult
calls int
}
func (self *scriptedRunner) next() (string, error) {
result := self.results[self.calls]
self.calls++
return result.output, result.err
}
func (self *scriptedRunner) Run(*oscommands.CmdObj) error {
_, err := self.next()
return err
}
func (self *scriptedRunner) RunWithOutput(*oscommands.CmdObj) (string, error) {
return self.next()
}
func (self *scriptedRunner) RunWithOutputs(*oscommands.CmdObj) (string, string, error) {
output, err := self.next()
return output, "", err
}
func (self *scriptedRunner) RunAndProcessLines(*oscommands.CmdObj, func(string) (bool, error)) error {
panic("not implemented")
}
func newTestRunner(inner *scriptedRunner) *gitCmdObjRunner {
return &gitCmdObjRunner{
log: utils.NewDummyLog(),
innerRunner: inner,
// don't actually sleep between retries
initialRetryDelay: 0,
}
}
// dummyCmdObj returns a throwaway command; only its clonability matters, since
// the scriptedRunner ignores it and returns preconfigured results.
func dummyCmdObj() *oscommands.CmdObj {
return oscommands.NewDummyCmdObjBuilder(nil).New([]string{"git", "status"})
}
func TestRunWithOutputReturnsSuccessWithoutRetrying(t *testing.T) {
inner := &scriptedRunner{results: []runnerResult{{output: "done", err: nil}}}
output, err := newTestRunner(inner).RunWithOutput(dummyCmdObj())
assert.NoError(t, err)
assert.Equal(t, "done", output)
assert.Equal(t, 1, inner.calls)
}
func TestRunWithOutputDoesNotRetryNonLockError(t *testing.T) {
inner := &scriptedRunner{results: []runnerResult{{output: "boom", err: errors.New("boom")}}}
_, err := newTestRunner(inner).RunWithOutput(dummyCmdObj())
assert.Error(t, err)
assert.Equal(t, 1, inner.calls)
}
func TestRunWithOutputRetriesWhenLockErrorIsInOutput(t *testing.T) {
inner := &scriptedRunner{results: []runnerResult{
{output: "fatal: Unable to create '/repo/.git/index.lock': File exists.", err: errors.New("exit status 128")},
{output: "done", err: nil},
}}
output, err := newTestRunner(inner).RunWithOutput(dummyCmdObj())
assert.NoError(t, err)
assert.Equal(t, "done", output)
assert.Equal(t, 2, inner.calls)
}
func TestRunWithOutputRetriesWhenLockErrorIsOnlyInError(t *testing.T) {
// A streamed command (e.g. an amend run through the gpg helper) doesn't
// capture its output, so a lock failure surfaces only in the returned error
// with an empty output string. The retry logic must still recognize it.
inner := &scriptedRunner{results: []runnerResult{
{output: "", err: errors.New("fatal: Unable to create '/repo/.git/index.lock': File exists.")},
{output: "", err: nil},
}}
_, err := newTestRunner(inner).RunWithOutput(dummyCmdObj())
assert.NoError(t, err)
assert.Equal(t, 2, inner.calls)
}
func TestRunWithOutputGivesUpAfterMaxRetries(t *testing.T) {
results := make([]runnerResult, maxRetries)
for i := range results {
results[i] = runnerResult{err: errors.New("fatal: Unable to create '/repo/.git/index.lock': File exists.")}
}
inner := &scriptedRunner{results: results}
_, err := newTestRunner(inner).RunWithOutput(dummyCmdObj())
assert.Error(t, err)
assert.Equal(t, maxRetries, inner.calls)
}
func TestRunWithOutputRetriesLockErrorInLinkedWorktree(t *testing.T) {
// In a linked worktree the lock lives at .git/worktrees/<name>/index.lock
// rather than .git/index.lock, so only matching the bare "index.lock"
// fragment lets the retry fire there too.
inner := &scriptedRunner{results: []runnerResult{
{output: "", err: errors.New("fatal: Unable to create '/repo/.git/worktrees/feature/index.lock': File exists.")},
{output: "", err: nil},
}}
_, err := newTestRunner(inner).RunWithOutput(dummyCmdObj())
assert.NoError(t, err)
assert.Equal(t, 2, inner.calls)
}
+30 -11
View File
@@ -1,12 +1,12 @@
package git_commands
import (
"fmt"
"strings"
"github.com/jesseduffield/lazygit/pkg/commands/models"
"github.com/jesseduffield/lazygit/pkg/commands/oscommands"
"github.com/jesseduffield/lazygit/pkg/common"
"github.com/samber/lo"
)
type CommitFileLoader struct {
@@ -29,7 +29,7 @@ func (self *CommitFileLoader) GetFilesInDiff(from string, to string, reverse boo
Arg("--no-ext-diff").
Arg("--name-status").
Arg("-z").
Arg("--no-renames").
Arg(fmt.Sprintf("--find-renames=%d%%", self.UserConfig().Git.RenameSimilarityThreshold)).
ArgIf(reverse, "-R").
Arg(from).
Arg(to).
@@ -44,18 +44,37 @@ func (self *CommitFileLoader) GetFilesInDiff(from string, to string, reverse boo
}
// filenames string is something like "MM\x00file1\x00MU\x00file2\x00AA\x00file3\x00"
// so we need to split it by the null character and then map each status-name pair to a commit file
// so we need to split it by the null character and then map each status-name pair
// to a commit file. Renames (and copies) are special: their status is followed by
// two paths (the old one and the new one) rather than one, e.g.
// "R100\x00old\x00new\x00".
func getCommitFilesFromFilenames(filenames string) []*models.CommitFile {
lines := strings.Split(strings.TrimRight(filenames, "\x00"), "\x00")
if len(lines) == 1 {
fields := strings.Split(strings.TrimRight(filenames, "\x00"), "\x00")
if len(fields) == 1 {
return []*models.CommitFile{}
}
// typical result looks like 'A my_file' meaning my_file was added
return lo.Map(lo.Chunk(lines, 2), func(chunk []string, _ int) *models.CommitFile {
return &models.CommitFile{
ChangeStatus: chunk[0],
Path: chunk[1],
commitFiles := make([]*models.CommitFile, 0, len(fields)/2)
for i := 0; i < len(fields)-1; {
changeStatus := fields[i]
if changeStatus[0] == 'R' || changeStatus[0] == 'C' {
// The status has a similarity score appended (e.g. "R100"); drop it
// so the rest of the code only has to deal with a plain "R" or "C".
commitFiles = append(commitFiles, &models.CommitFile{
ChangeStatus: changeStatus[:1],
PreviousPath: fields[i+1],
Path: fields[i+2],
})
i += 3
} else {
// typical result looks like 'A my_file' meaning my_file was added
commitFiles = append(commitFiles, &models.CommitFile{
ChangeStatus: changeStatus,
Path: fields[i+1],
})
i += 2
}
})
}
return commitFiles
}
@@ -60,6 +60,25 @@ func TestGetCommitFilesFromFilenames(t *testing.T) {
},
},
},
{
testName: "a rename among regular files",
input: "M\x00Myfile\x00R100\x00before\x00after\x00A\x00Added\x00",
output: []*models.CommitFile{
{
Path: "Myfile",
ChangeStatus: "M",
},
{
Path: "after",
PreviousPath: "before",
ChangeStatus: "R",
},
{
Path: "Added",
ChangeStatus: "A",
},
},
},
}
for _, test := range tests {
+9 -3
View File
@@ -432,8 +432,14 @@ func (self *WorkingTreeCommands) WorktreeFileDiffCmdObj(node models.IFile, plain
// ShowFileDiff get the diff of specified from and to. Typically this will be used for a single commit so it'll be 123abc^..123abc
// but when we're in diff mode it could be any 'from' to any 'to'. The reverse flag is also here thanks to diff mode.
func (self *WorkingTreeCommands) ShowFileDiff(from string, to string, reverse bool, fileName string, plain bool) (string, error) {
return self.ShowFileDiffCmdObj(from, to, reverse, []string{fileName}, plain).RunWithOutput()
// For a renamed file, previousPath is the path it was renamed from (empty otherwise);
// both paths must be passed to git for the rename to be detected.
func (self *WorkingTreeCommands) ShowFileDiff(from string, to string, reverse bool, fileName string, previousPath string, plain bool) (string, error) {
fileNames := []string{fileName}
if previousPath != "" {
fileNames = append(fileNames, previousPath)
}
return self.ShowFileDiffCmdObj(from, to, reverse, fileNames, plain).RunWithOutput()
}
func (self *WorkingTreeCommands) ShowFileDiffCmdObj(from string, to string, reverse bool, fileNames []string, plain bool) *oscommands.CmdObj {
@@ -454,7 +460,7 @@ func (self *WorkingTreeCommands) ShowFileDiffCmdObj(from string, to string, reve
ArgIfElse(useExtDiff || useExtDiffGitConfig, "--ext-diff", "--no-ext-diff").
Arg("--submodule").
Arg(fmt.Sprintf("--unified=%d", contextSize)).
Arg("--no-renames").
Arg(fmt.Sprintf("--find-renames=%d%%", self.UserConfig().Git.RenameSimilarityThreshold)).
Arg(fmt.Sprintf("--color=%s", colorArg)).
Arg(from).
Arg(to).
+22 -4
View File
@@ -339,6 +339,8 @@ func TestWorkingTreeShowFileDiff(t *testing.T) {
from string
to string
reverse bool
fileName string
previousPath string
plain bool
ignoreWhitespace bool
contextSize uint64
@@ -353,33 +355,49 @@ func TestWorkingTreeShowFileDiff(t *testing.T) {
from: "1234567890",
to: "0987654321",
reverse: false,
fileName: "test.txt",
plain: false,
ignoreWhitespace: false,
contextSize: 3,
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=3", "--no-renames", "--color=always", "1234567890", "0987654321", "--", "test.txt"}, expectedResult, nil),
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=3", "--find-renames=50%", "--color=always", "1234567890", "0987654321", "--", "test.txt"}, expectedResult, nil),
},
{
testName: "Show diff with custom context size",
from: "1234567890",
to: "0987654321",
reverse: false,
fileName: "test.txt",
plain: false,
ignoreWhitespace: false,
contextSize: 123,
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=123", "--no-renames", "--color=always", "1234567890", "0987654321", "--", "test.txt"}, expectedResult, nil),
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=123", "--find-renames=50%", "--color=always", "1234567890", "0987654321", "--", "test.txt"}, expectedResult, nil),
},
{
testName: "Default case (ignore whitespace)",
from: "1234567890",
to: "0987654321",
reverse: false,
fileName: "test.txt",
plain: false,
ignoreWhitespace: true,
contextSize: 3,
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=3", "--no-renames", "--color=always", "1234567890", "0987654321", "--ignore-all-space", "--", "test.txt"}, expectedResult, nil),
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=3", "--find-renames=50%", "--color=always", "1234567890", "0987654321", "--ignore-all-space", "--", "test.txt"}, expectedResult, nil),
},
{
testName: "Renamed file passes both paths so the rename is detected",
from: "1234567890",
to: "0987654321",
reverse: false,
fileName: "new.txt",
previousPath: "old.txt",
plain: false,
ignoreWhitespace: false,
contextSize: 3,
runner: oscommands.NewFakeRunner(t).
ExpectGitArgs([]string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "diff", "--no-ext-diff", "--submodule", "--unified=3", "--find-renames=50%", "--color=always", "1234567890", "0987654321", "--", "new.txt", "old.txt"}, expectedResult, nil),
},
}
@@ -394,7 +412,7 @@ func TestWorkingTreeShowFileDiff(t *testing.T) {
instance := buildWorkingTreeCommands(commonDeps{runner: s.runner, userConfig: userConfig, appState: &config.AppState{}, repoPaths: &repoPaths})
result, err := instance.ShowFileDiff(s.from, s.to, s.reverse, "test.txt", s.plain)
result, err := instance.ShowFileDiff(s.from, s.to, s.reverse, s.fileName, s.previousPath, s.plain)
assert.NoError(t, err)
assert.Equal(t, expectedResult, result)
s.runner.CheckForMissingCalls()
+21
View File
@@ -4,6 +4,9 @@ package models
type CommitFile struct {
Path string
// For a renamed file, the path it was renamed from; empty otherwise.
PreviousPath string
ChangeStatus string // e.g. 'A' for added or 'M' for modified. This is based on the result from git diff --name-status
}
@@ -23,6 +26,24 @@ func (f *CommitFile) Deleted() bool {
return f.ChangeStatus == "D"
}
func (f *CommitFile) IsRename() bool {
return f.PreviousPath != ""
}
// Names returns an array containing just the path, or in the case of a rename,
// the after path and the before path.
func (f *CommitFile) Names() []string {
result := []string{f.Path}
if f.PreviousPath != "" {
result = append(result, f.PreviousPath)
}
return result
}
func (f *CommitFile) GetPath() string {
return f.Path
}
func (f *CommitFile) GetPreviousPath() string {
return f.PreviousPath
}
+30 -23
View File
@@ -7,6 +7,7 @@ import (
"sync"
"unsafe"
"github.com/jesseduffield/lazygit/pkg/utils"
"golang.org/x/sys/windows"
)
@@ -15,15 +16,13 @@ type winPty struct {
inWrite *os.File
outRead *os.File
// mu guards the teardown state below and serializes it against Resize.
// hpcClosed gates ClosePseudoConsole (it must run exactly once) and also
// keeps Resize from touching the HPCON once it's been freed: the
// background waiter in StartPty closes the pseudoconsole on child exit,
// which would otherwise race a concurrent onResize and hand
// ResizePseudoConsole a freed handle.
// mu guards hpcClosed, which gates ClosePseudoConsole (it must run
// exactly once) and also keeps Resize from touching the HPCON once it's
// been freed: the background waiter in StartPty closes the pseudoconsole
// on child exit, which would otherwise race a concurrent onResize and
// hand ResizePseudoConsole a freed handle.
mu sync.Mutex
hpcClosed bool
closed bool
}
func (p *winPty) Read(buf []byte) (int, error) { return p.outRead.Read(buf) }
@@ -49,11 +48,6 @@ func (p *winPty) Resize(cols, rows uint16) error {
func (p *winPty) closeHpc() {
p.mu.Lock()
defer p.mu.Unlock()
p.closeHpcLocked()
}
// closeHpcLocked closes the pseudoconsole; the caller must hold p.mu.
func (p *winPty) closeHpcLocked() {
if p.hpcClosed {
return
}
@@ -61,18 +55,31 @@ func (p *winPty) closeHpcLocked() {
windows.ClosePseudoConsole(p.hpc)
}
// Close tears the pty down without waiting for it: the teardown runs on a
// background goroutine and Close returns immediately.
//
// It has to, because ClosePseudoConsole can block for a long time: before
// Windows 11 24H2 it waits for the console host to exit, and since closing
// only delivers CTRL_CLOSE_EVENT to the attached client without terminating
// it, a client that keeps running (git still computing an expensive diff, a
// pager waiting for input) keeps the host — and with it ClosePseudoConsole —
// alive arbitrarily long. Close is called while holding the global PtyMutex
// and while the task's onDone once is executing, where blocking wedges every
// subsequent task for the view (and with it the UI), so none of this may
// happen on the caller's thread.
//
// Within the teardown, the pipe ends must be closed before the
// pseudoconsole, and without holding p.mu: closing the pseudoconsole flushes
// the client's pending output into the out pipe, and with the task stopped
// nobody is reading anymore, so that flush can only complete once the pipe
// is broken. The background waiter's closeHpc may already be wedged in such
// a flush while holding p.mu; closing the pipes is what unblocks it.
func (p *winPty) Close() error {
p.mu.Lock()
defer p.mu.Unlock()
if p.closed {
return nil
}
p.closed = true
// Closing the pseudoconsole breaks the pipes; the child's next write
// fails and it exits. Then we close our ends of the pipes.
p.closeHpcLocked()
p.inWrite.Close()
p.outRead.Close()
go utils.Safe(func() {
p.inWrite.Close()
p.outRead.Close()
p.closeHpc()
})
return nil
}
+30 -17
View File
@@ -25,10 +25,14 @@ type fileInfo struct {
mode PatchStatus
includedLineIndices []int
diff string
// For a renamed file, the path it was renamed from; empty otherwise. We
// need to keep hold of it so we can re-render the file's patch (which is
// keyed by the new path) without the caller having to supply it again.
previousPath string
}
type (
loadFileDiffFunc func(from string, to string, reverse bool, filename string, plain bool) (string, error)
loadFileDiffFunc func(from string, to string, reverse bool, filename string, previousPath string, plain bool) (string, error)
)
// PatchBuilder manages the building of a patch for a commit to be applied to another commit (or the working tree, or removed from the current commit). We also support building patches from things like stashes, for which there is less flexibility
@@ -75,6 +79,7 @@ func (p *PatchBuilder) PatchToApply(reverse bool, turnAddedFilesIntoDiffAgainstE
patch.WriteString(p.RenderPatchForFile(RenderPatchForFileOpts{
Filename: filename,
PreviousPath: info.previousPath,
Plain: true,
Reverse: reverse,
TurnAddedFilesIntoDiffAgainstEmptyFile: turnAddedFilesIntoDiffAgainstEmptyFile,
@@ -102,8 +107,8 @@ func (p *PatchBuilder) removeFile(info *fileInfo) {
info.includedLineIndices = nil
}
func (p *PatchBuilder) AddFileWhole(filename string) error {
info, err := p.getFileInfo(filename)
func (p *PatchBuilder) AddFileWhole(filename string, previousPath string) error {
info, err := p.getFileInfo(filename, previousPath)
if err != nil {
return err
}
@@ -113,8 +118,8 @@ func (p *PatchBuilder) AddFileWhole(filename string) error {
return nil
}
func (p *PatchBuilder) RemoveFile(filename string) error {
info, err := p.getFileInfo(filename)
func (p *PatchBuilder) RemoveFile(filename string, previousPath string) error {
info, err := p.getFileInfo(filename, previousPath)
if err != nil {
return err
}
@@ -124,19 +129,20 @@ func (p *PatchBuilder) RemoveFile(filename string) error {
return nil
}
func (p *PatchBuilder) getFileInfo(filename string) (*fileInfo, error) {
func (p *PatchBuilder) getFileInfo(filename string, previousPath string) (*fileInfo, error) {
info, ok := p.fileInfoMap[filename]
if ok {
return info, nil
}
diff, err := p.loadFileDiff(p.From, p.To, p.reverse, filename, true)
diff, err := p.loadFileDiff(p.From, p.To, p.reverse, filename, previousPath, true)
if err != nil {
return nil, err
}
info = &fileInfo{
mode: UNSELECTED,
diff: diff,
mode: UNSELECTED,
diff: diff,
previousPath: previousPath,
}
p.fileInfoMap[filename] = info
@@ -144,8 +150,8 @@ func (p *PatchBuilder) getFileInfo(filename string) (*fileInfo, error) {
return info, nil
}
func (p *PatchBuilder) AddFileLineRange(filename string, lineIndices []int) error {
info, err := p.getFileInfo(filename)
func (p *PatchBuilder) AddFileLineRange(filename string, previousPath string, lineIndices []int) error {
info, err := p.getFileInfo(filename, previousPath)
if err != nil {
return err
}
@@ -155,8 +161,8 @@ func (p *PatchBuilder) AddFileLineRange(filename string, lineIndices []int) erro
return nil
}
func (p *PatchBuilder) RemoveFileLineRange(filename string, lineIndices []int) error {
info, err := p.getFileInfo(filename)
func (p *PatchBuilder) RemoveFileLineRange(filename string, previousPath string, lineIndices []int) error {
info, err := p.getFileInfo(filename, previousPath)
if err != nil {
return err
}
@@ -171,13 +177,14 @@ func (p *PatchBuilder) RemoveFileLineRange(filename string, lineIndices []int) e
type RenderPatchForFileOpts struct {
Filename string
PreviousPath string
Plain bool
Reverse bool
TurnAddedFilesIntoDiffAgainstEmptyFile bool
}
func (p *PatchBuilder) RenderPatchForFile(opts RenderPatchForFileOpts) string {
info, err := p.getFileInfo(opts.Filename)
info, err := p.getFileInfo(opts.Filename, opts.PreviousPath)
if err != nil {
p.Log.Error(err)
return ""
@@ -198,7 +205,12 @@ func (p *PatchBuilder) RenderPatchForFile(opts RenderPatchForFileOpts) string {
Transform(TransformOpts{
Reverse: opts.Reverse,
TurnAddedFilesIntoDiffAgainstEmptyFile: opts.TurnAddedFilesIntoDiffAgainstEmptyFile,
IncludedLineIndices: info.includedLineIndices,
// For a partial selection of a renamed file we keep only the
// content change and drop the rename, so that the rename stays in
// the commit. A whole-file selection keeps the rename (and short-
// circuits before this for plain output).
StripRename: info.mode == PART && info.previousPath != "",
IncludedLineIndices: info.includedLineIndices,
})
if opts.Plain {
@@ -215,6 +227,7 @@ func (p *PatchBuilder) renderEachFilePatch(plain bool) []string {
patches := lo.Map(filenames, func(filename string, _ int) string {
return p.RenderPatchForFile(RenderPatchForFileOpts{
Filename: filename,
PreviousPath: p.fileInfoMap[filename].previousPath,
Plain: plain,
Reverse: false,
TurnAddedFilesIntoDiffAgainstEmptyFile: true,
@@ -244,8 +257,8 @@ func (p *PatchBuilder) GetFileStatus(filename string, parent string) PatchStatus
return info.mode
}
func (p *PatchBuilder) GetFileIncLineIndices(filename string) ([]int, error) {
info, err := p.getFileInfo(filename)
func (p *PatchBuilder) GetFileIncLineIndices(filename string, previousPath string) ([]int, error) {
info, err := p.getFileInfo(filename, previousPath)
if err != nil {
return nil, err
}
+55
View File
@@ -19,6 +19,22 @@ index dcd3485..1ba5540 100644
...
`
const renameWithModificationDiff = `diff --git a/oldname b/newname
similarity index 62%
rename from oldname
rename to newname
index dcd3485..1ba5540 100644
--- a/oldname
+++ b/newname
@@ -1,5 +1,5 @@
apple
-orange
+grape
...
...
...
`
const addNewlineToEndOfFile = `diff --git a/filename b/filename
index 80a73f1..e48a11c 100644
--- a/filename
@@ -152,6 +168,7 @@ func TestTransform(t *testing.T) {
firstLineIndex int
lastLineIndex int
reverse bool
stripRename bool
expected string
}
@@ -515,6 +532,43 @@ func TestTransform(t *testing.T) {
orange
banana
lemon
`,
},
{
testName: "renamed file, whole change selected, strips the rename so only the content change is applied",
firstLineIndex: 9,
lastLineIndex: 10,
stripRename: true,
diffText: renameWithModificationDiff,
expected: `diff --git a/newname b/newname
index dcd3485..1ba5540 100644
--- a/newname
+++ b/newname
@@ -1,5 +1,5 @@
apple
-orange
+grape
...
...
...
`,
},
{
testName: "renamed file, only removal selected, strips the rename",
firstLineIndex: 9,
lastLineIndex: 9,
stripRename: true,
diffText: renameWithModificationDiff,
expected: `diff --git a/newname b/newname
index dcd3485..1ba5540 100644
--- a/newname
+++ b/newname
@@ -1,5 +1,4 @@
apple
-orange
...
...
...
`,
},
}
@@ -527,6 +581,7 @@ func TestTransform(t *testing.T) {
Transform(TransformOpts{
Reverse: s.reverse,
FileNameOverride: s.filename,
StripRename: s.stripRename,
IncludedLineIndices: lineIndices,
}).
FormatPlain()
+53 -6
View File
@@ -33,6 +33,13 @@ type TransformOpts struct {
// treat it as a diff against an empty file.
TurnAddedFilesIntoDiffAgainstEmptyFile bool
// When building a partial patch for a renamed file, strip the rename
// metadata from the header and point it at the new path. Applying the
// resulting patch then only changes the file's contents and leaves the
// rename itself in place. (For a whole-file selection we keep the rename
// so that it moves or is discarded together with the contents.)
StripRename bool
// The indices of lines that should be included in the patch.
IncludedLineIndices []int
}
@@ -72,21 +79,61 @@ func (self *patchTransformer) transformHeader() []string {
"--- a/" + self.opts.FileNameOverride,
"+++ b/" + self.opts.FileNameOverride,
}
} else if self.opts.TurnAddedFilesIntoDiffAgainstEmptyFile {
result := make([]string, 0, len(self.patch.header))
for idx, line := range self.patch.header {
}
header := self.patch.header
if self.opts.StripRename {
header = stripRenameFromHeader(header)
}
if self.opts.TurnAddedFilesIntoDiffAgainstEmptyFile {
result := make([]string, 0, len(header))
for idx, line := range header {
if strings.HasPrefix(line, "new file mode") {
continue
}
if line == "--- /dev/null" && strings.HasPrefix(self.patch.header[idx+1], "+++ b/") {
line = "--- a/" + self.patch.header[idx+1][6:]
if line == "--- /dev/null" && strings.HasPrefix(header[idx+1], "+++ b/") {
line = "--- a/" + header[idx+1][6:]
}
result = append(result, line)
}
return result
}
return self.patch.header
return header
}
// stripRenameFromHeader rewrites a rename diff header so that it looks like a
// plain modification of the new path: it drops the rename metadata and points
// the diff at the new path on both sides, while keeping the blob index line so
// that `git apply --3way` can still fall back to a blob merge. See the
// StripRename option for why we do this.
func stripRenameFromHeader(header []string) []string {
newPath := ""
for _, line := range header {
if path, ok := strings.CutPrefix(line, "+++ b/"); ok {
newPath = path
break
}
}
result := make([]string, 0, len(header))
for _, line := range header {
switch {
case strings.HasPrefix(line, "similarity index "),
strings.HasPrefix(line, "dissimilarity index "),
strings.HasPrefix(line, "rename from "),
strings.HasPrefix(line, "rename to "):
// drop the rename metadata
case strings.HasPrefix(line, "diff --git "):
result = append(result, "diff --git a/"+newPath+" b/"+newPath)
case strings.HasPrefix(line, "--- "):
result = append(result, "--- a/"+newPath)
default:
result = append(result, line)
}
}
return result
}
func (self *patchTransformer) transformHunks() []*Hunk {
+5 -5
View File
@@ -39,15 +39,15 @@ func setupViews(t *testing.T, g *Gui) (*View, *View) {
return status, main
}
// pushContentOnly pushes a content-only event directly to the channel
// (synchronous, deterministic — unlike Update which spawns a goroutine).
// pushContentOnly enqueues a content-only event directly, letting the test
// control the contentOnly flag (which Update/UpdateContentOnly hard-code).
func pushContentOnly(g *Gui, f func(*Gui) error) {
g.userEvents <- userEvent{f: f, task: g.NewTask(), contentOnly: true}
g.userEvents.enqueue(userEvent{f: f, task: g.NewTask(), contentOnly: true})
}
// pushRegular pushes a regular event directly to the channel.
// pushRegular enqueues a regular (non-content-only) event directly.
func pushRegular(g *Gui, f func(*Gui) error) {
g.userEvents <- userEvent{f: f, task: g.NewTask(), contentOnly: false}
g.userEvents.enqueue(userEvent{f: f, task: g.NewTask(), contentOnly: false})
}
func TestFlushContentOnly_SkipsUntaintedViews(t *testing.T) {
+118 -25
View File
@@ -131,7 +131,7 @@ type Gui struct {
viewMouseBindings []*ViewMouseBinding
lastClick *clickInfo
gEvents chan GocuiEvent
userEvents chan userEvent
userEvents *userEventQueue
views []*View
currentView *View
managers []Manager
@@ -238,12 +238,7 @@ func NewGui(opts NewGuiOpts) (*Gui, error) {
g.stop = make(chan struct{})
g.gEvents = make(chan GocuiEvent, 20)
// Update does a non-blocking send and panics on a full channel rather than
// blocking (which would deadlock the UI goroutine against itself) or
// silently reordering. The buffer is sized well above the peak occupancy we
// see in practice, so the panic stays unreachable in normal use; if it ever
// fires, that's a real anomaly to investigate, not a cue to grow the buffer.
g.userEvents = make(chan userEvent, 256)
g.userEvents = newUserEventQueue()
g.taskManager = newTaskManager()
if opts.PlayRecording {
@@ -608,6 +603,13 @@ func (g *Gui) SetRenderSearchStatusFunc(renderSearchStatusFunc func(*View, int,
g.renderSearchStatusFunc = renderSearchStatusFunc
}
// SetUpdateQueueHighWaterMarkHandler registers a diagnostic callback invoked
// with the new depth whenever the queue of pending Update callbacks reaches a
// new maximum. It may be called from any goroutine.
func (g *Gui) SetUpdateQueueHighWaterMarkHandler(f func(depth int)) {
g.userEvents.setHighWaterMarkHandler(f)
}
// userEvent represents an event triggered by the user.
type userEvent struct {
f func(*Gui) error
@@ -618,29 +620,108 @@ type userEvent struct {
contentOnly bool
}
// Update enqueues f on the user-events channel for the UI loop to run on its
// next iteration. Multiple Update calls from the same goroutine arrive in
// source order via the channel's FIFO. The send is non-blocking — if the
// channel is full we panic rather than block or silently reorder, since a
// blocked send from the UI goroutine would deadlock against itself and
// silently switching to inline execution would break the ordering guarantee
// callers rely on. The buffer is sized generously enough that this should
// never fire in practice; if it does, that's a signal to investigate, not
// to grow the buffer reflexively.
func (g *Gui) Update(f func(*Gui) error) {
task := g.NewTask()
// userEventQueue is an unbounded, order-preserving FIFO of work enqueued by
// Update and friends for the main loop to run.
//
// It's unbounded (rather than a fixed-size channel) because producers must
// never block or lose work. Update can be called from the UI goroutine itself,
// where a blocking send would deadlock against the loop that drains the queue;
// and it can be called from arbitrary worker goroutines that may enqueue faster
// than the loop drains. That happens while the loop is stalled — suspended for
// a subprocess (the editor runs on the UI thread), or hung in a long handler —
// and also when a long-running worker operation emits a steady stream of
// updates that outpaces the loop (e.g. the waiting-status spinner ticks while a
// large directory is toggled into a custom patch). A fixed channel forces a
// choice between blocking (deadlock), dropping or reordering, and panicking on
// overflow; an unbounded queue avoids all three while preserving FIFO order.
//
// enqueue appends under the mutex and rings the doorbell; the main loop selects
// on the doorbell to wake, then drains the slice to empty. The doorbell is
// buffered(1) and rung with a non-blocking send, so it's a coalescing "work
// pending" flag rather than a per-event signal: a burst of appends leaves at
// most one token, and the loop drains everything the token represents on a
// single wake. A token left over after a drain (because the drain happened to
// empty the slice after the ring) just causes one harmless empty wake.
type userEventQueue struct {
mutex sync.Mutex
events []userEvent
doorbell chan struct{}
// highWaterMark is the deepest the queue has ever been, and
// onHighWaterMark (if set) is called with the new depth each time that
// record is broken. Purely diagnostic: it lets us see how deep the queue
// gets in practice (see SetUpdateQueueHighWaterMarkHandler).
highWaterMark int
onHighWaterMark func(int)
}
func newUserEventQueue() *userEventQueue {
return &userEventQueue{doorbell: make(chan struct{}, 1)}
}
// enqueue appends an event and wakes the main loop. It never blocks.
func (q *userEventQueue) enqueue(ev userEvent) {
q.mutex.Lock()
q.events = append(q.events, ev)
newHighWaterMark := 0
if len(q.events) > q.highWaterMark {
q.highWaterMark = len(q.events)
newHighWaterMark = q.highWaterMark
}
onHighWaterMark := q.onHighWaterMark
q.mutex.Unlock()
// Report outside the lock: the handler does I/O (logging) and must not
// stall other producers or the draining loop.
if newHighWaterMark > 0 && onHighWaterMark != nil {
onHighWaterMark(newHighWaterMark)
}
select {
case g.userEvents <- userEvent{f: f, task: task}:
case q.doorbell <- struct{}{}:
default:
panic("gocui: userEvents channel full; refusing to block or reorder")
}
}
func (q *userEventQueue) setHighWaterMarkHandler(f func(int)) {
q.mutex.Lock()
q.onHighWaterMark = f
q.mutex.Unlock()
}
// dequeue pops the oldest event, reporting false when the queue is empty.
func (q *userEventQueue) dequeue() (userEvent, bool) {
q.mutex.Lock()
defer q.mutex.Unlock()
if len(q.events) == 0 {
return userEvent{}, false
}
ev := q.events[0]
if len(q.events) == 1 {
// Release the backing array whenever the queue drains, so a one-off
// burst doesn't pin its peak size for the rest of the session.
q.events = nil
} else {
q.events[0] = userEvent{}
q.events = q.events[1:]
}
return ev, true
}
// Update enqueues f for the UI loop to run on its next iteration. Multiple
// Update calls from the same goroutine arrive in source order (the queue is
// FIFO). The enqueue never blocks and never drops work; see userEventQueue for
// why the queue is unbounded.
func (g *Gui) Update(f func(*Gui) error) {
task := g.NewTask()
g.userEvents.enqueue(userEvent{f: f, task: task})
}
// Like Update, but signals that the callback only modifies content.
func (g *Gui) UpdateContentOnly(f func(*Gui) error) {
task := g.NewTask()
g.userEvents <- userEvent{f: f, task: task, contentOnly: true}
g.userEvents.enqueue(userEvent{f: f, task: task, contentOnly: true})
}
// Calls a function in a goroutine. Handles panics gracefully and tracks
@@ -766,7 +847,14 @@ func (g *Gui) processEvent() error {
if err := g.handleError(g.handleEvent(&ev)); err != nil {
return err
}
case ev := <-g.userEvents:
case <-g.userEvents.doorbell:
ev, ok := g.userEvents.dequeue()
if !ok {
// A leftover doorbell token whose events were already drained by a
// previous iteration's processRemainingEvents: nothing to run and
// nothing new to render.
return nil
}
contentOnly = ev.contentOnly
defer func() { ev.task.Done() }()
@@ -798,15 +886,20 @@ func (g *Gui) processRemainingEvents() (bool, error) {
if err := g.handleError(g.handleEvent(&ev)); err != nil {
return false, err
}
case ev := <-g.userEvents:
default:
// No gui event is pending; drain a queued user event instead.
// gui events take priority so input stays responsive, but they're
// bounded (buffer of 20), so this can't starve the user-event queue.
ev, ok := g.userEvents.dequeue()
if !ok {
return contentOnly, nil
}
contentOnly = ev.contentOnly && contentOnly
err := g.handleError(ev.f(g))
ev.task.Done()
if err != nil {
return false, err
}
default:
return contentOnly, nil
}
}
}
+111
View File
@@ -0,0 +1,111 @@
package gocui
import (
"sync"
"testing"
"github.com/stretchr/testify/assert"
)
// Enqueuing far more events than the old fixed 256-slot buffer, without the
// main loop draining them, used to panic ("userEvents channel full"). It must
// not: producers can legitimately burst faster than a stalled UI loop drains
// (e.g. one command-log entry per git command when adding a large directory to
// a custom patch, or any producer while the loop is blocked in a subprocess).
// The events must also stay in FIFO order.
func TestUpdateIsUnboundedAndPreservesOrder(t *testing.T) {
g := newTestGui(t)
const n = 1000
var got []int
for i := range n {
g.Update(func(*Gui) error {
got = append(got, i)
return nil
})
}
// Drain the whole queue the way the main loop's inner drain does.
_, err := g.processRemainingEvents()
assert.NoError(t, err)
want := make([]int, n)
for i := range want {
want[i] = i
}
assert.Equal(t, want, got)
}
// The high-water-mark handler fires only when the queue reaches a new maximum
// depth, reporting that depth. It does not reset when the queue drains.
func TestUpdateQueueHighWaterMark(t *testing.T) {
g := newTestGui(t)
var marks []int
g.SetUpdateQueueHighWaterMarkHandler(func(depth int) { marks = append(marks, depth) })
noop := func(*Gui) error { return nil }
// Three enqueues with no drain: new highs 1, 2, 3.
g.Update(noop)
g.Update(noop)
g.Update(noop)
_, err := g.processRemainingEvents()
assert.NoError(t, err)
// Two enqueues stay below the previous high of 3: no new marks.
g.Update(noop)
g.Update(noop)
_, err = g.processRemainingEvents()
assert.NoError(t, err)
// Four enqueues with no drain: only depth 4 beats the previous high.
for range 4 {
g.Update(noop)
}
assert.Equal(t, []int{1, 2, 3, 4}, marks)
}
// Concurrent producers must be able to enqueue safely (run under -race). Only
// same-goroutine order is guaranteed, so we check that every event is delivered
// exactly once and that each producer's own events stay in order.
func TestUpdateConcurrentProducers(t *testing.T) {
g := newTestGui(t)
const producers = 8
const perProducer = 500
type item struct{ producer, seq int }
var got []item
var wg sync.WaitGroup
for p := range producers {
wg.Add(1)
go func() {
defer wg.Done()
for seq := range perProducer {
g.Update(func(*Gui) error {
got = append(got, item{p, seq})
return nil
})
}
}()
}
// Update is a synchronous, non-blocking enqueue, so once every producer has
// returned, every event is in the queue and a single drain sees them all.
wg.Wait()
_, err := g.processRemainingEvents()
assert.NoError(t, err)
assert.Len(t, got, producers*perProducer)
lastSeq := make([]int, producers)
for p := range lastSeq {
lastSeq[p] = -1
}
for _, it := range got {
assert.Equal(t, lastSeq[it.producer]+1, it.seq, "producer %d events out of order", it.producer)
lastSeq[it.producer] = it.seq
}
}
+5 -2
View File
@@ -60,8 +60,11 @@ func NewContextTree(c *ContextCommon) *ContextTree {
"main",
PATCH_BUILDING_MAIN_CONTEXT_KEY,
func() []int {
filename := commitFilesContext.GetSelectedPath()
includedLineIndices, err := c.Git().Patch.PatchBuilder.GetFileIncLineIndices(filename)
file := commitFilesContext.GetSelectedFile()
if file == nil {
return nil
}
includedLineIndices, err := c.Git().Patch.PatchBuilder.GetFileIncLineIndices(file.Path, file.PreviousPath)
if err != nil {
c.Log.Error(err)
return nil
@@ -191,11 +191,11 @@ func (self *CommitFilesController) GetOnRenderToMain() func() {
}
}
func (self *CommitFilesController) copyDiffToClipboard(path string, toastMessage string) error {
func (self *CommitFilesController) copyDiffToClipboard(paths []string, toastMessage string) error {
from, to := self.context().GetFromAndToForDiff()
from, reverse := self.c.Modes().Diffing.GetFromAndReverseArgsForDiff(from)
cmdObj := self.c.Git().WorkingTree.ShowFileDiffCmdObj(from, to, reverse, []string{path}, true)
cmdObj := self.c.Git().WorkingTree.ShowFileDiffCmdObj(from, to, reverse, paths, true)
diff, err := cmdObj.RunWithOutput()
if err != nil {
return err
@@ -263,7 +263,7 @@ func (self *CommitFilesController) openCopyMenu() error {
copyFileDiffItem := &types.MenuItem{
Label: self.c.Tr.CopySelectedDiff,
OnPress: func() error {
return self.copyDiffToClipboard(node.GetPath(), self.c.Tr.FileDiffCopiedToast)
return self.copyDiffToClipboard(self.pathsForDiff(node), self.c.Tr.FileDiffCopiedToast)
},
DisabledReason: self.require(self.singleItemSelected())(),
Keys: menuKey('s'),
@@ -271,7 +271,7 @@ func (self *CommitFilesController) openCopyMenu() error {
copyAllDiff := &types.MenuItem{
Label: self.c.Tr.CopyAllFilesDiff,
OnPress: func() error {
return self.copyDiffToClipboard(".", self.c.Tr.AllFilesDiffCopiedToast)
return self.copyDiffToClipboard([]string{"."}, self.c.Tr.AllFilesDiffCopiedToast)
},
DisabledReason: self.require(self.itemsSelected())(),
Keys: menuKey('a'),
@@ -348,7 +348,10 @@ func (self *CommitFilesController) discard(selectedNodes []*filetree.CommitFileN
for _, node := range selectedNodes {
_ = node.ForEachFile(func(file *models.CommitFile) error {
filePaths = append(filePaths, file.GetPath())
// For a rename we discard both the new and the old path,
// so that the new file is removed and the old one is
// restored.
filePaths = append(filePaths, file.Names()...)
return nil
})
}
@@ -465,7 +468,7 @@ func (self *CommitFilesController) toggleForPatch(selectedNodes []*filetree.Comm
for _, node := range selectedNodes {
err := node.ForEachFile(func(file *models.CommitFile) error {
return patchOperationFunction(file.Path)
return patchOperationFunction(file.Path, file.PreviousPath)
})
if err != nil {
return err
@@ -610,11 +613,16 @@ func (self *CommitFilesController) pathsForDiff(node *filetree.CommitFileNode) [
if !node.IsFile() && self.context().IsFiltering() {
var paths []string
_ = node.ForEachFile(func(file *models.CommitFile) error {
paths = append(paths, file.Path)
// For a rename we need to pass both paths so that git detects it as
// a rename rather than an unrelated delete and add.
paths = append(paths, file.Names()...)
return nil
})
return paths
}
if file := node.GetFile(); file != nil {
return file.Names()
}
return []string{node.GetPath()}
}
@@ -66,20 +66,21 @@ func (self *PatchBuildingHelper) RefreshPatchBuildingPanel(opts types.OnFocusOpt
}
// get diff from commit file that's currently selected
path := self.c.Contexts().CommitFiles.GetSelectedPath()
if path == "" {
file := self.c.Contexts().CommitFiles.GetSelectedFile()
if file == nil {
return
}
from, to := self.c.Contexts().CommitFiles.GetFromAndToForDiff()
from, reverse := self.c.Modes().Diffing.GetFromAndReverseArgsForDiff(from)
diff, err := self.c.Git().WorkingTree.ShowFileDiff(from, to, reverse, path, true)
diff, err := self.c.Git().WorkingTree.ShowFileDiff(from, to, reverse, file.Path, file.PreviousPath, true)
if err != nil {
return
}
secondaryDiff := self.c.Git().Patch.PatchBuilder.RenderPatchForFile(patch.RenderPatchForFileOpts{
Filename: path,
Filename: file.Path,
PreviousPath: file.PreviousPath,
Plain: false,
Reverse: false,
TurnAddedFilesIntoDiffAgainstEmptyFile: true,
@@ -138,8 +138,8 @@ func (self *PatchBuildingController) toggleSelection() error {
self.context().GetMutex().Lock()
defer self.context().GetMutex().Unlock()
filename := self.c.Contexts().CommitFiles.GetSelectedPath()
if filename == "" {
file := self.c.Contexts().CommitFiles.GetSelectedFile()
if file == nil {
return nil
}
@@ -152,7 +152,7 @@ func (self *PatchBuildingController) toggleSelection() error {
return nil
}
includedLineIndices, err := self.c.Git().Patch.PatchBuilder.GetFileIncLineIndices(filename)
includedLineIndices, err := self.c.Git().Patch.PatchBuilder.GetFileIncLineIndices(file.Path, file.PreviousPath)
if err != nil {
return err
}
@@ -164,7 +164,7 @@ func (self *PatchBuildingController) toggleSelection() error {
}
// add range of lines to those set for the file
if err := toggleFunc(filename, lineIndicesToToggle); err != nil {
if err := toggleFunc(file.Path, file.PreviousPath, lineIndicesToToggle); err != nil {
// might actually want to return an error here
self.c.Log.Error(err)
}
@@ -1,6 +1,7 @@
package controllers
import (
"errors"
"fmt"
"github.com/jesseduffield/lazygit/pkg/gui/context"
@@ -49,6 +50,10 @@ func (self *RenameSimilarityThresholdController) Context() types.Context {
}
func (self *RenameSimilarityThresholdController) Increase() error {
if err := self.checkCanChangeThreshold(); err != nil {
return err
}
old_size := self.c.UserConfig().Git.RenameSimilarityThreshold
if old_size < 100 {
@@ -59,6 +64,10 @@ func (self *RenameSimilarityThresholdController) Increase() error {
}
func (self *RenameSimilarityThresholdController) Decrease() error {
if err := self.checkCanChangeThreshold(); err != nil {
return err
}
old_size := self.c.UserConfig().Git.RenameSimilarityThreshold
if old_size > 5 {
@@ -73,11 +82,23 @@ func (self *RenameSimilarityThresholdController) applyChange() error {
currentContext := self.c.Context().CurrentSide()
switch currentContext.GetKey() {
// we make an exception for our files context, because it actually need to refresh its state afterwards.
// we make an exception for the files and commit-files contexts, because
// they actually need to refresh their state afterwards: a changed threshold
// can turn a rename into a separate delete and add, or vice versa.
case context.FILES_CONTEXT_KEY:
self.c.Refresh(types.RefreshOptions{Scope: []types.RefreshableView{types.FILES}})
case context.COMMIT_FILES_CONTEXT_KEY:
self.c.Refresh(types.RefreshOptions{Scope: []types.RefreshableView{types.COMMIT_FILES}})
default:
currentContext.HandleRenderToMain()
}
return nil
}
func (self *RenameSimilarityThresholdController) checkCanChangeThreshold() error {
if self.c.Git().Patch.PatchBuilder.Active() {
return errors.New(self.c.Tr.CantChangeRenameThresholdError)
}
return nil
}
+4
View File
@@ -414,6 +414,10 @@ func (gui *Gui) onNewRepo(startArgs appTypes.StartArgs, contextKey types.Context
return nil
})
gui.g.SetUpdateQueueHighWaterMarkHandler(func(depth int) {
gui.c.Log.Infof("User-event queue reached a new high-water mark: %d", depth)
})
gui.g.SetOnSelectSearchResultFunc(func(v *gocui.View, selectedLineIdx int) {
ctx, ok := gui.helpers.View.ContextForView(v.Name())
if ok {
+16 -1
View File
@@ -328,7 +328,8 @@ func fileNameAtDepth(node *filetree.Node[models.File], depth int, showRootItem b
func commitFileNameAtDepth(node *filetree.Node[models.CommitFile], depth int) string {
splitName := split(node.GetInternalPath())
if depth == 0 && splitName[0] == "." {
showRootItem := splitName[0] == "."
if depth == 0 && showRootItem {
if len(splitName) == 1 {
return "/"
}
@@ -336,6 +337,20 @@ func commitFileNameAtDepth(node *filetree.Node[models.CommitFile], depth int) st
}
name := join(splitName[depth:])
if node.File != nil && node.File.IsRename() {
splitPrevName := filetree.SplitFileTreePath(node.File.PreviousPath, showRootItem)
prevName := node.File.PreviousPath
// if the file has just been renamed inside the same directory, we can shave off
// the prefix for the previous path too. Otherwise we'll keep it unchanged
sameParentDir := len(splitName) == len(splitPrevName) && join(splitName[0:depth]) == join(splitPrevName[0:depth])
if sameParentDir {
prevName = join(splitPrevName[depth:])
}
return prevName + " → " + name
}
return name
}
+9 -1
View File
@@ -151,6 +151,14 @@ func TestRenderCommitFileTree(t *testing.T) {
showRootItem: true,
expected: []string{"A test"},
},
{
name: "renamed file",
files: []*models.CommitFile{
{Path: "new.txt", PreviousPath: "old.txt", ChangeStatus: "R"},
},
showRootItem: false,
expected: []string{"R old.txt → new.txt"},
},
{
name: "big example",
files: []*models.CommitFile{
@@ -219,7 +227,7 @@ M file1
}
patchBuilder := patch.NewPatchBuilder(
utils.NewDummyLog(),
func(from string, to string, reverse bool, filename string, plain bool) (string, error) {
func(from string, to string, reverse bool, filename string, previousPath string, plain bool) (string, error) {
return "", nil
},
)
+2
View File
@@ -819,6 +819,7 @@ type TranslationSet struct {
SortCommits string
SortCommitsTooltip string
CantChangeContextSizeError string
CantChangeRenameThresholdError string
OpenCommitInBrowser string
ViewBisectOptions string
ConfirmRevertCommit string
@@ -1966,6 +1967,7 @@ func EnglishTranslationSet() *TranslationSet {
SortCommits: "Commit sort order",
SortCommitsTooltip: "Change the sort order of the commits in the commit log.\n\nThe default can be changed in the config file with the key 'git.log.sortOrder'.",
CantChangeContextSizeError: "Cannot change context while in patch building mode because we were too lazy to support it when releasing the feature. If you really want it, please let us know!",
CantChangeRenameThresholdError: "Cannot change the rename similarity threshold while in patch building mode, because the custom patch can't cope with a rename turning into a delete and add underneath it.",
OpenCommitInBrowser: "Open commit in browser",
ViewBisectOptions: "View bisect options",
ConfirmRevertCommit: "Are you sure you want to revert {{.selectedCommit}}?",
-8
View File
@@ -207,7 +207,6 @@
"StashChanges": "変更をスタッシュ(一時保存)",
"RenameStash": "スタッシュの名前を変更",
"RenameStashPrompt": "スタッシュの名前を変更: {{.stashName}}",
"OpenConfig": "設定ファイルを開く",
"EditConfig": "設定ファイルを編集",
"ForcePush": "強制プッシュ",
"ForcePushPrompt": "ローカルブランチはリモートブランチから分岐しています。キャンセルするには{{.cancelKey}}を、強制プッシュするには{{.confirmKey}}を押してください。",
@@ -276,7 +275,6 @@
"ViewConflictsMenuItem": "コンフリクトを表示",
"AbortMenuItem": "%s を中止",
"PickHunk": "ハンクを選択",
"PickAllHunks": "すべてのハンクを選択",
"ViewMergeRebaseOptions": "マージ/リベースオプションを表示",
"ViewMergeRebaseOptionsTooltip": "現在のマージ/リベースを中止/継続/スキップするオプションを表示します。",
"ViewMergeOptions": "マージオプションを表示",
@@ -770,7 +768,6 @@
"DetachingWorktree": "ワークツリーをデタッチ中",
"WorktreesTitle": "ワークツリー",
"WorktreeTitle": "ワークツリー",
"RemoveWorktreePrompt": "ワークツリー '{{.worktreeName}}' を削除してよろしいですか?",
"RemovingWorktree": "ワークツリーを削除中",
"AddingWorktree": "ワークツリーを追加中",
"CantDeleteCurrentWorktree": "現在のワークツリーは削除できません!",
@@ -780,13 +777,8 @@
"MissingWorktree": "(見つかりません)",
"NewWorktree": "新しいワークツリー",
"NewWorktreePath": "新しいワークツリーのパス",
"NewWorktreeBase": "新しいワークツリーのベース参照",
"RemoveWorktreeTooltip": "選択したワークツリーを削除します。これはワークツリーのディレクトリとワークツリーに関するメタデータの両方を.gitディレクトリから削除します。",
"NewBranchName": "新しいブランチ名",
"NewBranchNameLeaveBlank": "新しいブランチ名({{.default}} をチェックアウトするには空白のままにしてください)",
"ViewWorktreeOptions": "ワークツリーオプションを表示",
"CreateWorktreeFrom": "{{.ref}} からワークツリーを作成",
"CreateWorktreeFromDetached": "{{.ref}} からワークツリーを作成(デタッチド)",
"LcWorktree": "ワークツリー",
"ChangingDirectoryTo": "ディレクトリを {{.path}} に変更中",
"Name": "名前",
-1
View File
@@ -101,7 +101,6 @@
"StashApply": "Stash 적용",
"SureApplyStashEntry": "정말로 Stash를 적용하시겠습니까?",
"StashChanges": "변경을 Stash",
"OpenConfig": "설정 파일 열기",
"EditConfig": "설정 파일 수정",
"ForcePush": "강제 푸시",
"ForcePushPrompt": "브랜치가 원격 브랜치에서 분기하고 있습니다. 'esc'를 눌러 취소하거나, 'enter'를 눌러 강제로 푸시하세요.",
+188 -5
View File
@@ -5,30 +5,81 @@
"BranchesTitle": "Branches",
"CommitsTitle": "Commits",
"StashTitle": "Stash",
"SnakeTitle": "Snake",
"EasterEgg": "Easter egg",
"UnstagedChanges": "Unstaged wijzigingen",
"StagedChanges": "Staged wijzigingen",
"StagingTitle": "Staging",
"MergingTitle": "Mergen",
"NormalTitle": "Normaal",
"LogTitle": "Log",
"LogXOfYTitle": "Log (%d van %d)",
"CommitSummary": "Commitbericht",
"CredentialsUsername": "Gebruikersnaam",
"CredentialsPassword": "Wachtwoord",
"CredentialsPassphrase": "Voer een wachtwoordzin in voor de SSH-sleutel",
"CredentialsPIN": "Voer PIN voor SSH sleutel in",
"CredentialsToken": "Voer Token voor SSH sleutel in",
"PassUnameWrong": "Wachtwoord en/of gebruikersnaam verkeerd",
"Commit": "Commit veranderingen",
"CommitTooltip": "Commit gestagede wijzigingen.",
"AmendLastCommit": "Wijzig laatste commit",
"AmendLastCommitTitle": "Wijzig laatste commit",
"SureToAmend": "Weet je zeker dat je de laatste commit wilt wijzigen? U kunt het commit-bericht wijzigen vanuit het commits-paneel.",
"NoCommitToAmend": "Er is geen commits om te wijzigen.",
"CommitChangesWithEditor": "Commit veranderingen met de git editor",
"FindBaseCommitForFixupTooltip": "Vind de commit waar je huidige wijzigingen bovenop zijn gebouwd met als doel die commit te amenden/fixen. Hierdoor hoef je dit niet met de hand te doen. Zie: <https://github.com/jesseduffield/lazygit/tree/master/docs/Fixup_Commits.md>",
"BaseCommitIsNotInCurrentView": "Basis commit is niet zichtbaar",
"StatusTitle": "Status",
"GlobalTitle": "Globale sneltoetsen",
"Execute": "Uitvoeren",
"Stage": "Toggle staged",
"ToggleStagedAll": "Toggle staged alle",
"ToggleTreeView": "Toggle bestandsboom weergave",
"OpenDiffTool": "Open externe diff applicatie (git difftool)",
"OpenMergeTool": "Open externe merge applicatie",
"Refresh": "Verversen",
"Push": "Push",
"Pull": "Pull",
"PushTooltip": "Push de huidige branch naar de bijbehorende upstream-branch. Als er geen upstream is geconfigureerd wordt er gevraagd om een upstream-branch te configureren.",
"PullTooltip": "Pull wijzigingen van de remote voor de huidige branch. Als er geen upstream is geconfigureerd wordt er gevraagd om een upstream-branch te configureren.",
"FileFilter": "Filter bestanden op status",
"CopyToClipboardMenu": "Kopieer naar klembord",
"CopyFileName": "Bestandsnaam",
"CopyRelativeFilePath": "Relatief pad",
"CopyAbsoluteFilePath": "Absoluut pad",
"CopyFileDiffTooltip": "Als er gestagede items zijn neemt dit commando alleen deze items mee. Zo niet, neemt het alle niet-gestagede items mee.",
"CopySelectedDiff": "Diff van geselecteerde bestand",
"CopyAllFilesDiff": "Diff van alle bestanden",
"CopyFileContent": "Inhoud van geselecteerde bestand",
"NoContentToCopyError": "Er is niks om te kopiëren",
"FileNameCopiedToast": "Bestandsnaam gekopieerd naar klembord",
"FilePathCopiedToast": "Bestandspad gekopieerd naar klembord",
"FileDiffCopiedToast": "Diff van bestand gekopieerd naar klembord",
"AllFilesDiffCopiedToast": "Diff van alle bestanden gekopieerd naar klembord",
"FileContentCopiedToast": "Bestandsinhoud gekopieerd naar klembord",
"FilterStagedFiles": "Toon alleen gestagede bestanden",
"FilterUnstagedFiles": "Toon alleen niet-gestagede bestanden",
"FilterTrackedFiles": "Toon alleen getrackte bestanden",
"FilterUntrackedFiles": "Toon alleen niet-getrackte bestanden",
"NoFilter": "Geen filter",
"FilterLabelStagedFiles": "(alleen gestaged)",
"FilterLabelUnstagedFiles": "(alleen niet-gestaged)",
"FilterLabelTrackedFiles": "(alleen getrackt)",
"FilterLabelUntrackedFiles": "(alleen niet-getrackt)",
"FilterLabelConflictingFiles": "(alleen conflicten)",
"MergeConflictsTitle": "Merge conflicten",
"MergeConflictDescription_UD": "Conflict: dit bestand is gewijzigd in de current changes en verwijderd in incoming changes.\n\nDe meest waarschijnlijke oplossing is om dit bestand te verwijderen nadat de current changes wijzigingen handmatig zijn toegepast op een andere plaats in de code.",
"MergeConflictIncomingDiff": "Inkomende wijziging:",
"MergeConflictCurrentDiff": "Huidige wijzigingen:",
"MergeConflictPressEnterToResolve": "Druk op %s om op te lossen.",
"MergeConflictKeepFile": "Behoud bestanden",
"MergeConflictDeleteFile": "Bestand verwijderen",
"Checkout": "Uitchecken",
"CheckoutTooltip": "Geselecteerd item uitchecken.",
"CantCheckoutBranchWhilePulling": "Je kan geen andere branch uitchecken tijdens het pullen van de huidige branch",
"TagCheckoutTooltip": "Geselecteerde tag uitchecken als detached HEAD.",
"RemoteBranchCheckoutTooltip": "Geselecteerde remote branch uitchecken als nieuwe locale branch of als detached head.",
"NoChangedFiles": "Geen veranderde bestanden",
"SoftReset": "Zacht reset",
"AlreadyCheckedOutBranch": "Je hebt deze branch al uitgecheckt",
@@ -37,54 +88,94 @@
"BranchName": "Branch naam",
"NewBranchNameBranchOff": "Nieuw branch naam (Branch is afgeleid van '{{.branchName}}')",
"CantDeleteCheckOutBranch": "Je kan een uitgecheckte branch niet verwijderen!",
"DeleteBranchTitle": "Verwijder branch '{{.selectedBranchName}}'?",
"DeleteBranchesTitle": "Geselecteerde branches verwijderen?",
"DeleteLocalBranch": "Lokale branch verwijderen",
"DeleteLocalBranches": "Lokale branches verwijderen",
"DeleteRemoteBranchPrompt": "Weet je zeker dat je de remote branch '{{.selectedBranchName}}' wilt verwijderen uit '{{.upstream}}'?",
"ForceDeleteBranchTitle": "Forceer verwijderen van branch",
"ForceDeleteBranchMessage": "Weet je zeker dat je branch '{{.selectedBranchName}}' geforceerd wil verwijderen?",
"RebaseBranch": "Rebase branch",
"RebaseBranchTooltip": "Rebase de uitgecheckte branch bovenop de geselecteerde branch.",
"CantRebaseOntoSelf": "Je kan niet een branch rebasen op zichzelf",
"CantMergeBranchIntoItself": "Je kan niet een branch in zichzelf mergen",
"ForceCheckout": "Forceer checkout",
"CheckoutByName": "Uitchecken bij naam",
"CheckoutPreviousBranch": "Vorige branch uitchecken",
"RemoteBranchCheckoutTitle": "{{.branchName}} uitchecken",
"RemoteBranchCheckoutPrompt": "Hoe wil je deze branch uitchecken?",
"CheckoutTypeNewBranch": "Nieuwe lokale branch",
"CheckoutTypeDetachedHead": "Detached head",
"NewBranch": "Nieuwe branch",
"MoveCommitsToNewBranch": "Verplaats commits naar nieuwe branch",
"MoveCommitsToNewBranchTooltip": "Maak een nieuwe branch en verplaats niet-gepushte commits van de huidige branch hier naar toe. Gebruik dit in het geval dat je deze commits eigenlijk op een nieuwe branch had willen maken.\n\nLet op dat de selectie genegeerd wordt. De nieuwe branch komt ofwel bovenop de main branch, of bovenop de huidige branch (je kan kiezen).",
"CannotMoveCommitsFromDetachedHead": "Kan geen commits verplaatsen van een detached head",
"CannotMoveCommitsNoUpstream": "Kan geen commits verplaatsen vanaf een branch die geen upstream-branch heeft",
"CannotMoveCommitsBehindUpstream": "Kan geen commits verplaatsen van een branch die achterloopt zijn upstream-branch",
"NoBranchesThisRepo": "Geen branches voor deze repo",
"CommitWithoutMessageErr": "Je kan geen commit maken zonder commit bericht",
"Close": "Sluiten",
"CloseCancel": "Sluiten",
"Confirm": "Bevestig",
"Quit": "Afsluiten",
"Fixup": "Fixup",
"SureSquashThisCommit": "Weet je zeker dat je deze commit wil samenvoegen met de commit hieronder?",
"Squash": "Squash",
"PickCommitTooltip": "Kies commit (wanneer midden in rebase)",
"Reword": "Hernoem commit",
"DropCommit": "Verwijder commit",
"MoveDownCommit": "Verplaats commit 1 naar beneden",
"MoveUpCommit": "Verplaats commit 1 naar boven",
"CannotMoveAnyFurther": "Kan niet verder verplaatsen",
"CannotMoveMergeCommit": "Kan een merge commit niet verplaatsen",
"EditCommitTooltip": "Wijzig commit",
"AmendCommitTooltip": "Wijzig commit met staged veranderingen",
"AddCoAuthor": "Voeg co-auteur toe",
"RewordCommitEditor": "Hernoem commit met editor",
"NoCommitsThisBranch": "Geen commits in deze branch",
"ExecCommandHere": "Voer het volgende commando hier uit:",
"Error": "Foutmelding",
"Undo": "Ongedaan maken",
"UndoReflog": "Ongedaan maken (via reflog) (experimenteel)",
"RedoReflog": "Redo (via reflog) (experimenteel)",
"DiscardAllTooltip": "Verwijder zowel gestagede als niet-gestagede wijzigingen in '{{.path}}'.",
"DiscardUnstagedTooltip": "Verwijder niet-gestagede wijzigingen in '{{.path}}'.",
"DiscardUnstagedDisabled": "De geselecteerde items hebben geen mix van gestagede en niet-gestagede wijzigingen.",
"Pop": "Pop",
"Drop": "Laten vallen",
"Apply": "Toepassen",
"NoStashEntries": "Geen stash items",
"StashDrop": "Stash laten vallen",
"SureDropStashEntry": "Weet je het zeker dat je de geselecteerde stash(es) wilt verwijderen?",
"StashPop": "Stash poppen",
"SurePopStashEntry": "Weet je zeker dat je deze stash entry wil poppen?",
"StashApply": "Stash toepassen",
"SureApplyStashEntry": "Weet je zeker dat je deze stash entry wil toepassen?",
"NoTrackedStagedFilesStash": "Je hebt geen tracked/staged bestanden om te laten stashen",
"NoFilesToStash": "Je hebt geen bestanden om te stashen",
"StashChanges": "Stash veranderingen",
"OpenConfig": "Open config bestand",
"RenameStash": "Hernoem stash",
"RenameStashPrompt": "Hernoem stash: {{.stashName}}",
"EditConfig": "Verander config bestand",
"ForcePush": "Forceer push",
"ForcePushPrompt": "Je branch is afgeweken van de remote branch. Druk {{.cancelKey}} om te annuleren, of {{.confirmKey}} om geforceerd te pushen.",
"CheckForUpdate": "Check voor updates",
"CheckingForUpdates": "Zoeken naar updates...",
"UpdateAvailableTitle": "Update beschikbaar!",
"FailedToRetrieveLatestVersionErr": "Ophalen versie-informatie mislukt",
"OnLatestVersionErr": "Je hebt al de laatste versie",
"MajorVersionErr": "Nieuwe versie ({{.newVersion}}) is niet backwards compatibele vergeleken met de huidige versie ({{.currentVersion}})",
"CouldNotFindBinaryErr": "Kon geen binary vinden op {{.url}}",
"ConfirmQuitDuringUpdate": "Er is een update bezig. Weet je zeker dat je wilt afsluiten?",
"IntroPopupMessage": "\nBedankt voor het gebruik van lazygit! Je bent een kanjer. Deze vier dingen wil ik met je delen:\n\n 1) Als je meer wilt weten over lazygit's features, kijk dan deze video:\n https://youtu.be/CPLdltN7wgE\n\n 2) Lees de laatste release notes hier:\n https://github.com/jesseduffield/lazygit/releases\n\n 3) Als je git gebruikt, dan ben je een programmeur! Met jouw hulp kunnen we\n lazygit beter maken, dus overweeg mee te helpen met coden op\n https://github.com/jesseduffield/lazygit\n Of geef het repo een ster om te laten zien dat je het leuk vindt!\n\n 4) Als lazygit je leven makkelijker heeft gemaakt kan je \"dank je wel\" zeggen door\n op de donatie knop rechtsonder te drukken. Doneren geeft geen recht op voorrang bij ondersteuning\n maar wordt wel zeer gewaardeerd.\n\nDruk op {{confirmationKey}} om te beginnen.\n",
"GitconfigParseErr": "Gogit kon je gitconfig bestand niet goed parsen door de aanwezigheid van losstaande '\\' tekens. Het weghalen van deze tekens zou het probleem moeten oplossen. ",
"EditFile": "Verander bestand",
"EditFileTooltip": "Open bestand in externe editor.",
"OpenFile": "Open bestand",
"OpenFileTooltip": "Open bestand in standaardapplicatie.",
"OpenInEditor": "Openen in editor",
"IgnoreFile": "Voeg toe aan .gitignore",
"ExcludeFile": "Toevoegen aan .git/info/exclude",
"RefreshFiles": "Refresh bestanden",
"Merge": "Merge in met huidige checked out branch",
"ConfirmQuit": "Weet je zeker dat je dit programma wil sluiten?",
@@ -92,6 +183,8 @@
"UnsupportedGitService": "Niet-ondersteunde git-service",
"CopyPullRequestURL": "Kopieer de URL van het pull-verzoek naar het klembord",
"NoBranchOnRemote": "Deze branch bestaat niet op de remote. U moet het eerst naar de remote pushen.",
"ExpandAll": "Vouw alle bestanden uit",
"ExpandAllTooltip": "Vouw alle mappen in de bestandsstructuur uit",
"FileEnter": "Stage individuele hunks/lijnen",
"StageSelectionTooltip": "Toggle lijnen staged / unstaged",
"DiscardSelection": "Verwijdert change (git reset)",
@@ -100,26 +193,56 @@
"ReturnToFilesPanel": "Ga terug naar het bestanden paneel",
"FastForward": "Fast-forward deze branch vanaf zijn upstream",
"FoundConflictsTitle": "Conflicten!",
"ViewConflictsMenuItem": "Toon conflicten",
"AbortMenuItem": "Breek %s af",
"PickHunk": "Kies stuk",
"PickAllHunks": "Kies beide stukken",
"ViewMergeRebaseOptions": "Bekijk merge/rebase opties",
"ViewMergeRebaseOptionsTooltip": "Toon abort/continue/skip opties voor huidige merge/rebase.",
"ViewMergeOptions": "Toon merge opties",
"ViewRebaseOptions": "Toon rebase opties",
"ViewCherryPickOptions": "Toon cherry-pick opties",
"ViewRevertOptions": "Toon revert opties",
"NotMergingOrRebasing": "Je bent momenteel niet aan het rebasen of mergen",
"AlreadyRebasing": "Deze actie kan niet worden uitgevoerd tijdens een rebase",
"NotMidRebase": "Deze actie werkt alleen tijdens een interactieve rebase",
"MustSelectFixupCommit": "Deze actie werkt alleen op fixup commits",
"RecentRepos": "Recente repositories",
"MergeOptionsTitle": "Merge opties",
"RebaseOptionsTitle": "Rebase opties",
"CherryPickOptionsTitle": "Cherry-pick opties",
"RevertOptionsTitle": "Revert opties",
"CommitSummaryTitle": "Commit bericht",
"CommitDescriptionTitle": "Commit beschrijving",
"LocalBranchesTitle": "Branches",
"SearchTitle": "Zoek",
"TagsTitle": "Tags",
"MenuTitle": "Menu",
"CommitMenuTitle": "Commit Menu",
"RemotesTitle": "Remotes",
"RemoteBranchesTitle": "Remote branches",
"PatchBuildingTitle": "Patch bouwen",
"InformationTitle": "Informatie",
"ReflogCommitsTitle": "Reflog",
"ConflictsResolved": "Alle mergeconflicten zijn opgelost. Doorgaan met de %s?",
"Continue": "Doorgaan",
"UnstagedFilesAfterConflictsResolved": "Er zijn bestanden gewijzigd nadat de mergeconflicten opgelost waren. Deze bestanden stagen en doorgaan?",
"RebasingTitle": "Rebase '{{.checkedOutBranch}}'",
"SimpleRebase": "Simpele rebase op '{{.ref}}'",
"InteractiveRebase": "Interactieve rebase op '{{.ref}}'",
"RebaseOntoBaseBranch": "Rebase op basis branch ({{.baseBranch}})",
"FwdNoUpstream": "Kan niet de branch vooruitspoelen zonder upstream",
"FwdCommitsToPush": "Je kan niet vooruitspoelen als de branch geen nieuwe commits heeft",
"ErrorOccurred": "Er is iets fout gegaan! Zou je hier een issue aan willen maken",
"ConflictLabel": "CONFLICT",
"CommitsSectionHeader": "Commits",
"YouDied": "JE BENT DOOD!",
"RewordNotSupported": "Herformatteren van commits in interactief rebasen is nog niet ondersteund",
"CherryPickCopy": "Kopieer commit (cherry-pick)",
"PasteCommits": "Plak commits (cherry-pick)",
"SureCherryPick": "Weet je zeker dat je de {{.numCommits}} gekopieerde commit(s) naar deze branch wilt cherry-picken?",
"CherryPick": "Cherry-Pick",
"Donate": "Doneer",
"AskQuestion": "Stel vraag",
"PrevHunk": "Selecteer de vorige hunk",
"NextHunk": "Selecteer de volgende hunk",
"PrevConflict": "Selecteer voorgaand conflict",
@@ -130,8 +253,10 @@
"ScrollUp": "Scroll omhoog",
"ScrollUpMainWindow": "Scroll naar beneden vanaf hoofdpaneel",
"ScrollDownMainWindow": "Scroll naar beneden vanaf hoofdpaneel",
"SuspendApp": "Pauzeer de applicatie",
"AmendCommitTitle": "Commit wijzigen",
"AmendCommitPrompt": "Weet je zeker dat je deze commit wil wijzigen met de vorige staged bestanden?",
"AmendCommitWithConflictsContinue": "Nee, doorgaan met rebase",
"DropCommitTitle": "Verwijder commit",
"DropCommitPrompt": "Weet je zeker dat je deze commit wil verwijderen?",
"PullingStatus": "Pullen",
@@ -145,12 +270,15 @@
"CherryPickingStatus": "Cherry-picken",
"UndoingStatus": "Ongedaan maken",
"CheckingOutStatus": "Uitchecken",
"RevertingStatus": "Bezig met reverten",
"CommitFiles": "Commit bestanden",
"ViewItemFiles": "Bekijk gecommite bestanden",
"CommitFilesTitle": "Commit bestanden",
"CheckoutCommitFileTooltip": "Bestand uitchecken",
"Remove": "Verwijderen",
"DiscardOldFileChangeTooltip": "Uitsluit deze commit zijn veranderingen aan dit bestand",
"DiscardFileChangesTitle": "Uitsluit bestand zijn veranderingen",
"CreateRepo": "Niet in een git repository. Maak een nieuwe git repository? (y/N): ",
"AutoStashPrompt": "Je moet je veranderingen stashen en poppen om ze over te brengen. Dit automatisch doen? (enter/esc)",
"Discard": "Bekijk 'veranderingen ongedaan maken' opties",
"Cancel": "Annuleren",
@@ -160,6 +288,8 @@
"DiscardAnyUnstagedChanges": "Gooi unstaged wijzigingen weg",
"DiscardUntrackedFiles": "Negeer niet-gevonden bestanden",
"HardReset": "Harde reset",
"Delete": "Verwijderen",
"Reset": "Resetten",
"ViewResetOptions": "Bekijk reset opties",
"CreateFixupCommit": "Creëer fixup commit",
"CreateFixupCommitTooltip": "Creëer fixup commit",
@@ -172,6 +302,8 @@
"StashAllChangesKeepIndex": "Stash staged wijzigingen",
"StashOptions": "Stash opties",
"NotARepository": "Fout: moet in een git repository uitgevoerd worden",
"ScrollLeft": "Scroll naar links",
"ScrollRight": "Scroll naar rechts",
"DiscardPatch": "Patch weg gooien",
"DiscardPatchConfirm": "Je kan alleen maar een patch bouwen van 1 commit. Huidige patch weggooien?",
"CantPatchWhileRebasingError": "Je kan geen patch bouwen of patch commando uitvoeren wanneer je in een merging of rebasing state zit",
@@ -185,12 +317,16 @@
"NewRemote": "Voeg een nieuwe remote toe",
"NewRemoteName": "Nieuwe remote name:",
"NewRemoteUrl": "Nieuwe remote url:",
"ViewBranches": "Bekijk branches",
"EditRemoteName": "Enter updated remote naam voor {{.remoteName}}:",
"EditRemoteUrl": "Enter updated remote url voor {{.remoteName}}:",
"RemoveRemote": "Verwijder remote",
"DeleteRemoteBranch": "Verwijder remote branch",
"SetAsUpstream": "Instellen als upstream",
"SetAsUpstreamTooltip": "Stel in als upstream van uitgecheckte branch",
"SetUpstream": "Stel in als upstream van uitgecheckte branch",
"DivergenceSectionHeaderLocal": "Lokaal",
"DivergenceSectionHeaderRemote": "Remote",
"SetUpstreamTitle": "Stel in als upstream branch",
"EditRemoteTooltip": "Wijzig remote",
"TagNameTitle": "Tag naam:",
@@ -207,6 +343,7 @@
"PrevScreenMode": "Vorige scherm modus",
"StartSearch": "Start met zoeken",
"Keybindings": "Sneltoetsen",
"KeybindingsMenuSectionGlobal": "Algemeen",
"RenameBranch": "Hernoem branch",
"NewGitFlowBranchPrompt": "Nieuwe '{{.branchType}}' naam:",
"RenameBranchWarning": "Deze branch volgt een remote. Deze actie zal alleen de locale branch name wijzigen niet de naam van de remote branch. Verder gaan?",
@@ -262,8 +399,54 @@
"CreatePullRequest": "Maak een pull-request",
"ConfirmRevertCommit": "Weet u zeker dat u {{.selectedCommit}} ongedaan wilt maken?",
"ToggleRangeSelect": "Toggle drag selecteer",
"Actions": {},
"Actions": {
"CopyCommitAuthorToClipboard": "Kopieer commit auteur naar klembord",
"CopyCommitAttributeToClipboard": "Kopieer naar klembord",
"CopyCommitTagsToClipboard": "Kopieer commit tags naar klembord",
"CopyPatchToClipboard": "Kopieer patch naar klembord",
"Commit": "Commit",
"Push": "Push",
"Pull": "Pull",
"OpenFile": "Open bestand",
"CopyToClipboard": "Kopieer naar klembord",
"CopySelectedTextToClipboard": "Kopieer geselecteerde tekst naar klembord",
"AddRemote": "Voeg remote toe",
"RemoveSubmodule": "Verwijder submodule",
"ResetSubmodule": "Reset submodule",
"AddSubmodule": "Voeg submodule toe",
"UpdateSubmoduleUrl": "Update submodule URL",
"InitialiseSubmodule": "Initialiseer submodule",
"UpdateSubmodule": "Update submodule",
"NukeWorkingTree": "Blaas de working tree op met een kernbom",
"RemoveUntrackedFiles": "Verwijder niet-getrackte bestanden",
"SoftReset": "Soft reset",
"MixedReset": "Mixed reset",
"HardReset": "Hard reset",
"Undo": "Ongedaan maken",
"Redo": "Herhalen",
"OpenCommitInBrowser": "Open commit in browser",
"OpenPullRequest": "Open pull request in browser",
"AddWorktree": "Voeg worktree toe"
},
"Bisect": {},
"Log": {},
"BreakingChangesByVersion": {}
"Log": {
"RemoveFile": "Verwijder pad '{{.path}}'",
"RemoveEmptyDir": "Verwijder de lege map '{{.path}}'",
"CopyToClipboard": "Kopieer '{{.str}}' naar klembord",
"Remove": "Verwijder '{{.filename}}'",
"CreateFileWithContent": "Maak bestand '{{.path}}'",
"AppendingLineToFile": "Voeg {{.line}}' toe aan bestand '{{.filename}} '",
"EditRebaseFromBaseCommit": "Begin een interactieve rebase van '{{.baseCommit}}' op '{{.targetBranchName}}'",
"DroppingStash": "Verwijder stash %s",
"PoppingStash": "Pop stash %s",
"DeletingBranch": "Verwijder branch '{{.branchName}}' (was {{.hash}})"
},
"BreakingChangesByVersion": {},
"ViewMergeConflictOptions": "Bekijk merge conflict opties",
"ViewMergeConflictOptionsTooltip": "Bekijk opties voor het oplossen van mergeconflicten.",
"NoFilesWithMergeConflicts": "Er zijn geen files met mergeconflicten.",
"MergeConflictOptionsTitle": "Los mergeconflicten op",
"UseCurrentChanges": "Gebruik huidige wijzigingen",
"UseIncomingChanges": "Gebruik binnenkomende wijzigingen",
"UseBothChanges": "Gebruik beide"
}
-8
View File
@@ -187,7 +187,6 @@
"StashChanges": "Schowaj zmiany",
"RenameStash": "Zmień nazwę schowka",
"RenameStashPrompt": "Zmień nazwę schowka: {{.stashName}}",
"OpenConfig": "Otwórz plik konfiguracyjny",
"EditConfig": "Edytuj plik konfiguracyjny",
"ForcePush": "Wymuś wysłanie",
"ForcePushPrompt": "Twoja gałąź rozbiegła się z gałęzią zdalną. Naciśnij {{.cancelKey}}, aby anulować, lub {{.confirmKey}}, aby wymusić wysłanie.",
@@ -244,7 +243,6 @@
"ViewConflictsMenuItem": "Pokaż konflikty",
"AbortMenuItem": "Przerwij %s",
"PickHunk": "Wybierz fragment",
"PickAllHunks": "Wybierz wszystkie fragmenty",
"ViewMergeRebaseOptions": "Pokaż opcje scalania/rebase",
"ViewMergeRebaseOptionsTooltip": "Pokaż opcje do przerwania/kontynuowania/pominięcia bieżącego scalania/rebase.",
"ViewMergeOptions": "Pokaż opcje scalania",
@@ -681,7 +679,6 @@
"DetachingWorktree": "Odłączanie drzewa pracy",
"WorktreesTitle": "Drzewa pracy",
"WorktreeTitle": "Drzewo pracy",
"RemoveWorktreePrompt": "Czy na pewno chcesz usunąć drzewo pracy '{{.worktreeName}}'?",
"RemovingWorktree": "Usuwanie drzewa pracy",
"AddingWorktree": "Dodawanie drzewa pracy",
"CantDeleteCurrentWorktree": "Nie możesz usunąć bieżącego drzewa pracy!",
@@ -691,13 +688,8 @@
"MissingWorktree": "(brakujące)",
"NewWorktree": "Nowe drzewo pracy",
"NewWorktreePath": "Nowa ścieżka drzewa pracy",
"NewWorktreeBase": "Nowa bazowa ref drzewa pracy",
"RemoveWorktreeTooltip": "Usuń wybrane drzewo pracy. To usunie zarówno katalog drzewa pracy, jak i metadane o drzewie pracy w katalogu .git.",
"NewBranchName": "Nowa nazwa brancha",
"NewBranchNameLeaveBlank": "Nowa nazwa brancha (pozostaw puste, aby przełączyć {{.default}})",
"ViewWorktreeOptions": "Zobacz opcje drzewa pracy",
"CreateWorktreeFrom": "Utwórz drzewo pracy z {{.ref}}",
"CreateWorktreeFromDetached": "Utwórz drzewo pracy z {{.ref}} (odłączone)",
"LcWorktree": "drzewo pracy",
"ChangingDirectoryTo": "Zmiana katalogu na {{.path}}",
"Name": "Nazwa",
-5
View File
@@ -206,7 +206,6 @@
"StashChanges": "Alterações preparadas",
"RenameStash": "Renomear o stash",
"RenameStashPrompt": "Renomear o estoque: {{.stashName}}",
"OpenConfig": "Abrir o ficheiro de config",
"EditConfig": "Editar arquivo de configuração",
"ForcePush": "Forçar push",
"ForcePushPrompt": "Seu branch divergiu do branch remoto. Pressione {{.cancelKey}} para cancelar, ou {{.confirmKey}} para forçar a push.",
@@ -279,7 +278,6 @@
"ViewConflictsMenuItem": "Visualizar conflitos",
"AbortMenuItem": "Abortar %s",
"PickHunk": "Escolha o local",
"PickAllHunks": "Pegar todos os pedaços",
"ViewMergeRebaseOptions": "Ver opções de mesclar/rebase",
"ViewMergeRebaseOptionsTooltip": "Ver opções para abortar/continuar/pular o merge/rebase atual.",
"ViewMergeOptions": "Visualizar opções de merge",
@@ -639,9 +637,6 @@
"MainWorktree": "(árvore de trabalho principal)",
"NewWorktree": "Nova árvore de trabalho",
"NewWorktreePath": "Caminho da nova árvore de trabalho",
"ViewWorktreeOptions": "Ver opções da árvore de trabalho",
"CreateWorktreeFrom": "Criar árvore de trabalho a partir de {{.ref}}",
"CreateWorktreeFromDetached": "Criar árvore de trabalho a partir de {{.ref}} (desanexado)",
"LcWorktree": "árvore de trabalho",
"Name": "Nome",
"Path": "Caminho",
-2
View File
@@ -106,7 +106,6 @@
"StashChanges": "Припрятать изменения",
"RenameStash": "Переименовать хранилище",
"RenameStashPrompt": "Переименовать хранилище: {{.stashName}}",
"OpenConfig": "Открыть файл конфигурации",
"EditConfig": "Редактировать файл конфигурации",
"ForcePush": "Принудительная отправка изменении",
"ForcePushPrompt": "Ветка отклонилась от удалённой ветки. Нажмите «esc», чтобы отменить, или «enter», чтобы начать принудительную отправку изменении.",
@@ -152,7 +151,6 @@
"ViewConflictsMenuItem": "Просмотр конфликтов",
"AbortMenuItem": "Прервать %s",
"PickHunk": "Выбрать эту часть",
"PickAllHunks": "Выбрать все части",
"ViewMergeRebaseOptions": "Просмотреть параметры слияния/перебазирования",
"NotMergingOrRebasing": "В данный момент вы не выполняете ни перебазирования, ни слияние",
"AlreadyRebasing": "Невозможно выполнить это действие во время перебазирования",
+2 -9
View File
@@ -219,7 +219,6 @@
"StashChanges": "贮藏变更",
"RenameStash": "重命名贮藏",
"RenameStashPrompt": "重命名贮藏: {{.stashName}}",
"OpenConfig": "打开配置文件",
"EditConfig": "编辑配置文件",
"ForcePush": "强制推送",
"ForcePushPrompt": "您的分支已与远程分支不同。按‘esc’取消,或‘enter’强制推送.",
@@ -305,7 +304,6 @@
"ViewConflictsMenuItem": "查看冲突",
"AbortMenuItem": "中止 %s",
"PickHunk": "选中区块",
"PickAllHunks": "选中所有区块",
"ViewMergeRebaseOptions": "查看合并/变基选项",
"ViewMergeRebaseOptionsTooltip": "查看当前合并或变基的中止、继续、跳过选项",
"ViewMergeOptions": "查看合并选项",
@@ -855,7 +853,6 @@
"DetachingWorktree": "正在分离工作树",
"WorktreesTitle": "工作区",
"WorktreeTitle": "工作区",
"RemoveWorktreePrompt": "您确定要删除工作树 {{.worktreeName}}' ?",
"ForceRemoveWorktreePrompt": "'{{.worktreeName}}' 包含已修改或未跟踪的文件,或子模块(或包含所有这些)。确定要移除它吗?",
"RemovingWorktree": "正在删除工作树",
"AddingWorktree": "添加工作区",
@@ -867,13 +864,8 @@
"MainWorktree": "(主工作树)",
"NewWorktree": "新建工作树",
"NewWorktreePath": "新建工作树路径",
"NewWorktreeBase": "新建工作树基于ref",
"RemoveWorktreeTooltip": "删除选定的工作树。这将删除工作树的目录以及 .git 目录中有关工作树的元数据。",
"NewBranchName": "新分支名称",
"NewBranchNameLeaveBlank": "新分支名称(为空则默认检出为 {{.default}})",
"ViewWorktreeOptions": "查看工作区选项",
"CreateWorktreeFrom": "从 {{.ref}} 创建工作树",
"CreateWorktreeFromDetached": "从 {{.ref}} 创建工作树(分离)",
"LcWorktree": "工作区",
"ChangingDirectoryTo": "将目录更改为 {{.path}}",
"Name": "名称",
@@ -1068,7 +1060,8 @@
"0.50.0": "- 拉取后,如果主分支落后于其上游分支,现在会自动前推。这对于自动保持主分支或 master 分支最新很有用。如果不希望这样,可以通过在配置中设置以下内容来禁用它:\n\ngit:\n autoForwardBranches: none\n\n相反,如果希望功能分支也这样做,可以将其设置为 'allBranches'。",
"0.51.0": "- 自定义命令的 'subprocess'、'stream' 和 'showOutput' 字段已被替换为单个 'output' 字段。这应该是透明的,如果您在配置文件中使用了这些字段,它们应该已自动更新。但有一个显著变化:'stream' 字段过去意味着命令输出将流式传输到命令日志,并且命令将在伪终端 (pty) 中运行。我们将其转换为 'output: log',这意味着命令输出将流式传输到命令日志,但不使用 pty,假设这是大多数人想要的。如果您确实希望在 pty 中运行命令,可以将其更改为 'output: logWithPty'。",
"0.54.0": "- 本地和远程分支的默认排序顺序已更改:过去本地分支是 'recency'(基于 reflog),远程分支是 'alphabetical'。这两者都已更改为 'date'(即提交者日期)。如果您更喜欢旧的默认设置,可以通过以下配置恢复:\n\ngit:\n localBranchSortOrder: recency\n remoteBranchSortOrder: alphabetical\n\n- 暂存区和自定义补丁构建视图中的默认选择模式已更改为块模式。在大多数情况下,这是更有用的模式,因为它通常可以节省大量按键。如果想切换回旧的行模式默认设置,可以通过在配置中添加以下内容来实现:\n\ngui:\n useHunkModeInStagingView: false\n",
"0.55.0": "- 原先绑定到 ctrl-z 的 'redo' 命令,现在改为绑定到 shift-Z。这是因为 ctrl-z 现在用于挂起应用程序;在 Linux 世界中,这是该功能的常用键绑定。如果你想恢复此更改,可以在配置中添加以下内容:\n\nkeybinding:\n universal:\n suspendApp: <disabled>\n redo: <ctrl+z>\n\n- 'git.paging.useConfig' 选项已被移除。如果你之前依赖它来配置你的分页器,现在必须使用 'git.paging.pager' 选项重新明确设置分页器。"
"0.55.0": "- 原先绑定到 ctrl-z 的 'redo' 命令,现在改为绑定到 shift-Z。这是因为 ctrl-z 现在用于挂起应用程序;在 Linux 世界中,这是该功能的常用键绑定。如果你想恢复此更改,可以在配置中添加以下内容:\n\nkeybinding:\n universal:\n suspendApp: <disabled>\n redo: <ctrl+z>\n\n- 'git.paging.useConfig' 选项已被移除。如果你之前依赖它来配置你的分页器,现在必须使用 'git.paging.pager' 选项重新明确设置分页器。",
"0.62.0": "从提交描述编辑器提交变更的默认快捷键已从 Mac 上的 alt-enter 改为 command-enter,在 Linux 和 Windows 上改为 ctrl-enter;这些和很多多行编辑框里用的快捷键一样,比如 GitHub 评论里用的那种。很遗憾,并非所有终端都支持这些快捷键;更多说明见:https://github.com/jesseduffield/lazygit/blob/master/docs/keybindings/Custom_Keybindings.md#terminal-compatibility。如果你想恢复这个改动,可以在配置里加上:\n\nkeybinding:\n universal:\n confirmInEditor: <a-enter>\n"
},
"ViewMergeConflictOptions": "查看合并冲突选项",
"ViewMergeConflictOptionsTooltip": "查看用于解决合并冲突的选项。",
-8
View File
@@ -128,7 +128,6 @@
"StashChanges": "安置現有變更到收藏中",
"RenameStash": "重新命名收藏",
"RenameStashPrompt": "重新命名收藏:{{.stashName}}",
"OpenConfig": "開啟設定檔案",
"EditConfig": "編輯設定檔案",
"ForcePush": "強制推送",
"ForcePushPrompt": "你的分支與遠端分支分岔。按 'ESC' 取消,或按 'Enter' 強制推送。",
@@ -179,7 +178,6 @@
"ViewConflictsMenuItem": "檢視衝突",
"AbortMenuItem": "中止%s",
"PickHunk": "挑選程式碼片段",
"PickAllHunks": "挑選所有程式碼片段",
"ViewMergeRebaseOptions": "查看合併/變基選項",
"ViewRebaseOptions": "查看合併/變基選項",
"NotMergingOrRebasing": "你當前既不在變基也不在合併中",
@@ -528,7 +526,6 @@
"DetachingWorktree": "正在解除工作目錄連結",
"WorktreesTitle": "工作目錄",
"WorktreeTitle": "工作目錄",
"RemoveWorktreePrompt": "是否刪除 {{.worktreeName}} 工作目錄?",
"RemovingWorktree": "正在刪除工作目錄",
"AddingWorktree": "正在建立工作目錄",
"CantDeleteCurrentWorktree": "無法刪除當前工作目錄!",
@@ -537,12 +534,7 @@
"NoWorktreesThisRepo": "無工作目錄",
"MissingWorktree": "(失蹤)",
"NewWorktreePath": "工作目錄路徑",
"NewWorktreeBase": "工作目錄來源",
"NewBranchName": "分支名稱",
"NewBranchNameLeaveBlank": "分支名稱(留空將檢出 {{.default}})",
"ViewWorktreeOptions": "檢視工作目錄選項",
"CreateWorktreeFrom": "從 {{.ref}} 建立工作目錄",
"CreateWorktreeFromDetached": "從 {{.ref}} 建立工作目錄(未連結)",
"LcWorktree": "工作目錄",
"ChangingDirectoryTo": "切換至 {{.path}}",
"Name": "名稱",
-12
View File
@@ -4,7 +4,6 @@ import (
"fmt"
"time"
"github.com/atotto/clipboard"
"github.com/jesseduffield/lazygit/pkg/config"
integrationTypes "github.com/jesseduffield/lazygit/pkg/integration/types"
)
@@ -125,17 +124,6 @@ func (self *TestDriver) ExpectToast(matcher *TextMatcher) *TestDriver {
return self
}
func (self *TestDriver) ExpectClipboard(matcher *TextMatcher) {
self.assertWithRetries(func() (bool, string) {
text, err := clipboard.ReadAll()
if err != nil {
return false, "Error occurred when reading from clipboard: " + err.Error()
}
ok, _ := matcher.test(text)
return ok, fmt.Sprintf("Expected clipboard to match %s, but got %s", matcher.name(), text)
})
}
func (self *TestDriver) ExpectSearch() *SearchDriver {
self.inSearch()
@@ -0,0 +1,57 @@
package commit
import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)
var DiscardRenamedFile = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Discard a renamed file from an old commit; both the new and the old path are handled so the rename is undone",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {},
SetupRepo: func(shell *Shell) {
shell.CreateFileAndAdd("original", "line1\nline2\nline3\nline4\nline5\n")
shell.CreateFileAndAdd("other", "other content\n")
shell.Commit("first commit")
shell.RenameFileInGit("original", "renamed")
shell.UpdateFileAndAdd("renamed", "line1\nline2 changed\nline3\nline4\nline5\n")
shell.Commit("rename with modification")
},
Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("rename with modification").IsSelected(),
Contains("first commit"),
).
PressEnter()
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("original → renamed").IsSelected(),
).
Press(keys.Universal.Remove)
t.ExpectPopup().Confirmation().
Title(Equals("Discard file changes")).
Content(Contains("Are you sure you want to discard changes to the selected file(s) from this commit?")).
Confirm()
// The rename is undone: the commit no longer touches any file. (If only
// the new path were discarded, the commit would still delete the old
// path and show "D original" here instead.)
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("(none)"),
).
PressEscape()
// The working tree is clean; the original file is back at HEAD.
t.Views().Files().
IsEmpty()
},
})
@@ -0,0 +1,60 @@
package patch_building
import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)
// note: this is required to simulate the clipboard during CI
func expectClipboard(t *TestDriver, matcher *TextMatcher) {
defer t.Shell().DeleteFile("clipboard")
t.FileSystem().FileContent("clipboard", matcher)
}
var CopyRenamedFileDiff = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Copy the diff of a renamed file to the clipboard; the diff shows the rename rather than a delete and add",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {
config.GetUserConfig().OS.CopyToClipboardCmd = "printf '%s' {{text}} > clipboard"
},
SetupRepo: func(shell *Shell) {
shell.CreateFileAndAdd("original", "line1\nline2\nline3\nline4\nline5\n")
shell.Commit("first commit")
shell.RenameFileInGit("original", "renamed")
shell.UpdateFileAndAdd("renamed", "line1\nline2 changed\nline3\nline4\nline5\n")
shell.Commit("rename with modification")
},
Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("rename with modification").IsSelected(),
Contains("first commit"),
).
PressEnter()
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("original → renamed").IsSelected(),
).
Press(keys.Files.CopyFileInfoToClipboard)
t.ExpectPopup().Menu().
Title(Equals("Copy to clipboard")).
Select(Contains("Diff of selected file")).
Confirm()
t.ExpectToast(Contains("File diff copied to clipboard"))
expectClipboard(t,
Contains("rename from original").
Contains("rename to renamed").
Contains("-line2").
Contains("+line2 changed"),
)
},
})
@@ -0,0 +1,66 @@
package patch_building
import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)
var RenameSimilarityThresholdChange = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Changing the rename similarity threshold refreshes the commit files panel, but is disabled while building a patch",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {},
SetupRepo: func(shell *Shell) {
shell.CreateFileAndAdd("original", "one\ntwo\nthree\nfour\nfive\n")
shell.Commit("add original")
shell.RenameFileInGit("original", "renamed")
shell.UpdateFileAndAdd("renamed", "one\ntwo\nthree\nfour\nfive\nsix\nseven\neight\nnine\nten\n")
shell.Commit("change name and contents")
},
Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("change name and contents").IsSelected(),
Contains("add original"),
).
PressEnter()
// At the default threshold of 50% the 50%-similar change is not detected
// as a rename.
t.Views().CommitFiles().
IsFocused().
Lines(
Equals("▼ /"),
Equals(" D original"),
Equals(" A renamed"),
).
// Lowering the threshold turns it into a rename; the panel refreshes.
Press(keys.Universal.DecreaseRenameSimilarityThreshold).
Tap(func() {
t.ExpectToast(Equals("Changed rename similarity threshold to 45%"))
}).
Lines(
Equals("R original → renamed"),
).
// Start building a patch from the renamed file.
PressPrimaryAction().
Tap(func() {
t.Views().Information().Content(Contains("Building patch"))
// Changing the threshold is now disabled: the patch builder
// can't cope with the rename turning into a delete and add.
t.Views().CommitFiles().
Press(keys.Universal.IncreaseRenameSimilarityThreshold)
t.ExpectPopup().Alert().
Title(Equals("Error")).
Content(Contains("Cannot change the rename similarity threshold while in patch building mode")).
Confirm()
}).
// The file is unchanged: still a rename, still in the patch.
Lines(
Contains("original → renamed").IsSelected(),
)
},
})
@@ -0,0 +1,73 @@
package patch_building
import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)
var RenamedFilePartial = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Select part of a renamed file's changes into a custom patch and remove it from the commit, keeping the rename in place",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {},
SetupRepo: func(shell *Shell) {
shell.CreateFileAndAdd("original", "line1\nline2\nline3\nline4\nline5\n")
shell.Commit("first commit")
shell.RenameFileInGit("original", "renamed")
shell.UpdateFileAndAdd("renamed", "line1\nline2 changed\nline3\nline4\nline5\n")
shell.Commit("rename with modification")
},
Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("rename with modification").IsSelected(),
Contains("first commit"),
).
PressEnter()
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("original → renamed").IsSelected(),
).
PressEnter()
// The main view shows the rename together with its content change.
t.Views().PatchBuilding().
IsFocused().
Content(Contains("rename from original").Contains("rename to renamed")).
ContainsLines(
Contains(" line1"),
Contains("-line2"),
Contains("+line2 changed"),
Contains(" line3"),
).
// Add the hunk (a line selection, as opposed to adding the whole
// file), so this is a partial patch.
PressPrimaryAction()
t.Views().Information().Content(Contains("Building patch"))
t.Common().SelectPatchOption(Contains("Remove patch from original commit"))
// The rename is preserved; only the content change is gone, so the file
// is still shown as a rename but now has no content change.
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("original → renamed").IsSelected(),
)
t.Views().Main().
Content(DoesNotContain("line2 changed"))
t.Views().Commits().
Focus().
Lines(
Contains("rename with modification").IsSelected(),
Contains("first commit"),
)
},
})
@@ -0,0 +1,62 @@
package patch_building
import (
"github.com/jesseduffield/lazygit/pkg/config"
. "github.com/jesseduffield/lazygit/pkg/integration/components"
)
var RenamedFileWhole = NewIntegrationTest(NewIntegrationTestArgs{
Description: "Add a whole renamed file to a custom patch and remove it from the commit, taking the rename with it",
ExtraCmdArgs: []string{},
Skip: false,
SetupConfig: func(config *config.AppConfig) {},
SetupRepo: func(shell *Shell) {
shell.CreateFileAndAdd("original", "line1\nline2\nline3\nline4\nline5\n")
shell.Commit("first commit")
shell.RenameFileInGit("original", "renamed")
shell.UpdateFileAndAdd("renamed", "line1\nline2 changed\nline3\nline4\nline5\n")
shell.Commit("rename with modification")
},
Run: func(t *TestDriver, keys config.KeybindingConfig) {
t.Views().Commits().
Focus().
Lines(
Contains("rename with modification").IsSelected(),
Contains("first commit"),
).
PressEnter()
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("original → renamed").IsSelected(),
).
PressPrimaryAction()
t.Views().Information().Content(Contains("Building patch"))
// The whole file is added, so the patch carries the rename itself.
t.Views().Secondary().
ContainsLines(
Contains("rename from original"),
Contains("rename to renamed"),
)
t.Common().SelectPatchOption(Contains("Remove patch from original commit"))
// The rename went with the patch, so the commit no longer touches the file.
t.Views().CommitFiles().
IsFocused().
Lines(
Contains("(none)"),
)
t.Views().Commits().
Focus().
Lines(
Contains("rename with modification").IsSelected(),
Contains("first commit"),
)
},
})
+5
View File
@@ -128,6 +128,7 @@ var tests = []*components.IntegrationTest{
commit.CreateTag,
commit.DisableCopyCommitMessageBody,
commit.DiscardOldFileChanges,
commit.DiscardRenamedFile,
commit.DiscardSubmoduleChanges,
commit.DoNotShowBranchMarkerForHeadCommit,
commit.FailHooksThenCommitNoHooks,
@@ -351,6 +352,7 @@ var tests = []*components.IntegrationTest{
patch_building.ApplyInReverseWithConflict,
patch_building.ApplyWithModifiedFileConflict,
patch_building.ApplyWithModifiedFileNoConflict,
patch_building.CopyRenamedFileDiff,
patch_building.DiscardLinesFromCommit,
patch_building.EditLineInPatchBuildingPanel,
patch_building.MoveRangeToIndex,
@@ -373,6 +375,9 @@ var tests = []*components.IntegrationTest{
patch_building.MoveToNewCommitPartialHunk,
patch_building.RemoveFromCommit,
patch_building.RemovePartsOfAddedFile,
patch_building.RenameSimilarityThresholdChange,
patch_building.RenamedFilePartial,
patch_building.RenamedFileWhole,
patch_building.ResetWithEscape,
patch_building.SelectAllFiles,
patch_building.SpecificSelection,
+116 -15
View File
@@ -321,7 +321,7 @@
"$ref": "#/$defs/PagingConfig"
},
"type": "array",
"description": "Array of pagers. Each entry has the following format:\n\n # Value of the --color arg in the git diff command. Some pagers want\n # this to be set to 'always' and some want it set to 'never'\n colorArg: \"always\"\n\n # e.g.\n # diff-so-fancy\n # delta --dark --paging=never\n # ydiff -p cat -s --wrap --width={{columnWidth}}\n pager: \"\"\n\n # e.g. 'difft --color=always'\n externalDiffCommand: \"\"\n\n # If true, Lazygit will use git's `diff.external` config for paging.\n # The advantage over `externalDiffCommand` is that this can be\n # configured per file type in .gitattributes; see\n # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver.\n useExternalDiffGitConfig: false\n\nSee https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md for more information."
"description": "Array of pagers. Each entry has the following format:\n\n # A name for the pager, shown in the notification when cycling pagers.\n # If not set, the name is derived from the first word of the pager\n # command (or of the external diff command).\n name: \"\"\n\n # Value of the --color arg in the git diff command. Some pagers want\n # this to be set to 'always' and some want it set to 'never'\n colorArg: \"always\"\n\n # e.g.\n # diff-so-fancy\n # delta --dark --paging=never\n # ydiff -p cat -s --wrap --width={{columnWidth}}\n pager: \"\"\n\n # e.g. 'difft --color=always'\n externalDiffCommand: \"\"\n\n # If true, Lazygit will use git's `diff.external` config for paging.\n # The advantage over `externalDiffCommand` is that this can be\n # configured per file type in .gitattributes; see\n # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver.\n useExternalDiffGitConfig: false\n\n'pager', 'externalDiffCommand', and 'useExternalDiffGitConfig' are mutually exclusive; set at most one per entry.\n\nSee https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md for more information."
},
"commit": {
"$ref": "#/$defs/CommitConfig",
@@ -358,6 +358,11 @@
"description": "If true, periodically refresh files and submodules",
"default": true
},
"autoDetectExternalChanges": {
"type": "boolean",
"description": "If true, poll the repo periodically for external ref changes (commits, branch updates, checkouts made outside lazygit) and refresh when one is detected. Independent of autoRefresh, which only governs the files panel.",
"default": true
},
"autoForwardBranches": {
"type": "string",
"enum": [
@@ -585,6 +590,40 @@
"description": "The weight of the expanded side panel, relative to the other panels. 2 means twice as tall as the other panels. Only relevant if `expandFocusedSidePanel` is true.",
"default": 2
},
"shrinkSidePanelsToContent": {
"type": "boolean",
"description": "If true, don't give a side panel more height than it needs to show its content; when all panels fit, the leftover height is shared among them so that they still fill the screen.",
"default": false
},
"sidePanels": {
"items": {
"$ref": "#/$defs/SidePanel"
},
"type": "array",
"description": "The side panels, in the order they appear from top to bottom.\nEach entry is a list of one or more names that share a single panel as tabs (cycle through them with the next-tab/previous-tab keys).\nOmit a name to hide it; give a name its own one-element list to promote a tab to a top-level panel.\nValid names are: 'status', 'files', 'worktrees', 'submodules', 'branches', 'remotes', 'tags', 'commits', 'reflog', 'stash'. 'files', 'branches', and 'commits' must always be included; they can't be hidden.",
"default": [
[
"status"
],
[
"files",
"worktrees",
"submodules"
],
[
"branches",
"remotes",
"tags"
],
[
"commits",
"reflog"
],
[
"stash"
]
]
},
"mainPanelSplitMode": {
"type": "string",
"enum": [
@@ -1624,9 +1663,6 @@
"branches": {
"$ref": "#/$defs/KeybindingBranchesConfig"
},
"worktrees": {
"$ref": "#/$defs/KeybindingWorktreesConfig"
},
"commits": {
"$ref": "#/$defs/KeybindingCommitsConfig"
},
@@ -2847,6 +2883,20 @@
],
"default": "n"
},
"newWorktree": {
"oneOf": [
{
"type": "string"
},
{
"items": {
"type": "string"
},
"type": "array"
}
],
"default": "w"
},
"edit": {
"oneOf": [
{
@@ -3127,6 +3177,20 @@
],
"default": "|"
},
"cyclePagersReverse": {
"oneOf": [
{
"type": "string"
},
{
"items": {
"type": "string"
},
"type": "array"
}
],
"default": "\\"
},
"undo": {
"oneOf": [
{
@@ -3340,14 +3404,8 @@
}
],
"default": "\u003cctrl+t\u003e"
}
},
"additionalProperties": false,
"type": "object"
},
"KeybindingWorktreesConfig": {
"properties": {
"viewWorktreeOptions": {
},
"editConfig": {
"oneOf": [
{
"type": "string"
@@ -3359,7 +3417,7 @@
"type": "array"
}
],
"default": "w"
"default": "\u003calt+shift+c\u003e"
}
},
"additionalProperties": false,
@@ -3488,6 +3546,10 @@
},
"PagingConfig": {
"properties": {
"name": {
"type": "string",
"description": "A name for the pager, shown in the notification when cycling pagers. If not set, the name is derived from the first word of the pager command (or of the external diff command)."
},
"colorArg": {
"type": "string",
"enum": [
@@ -3521,21 +3583,45 @@
"properties": {
"refreshInterval": {
"type": "integer",
"minimum": 0,
"exclusiveMinimum": 0,
"description": "File/submodule refresh interval in seconds.\nAuto-refresh can be disabled via option 'git.autoRefresh'.",
"default": 10
},
"fetchInterval": {
"type": "integer",
"minimum": 0,
"exclusiveMinimum": 0,
"description": "Re-fetch interval in seconds.\nAuto-fetch can be disabled via option 'git.autoFetch'.",
"default": 60
},
"externalChangeCheckInterval": {
"type": "integer",
"exclusiveMinimum": 0,
"description": "Interval in seconds at which lazygit polls for external ref changes (commits, branch updates, checkouts made outside lazygit).\nDetection can be disabled via option 'git.autoDetectExternalChanges'.",
"default": 2
}
},
"additionalProperties": false,
"type": "object",
"description": "Background refreshes"
},
"SidePanel": {
"items": {
"type": "string",
"enum": [
"status",
"files",
"worktrees",
"submodules",
"branches",
"remotes",
"tags",
"commits",
"reflog",
"stash"
]
},
"type": "array"
},
"SpinnerConfig": {
"properties": {
"frames": {
@@ -3744,6 +3830,10 @@
"$ref": "#/$defs/GitConfig",
"description": "Config relating to git"
},
"worktree": {
"$ref": "#/$defs/WorktreeConfig",
"description": "Config relating to git worktrees"
},
"update": {
"$ref": "#/$defs/UpdateConfig",
"description": "Periodic update checks"
@@ -3809,6 +3899,17 @@
},
"additionalProperties": false,
"type": "object"
},
"WorktreeConfig": {
"properties": {
"defaultPath": {
"type": "string",
"description": "Default parent directory for new worktrees. It is offered as a candidate location alongside the parent directories of any worktrees you already have.\nA relative path is resolved against the repository's root directory, so \"../worktrees\" sits beside the repo and \".worktrees\" sits inside it.\nA leading \"~\" is expanded to your home directory, so \"~/worktrees\" works."
}
},
"additionalProperties": false,
"type": "object",
"description": "Config relating to git worktrees"
}
}
}