Update Mercurial to support multi-commit patches via the new Patcher API.
Review Request #14239 — Created Nov. 10, 2024 and updated
Mercurial has some restrictions on how patches may be applied. Unlike
Git, Subversion, etc.,hg import
will not apply a patch if there are
changes in the working directory. This means that a group of patches
must be applied in one go, and not one-by-one. Our old patching model
didn't allow for this level of control, and this was the reason the new
Patcher API was created.The Patcher API is now used to apply patches without commits, and with
commits. It supports Git-style and Mercurial-style diffs.When applying patches without committing, we open all the patches and
then pass their filenames directly tohg import
, allowing it to apply
them all without hitting the working directory changes error.When applying with committing, we use the standard Patcher logic to
manage the patches, and then patch each patch usinghg import
individually. Whilehg import
does support committing as part of the
patch operation, we instead use our existing commit-creation
functionality in order to utilize common logic and checks.Conflicts are tracked, as Mercurial uses the standard patch tool's
output for conflict information. We apply usinghg diff --partial
,
which will apply what changes it can while leaving the user responsible
for applying the rest, keeping with the behavior in most other SCMs.Some notable limitations are that we can't revert or squash commits in
Mercurial, and we generally don't have commit message or author
information in the patches (requiring defaults to be used based on the
review request). If applying Hg-style diffs, empty files won't be
represented, so Git-style diffs are recommended.Squashing may be able to be resolved through further updates to RBTools
(by applying and amending each commit in succession), but would require
additional changes to the API for creating commits. We're leaving it off
for now.There may be some other peculiarities of Mercurial's patching, and this
will likely need some changes based on usage in production.
Unit tests passed.
-
-
You technically can squash hg commits. The
rebase
extension ships with Mercurial, but it is not enabled by default. However, you can enable it during a single hg invocation by doinghg --config extensions.rebase=
.So you can squash the range a::b into a single commit based on c with
hg --config extensions.rebase= rebase -r a::b -d c --collapse
- Change Summary:
-
- Switched
hg patch
tohg import
everywhere. - Fixed typos in the docs.
- Switched
- Description:
-
Mercurial has some restrictions on how patches may be applied. Unlike
~ Git, Subversion, etc., hg patch
will not apply a patch if there are~ Git, Subversion, etc., hg import
will not apply a patch if there arechanges in the working directory. This means that a group of patches must be applied in one go, and not one-by-one. Our old patching model didn't allow for this level of control, and this was the reason the new Patcher API was created. The Patcher API is now used to apply patches without commits, and with
commits. It supports Git-style and Mercurial-style diffs. When applying patches without committing, we open all the patches and
~ then pass their filenames directly to hg patch
, allowing it to apply~ then pass their filenames directly to hg import
, allowing it to applythem all without hitting the working directory changes error. When applying with committing, we use the standard Patcher logic to
~ manage the patches, and then patch each patch using hg patch
~ individually. While hg patch
does support committing as part of the~ manage the patches, and then patch each patch using hg import
~ individually. While hg import
does support committing as part of thepatch operation, we instead use our existing commit-creation functionality in order to utilize common logic and checks. Conflicts are tracked, as Mercurial uses the standard patch tool's
output for conflict information. We apply using hg diff --partial
,which will apply what changes it can while leaving the user responsible for applying the rest, keeping with the behavior in most other SCMs. Some notable limitations are that we can't revert or squash commits in
Mercurial, and we generally don't have commit message or author information in the patches (requiring defaults to be used based on the review request). If applying Hg-style diffs, empty files won't be represented, so Git-style diffs are recommended. + Squashing may be able to be resolved through further updates to RBTools
+ (by applying and amending each commit in succession), but would require + additional changes to the API for creating commits. We're leaving it off + for now. + There may be some other peculiarities of Mercurial's patching, and this
will likely need some changes based on usage in production. - Commits:
-
Summary ID a1c2f56f08c23d1e67bb1421e72652b867d8b722 7203be5ee101f08fc3280d5d0392510e3c75169e