mercurial/bookmarks.py
changeset 42347 526750cdd02d
parent 42339 2b77183ac477
child 42920 08fce968d00b
equal deleted inserted replaced
42346:b162229ebe0d 42347:526750cdd02d
    31 # until 3.5, bookmarks.current was the advertised name, not
    31 # until 3.5, bookmarks.current was the advertised name, not
    32 # bookmarks.active, so we must use both to avoid breaking old
    32 # bookmarks.active, so we must use both to avoid breaking old
    33 # custom styles
    33 # custom styles
    34 activebookmarklabel = 'bookmarks.active bookmarks.current'
    34 activebookmarklabel = 'bookmarks.active bookmarks.current'
    35 
    35 
       
    36 BOOKMARKS_IN_STORE_REQUIREMENT = 'bookmarksinstore'
       
    37 
       
    38 def bookmarksinstore(repo):
       
    39     return BOOKMARKS_IN_STORE_REQUIREMENT in repo.requirements
       
    40 
       
    41 def bookmarksvfs(repo):
       
    42     return repo.svfs if bookmarksinstore(repo) else repo.vfs
       
    43 
    36 def _getbkfile(repo):
    44 def _getbkfile(repo):
    37     """Hook so that extensions that mess with the store can hook bm storage.
    45     """Hook so that extensions that mess with the store can hook bm storage.
    38 
    46 
    39     For core, this just handles wether we should see pending
    47     For core, this just handles wether we should see pending
    40     bookmarks or the committed ones. Other extensions (like share)
    48     bookmarks or the committed ones. Other extensions (like share)
    41     may need to tweak this behavior further.
    49     may need to tweak this behavior further.
    42     """
    50     """
    43     fp, pending = txnutil.trypending(repo.root, repo.vfs, 'bookmarks')
    51     fp, pending = txnutil.trypending(repo.root, bookmarksvfs(repo), 'bookmarks')
    44     return fp
    52     return fp
    45 
    53 
    46 class bmstore(object):
    54 class bmstore(object):
    47     r"""Storage for bookmarks.
    55     r"""Storage for bookmarks.
    48 
    56 
    89                         # TypeError:
    97                         # TypeError:
    90                         # - bin(...)
    98                         # - bin(...)
    91                         # ValueError:
    99                         # ValueError:
    92                         # - node in nm, for non-20-bytes entry
   100                         # - node in nm, for non-20-bytes entry
    93                         # - split(...), for string without ' '
   101                         # - split(...), for string without ' '
    94                         repo.ui.warn(_('malformed line in .hg/bookmarks: %r\n')
   102                         bookmarkspath = '.hg/bookmarks'
    95                                      % pycompat.bytestr(line))
   103                         if bookmarksinstore(repo):
       
   104                             bookmarkspath = '.hg/store/bookmarks'
       
   105                         repo.ui.warn(_('malformed line in %s: %r\n')
       
   106                                      % (bookmarkspath, pycompat.bytestr(line)))
    96         except IOError as inst:
   107         except IOError as inst:
    97             if inst.errno != errno.ENOENT:
   108             if inst.errno != errno.ENOENT:
    98                 raise
   109                 raise
    99         self._active = _readactive(repo, self)
   110         self._active = _readactive(repo, self)
   100 
   111 
   190 
   201 
   191     def _recordchange(self, tr):
   202     def _recordchange(self, tr):
   192         """record that bookmarks have been changed in a transaction
   203         """record that bookmarks have been changed in a transaction
   193 
   204 
   194         The transaction is then responsible for updating the file content."""
   205         The transaction is then responsible for updating the file content."""
       
   206         location = '' if bookmarksinstore(self._repo) else 'plain'
   195         tr.addfilegenerator('bookmarks', ('bookmarks',), self._write,
   207         tr.addfilegenerator('bookmarks', ('bookmarks',), self._write,
   196                             location='plain')
   208                             location=location)
   197         tr.hookargs['bookmark_moved'] = '1'
   209         tr.hookargs['bookmark_moved'] = '1'
   198 
   210 
   199     def _writerepo(self, repo):
   211     def _writerepo(self, repo):
   200         """Factored out for extensibility"""
   212         """Factored out for extensibility"""
   201         rbm = repo._bookmarks
   213         rbm = repo._bookmarks
   202         if rbm.active not in self._refmap:
   214         if rbm.active not in self._refmap:
   203             rbm.active = None
   215             rbm.active = None
   204             rbm._writeactive()
   216             rbm._writeactive()
   205 
   217 
   206         with repo.wlock():
   218         if bookmarksinstore(repo):
   207             with repo.vfs('bookmarks', 'w', atomictemp=True,
   219             vfs = repo.svfs
   208                           checkambig=True) as f:
   220             lock = repo.lock()
       
   221         else:
       
   222             vfs = repo.vfs
       
   223             lock = repo.wlock()
       
   224         with lock:
       
   225             with vfs('bookmarks', 'w', atomictemp=True, checkambig=True) as f:
   209                 self._write(f)
   226                 self._write(f)
   210 
   227 
   211     def _writeactive(self):
   228     def _writeactive(self):
   212         if self._aclean:
   229         if self._aclean:
   213             return
   230             return
   426     for book, node in listbinbookmarks(repo):
   443     for book, node in listbinbookmarks(repo):
   427         d[book] = hex(node)
   444         d[book] = hex(node)
   428     return d
   445     return d
   429 
   446 
   430 def pushbookmark(repo, key, old, new):
   447 def pushbookmark(repo, key, old, new):
   431     with repo.wlock(), repo.lock(), repo.transaction('bookmarks') as tr:
   448     if bookmarksinstore(repo):
       
   449         wlock = util.nullcontextmanager()
       
   450     else:
       
   451         wlock = repo.wlock()
       
   452     with wlock, repo.lock(), repo.transaction('bookmarks') as tr:
   432         marks = repo._bookmarks
   453         marks = repo._bookmarks
   433         existing = hex(marks.get(key, ''))
   454         existing = hex(marks.get(key, ''))
   434         if existing != old and existing != new:
   455         if existing != old and existing != new:
   435             return False
   456             return False
   436         if new == '':
   457         if new == '':