changeset 14266:89e7d35e0ef0 stable

fix bookmarks rollback behavior Before this patch undo.bookmarks was created on bookmarks write and not with other transaction-related files. There were two issues: first is that if you have changed bookmarks few times after a transaction happened, rollback will give you a state which can point to non-existing revision. Second is that if you have not changed bookmarks after a transaction, rollback will touch your state anyway. This change also adds `localrepo._writejournal` method, which can be used by other extensions to save their transaction-related backup in right time.
author Alexander Solovyov <alexander@solovyov.net>
date Sun, 01 May 2011 13:07:00 +0200
parents b00ab6890fe9
children a55a0045704c 2a6ee654655e
files mercurial/bookmarks.py mercurial/localrepo.py tests/test-bookmarks.t tests/test-fncache.t tests/test-hardlinks.t tests/test-hup.t tests/test-inherit-mode.t
diffstat 7 files changed, 46 insertions(+), 17 deletions(-) [+]
line wrap: on
line diff
--- a/mercurial/bookmarks.py	Fri May 06 15:37:38 2011 +0300
+++ b/mercurial/bookmarks.py	Sun May 01 13:07:00 2011 +0200
@@ -61,12 +61,6 @@
     '''
     refs = repo._bookmarks
 
-    try:
-        bms = repo.opener('bookmarks').read()
-    except IOError:
-        bms = ''
-    repo.opener('undo.bookmarks', 'w').write(bms)
-
     if repo._bookmarkcurrent not in refs:
         setcurrent(repo, None)
     for mark in refs.keys():
--- a/mercurial/localrepo.py	Fri May 06 15:37:38 2011 +0300
+++ b/mercurial/localrepo.py	Sun May 01 13:07:00 2011 +0200
@@ -669,6 +669,17 @@
             raise error.RepoError(
                 _("abandoned transaction found - run hg recover"))
 
+        journalfiles = self._writejournal(desc)
+        renames = [(x, undoname(x)) for x in journalfiles]
+
+        tr = transaction.transaction(self.ui.warn, self.sopener,
+                                     self.sjoin("journal"),
+                                     aftertrans(renames),
+                                     self.store.createmode)
+        self._transref = weakref.ref(tr)
+        return tr
+
+    def _writejournal(self, desc):
         # save dirstate for rollback
         try:
             ds = self.opener("dirstate").read()
@@ -679,16 +690,15 @@
             encoding.fromlocal(self.dirstate.branch()))
         self.opener("journal.desc", "w").write("%d\n%s\n" % (len(self), desc))
 
-        renames = [(self.sjoin("journal"), self.sjoin("undo")),
-                   (self.join("journal.dirstate"), self.join("undo.dirstate")),
-                   (self.join("journal.branch"), self.join("undo.branch")),
-                   (self.join("journal.desc"), self.join("undo.desc"))]
-        tr = transaction.transaction(self.ui.warn, self.sopener,
-                                     self.sjoin("journal"),
-                                     aftertrans(renames),
-                                     self.store.createmode)
-        self._transref = weakref.ref(tr)
-        return tr
+        bkname = self.join('bookmarks')
+        if os.path.exists(bkname):
+            util.copyfile(bkname, self.join('journal.bookmarks'))
+        else:
+            self.opener('journal.bookmarks', 'w').write('')
+
+        return (self.sjoin('journal'), self.join('journal.dirstate'),
+                self.join('journal.branch'), self.join('journal.desc'),
+                self.join('journal.bookmarks'))
 
     def recover(self):
         lock = self.lock()
@@ -2027,6 +2037,11 @@
             util.rename(src, dest)
     return a
 
+def undoname(fn):
+    base, name = os.path.split(fn)
+    assert name.startswith('journal')
+    return os.path.join(base, name.replace('journal', 'undo', 1))
+
 def instance(ui, path, create):
     return localrepository(ui, util.drop_scheme('file', path), create)
 
--- a/tests/test-bookmarks.t	Fri May 06 15:37:38 2011 +0300
+++ b/tests/test-bookmarks.t	Sun May 01 13:07:00 2011 +0200
@@ -231,6 +231,7 @@
      Y                         2:db815d6d32e6
    * Z                         2:db815d6d32e6
      x  y                      2:db815d6d32e6
+
 test summary
 
   $ hg summary
@@ -244,3 +245,16 @@
 
   $ hg id
   db815d6d32e6 tip Y/Z/x  y
+
+test rollback
+
+  $ hg bookmark -f Y -r 1
+  $ hg bookmark -f Z -r 1
+  $ hg rollback
+  repository tip rolled back to revision 1 (undo commit)
+  working directory now based on revision 0
+  $ hg bookmarks
+     X                         0:f7b1eb17ad24
+     X2                        1:925d80f479bb
+     Y                         -1:000000000000
+   * Z                         0:f7b1eb17ad24
--- a/tests/test-fncache.t	Fri May 06 15:37:38 2011 +0300
+++ b/tests/test-fncache.t	Sun May 01 13:07:00 2011 +0200
@@ -76,6 +76,7 @@
   .hg/last-message.txt
   .hg/requires
   .hg/undo
+  .hg/undo.bookmarks
   .hg/undo.branch
   .hg/undo.desc
   .hg/undo.dirstate
@@ -102,6 +103,7 @@
   .hg/store/data/tst.d.hg
   .hg/store/data/tst.d.hg/_foo.i
   .hg/store/undo
+  .hg/undo.bookmarks
   .hg/undo.branch
   .hg/undo.desc
   .hg/undo.dirstate
--- a/tests/test-hardlinks.t	Fri May 06 15:37:38 2011 +0300
+++ b/tests/test-hardlinks.t	Sun May 01 13:07:00 2011 +0200
@@ -195,6 +195,7 @@
   2 r4/.hg/store/data/f1.i
   2 r4/.hg/store/fncache
   2 r4/.hg/store/undo
+  2 r4/.hg/undo.bookmarks
   2 r4/.hg/undo.branch
   2 r4/.hg/undo.desc
   2 r4/.hg/undo.dirstate
@@ -223,6 +224,7 @@
   2 r4/.hg/store/data/f1.i
   2 r4/.hg/store/fncache
   2 r4/.hg/store/undo
+  2 r4/.hg/undo.bookmarks
   2 r4/.hg/undo.branch
   2 r4/.hg/undo.desc
   2 r4/.hg/undo.dirstate
--- a/tests/test-hup.t	Fri May 06 15:37:38 2011 +0300
+++ b/tests/test-hup.t	Sun May 01 13:07:00 2011 +0200
@@ -17,4 +17,4 @@
   rollback completed
   killed!
   $ echo .hg/* .hg/store/*
-  .hg/00changelog.i .hg/journal.branch .hg/journal.desc .hg/journal.dirstate .hg/requires .hg/store .hg/store/00changelog.i .hg/store/00changelog.i.a
+  .hg/00changelog.i .hg/journal.bookmarks .hg/journal.branch .hg/journal.desc .hg/journal.dirstate .hg/requires .hg/store .hg/store/00changelog.i .hg/store/00changelog.i.a
--- a/tests/test-inherit-mode.t	Fri May 06 15:37:38 2011 +0300
+++ b/tests/test-inherit-mode.t	Sun May 01 13:07:00 2011 +0200
@@ -77,6 +77,7 @@
   00660 ./.hg/store/data/foo.i
   00660 ./.hg/store/fncache
   00660 ./.hg/store/undo
+  00660 ./.hg/undo.bookmarks
   00660 ./.hg/undo.branch
   00660 ./.hg/undo.desc
   00660 ./.hg/undo.dirstate
@@ -117,6 +118,7 @@
   00660 ../push/.hg/store/data/foo.i
   00660 ../push/.hg/store/fncache
   00660 ../push/.hg/store/undo
+  00660 ../push/.hg/undo.bookmarks
   00660 ../push/.hg/undo.branch
   00660 ../push/.hg/undo.desc
   00660 ../push/.hg/undo.dirstate