[PATCH 6 of 6 v2] import: relax import --exact if there is no # Node
timeless
timeless at mozdev.org
Thu Dec 31 00:47:20 CST 2015
# HG changeset patch
# User timeless <timeless at mozdev.org>
# Date 1451521862 0
# Thu Dec 31 00:31:02 2015 +0000
# Node ID b9f3eb03b1a009dc4a95a063a612c816ee4821f4
# Parent 37c3ba3d2f3678daa5439947f20d89496282d8b0
import: relax import --exact if there is no # Node
This allows for a patch where the # Parent node is correct,
and # Node is ommitted, allowing for memory based
grafting against alternative Nodes merely by doing:
hg export REV | rewrite Parent | grep -v '# Node ' | \
hg import --exact --bypass -
This is a poor man's cross between graft and rebase for
when your working directory is dirty.
diff --git a/mercurial/cmdutil.py b/mercurial/cmdutil.py
--- a/mercurial/cmdutil.py
+++ b/mercurial/cmdutil.py
@@ -874,6 +874,7 @@
date = opts.get('date') or extractdata.get('date')
branch = extractdata.get('branch')
nodeid = extractdata.get('nodeid')
+ hgpatch = extractdata.get('hgpatch')
p1 = extractdata.get('p1')
p2 = extractdata.get('p2')
@@ -906,7 +907,7 @@
if len(parents) == 1:
parents.append(repo[nullid])
if usenode:
- if not nodeid or not p1:
+ if not p1 or not (nodeid or hgpatch):
raise error.Abort(_('not a Mercurial patch'))
p1 = repo[p1]
p2 = repo[p2 or nullid]
@@ -1010,7 +1011,7 @@
# --exact with --no-commit is still useful in that it does merge
# and branch bits
ui.warn(_("warning: can't check exact import with --no-commit\n"))
- elif exact and hex(n) != nodeid:
+ elif exact and not (nodeid is None and hgpatch) and hex(n) != nodeid:
raise error.Abort(_('patch is damaged or loses information'))
msg = _('applied to working directory')
if n:
diff --git a/mercurial/commands.py b/mercurial/commands.py
--- a/mercurial/commands.py
+++ b/mercurial/commands.py
@@ -4598,11 +4598,12 @@
body. Values given on command line with -m/--message and -u/--user
override these.
- If --exact is specified, import will set the working directory to
- the parent of each patch before applying it, and will abort if the
- resulting changeset has a different ID than the one recorded in
- the patch. This may happen due to character set problems or other
- deficiencies in the text patch format.
+ If --exact is specified, import will apply the changes based on the
+ parent specified in each patch (setting the working directory
+ unless --bypass). If there is a `# Node ID ` line in the patch, it
+ will abort if the resulting changeset has a different Node ID.
+ This may happen due to character set problems or other deficiencies
+ in the text patch format.
Use --partial to ensure a changeset will be created from the patch
even if some hunks fail to apply. Hunks that fail to apply will be
diff --git a/tests/test-import-bypass.t b/tests/test-import-bypass.t
--- a/tests/test-import-bypass.t
+++ b/tests/test-import-bypass.t
@@ -306,6 +306,44 @@
|/
o 0:07f494440405 test 0 0 - default - adda
+Test --bypass --exact for a modified Parent node
+
+ $ cat ../patch1.diff | env \
+ > DEST=`hg log -r 3 --template '{node}'` \
+ > sh -c 'sed -e "s/^\(# Parent \).*/\1$DEST/"' \
+ > ../patch1.diff > ../patch1m.diff
+ $ mkdir e
+ $ hg import ../patch1m.diff
+ applying ../patch1m.diff
+ abort: Is a directory: $TESTTMP/repo-multi2/e
+ [255]
+ $ rmdir e
+ $ echo a >> a
+ $ hg import ../patch1m.diff
+ abort: uncommitted changes
+ [255]
+ $ hg import --bypass --exact ../patch1m.diff
+ applying ../patch1m.diff
+ transaction abort!
+ rollback completed
+ abort: patch is damaged or loses information
+ [255]
+ $ egrep -v '^# Node ID ' ../patch1m.diff > ../patch1p.diff
+ $ hg import --bypass --exact ../patch1p.diff
+ applying ../patch1p.diff
+ $ shortlog
+ o 4:4e6b5d637a35 test 0 0 - default - adde
+ |
+ o 3:d60cb8989666 test 0 0 - foo - addf
+ |
+ | o 2:16581080145e test 0 0 - default - adde
+ | |
+ @ | 1:4e322f7ce8e3 test 0 0 - foo - changea
+ |/
+ o 0:07f494440405 test 0 0 - default - adda
+
+ $ hg rollback
+ repository tip rolled back to revision 3 (undo import)
$ cd ..
More information about the Mercurial-devel
mailing list