Use "hg unshelve" like unstashing with Git - mercurial

When invoking hg unshelve --keep and I get a conflict, I need to resolve the conflict and then invoke hg unshelve --continue --keep again. Why is the last step necessary? And why I can't invoke hg unshelve --continue --keep directly without resolving the commit - to get out of the unshelving state?
c:\temp\hg test>hg st
M new.txt
c:\temp\hg test>hg commit -m "fjdjkfs"
c:\temp\hg test>hg unshelve --keep
unshelving change 'shelve'
adding changesets
adding manifests
adding file changes
added 1 changesets with 1 changes to 1 files (+1 heads)
merging new.txt
warning: conflicts during merge.
merging new.txt incomplete! (edit conflicts, then use 'hg resolve --mark')
unresolved conflicts (see 'hg resolve', then 'hg unshelve --continue')
c:\temp\hg test>hg st
M new.txt
? new.txt.orig
c:\temp\hg test>hg unshelve --keep --continue
abort: unresolved conflicts, can't continue
(see 'hg resolve', then 'hg unshelve --continue')
c:\temp\hg test>hg resolve --mark
c:\temp\hg test>hg unshelve --keep --continue
no changes needed to new.txt
unshelve of 'shelve' complete
c:\temp\hg test>hg st
warning: ignoring unknown working parent 11667b875a2d!
? new.txt.orig

Why is the last step necessary?
Because it's possible that not all changes have been applied yet. The merge conflict may happen halfway through the unshelving operation. In this case, you need to pass control back to Mercurial to apply the remaining changes.
And why I can't invoke hg unshelve --continue --keep directly without resolving the commit - to get out of the unshelving state?
If you just want to get out of the unshelving state, and don't care about applying the changes correctly to your working directory, you should just do hg unshelve --abort. The --continue flag is for resuming the unshelve after fixing merge conflicts. Mercurial won't let you do that without resolving the conflicts because this would leave your working directory in a broken state.
See hg help unshelve for more information about these arguments.

This seemed to be a problem with the Mercurial version I was using. With latest version 3.4 it works as expected.

Related

Is there any way to squash commits with uncommitted changes?

I want to squash two commits.
I'm executing the following command:
hg rebase --dest .~2 --base . --collapse
Which gives me:
abort: uncommitted changes
Yes, I have uncommitted changes and I want to keep them.
Is there any way to force this?
You can shelve the uncommitted changes and then do the rebase. Once you are done, unshelve the changes.
hg shelve
hg rebase ...
hg unshelve
I highly recommend backing up your repository first, just to be on the safe side.

taking uncommitted changes on the wrong branch to the right branch

I am using Mercurial.
I have some uncommitted changes but I am on the wrong branch, how do I update to the right branch and take the changes with me?
For uncommited changes you can use the Shelve extension:
hg shelve --all
hg up correct_branch_name
hg unshelve
I asked on irc
mpm said
hg diff > mychanges; hg up -C somewhere; hg import --no-commit mychanges
which I had considered but is what I was trying to avoid.
d70 said
i think you can easily do it by "hg update"ing to a changeset that is a
parent of the branch you're trying to switch to, and then "hg update"ing to the
tip of that branch
so I did that.
hg up -r <shared root rev>
hg up branchIwant
I asked about "why" and was told "you are not allowed to update across branches" which didn't make sense to me at first. Then I realized that because I went through the shared root rev, it isn't across branches.
I usually use
hg qnew
hg qpop
hg up -c <target-rev>
hg qpush
hg qfinish qtip
But I also use jrwren’s approach of going through an ancestor quite regularly.

How to untangle/undo a merge over applied MQ patches?

I accidentally merged a branch into a workspace with applied patches.
How do I clean up this mess? Do I have to clean the merge (hg up -C) or is there some way to save my merge?
Mercurial 1.9.1, TortoiseHg 2.1.2
I reproduced the basis of the situation with these commands on a fresh repo:
echo first > file.txt
hg add
hg ci -m first
hg branch test
echo test1 >> file.txt
hg ci -m test1
hg up 0
echo patch >> file.txt
hg qnew -f patch.diff
Then I performed hg merge test and resolved conflicts, and tried some different things:
Committing is denied due to the involvement of patches:
abort: cannot commit over an applied mq patch
I could not shelve the merge in TortoiseHg.
I could not qnew:
abort: cannot manage merge changesets
The only thing I found I could do to keep the merge was to finish the patches and commit the merge changeset. With the givens, I think keeping the patches and keeping the merge are mutually exclusive.
I know that pbranch allows merging with patches, and there's probably some way to import your MQ patches into it. I don't think it's supported in TortoiseHg, though.

Mercurial: Unable to push to remote repository after pull-merge-commit

I can't figure out why i'm still unable to push to a remote repository:
> hg pull
pulling from ......
searching for changes
no changes found
> hg merge
abort: branch 'default' has one head - please merge with an explicit rev
(run 'hg heads' to see all heads)
> hg heads
changeset: 12942:...
tag: tip
parent: 12940:...
parent: 12941:...
summary: merge
> hg branches
default 12942:...
> hg commit
nothing changed
and finally
> hg push
pushing to ...
searching for changes
abort: push creates new remote heads on branch 'default'!
(did you forget to merge? use push -f to force)
why would that be?
Not sure why, but this solved the issue:
hg push -r tip
where -r is
-r --rev REV [+] a changeset intended to be included in the destination

Transplanting into one changeset

I'm trying to move changes from a couple of changesets into one changeset on the other branch. There are other changes in between that I want to skip, so I don't want to simply merge everything.
hg transplant moves the changes correctly, but now I'd like to flatten them into a single commit. How can I do that?
You can fold them by
Backup the repository, a failure during the process can destroy data
transplant the desired changes to the target branch
transform them there into a mercurial queue (hg qimport -r first-to-fold-rev:)
fold them into one patch (hg qpop until the first patch is applied, then hg qfold <<patch name>> the following patches into this one)
Edit the commit message (When there are NO OUTSTANDING CHANGES hg qrefresh -e)
apply the single patch to your repository (hg qfinish -a).
When there are further unfolded patches:
hg qpush until the head patch
hg qfinish -a
Review the new repo state (hg glog/hg incoming)
hg rebase has an '--collapse` option. I think this is what you are looking for.