I have noticed by mercurial repository expanding in size when ever I use repo B to pull changes from repo A.
It seems that TortoiseHG creates files like hg-bundle-r3e6uf.hg10un under .hg directory. These files are usually 1-2MB in size each, so nothing too big, but together they create a lot, and can be an annoyance when doing backups.
This does not seem to happen if I pull changes instantly without reviewing them, or if I use repo A to push changes to B.
These bundle files seem useless as they are not copied when cloning the repository B.
Also the cloned repo is almost half smaller without them, so it is like data in these files wasn't moved to other files either.
Is it possible to:
A) Avoid creating these bundles on pull. (Pushing is option only when I have access to both repos)
B) Use some command to cleanup .hg directory. (Cloning is not very elegant)
EDIT:
When I select 'Incoming' first bundle is created:
% hg --repository C:\temp\hg\testB incoming --quiet --bundle c:\docume~1\username\locals~1\temp\thg.hlngus\CtemphgtestA_iavzew.hg C:\temp\hg\testA
1:d806c8cb0355
2:e0e3b20d5cb2
3:4e803a7ecefc
[command completed successfully Fri Aug 02 09:59:12 2013]
and then 'Accept', the second bundle is created:
% hg --repository C:\temp\hg\testB pull --verbose c:\docume~1\username\locals~1\temp\thg.hlngus\CtemphgtestA_iavzew.hg
pulling from c:\docume~1\username\locals~1\temp\thg.hlngus\CtemphgtestA_iavzew.hg
searching for changes
all local heads known remotely
3 changesets found
adding changesets
adding manifests
adding file changes
added 3 changesets with 3 changes to 1 files
(run 'hg update' to get a working copy)
[command completed successfully Fri Aug 02 10:00:10 2013]
Where as using 'Pull' directly, no extra bundles are created:
% hg --repository C:\temp\hg\testB pull --verbose C:\temp\hg\testA
pulling from C:\temp\hg\testA
searching for changes
all local heads known remotely
3 changesets found
adding changesets
adding manifests
adding file changes
added 3 changesets with 3 changes to 1 files
(run 'hg update' to get a working copy)
[command completed successfully Fri Aug 02 10:01:52 2013]
It seems this is TortoiseHg specific issue. Solution is either use push or use pull directly from command line to avoid extra bundles. Only (safe) way to cleanup seems to be the repository cloning.
Related
We discovered that our Hg repository got corrupted several weeks ago. This corruption seems to have propagated: all clones (the central repo and the user repos) are corrupted, pretty badly, in the same way. I think we could have prevented it if we did verification at that time.
Is there some Hg setting that would cause verification on each push, and prevent push in case of verification failure? I know I could implement it as a hook in Python, but is there maybe a simpler solution?
Is it also possible to do the opposite: make sure the remote repository is verified before pulling?
FWIW, I am on Windows 10 and we are using TortoiseHg.
Update: I've tried creating hooks as suggested by Jordi. Hg now hangs waiting for locks. Here is what I see:
c:\Users\username\test-hook>hg init
c:\Users\username\test-hook>cd ..
c:\Users\username>hg clone test-hook test-hook-clone
updating to branch default
0 files updated, 0 files merged, 0 files removed, 0 files unresolved
# At this point I edited clone repository settings to include
# [hooks]
# preoutgoing = hg verify
#
# Then I created a test.txt file and "added" it via TortoiseHg context menu.
c:\Users\username\test-hook-clone>hg commit
c:\Users\username\test-hook-clone>hg status
c:\Users\username\test-hook-clone>hg outgoing
comparing with c:\Users\username\test-hook
searching for changes
changeset: 0:a61d33af6cdb
tag: tip
user: username
date: Mon May 06 20:32:54 2019 +0200
summary: test file added
c:\Users\username\test-hook-clone>hg push -verbose
pushing to c:\Users\username\test-hook
searching for changes
running hook preoutgoing: hg verify
waiting for lock on repository c:\Users\username\test-hook-clone held by process '16840' on host 'LT407233'
To answer your question, the hook does not have to be written in Python. In the appropriate server's hgrc (either at the repository level or the system level), simply set
[hooks]
preoutgoing = hg verify
preincoming = hg verify
This may significantly slow down all pull and push operations, but perhaps you are willing to sacrifice speed for correctness.
This will result in output like this when a client tries to pull from a corrupt repo:
$ hg clone http://localhost:9000 sample-repo
requesting all changes
remote: abort: preoutgoing hook exited with status 1
and in your server logs, you should see output similar to
127.0.0.1 - - [18/Apr/2019 12:41:09] "GET /?cmd=batch HTTP/1.1" 200 - x-hgarg-1:cmds=lheads+%3Bknown+nodes%3D x-hgproto-1:0.1 0.2 comp=zstd,zlib,none,bzip2 partial-pull
checking changesets
checking manifests
crosschecking files in changesets and manifests
checking files
a#0: broken revlog! (index data/a.i is corrupted)
warning: orphan data file 'data/a.i'
checked 2 changesets with 1 changes to 2 files
1 warnings encountered!
1 integrity errors encountered!
(first damaged changeset appears to be 0)
You can enable a server side option to perform more validation all incoming content, just set the server.validate=yes option on your server.
The simplest way is to enable it in your server global hgrc or in the repository .hg/hgrc file by adding the following two lines:
[server]
validate = yes
This is a server option but you can also use it on the client. It should validate pull too.
(By the way, what kind of corruption are you seeing?)
I have a repo on a network drive (served by Windows server), with local repos pushing/pulling to it on the various machines I work on.
I just dealt with this problem, and solved it by cloning the repo from the network drive to a local disk, pushing, then cloning it back again. The machine from which I did this had not problem pushing further changes after this.
Now I just tried pushing from my laptop, and this happens:
% hg --debug push "Z:\[main repo]"
pushing to Z:\[main repo]
query 1; heads
searching for changes
all remote heads known locally
listing keys for "bookmarks"
2 changesets found
list of changesets:
2ed25c8975482734e3b9eed828573fd711d26fd8
19a424c011ffd0c887cf1d54ed0b537a6c1af714
adding changesets
add changeset 2ed25c897548
add changeset 19a424c011ff
adding manifests
adding file changes
adding GEM.py revisions
transaction abort!
rollback completed
abort: No usable temporary file name found
[command returned code 255 Thu Mar 09 18:51:11 2017]
The only info pertaining to this error message I have found so far is this, and I definitely have no files named con.*in my project. There are several named con*.py but they have never been a problem, and both the laptop and my workstation are running Windows 7, and I've been working on this project for a few years now.
I have happily pushed from this laptop for over a year, and it was never a problem. I don't really have any good idea where to even start looking. Could it be connected to the fact that my workstation had the main repo opened at the same time? It was definitely not doing anything to it at the time.
Update:
I ran hg verify, and this is what it returns -- no problem as far as aI can tell
% hg --debug verify
repository uses revlog format 1
checking changesets
checking manifests
crosschecking files in changesets and manifests
checking files
73 files, 74 changesets, 226 total revisions
[command completed successfully Fri Mar 10 08:58:02 2017]
I had faced the same error as well.
I just ran tortoise hg as as administrator and that fixed it for me
I don't have an answer yet but I would try the following:
Update to the latest mercurial version (4.1) and try again
Verify the repo integrity with hg verify
Although I understand it always worked as is, try to rename all the con.py files. The thing with CON is that it represents a device, I think it comes from DOS times :-)
If I understand correctly, you push to Z:[main repo] where Z: is a Windows share. Try to push to the same repo in another way, with ssh (requires some setup, yes)
Good luck, very bizarre problem :-/
I'm working on my thesis and storing changes in mercurial. I'm not getting an error that I've got multiple heads, which I'm confused about -- I've only got one working repository which I push occasionally to bitbucket. Here's what happened:
$ hg commit -m "Fixing up..."
abort: No such file or directory: /Users/me/Dropbox/thesis/thesis_tex/simple.pdf
$ hg commit -m "Adding in page headers"
created new head
...one more commit, not having realized that having created a new head was a problem...
$ hg push
pushing to ssh://hg#bitbucket.org/...
searching for changes
abort: push creates new remote heads!
(did you forget to merge? use push -f to force)
$ hg heads
changeset: 26:3823a395b1ce
tag: tip
user: me
date: Fri Aug 26 09:39:45 2011 -0400
summary: Adding...
changeset: 24:c7c6517d4281
user: me
date: Thu Aug 25 16:34:42 2011 -0400
summary: Fixing up...
How can I easily get rid of the other head, without messing up my working directory? Why did a second head get created? Is there a problem with keeping mercurial repositories in dropbox folders?
How can I easily get rid of the other head, without messing up my working directory?
Merge the branches with hg merge.
Is there a problem with keeping mercurial repositories in dropbox folders?
This seems redundant to me, since Dropbox keeps a 30-day history on your files. I'd choose either Hg+Bitbucket (or whatever Mercurial hosting) or Dropbox, but not both.
Edit: Why not use Mercurial and Dropbox? Here's why.
Ben Hughes said it well:
By keeping your Mercurial repo on Dropbox you’re version controlling your version control system files. If you somehow manage to cause a conflict with files in your .hg directory, things could get messy. Recoverable, but messy.
I disagree with #Matt Ball on the dropbox matter.
I think redundancy is your friend. Also the purpose of Hg and the dropbox is slightly different in your case.
Dropbox backs up for you automatically (as well as tracking file changes and letting you work on any machine with internet and making it easy to share your work.) and Hg lets you work offline and commit in logical chunks (as well as working as backup when you sync).
I have used Hg in my dropbox folder without problem for at least a year and I have not experienced any problems.
If you work on more than one machine and have the dropbox/Hg combo on all machines I suggest that you let dropbox do the syncing.
I have a local repository and I want to get the latest changes from a remote repository. I know i can clone but clone only works on new directories. I know i can delete the local repository and then clone but i want to know how do it the Mercurial way if there is one.
EDIT: hg pull -u doesn't work if there are conflicts. I don't want to resolve conflicts I just want to get a fresh copy of the remote repo regardless of local changes.
ANSWER: Short answer: Maybe it can be done (see answer below) but re-clone is easier.
Long answer: if you want to get the latest from a remote and disregard your local changes and commits then you'll have to clone to a new local repository or remove the local repository and clone another one. This is because if you have conflicting changes then hg will force you to resolve them manually.
Which is OK but I just wanted to know if it can be done without removing my local repo.
I think you're just looking for this:
hg pull
hg up --clean
That will pull latest set of revisions from the remote repoistory and then update your local repository with a clean copy, regardless of whether or not you have made any changes to the files. No merging necessary.
The only caveat is, if you have added files to your local repository, and they have not been committed, they will be orphaned (left in place, but not in the repository) after the update. If you do an hg stat you should see them denoted with question marks. If the added files have been committed to your local repository, Mercurial will properly clean up after them.
Here's the remote repository (remote rev 6):
Mode LastWriteTime Length Name
---- ------------- ------ ----
d---- 3/24/2011 2:16 PM .hg
-a--- 3/24/2011 2:16 PM 83 addedtoremote.txt
-a--- 3/24/2011 1:56 PM 726 sample.txt
Here's the local repository (cloned from remote rev 4 earlier) with changed and added files (local rev 5):
Mode LastWriteTime Length Name
---- ------------- ------ ----
d---- 3/24/2011 2:03 PM .hg
-a--- 3/24/2011 2:05 PM 9 sample.txt
-a--- 3/24/2011 2:05 PM 58 addedtolocal.txt
Here's the local repository after doing a pull and clean update (local rev 6):
Mode LastWriteTime Length Name
---- ------------- ------ ----
d---- 3/24/2011 2:17 PM .hg
-a--- 3/24/2011 2:17 PM 83 addedtoremote.txt
-a--- 3/24/2011 2:15 PM 726 sample.txt
The changes to sample.txt have been wiped out, addedtolocal.txt has been deleted and addedtoremote.txt has been added.
Looks like you are looking for hg strip, which isn't part of the Mercurial core. It's available through the MqExtension. You can enable it by adding the following in your .hgrc or Mercurial.ini file (https://www.mercurial-scm.org/wiki/MqExtension)
[extensions]
mq =
Then you will be able to:
hg strip rev
This will remove your changesets to the point where you shouldn't have any merge conflicts. This will impact the branch history though. But then again, that's not so bad, if you keep them any good future changeset will have an ancestor that you decided to trash.
If you are just trying something out, you're better of doing it in a separate branch which is easy to close and abandon later.
If you really are looking to keep the bad changeset you can pass in configuration option to the merge command like this
hg --config ui.merge=internal:other merge
This is documented in Mercurial tips and tricks.
Just "pull" changes from the remote repo. Think that "pull" and "push" are change-sets transactions between repos.
Once done, you have to "update" the sources.
You can rebase your modifications, minimizing the need for merges. Just call hg pull --rebase
You'll have to have rebase extension enabled in your ~/.hgrc:
[extensions]
rebase =
Since this is such a common action, there is an extension that does a hg pull -u, hg merge and hg commit in one command:
hg fetch
From the hg book:
Enabling the fetch extension is easy.
Edit the .hgrc file in your home
directory, and either go to the
extensions section or create an
extensions section. Then add a line
that simply reads “fetch=”.
[extensions]
fetch =
When remotely updating a Mercurial Repository, I am getting the following error from the hg update command that is being run on the remote server after the push. I looked around online for some help for this however was unsuccessful in finding anything useful. At this point, I am hoping for some ideas and / or insight as to what would be causing this problem.
The error is just below. It occurred when pushing two changesets. One changeset included an unrelated index.html file change. The other changeset was a merge, which included the index.html change as well as the renaming of the two image files.
levinaris#server01:/home/web/repository$ hg push
pushing to ssh://10.10.1.12//home/web/repository
searching for changes`remote: adding changesets
remote: adding manifests
remote: adding file changes
remote: added 2 changesets with 1 changes to 1 files
remote: abort: Operation not permitted: /home/web/repository/html/images/image.gif
remote: warning: changegroup hook exited with status 255
Additional details:
Both images are 10385 bytes in size. (yes, this error occurs on two images I have)
The two images had their names changed in changesets that were already pushed and hg updated due to case-folding collisions when attempting to pull the repositories down to Windows PCs.
The target server has the following hook in /etc/mercurial/hgrc:
[hooks]
changegroup = hg update
As a work-around, I did the following:
Deleted image.gif.
Deleted another image file that produced the error.
Ran hg update - success!
Ran hg revert html/image/image.gif
Ran hg revert html/image/otherimage.gif
At this point, I am trying to better understand the cause of this problem, so that I can ensure a solid, easy-to-use implementation in my environment. I really appreciate your help!!
After using hg --debug update in the hook, I received this output:
levinaris#server01:/home/web/repository$ hg push
pushing to /home/web/staging/repository
searching for changes
adding changesets
adding manifests
adding file changes
added 2 changesets with 1 changes to 1 files
resolving manifests
overwrite False partial False
ancestor 58a5edb95c9a local 58a5edb95c9a+ remote 3aafb97b148c
searching for copies back to rev 6
html/index.php: remote is newer -> g
html/images/otherimage.gif.casefolding: update permissions -> e
html/images/image.gif: update permissions -> e
abort: Operation not permitted: /home/web/staging/repository/html/images/image.gif
warning: changegroup hook exited with status 255
Additional Permission Information:
All 3 files in the 2 changesets have 775 permission with the webuser:dev user:group.
My Global hgrc file has the webuser trusted
[trusted]
users = webuser
Is it possible that the permissions that file on the server were such that it couldn't be overwitten by the person doing the push?
If, for example, two different people have done that push (and thus update) the second person isn't going to be able to overwrite the files created by the first person's push triggered update.
Maybe try changing the hook to this for a test (you don't actually have those single quotes on your hook, right?):
[hooks]
changegroup = hg --debug update
If it is a permissions issue the usual fix is to put everyone who will be pushing and updating into the same group (I call mine 'hg') and then using the sticky group bit on all the directories in the repo to make sure new files have that group.