Skip to content

Commit

Permalink
Improve squash merge detection (#1238)
Browse files Browse the repository at this point in the history
  • Loading branch information
gjulianm authored May 24, 2024
1 parent d2ae146 commit fd0c4b5
Show file tree
Hide file tree
Showing 23 changed files with 641 additions and 119 deletions.
5 changes: 5 additions & 0 deletions RELEASE_NOTES.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
# Release notes

## New in git-machete 3.26.0

- added: better detection of squash merges and rebases, controlled by flag `--squash-merge-detection={none,simple,exact}` (`status` and `traverse`) and git config key `machete.squashMergeDetection` (contributed by @gjulianm)
- deprecated: `--no-detect-squash-merges` flag in `status` and `traverse` — use `--squash-merge-detection=none` instead (contributed by @gjulianm)

## New in git-machete 3.25.3

- fixed: `-y` option in `git machete traverse` automatically sets `--no-edit-merge` flag, to retain behavior when the `update=merge` qualifier is set (contributed by @gjulianm)
Expand Down
103 changes: 94 additions & 9 deletions docs/man/git-machete.1
Original file line number Diff line number Diff line change
Expand Up @@ -27,9 +27,9 @@ level margin: \\n[rst2man-indent\\n[rst2man-indent-level]]
.\" new: \\n[rst2man-indent\\n[rst2man-indent-level]]
.in \\n[rst2man-indent\\n[rst2man-indent-level]]u
..
.TH "GIT-MACHETE" "1" "May 08, 2024" "" "git-machete"
.TH "GIT-MACHETE" "1" "May 24, 2024" "" "git-machete"
.SH NAME
git-machete \- git-machete 3.25.3
git-machete \- git-machete 3.26.0
.sp
git machete is a robust tool that \fBsimplifies your git workflows\fP\&.
.sp
Expand Down Expand Up @@ -410,6 +410,28 @@ The override data is stored under \fBmachete.overrideForkPoint.<branch>.to\fP gi
There should be \fBno\fP need for the user to interact with this key directly,
\fBgit machete fork\-point\fP with flags should be used instead.
.TP
.B \fBmachete.squashMergeDetection\fP:
Controls the algorithm used to detect squash merges. Possible values are:
.INDENT 7.0
.IP \(bu 2
\fBnone\fP: Fastest mode, with no squash merge/rebase detection. Only \fIstrict\fP (fast\-forward or 2\-parent) merges are detected.
.IP \(bu 2
\fBsimple\fP (default): Compares the tree (files & directories in the commit) of the downstream branch with the trees of the upstream branch.
This detects squash merges/rebases as long as there exists a squash/rebase commit in the upstream that has the identical tree to what\(aqs in the downstream branch.
.IP \(bu 2
\fBexact\fP: Compares the patch (diff introduced by the commits) of the downstream branch with the patches of the upstream branch.
This detects squash merges in more cases than \fBsimple\fP mode.
However, it might have a significant performance impact on large repositories as it requires computing patches for commits in the upstream branch.
.UNINDENT
.sp
This has an impact on:
.INDENT 7.0
.IP \(bu 2
whether a grey edge is displayed in \fBstatus\fP,
.IP \(bu 2
whether \fBtraverse\fP suggests to slide out the branch.
.UNINDENT
.TP
.B \fBmachete.status.extraSpaceBeforeBranchName\fP:
To make it easier to select branch name from the \fBstatus\fP output on certain terminals
(like \fI\%Alacritty\fP), you can add an extra space between └─ and \fBbranch name\fP
Expand Down Expand Up @@ -474,6 +496,9 @@ Example: \fBGIT_MACHETE_REBASE_OPTS=\(dq\-\-keep\-empty \-\-rebase\-merges\(dq g
.TP
.B \fBGITHUB_TOKEN\fP
Used to store GitHub API token. Used by commands such as \fBanno \-\-sync\-github\-prs\fP and \fBgithub\fP\&.
.TP
.B \fBGITLAB_TOKEN\fP
Used to store GitLab API token. Used by commands such as \fBanno \-\-sync\-gitlab\-prs\fP and \fBgitlab\fP\&.
.UNINDENT
.SH CLEAN
.sp
Expand Down Expand Up @@ -1653,7 +1678,9 @@ since all branches are usually meant to be ultimately merged to one of those.
.nf
.ft C
git machete slide\-out \-\-removed\-from\-remote [\-\-delete]
git machete slide\-out [\-d|\-\-down\-fork\-point=<down\-fork\-point\-commit>] [\-\-delete] [\-M|\-\-merge] [\-n|\-\-no\-edit\-merge|\-\-no\-interactive\-rebase] [<branch> [<branch> [<branch> ...]]]
git machete slide\-out [\-d|\-\-down\-fork\-point=<down\-fork\-point\-commit>] [\-\-delete]
[\-M|\-\-merge] [\-n|\-\-no\-edit\-merge|\-\-no\-interactive\-rebase]
[<branch> [<branch> [<branch> ...]]]
.ft P
.fi
.UNINDENT
Expand Down Expand Up @@ -1814,7 +1841,9 @@ Specifies the alternative fork point commit after which the squashed part of his
.sp
.nf
.ft C
git machete s[tatus] [\-\-color=WHEN] [\-l|\-\-list\-commits] [\-L|\-\-list\-commits\-with\-hashes] [\-\-no\-detect\-squash\-merges]
git machete s[tatus] [\-\-color=WHEN]
[\-l|\-\-list\-commits] [\-L|\-\-list\-commits\-with\-hashes]
[\-\-squash\-merge\-detection=MODE]
.ft P
.fi
.UNINDENT
Expand Down Expand Up @@ -1935,13 +1964,41 @@ Additionally list the commits introduced on each branch.
Additionally list the short hashes and messages of commits introduced on each branch.
.TP
.B \-\-no\-detect\-squash\-merges
\fBDeprecated\fP, use \fB\-\-squash\-merge\-detection=none\fP instead.
Only consider \fIstrict\fP (fast\-forward or 2\-parent) merges, rather than rebase/squash merges,
when detecting if a branch is merged into its upstream (parent).
.TP
.BI \-\-squash\-merge\-detection\fB= MODE
Specify the mode for detection of rebase/squash merges (grey edges).
\fBMODE\fP can be \fBnone\fP (fastest, no squash merges are detected), \fBsimple\fP (default) or \fBexact\fP (slowest).
See the below paragraph on \fBmachete.squashMergeDetection\fP git config key for more details.
.UNINDENT
.sp
\fBGit config keys:\fP
.INDENT 0.0
.TP
.B \fBmachete.squashMergeDetection\fP:
Controls the algorithm used to detect squash merges. Possible values are:
.INDENT 7.0
.IP \(bu 2
\fBnone\fP: Fastest mode, with no squash merge/rebase detection. Only \fIstrict\fP (fast\-forward or 2\-parent) merges are detected.
.IP \(bu 2
\fBsimple\fP (default): Compares the tree (files & directories in the commit) of the downstream branch with the trees of the upstream branch.
This detects squash merges/rebases as long as there exists a squash/rebase commit in the upstream that has the identical tree to what\(aqs in the downstream branch.
.IP \(bu 2
\fBexact\fP: Compares the patch (diff introduced by the commits) of the downstream branch with the patches of the upstream branch.
This detects squash merges in more cases than \fBsimple\fP mode.
However, it might have a significant performance impact on large repositories as it requires computing patches for commits in the upstream branch.
.UNINDENT
.sp
This has an impact on:
.INDENT 7.0
.IP \(bu 2
whether a grey edge is displayed in \fBstatus\fP,
.IP \(bu 2
whether \fBtraverse\fP suggests to slide out the branch.
.UNINDENT
.TP
.B \fBmachete.status.extraSpaceBeforeBranchName\fP
To make it easier to select branch name from the \fBstatus\fP output on certain terminals
(like \fI\%Alacritty\fP), you can add an extra space between └─ and \fBbranch name\fP
Expand All @@ -1956,9 +2013,9 @@ by setting \fBgit config machete.status.extraSpaceBeforeBranchName true\fP\&.
.nf
.ft C
git machete t[raverse] [\-F|\-\-fetch] [\-l|\-\-list\-commits] [\-M|\-\-merge]
[\-n|\-\-no\-edit\-merge|\-\-no\-interactive\-rebase] [\-\-no\-detect\-squash\-merges]
[\-\-[no\-]push] [\-\-[no\-]push\-untracked]
[\-\-return\-to=WHERE] [\-\-start\-from=WHERE] [\-w|\-\-whole] [\-W] [\-y|\-\-yes]
[\-n|\-\-no\-edit\-merge|\-\-no\-interactive\-rebase] [\-\-[no\-]push] [\-\-[no\-]push\-untracked]
[\-\-return\-to=WHERE] [\-\-start\-from=WHERE] [\-\-squash\-merge\-detection=MODE]
[\-w|\-\-whole] [\-W] [\-y|\-\-yes]
.ft P
.fi
.UNINDENT
Expand Down Expand Up @@ -2023,7 +2080,7 @@ It can also be customized using options: \fB\-\-[no\-]push\fP or \fB\-\-[no\-]pu
If the traverse flow is stopped (typically due to merge/rebase conflicts), just run \fBgit machete traverse\fP after the merge/rebase is finished.
It will pick up the walk from the current branch.
Unlike with \fBgit rebase\fP or \fBgit cherry\-pick\fP, there is no special \fB\-\-continue\fP flag, as \fBtraverse\fP is stateless.
\fBtraverse\fP doesn\(aqt keep a state of its own like \fBgit rebase\fP does in \fB\&.git/rebase\-apply/\fP\&.
\fBtraverse\fP does \fBnot\fP keep a state of its own like \fBgit rebase\fP does in \fB\&.git/rebase\-apply/\fP\&.
.sp
The rebase, push and slide\-out behaviors of \fBtraverse\fP can also be customized for each branch separately using \fIbranch qualifiers\fP\&.
There are \fBpush=no\fP, \fBrebase=no\fP and \fBslide\-out=no\fP qualifiers that can be used to opt out of default behavior (rebasing, pushing and sliding the branch out).
Expand Down Expand Up @@ -2065,6 +2122,7 @@ Update by merge rather than by rebase.
If updating by rebase, equivalent to \fB\-\-no\-interactive\-rebase\fP\&. If updating by merge, equivalent to \fB\-\-no\-edit\-merge\fP\&.
.TP
.B \-\-no\-detect\-squash\-merges
\fBDeprecated\fP, use \fB\-\-squash\-merge\-detection=none\fP instead.
Only consider \fIstrict\fP (fast\-forward or 2\-parent) merges, rather than rebase/squash merges,
when detecting if a branch is merged into its upstream (parent).
.TP
Expand Down Expand Up @@ -2097,6 +2155,11 @@ WHERE can be \fBhere\fP (the current branch at the moment when traversal starts)
\fBstay\fP (the default \-\-\- just stay wherever the traversal stops). Note: when user quits by \fBq\fP/\fByq\fP
or when traversal is stopped because one of git actions fails, the behavior is always \fBstay\fP\&.
.TP
.BI \-\-squash\-merge\-detection\fB= MODE
Specifies the mode for detection of rebase/squash merges (grey edges).
\fBMODE\fP can be \fBnone\fP (fastest, no squash merges are detected), \fBsimple\fP (default) or \fBexact\fP (slowest).
See the below paragraph on \fBmachete.squashMergeDetection\fP git config key for more details.
.TP
.BI \-\-start\-from\fB= WHERE
Specifies the branch to start the traversal from; WHERE can be \fBhere\fP
(the default \-\-\- current branch, must be managed by git machete), \fBroot\fP (root branch of the current branch,
Expand Down Expand Up @@ -2125,6 +2188,28 @@ Example: \fBGIT_MACHETE_REBASE_OPTS=\(dq\-\-keep\-empty \-\-rebase\-merges\(dq g
\fBGit config keys:\fP
.INDENT 0.0
.TP
.B \fBmachete.squashMergeDetection\fP:
Controls the algorithm used to detect squash merges. Possible values are:
.INDENT 7.0
.IP \(bu 2
\fBnone\fP: Fastest mode, with no squash merge/rebase detection. Only \fIstrict\fP (fast\-forward or 2\-parent) merges are detected.
.IP \(bu 2
\fBsimple\fP (default): Compares the tree (files & directories in the commit) of the downstream branch with the trees of the upstream branch.
This detects squash merges/rebases as long as there exists a squash/rebase commit in the upstream that has the identical tree to what\(aqs in the downstream branch.
.IP \(bu 2
\fBexact\fP: Compares the patch (diff introduced by the commits) of the downstream branch with the patches of the upstream branch.
This detects squash merges in more cases than \fBsimple\fP mode.
However, it might have a significant performance impact on large repositories as it requires computing patches for commits in the upstream branch.
.UNINDENT
.sp
This has an impact on:
.INDENT 7.0
.IP \(bu 2
whether a grey edge is displayed in \fBstatus\fP,
.IP \(bu 2
whether \fBtraverse\fP suggests to slide out the branch.
.UNINDENT
.TP
.B \fBmachete.traverse.push\fP
To change the behavior of \fBgit machete traverse\fP command so that it doesn\(aqt push branches by default,
you need to set config key \fBgit config machete.traverse.push false\fP\&.
Expand All @@ -2139,7 +2224,7 @@ Configuration key value can be overridden by the presence of the \fB\-\-push\fP
.sp
.nf
.ft C
git machete update [\-f|\-\-fork\-point=] [\-M|\-\-merge] [\-n|\-\-no\-edit\-merge|\-\-no\-interactive\-rebase]
git machete update [\-f|\-\-fork\-point=<fork\-point\-commit>] [\-M|\-\-merge] [\-n|\-\-no\-edit\-merge|\-\-no\-interactive\-rebase]
.ft P
.fi
.UNINDENT
Expand Down
7 changes: 6 additions & 1 deletion docs/source/cli/config.rst
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,9 @@ Note: ``config`` is not a command as such, just a help topic (there is no ``git
There should be **no** need for the user to interact with this key directly,
``git machete fork-point`` with flags should be used instead.

``machete.squashMergeDetection``:
.. include:: git-config-keys/squashMergeDetection.rst

``machete.status.extraSpaceBeforeBranchName``:
.. include:: git-config-keys/status_extraSpaceBeforeBranchName.rst

Expand All @@ -49,7 +52,6 @@ Note: ``config`` is not a command as such, just a help topic (there is no ``git
If you want the worktree to have its own branch layout file (located under ``.git/worktrees/.../machete``),
set ``git config machete.worktree.useTopLevelMacheteFile false``.


**Environment variables:**

``GIT_MACHETE_EDITOR``
Expand All @@ -62,3 +64,6 @@ Note: ``config`` is not a command as such, just a help topic (there is no ``git

``GITHUB_TOKEN``
Used to store GitHub API token. Used by commands such as ``anno --sync-github-prs`` and ``github``.

``GITLAB_TOKEN``
Used to store GitLab API token. Used by commands such as ``anno --sync-gitlab-prs`` and ``gitlab``.
4 changes: 3 additions & 1 deletion docs/source/cli/slide-out.rst
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@ slide-out
.. code-block:: shell
git machete slide-out --removed-from-remote [--delete]
git machete slide-out [-d|--down-fork-point=<down-fork-point-commit>] [--delete] [-M|--merge] [-n|--no-edit-merge|--no-interactive-rebase] [<branch> [<branch> [<branch> ...]]]
git machete slide-out [-d|--down-fork-point=<down-fork-point-commit>] [--delete]
[-M|--merge] [-n|--no-edit-merge|--no-interactive-rebase]
[<branch> [<branch> [<branch> ...]]]
Removes the given branch (or multiple branches) from the branch layout.
If no branch has been specified, current branch is slid out.
Expand Down
14 changes: 12 additions & 2 deletions docs/source/cli/status.rst
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,9 @@ status

.. code-block:: shell
git machete s[tatus] [--color=WHEN] [-l|--list-commits] [-L|--list-commits-with-hashes] [--no-detect-squash-merges]
git machete s[tatus] [--color=WHEN]
[-l|--list-commits] [-L|--list-commits-with-hashes]
[--squash-merge-detection=MODE]
Displays a tree-shaped status of the branches listed in the branch layout file.

Expand Down Expand Up @@ -83,11 +85,19 @@ When colors are disabled, relation between branches is represented in the follow

-L, --list-commits-with-hashes Additionally list the short hashes and messages of commits introduced on each branch.

--no-detect-squash-merges Only consider *strict* (fast-forward or 2-parent) merges, rather than rebase/squash merges,
--no-detect-squash-merges **Deprecated**, use ``--squash-merge-detection=none`` instead.
Only consider *strict* (fast-forward or 2-parent) merges, rather than rebase/squash merges,
when detecting if a branch is merged into its upstream (parent).

--squash-merge-detection=MODE Specify the mode for detection of rebase/squash merges (grey edges).
``MODE`` can be ``none`` (fastest, no squash merges are detected), ``simple`` (default) or ``exact`` (slowest).
See the below paragraph on ``machete.squashMergeDetection`` git config key for more details.

**Git config keys:**

``machete.squashMergeDetection``:
.. include:: git-config-keys/squashMergeDetection.rst

``machete.status.extraSpaceBeforeBranchName``
.. include:: git-config-keys/status_extraSpaceBeforeBranchName.rst
:end-line: 3
Loading

0 comments on commit fd0c4b5

Please sign in to comment.