hg qnew: abort: working directory revision is not qtip - mercurial

I am trying to create a new patch. So I wrote:
hg qnew -e -f mypatch.patch
But I get a message:
abort: working directory revision is not qtip
What exactly is the error here and how to resolve it?

qtip is the tag that represents the tip of the currently applied patches and must be the parent of the working directory to create patches when one is already applied. You can't have more than one patch series applied at a time, so you have to update to the current tip of the applied patches to create another patch in the currently applied series.

Related

What is the name for the commit/head that corresponds to the local checked-out state?

There is a commit in my hg repository with hash 123abc. This is the last commit I made in the repo. When I run hg diff --from 123abc, I see no output. When I run hg log --graph, I see an # next to 123abc.
In Git this commit would be called "HEAD". I'm not sure what it's called in Mercurial. It is not the "tip", because I pulled other changes after the last time I committed (and hg log -r tip shows commit 456def).
What is this commit/head called?
Mercurial calls this the "parent" or the "parent revision of the working directory", and you can see it by running hg parent, hg id, or hg summary.
You can refer to it as . with the hg log command:
hg log -r . # show the commit message for the parent
If 123abc has no children, then it is a "head".
A head is a changeset with no child changesets. The tip is the most
recently changed head. Other heads are recent pulls into a repository
that have not yet been merged.
(https://www.mercurial-scm.org/wiki/Head)
Regardless whether the current working directory derives from a head or a non-head, I would refer to the commit that precedes it as the "working directory parent" changeset or commit. (That may just be the term my team uses - not sure it is "official".)
The parent may be visible in a GUI tool (like Tortoise) or you can get it using hg parent.
Based on the statements about 456def I'm a little confused whether it has no children, or not? (Maybe update the question to clarify / add more detail)

Hg working directory revision is not a qtip

I'm using mercurial Hg in command line. After created a patch, I needed to revert to another changeset due to some errors happened later. Now it's needed to refresh the patch file. When executing Hg qref it says, abort: working directory revision is not qtip. Also, hg parent is a tip.
I'll add an answer to help other people that may encounter the same error message in the future. I'm not sure our issues was identical but definitely related.
I got "abort: working directory revision is not qtip" while trying to apply a patch onto my working directory.
It turned out that I had older patches in the patch queue which caused the problem and after I deleted these and tried again it worked!
Here's what I did:
Opened a console window and navigated to the working directory where I entered the command:
hg qseries
this listed the patch queue. Then to delete the old patches I entered:
hg qdelete [patch name (which was just listed)]
The response in my case was "abort: cannot delete applied patch ..." and to resolve this I entered:
hg qpop
This unapplied the patch and then I could use the "hg qdelete" command again which now work. Repeated this until all old patches were gone and tried to apply the new patch again.
Found the solution in the "Mercurial: The Definitive Guide", written by Bryan O'Sullivan, under section 12.7.1. http://tortoisehg.bitbucket.io/hgbook/1.4/managing-change-with-mercurial-queues.html#id2858507
Hope someone finds this useful!
It happened due to popping the current head out of the queue. In order to refresh, the patch should have been taken into the head of the queue by qpush.

Someone committed in our central repository. How do we revert it?

We're using a local central repository where everyone pushes to and pulls from. Until recently this repository only contained the .hg folder. Then someone went ahead and committed directly in the central repository creating an "island" changeset with no parent (parent = -1) nor child. The correct way would have been to add it in a local repository and push the changes.
Is there any way to get the working copy of the central repository to get back to the state where it only contain .hg and not be associated with a specific changeset?
The command:
hg update null
Updates a repository's working directory to the point before the first commit, so there are no files in the working directory and hg parents shows -1.
You'll still need to remove the commit if you don't want it, but that's a separate question/issue.
Since this is your local central repository and these are commands that edit history, please take every precaution, like trying things out on a copy of the repository first.
hg rollback (to remove the last repository change)
https://www.mercurial-scm.org/wiki/Rollback
Roll back the last transaction in a repository.
hg strip (to remove specific revisions)
https://www.mercurial-scm.org/wiki/Strip
hg strip rev removes the rev revision and all its descendants from a repository.
Also see:
https://www.mercurial-scm.org/wiki/EditingHistory
If you catch your mistake immediately (or reasonably soon), you can just use hg strip REV to roll back the latest (one or more) changes. ...
Edit: This answers the question in its original form. The OP has since edited the question.
Just delete everything except the .hg folder.
If I understand correctly what happened, someone changed into the repository directory and committed a single file as an 'added file' without first checking out any changeset from the active directory.
What you ended up with is something like the following history graph:
0:a43f 1:2843 2:bc81 3:2947
o ------ o ------ o ------ o
4:228f
o
where changeset 4:228f has the "null id" as its parent changeset.
Depending on whether you want to keep changeset 4:228f or not, you can follow one of the following strategies:
Option 1: Clone the repository without the offending change
You can create a new clone of the repository, specifying revision 3:2947 as the target revision. This will pull change 3:2947 and all its ancestor changesets into the new repository. Since the offending changeset is not linked into the ancestry of changeset 3:2947, it will not be part of the new clone.
I recommend saving the old repository first, and then moving everything over to a new clone, e.g. any repository-specific setup files you keep in its .hg/ directory.
If your current repository lives in /work/repo/foo, one way to do this would be:
$ cd /work/repo
$ mv foo foo.bak
$ hg clone -r 2947 foo.bak newfoo
Now copy over any .hg/ setup files, e.g. your original .hg/hgrc file:
$ cp foo.bak/.hg/hgrc newfoo/.hg/hgrc
Finally move the new foo repository in place:
$ mv newfoo foo
Option 2: Clone the repository and keep but rebase the change
Do the same as before, but before you move the newfoo repository in place, use the "hg export" command to extract a copy of the offending change from the old repository. Then check out a working copy of the tip-most changeset in the newfoo tree and import the file changes of the offending change as a normal changeset of your current history graph.
So, right before mv newfoo foo, save the patch of the offending change by typing:
$ cd /work/repo/foo.bak
$ hg export -r 228f --git > /tmp/patchfile.diff
then you can check-out the latest revision of the new repository, and re-import the patch on top of your current history:
$ cd /work/repo/newfoo
$ hg update --clean tip
$ hg import /tmp/patchfile.diff
If the offending changeset merely adds a new file, this should work fine and you are ready to move the new repository in place!
Before doing the final rename though, it may be a good idea to remove the working-copy files of the new repository:
$ cd /work/repo/newfoo
$ hg update --clean null

Adding uncommitted change into a new patch with Mercurial queues

The process of creating patches in Mercurial is as follows:
Create patch with qnew -> Make changes -> Refresh patch
What if I have already made (uncommited) changes and I want to add them to the queue?
It depends on your version, and it looks like it changed in 1.5.1.
1.5.1 or later
The command will add any uncommitted changes by default
qnew creates a new patch on top of the currently-applied patch (if any).
The patch will be initialized with any outstanding changes in the working
directory.
earlier than 1.5.1
You want to use qnew -f. From the docs:
-f: Create a new patch if the contents of the working directory are modified. Any outstanding modifications are added to the newly created patch, so after this command completes, the working directory will no longer be modified.
Actually, the patch process works the same whether there are uncommitted changes or not. I always do it as follows:
[... make changes ...]
hg qnew -m "foo bar changes" foobar.patch
--> new empty patch at top of queue
hg qrefresh
--> this adds all diffs from 'hg diff' into the current top patch
EDIT: #CaseBash has correctly pointed out that I'm wrong about the current default behavior!

Hg Pull vs. Update to branch tip

Using TortoiseHg Synchronize, clicking "Pull" pulls down the 2nd most recent revision.
At the bottom of the Synchronize interface is a button, "Update to branch tip." Clicking this button pulls down the most recent revision.
What is happening here?
Command line hg tells this:
$ hg help pull
...
Pull changes from a remote repository to a local one.
...
-R is specified). By default, this does not update the copy of the
project in the working directory.
vs.
$ hg help up
...
Update the repository's working directory to the specified
revision, or the tip of the current branch if none is specified.
If you are new to mercurial or want to know you havent missed any options, this is could be helpful:
http://blog.hanxiaogang.com/hg-guide/