merge a child changeset Y into an ancestor X - mercurial

Hi I have a change Y posterior to X, and I want to branch now from X and select only some changes that were made afterwards. In svn I'd do svn up -rX svn merge -cY. Any ideas if I can do this in mercurial without resorting to export or xplant?

The transplant extension may be what you're looking for. (Untested) I think it would be
hg update X
hg transplant Y

Related

Mercurial: retrospectively merging revisions

I have just been asked by a fellow developer whether they need to do anything when that merge window appears. Apparently their default course of action has been to simply close the window immediately.
Anyway, we're now in a situation where they have made minor changes to a number of files where another developer made a large number of changes. They then 'merged' them, essentially backing out all remote changes to the files, committed the code, and pushed to the central repository.
So we're in the situation that there is revision x with changes we want, revision y with changes we want, and revision z that is a merge of x+y, but actually just contains the code from y.
Is there a way now to retrospectively get back into the merge tool?
I'd like to run a command and get a meld window up to let me merge back in the changes from y into the current revision.
First, clone your repository somewhere, and test these instructions in there. I tested them on a very small repository made for the purpose, so I may have overlooked something.
hg clone yourrepo testrepo
cd testrepo
You can check out the code as of revision x, and repeat the merge. That will give you a new head. Then, if you have not made changes since, you can use hg strip to get rid of the bad one. If you don't want to risk the strip, then merge the two heads, telling hg to keep the version of the code in the good version. If you have it checked out, as you will immediately after making it, then give the argument -t internal:local to throw away the changes from the other, bad, head. It's a lot simpler to do than to explain:
hg update x
hg merge -r y
hg commit -m 'Redo the merge.'
Then either:
hg strip z
or:
hg merge -t internal:local -r z
hg commit -m 'Get rid of the bad merge.'
You can look at the state of the graph with the very useful hg view extension.
Once again, I tested this on a toy repository. Back it up first!

Reverse of hg backout

I'm looking for a method like hg backout, but in reverse. Specifically, instead of undoing the diffs associated with a given changset, I want to actually apply them on top of an arbitrary revision. Is this possible?
hg transplant (bundled extension) or hg graft (core, since 2.0) do this.

Reassigning local commits to a different branch in Mercurial

I'm using hg bookmarks in my repo because they allow me to work with ease on different features. The thing with Mercurial is that, still, all commits are associated with a branch. So, what I did is that I have a lot of local changes, with a lot of pulled (but not updated changes) to the same branch. In other words, my local repo looks like this:
default -------E-F---------
newf -A-C-D---------J---
newf,bmark --\--------H-I----K
newf is a branch that is on remote, pulled up to J, and bmark is the bookmark I created. Everything in newf, marked with bmark is strictly local to my machine.
Now, I would like to re-assign H, I, and K (actually, there are ~20 changes) to a different branch, which I can push to the repo. Is there a way to do it in Mercurial, so that my working copy (I still have some uncommitted changes) remains as unaffected as possible?
Based on the suggestion to use 'rebase', I tried the following steps:
hg up -r A
hg branch newbranch && hg ci -m "will hold some development"
# This effectively made a commit X
hg up bmark
hg rebase -d newbranch
Apart from getting some errors about phases, the rebase gives me something I would not expect:
default -------E-F---------
newf -A-C-D---------J---
newf,bmark \ -----H-I----K
newbranch \X/
That is, H,I, and K are listed to still belong to newf and bmark, and they are on top on commit X that belongs to branch newbranch. Am I doing something wrong here?
I use rebase to move commits from one branch to another. Would it work in your case?

Push mercurial merged branch without history

Given that I have created a branch in Mercurial how can I push the resulting merge of that branch to a remote repository without the history of how I got to that merged branch result. For example.
[a] - [b] -----------------[k]
\ /
[g] - [h] - [i] - [j]
[a], [b] and [k] being the 'default' branch, [g] through [j] being the feature branch. Once I merge the feature branch into the default branch how can I have just [a] - [b] - [k] change sets in the remote repository when I push? I don't want to simply not see the branch, I do not want those change sets pushed to the remote repository at all. I don't care how I got to [k], I do care what the [k] end result is though.
I am currently leaning toward the branch by cloning method but how can I accomplish this with cloning? Would there also be a way to make this work with named branches?
I have been looking for an answer to this but there is so much documentation out there it's difficult to find this needle in a haystack.
Instead of merging, you want to use hg rebase with the --collapse option.
hg rebase --collapse --source [g] --dest [b]
The rebase extension is shipped with Mercurial, you just need to enable it in your settings file.
p.s. If you have already committed the merge [k], you should rollback (or strip) it first before rebasing.
how can I push the resulting merge of that branch to a remote repository without the history of how I got to that merged branch result
No ways to get stripped history for merged branches

How to compare sets of changesets between 2 Mercurial branches?

I've got a (remote) Hg repository with a couple branches. I want to verify that branch A has every changeset that branch B has (it may have more, and that's OK).
Is there an easy way to do this with just hg?
I can write a little shell script to do it, but it seems like the sort of thing that might come up a lot, so maybe there's an easy built-in way.
This will show any ancestors of changeset b which are not an ancestor of changeset a:
hg log -r "ancestors(b) and not ancestors(a)"
This should show you which changes still need to be merged from B to A if you give the head of branch B for b, and the head of branch A for a.