Problem with importing a merge changeset

Julian Cowley julian at lava.net
Sun May 18 16:12:04 CDT 2008


On Sun, 18 May 2008, Adrian Buehlmann wrote:
> On 18.05.2008 07:45, Julian Cowley wrote:
>> I'm having a problem with the hg import command.  Say I have a repo with
>> the following:
>>
>>     o    changeset:   3:aed80a0542a6
>>     |\
>>     | o  changeset:   2:43201c19d28d
>>     | |
>>     o |  changeset:   1:258012f5089c
>>     |/
>>     o    changeset:   0:0518cfc51257
>>
>> After changeset 0, the repo is cloned.  Changeset 2 is committed to the
>> original.  Changesets 1 and 3 are committed to the clone and then exported
>> using hg export.
>
> There is a contradiction here, IMHO:
>
> You say cset 3 has been committed to the clone. From your picture above
> I gather that cset 3 is a merge cset (it has two parents).

Right, I meant for changeset 3 to be taken as a merge.

> Cset 3 can only have been committed to the clone if cset 2 has been
> committed to the clone as well, since 3 depends on 2 per your graph.
> But you say the clone was cloned from the original before cset 2 had
> been committed to the original, from which I infer that 2 should be missing
> in the clone. But if you have a 3 as shown in the graph (a merge of
> 2 and 1) then both 2 and 1 must have been present in the clone when
> committing merge cset 3 to the clone.
>
> Either your graph or your text or both or wrong.

I think I was being too terse there since the graph is a condensed glog of 
what's in the *clone* after the merge.

I did do a pull of changeset 2 into the clone before merging.  Sorry that 
I neglected to mention that since it would have made the example clearer. 
I didn't change the parent before the merge, though, so parent 1 is 
changeset 1 and parent 2 is changeset 2.

The basic problem I am having is when giving hg import a merge changeset; 
that is, a merge changeset generated by hg export.

The goal was to create a merge changset with hg export.  Here I've created 
a new repo (with different changeset IDs, of course) using the same steps 
as above:

Create the initial changset for original repo:

     mkdir repo
     cd repo
     hg init
     echo 0 >> x
     hg add x
     hg ci -m 0
     cd ..

Create the clone repo:

     hg -q clone repo clone

Add to the original repo (this will become changset 2 in the clone):

     cd repo
     echo 1 >> x
     hg ci -m 1
     cd ..

Add to the clone repo (this will become changeset 1 in the clone):

     cd clone
     echo 2 >> x
     hg ci -m 2
     cd ..

Merge the changesets in the clone:

     cd clone
     hg -q pull
     hg merge
     [run merge tool and merge by sorting text into numerical order]

Diffs of the changes before commit:

     $ hg diff -r 1
     diff -r e30cf7576e57 x
     --- a/x	Sat May 17 23:23:36 2008 -1000
     +++ b/x	Sat May 17 23:25:27 2008 -1000
     @@ -1,2 +1,3 @@
      0
     +1
      2

     $ hg diff -r 2
     diff -r f8e25f2b8581 x
     --- a/x	Sat May 17 23:23:02 2008 -1000
     +++ b/x	Sat May 17 23:25:29 2008 -1000
     @@ -1,2 +1,3 @@
      0
      1
     +2

Commit it:

     hg ci -m merge

Here is the hg export of the merge:

     $ hg export tip
     # HG changeset patch
     # User julian at lava.net
     # Date 1211102736 36000
     # Node ID 0ee59e79d99fa6bf642e2ebdfccdf6f155683648
     # Parent  e30cf7576e5712d7727b2ed8ab5c1b19c5111d2d
     # Parent  f8e25f2b85816d10977f71c8861140af795b2e84
     merge

     diff -r e30cf7576e57 -r 0ee59e79d99f x
     --- a/x	Sat May 17 23:23:36 2008 -1000
     +++ b/x	Sat May 17 23:25:36 2008 -1000
     @@ -1,2 +1,3 @@
      0
     +1
      2

> If your original repo would have had csets 0 and 2 and your clone would
> have had csets 0 and 1 (not 3!), it would have had made sense to export 1
> from the clone using hg export and to hg import that into the original.

Yes, but then I wouldn't have a merge to use as an example with hg 
import. :)

> As a general note (as I understand it, the real hg gurus might correct me
> please if I'm wrong) hg export/import isn't meant to be used as a transfer
> method for *merge* changesets, since the patch format in the output of hg
> export does the diff against the first parent only.

I think you might be onto something here as to why hg import fails.

My understanding is that the output of hg export is enough to reproduce a 
merge, but I too defer to the gurus.  Three things are needed to specify a 
merge, the two parents and the child.  The two parents are given as 
changeset IDs (which implies that they both have to be in a repo for the 
hg import --exact to work), and the child is given as a patch of the first 
parent.  The hg export could include a patch against the second parent, 
too, but that is redundant (right?).

> Quote from "hg help export":
> '''
>    NOTE: export may generate unexpected diff output for merge changesets,
>    as it will compare the merge changeset against its first parent only.
> '''
>
> To transfer merge changesets, you should either use "hg pull" from one repo
> into the other or use "hg bundle" to create a bundle file and "hg pull" from
> that bundle file into the target repo.

I use pull all the time, but I also like the idea of using text to send 
changesets around, especially via email or other streams.

-- 
The revolution has been cancelled due to low ratings.


More information about the Mercurial mailing list