5115
Comment: Fix graph (d and D were missing)
|
5190
just "hgrc" was kinda misleading
|
Deletions are marked like this. | Additions are marked like this. |
Line 21: | Line 21: |
Enable the extension by adding following lines to your configuration file (hgrc): | Enable the extension by adding following lines to your configuration file (~/.hgrc or system-wide's one): |
Line 25: | Line 25: |
hgext.transplant= | transplant= |
Line 135: | Line 135: |
=== See also === * [[RebasePlan| Rebase Command]] |
Transplant extension
This extension now is distributed along with Mercurial.
Author: Brendan Cully
Overview
This extension allows you to transplant patches from another branch or repository.
It records the original changeset ID in the transplanted changeset, and avoids transplanting previously-transplanted patches.
It can also be used to rebase a branch against upstream changes (including dropping changesets that have been adopted upstream), to rewrite changesets and to cherrypick some changesets.
Transplanted patches are recorded in a .hg/transplant/transplants file, as a map from a changeset hash to its hash in the source repository.
Selected changesets will be applied on top of the current working directory with the log of the original changeset. Optionally, the transplanted changeset changelog can show an additional comment to show which changeset it has been transplanted from.
Configuration
Enable the extension by adding following lines to your configuration file (~/.hgrc or system-wide's one):
[extensions] transplant=
Usage
The extension can be used either as a normal command or interactively, using a text interface:
hg transplant [-s REPOSITORY] [-b BRANCH [-a]] [-p REV] [-m REV] [REV]...
where the options are:
-s or --source |
pull patches from repository REPOSITORY |
-b or --branch |
pull patches from branch BRANCH |
-a or --all |
pull all changesets up to BRANCH |
-p or --prune |
skip over or prune REV |
-m or --merge |
merge at REV |
--log |
append transplant info to log message |
-c or --continue |
continue last transplant session after repair |
--filter |
filter changesets through FILTER |
Using transplant in interactive mode
If no merges or revisions are provided to transplant, then it starts in interactive mode, showing a changeset browser to select the desired revisions to transplant.
Using transplant to cherrypick a set of changesets
Transplant can manage multiple changesets or changeset ranges like this:
hg transplant REV1:REV2 REV3
This example would cherrypick the range of changesets specified by REV1:REV2 and the additional changeset REV3 upon the working directory revision.
Using transplant to rebase some changesets
hg transplant --branch REV4
This example would rebase the changesets from REV4 till its (branch) head upon the working directory revision.
Using transplant to rewrite changesets using a filter
The transplant extension accepts a --filter option, which lets you edit the changelog message and patch before applying it to its destination (they are supplied to the script as $1 and $2, respectively). For example, you could add a "Signed-off-by: " header to each changeset with a script like this:
cat <<EOF >> "$1" Signed-off-by: Me EOF
As a slightly more complicated example, I used the following script to import my transplant extension from a standalone repository into mercurial's hgext folder (transplant uses git-style patches, so a little extra work was required):
import.sh:
MESSAGE="$1" PATCH="$2" sed -e's,^\(--- a/\)\|\(+++ b/\),&hgext/,' \ -e'/^diff --git/s,a/\(.*\) b/\(.*\),a/hgext/\1 b/hgext/\2,' \ -e's,^\(rename\|copy\) \(from\|to\) ,&hgext/', \ -i "$PATCH"
I then did the import like so:
hg transplant -s ../transplant --filter import.sh 0:tip
Merging with transplants
Three-way merge doesn't cope particularly well with transplanted patches - it will tend to generate false conflicts. Here's a possible strategy for handling transplant merges that I mean to integrate into the transplant extension soon:
- Walk forward from the merge base to the first node that is transplanted from one tree to the other.
- Find the source node on the other tree.
- Perform a merge where the local node is the node found above (whichever is on the local branch) and the remote node is the "parent" of the corresponding node.
- Use the result as the merge base, skipping over the remote node found above, and repeat until the target heads are merged.
In the following example, c1 is transplanted from C.
To produce the merge node F, we'd start with a merge base of a, and merge local node C with remote node b to produce CM. We'd then use CM as a merge base for e and E to produce F: