1

In a nutshell:

What file format are Mercurial bundles in? How can I extract the commit date information?

Whole story:

I've started using HgSubversion. This Mercurial extension allows you to work on a Mercurial repo and push and pull from Subversion.

Yesterday I pushed two months worth of changes back to Subversion. Two surprises:

  • The hg push needed about two hours for 200 commits.
  • The original hg commit date is lost and supplanted by the hg push date.

I found the explanation for the push slowness on the mailing list. Okay, I can easily adapt to that: push early, push often. You just have to know you have to do this.

I'm disappointed with the original commit date being lost. I can see the date replacement enacted by HgSubversion makes sense for most scenarios. However, it does not make sense for my scenario.

Fortunately, the original commit date is contained in the strip-backup files. These files reside in .hg/strip-backup/; it seems they're called bundles. (They're created when, while pushing to Subversion, subtrees are repeatedly stripped off the tree to be reattached after the SVN commit created by hg push is pulled back into Mercurial. See the "slowness" link above and search the page for Patrick Mézards comments.) I could extract the date from the bundle and then reset the svn:date in Subversion.

But how can I access the information contained in the bundle? It doesn't seem to a known compression format.

$ mkdir bundle
$ cd bundle
$ cp ~/RepoHgSvn/.hg/strip-backup/ecbe9ff1cf0b-backup.hg .
$ file ecbe9ff1cf0b-backup.hg
ecbe9ff1cf0b-backup.hg: Mercurial changeset bundle (bzip2 compressed)
# Okay then ...
$ bzip2 -d ecbe9ff1cf0b-backup.hg
bzip2: Can't guess original name for ecbe9ff1cf0b-backup.hg
       -- using ecbe9ff1cf0b-backup.hg.out
bzip2: ecbe9ff1cf0b-backup.hg is not a bzip2 file.
# Okay, the file utility often goes wrong ...
$ mv ecbe9ff1cf0b-backup.hg ecb.bz2
$ bzip2 -d ecb.bz2
bzip2: ecb.bz2 is not a bzip2 file.
$ mv ecb.bz2 ecb.gz
$ gzip -d ecb.gz
gzip: ecb.gz: not in gzip format
$ mv ecb.gz ecb.zip
$ unzip ecb.zip
Archive:  ecb.zip
  End-of-central-directory signature not found.
$ 7z l ecb.zip
Error: ecb.zip: is not supported archive

What file format is the bundle in and how can I extract the commit date information?

Community
  • 1
  • 1
Lumi
  • 14,775
  • 8
  • 59
  • 92

1 Answers1

1

You can get a repository with the old revisions by

mkdir foo
cd foo
hg init
hg pull ~/RepoHgSvn
hg pull ~/RepoHgSvn/.hg/strip-backup/ecbe9ff1cf0b-backup.hg

then you have a repo where the svn revisions are along the original revisions.

But when you change the commit dates in svn you need to redo the cloning of the original svn repository, since the svn metadata in the repository, from where you pushed the changesets into subversion, is wrong afterward the svn property change (the current svn clone has all revisions set to their push times, and it might be impossible to re-fetch those changed revisions).

Rudi
  • 19,366
  • 3
  • 55
  • 77
  • Thanks. Indeed the earliest backup will contain *all* original commit dates for subsequent commits. I mistakenly thought I'd have to go through all backup files. Also thanks for the notice regarding recloning; will actually have to do that unless I accept to have wrong dates in my Mercurial repo. It would be just cool if I could trick HgSubversion into setting the commit date with the commit *before* pulling the revision back from Subversion. Will take a look at the source if I find the time. – Lumi Dec 04 '11 at 16:56