mercurial/rewriteutil.py
changeset 45424 0a57ef4b3bdb
parent 45122 a391d0710f22
child 45425 f7e293e0475f
equal deleted inserted replaced
45423:d4cf80341589 45424:0a57ef4b3bdb
     5 # This software may be used and distributed according to the terms of the
     5 # This software may be used and distributed according to the terms of the
     6 # GNU General Public License version 2 or any later version.
     6 # GNU General Public License version 2 or any later version.
     7 
     7 
     8 from __future__ import absolute_import
     8 from __future__ import absolute_import
     9 
     9 
       
    10 import re
       
    11 
    10 from .i18n import _
    12 from .i18n import _
    11 
    13 
    12 from . import (
    14 from . import (
    13     error,
    15     error,
    14     node,
    16     node,
    15     obsolete,
    17     obsolete,
       
    18     obsutil,
    16     revset,
    19     revset,
       
    20     scmutil,
    17 )
    21 )
       
    22 
       
    23 
       
    24 sha1re = re.compile(br'\b[0-9a-f]{6,40}\b')
    18 
    25 
    19 
    26 
    20 def precheck(repo, revs, action=b'rewrite'):
    27 def precheck(repo, revs, action=b'rewrite'):
    21     """check if revs can be rewritten
    28     """check if revs can be rewritten
    22     action is used to control the error message.
    29     action is used to control the error message.
    68                 b"rewrite.empty-successor=%s (only 'skip' and 'keep' are "
    75                 b"rewrite.empty-successor=%s (only 'skip' and 'keep' are "
    69                 b"supported)"
    76                 b"supported)"
    70             )
    77             )
    71             % (command, empty_successor)
    78             % (command, empty_successor)
    72         )
    79         )
       
    80 
       
    81 
       
    82 def update_hash_refs(repo, commitmsg):
       
    83     """Replace all obsolete commit hashes in the message with the current hash.
       
    84 
       
    85     If the obsolete commit was split or is divergent, the hash is not replaced
       
    86     as there's no way to know which successor to choose.
       
    87     """
       
    88     cache = {}
       
    89     sha1s = re.findall(sha1re, commitmsg)
       
    90     unfi = repo.unfiltered()
       
    91     for sha1 in sha1s:
       
    92         fullnode = scmutil.resolvehexnodeidprefix(unfi, sha1)
       
    93         if fullnode is None:
       
    94             continue
       
    95         ctx = unfi[fullnode]
       
    96         if not ctx.obsolete():
       
    97             continue
       
    98 
       
    99         successors = obsutil.successorssets(repo, ctx.node(), cache=cache)
       
   100 
       
   101         # We can't make any assumptions about how to update the hash if the
       
   102         # cset in question was split or diverged.
       
   103         if len(successors) == 1 and len(successors[0]) == 1:
       
   104             newsha1 = node.hex(successors[0][0])
       
   105             commitmsg = commitmsg.replace(sha1, newsha1[: len(sha1)])
       
   106         else:
       
   107             repo.ui.note(
       
   108                 _(
       
   109                     b'The stale commit message reference to %s could '
       
   110                     b'not be updated\n'
       
   111                 )
       
   112                 % sha1
       
   113             )
       
   114 
       
   115     return commitmsg