mercurial/subrepoutil.py
changeset 43077 687b865b95ad
parent 43076 2372284d9457
child 43089 c59eb1560c44
--- a/mercurial/subrepoutil.py	Sun Oct 06 09:45:02 2019 -0400
+++ b/mercurial/subrepoutil.py	Sun Oct 06 09:48:39 2019 -0400
@@ -23,7 +23,7 @@
 )
 from .utils import stringutil
 
-nullstate = ('', '', 'empty')
+nullstate = (b'', b'', b'empty')
 
 
 def state(ctx, ui):
@@ -43,38 +43,38 @@
                     raise
                 # handle missing subrepo spec files as removed
                 ui.warn(
-                    _("warning: subrepo spec file \'%s\' not found\n")
+                    _(b"warning: subrepo spec file \'%s\' not found\n")
                     % repo.pathto(f)
                 )
                 return
             p.parse(f, data, sections, remap, read)
         else:
             raise error.Abort(
-                _("subrepo spec file \'%s\' not found") % repo.pathto(f)
+                _(b"subrepo spec file \'%s\' not found") % repo.pathto(f)
             )
 
-    if '.hgsub' in ctx:
-        read('.hgsub')
+    if b'.hgsub' in ctx:
+        read(b'.hgsub')
 
-    for path, src in ui.configitems('subpaths'):
-        p.set('subpaths', path, src, ui.configsource('subpaths', path))
+    for path, src in ui.configitems(b'subpaths'):
+        p.set(b'subpaths', path, src, ui.configsource(b'subpaths', path))
 
     rev = {}
-    if '.hgsubstate' in ctx:
+    if b'.hgsubstate' in ctx:
         try:
-            for i, l in enumerate(ctx['.hgsubstate'].data().splitlines()):
+            for i, l in enumerate(ctx[b'.hgsubstate'].data().splitlines()):
                 l = l.lstrip()
                 if not l:
                     continue
                 try:
-                    revision, path = l.split(" ", 1)
+                    revision, path = l.split(b" ", 1)
                 except ValueError:
                     raise error.Abort(
                         _(
-                            "invalid subrepository revision "
-                            "specifier in \'%s\' line %d"
+                            b"invalid subrepository revision "
+                            b"specifier in \'%s\' line %d"
                         )
-                        % (repo.pathto('.hgsubstate'), (i + 1))
+                        % (repo.pathto(b'.hgsubstate'), (i + 1))
                     )
                 rev[path] = revision
         except IOError as err:
@@ -82,7 +82,7 @@
                 raise
 
     def remap(src):
-        for pattern, repl in p.items('subpaths'):
+        for pattern, repl in p.items(b'subpaths'):
             # Turn r'C:\foo\bar' into r'C:\\foo\\bar' since re.sub
             # does a string decode.
             repl = stringutil.escapestr(repl)
@@ -94,21 +94,21 @@
                 src = re.sub(pattern, repl, src, 1)
             except re.error as e:
                 raise error.Abort(
-                    _("bad subrepository pattern in %s: %s")
+                    _(b"bad subrepository pattern in %s: %s")
                     % (
-                        p.source('subpaths', pattern),
+                        p.source(b'subpaths', pattern),
                         stringutil.forcebytestr(e),
                     )
                 )
         return src
 
     state = {}
-    for path, src in p[''].items():
-        kind = 'hg'
-        if src.startswith('['):
-            if ']' not in src:
-                raise error.Abort(_('missing ] in subrepository source'))
-            kind, src = src.split(']', 1)
+    for path, src in p[b''].items():
+        kind = b'hg'
+        if src.startswith(b'['):
+            if b']' not in src:
+                raise error.Abort(_(b'missing ] in subrepository source'))
+            kind, src = src.split(b']', 1)
             kind = kind[1:]
             src = src.lstrip()  # strip any extra whitespace after ']'
 
@@ -116,7 +116,7 @@
             parent = _abssource(repo, abort=False)
             if parent:
                 parent = util.url(parent)
-                parent.path = posixpath.join(parent.path or '', src)
+                parent.path = posixpath.join(parent.path or b'', src)
                 parent.path = posixpath.normpath(parent.path)
                 joined = bytes(parent)
                 # Remap the full joined path and use it if it changes,
@@ -128,7 +128,7 @@
                     src = remapped
 
         src = remap(src)
-        state[util.pconvert(path)] = (src.strip(), rev.get(path, ''), kind)
+        state[util.pconvert(path)] = (src.strip(), rev.get(path, b''), kind)
 
     return state
 
@@ -136,11 +136,11 @@
 def writestate(repo, state):
     """rewrite .hgsubstate in (outer) repo with these subrepo states"""
     lines = [
-        '%s %s\n' % (state[s][1], s)
+        b'%s %s\n' % (state[s][1], s)
         for s in sorted(state)
         if state[s][1] != nullstate[1]
     ]
-    repo.wwrite('.hgsubstate', ''.join(lines), '')
+    repo.wwrite(b'.hgsubstate', b''.join(lines), b'')
 
 
 def submerge(repo, wctx, mctx, actx, overwrite, labels=None):
@@ -153,67 +153,67 @@
     sa = actx.substate
     sm = {}
 
-    repo.ui.debug("subrepo merge %s %s %s\n" % (wctx, mctx, actx))
+    repo.ui.debug(b"subrepo merge %s %s %s\n" % (wctx, mctx, actx))
 
-    def debug(s, msg, r=""):
+    def debug(s, msg, r=b""):
         if r:
-            r = "%s:%s:%s" % r
-        repo.ui.debug("  subrepo %s: %s %s\n" % (s, msg, r))
+            r = b"%s:%s:%s" % r
+        repo.ui.debug(b"  subrepo %s: %s %s\n" % (s, msg, r))
 
     promptssrc = filemerge.partextras(labels)
     for s, l in sorted(s1.iteritems()):
         a = sa.get(s, nullstate)
         ld = l  # local state with possible dirty flag for compares
         if wctx.sub(s).dirty():
-            ld = (l[0], l[1] + "+")
+            ld = (l[0], l[1] + b"+")
         if wctx == actx:  # overwrite
             a = ld
 
         prompts = promptssrc.copy()
-        prompts['s'] = s
+        prompts[b's'] = s
         if s in s2:
             r = s2[s]
             if ld == r or r == a:  # no change or local is newer
                 sm[s] = l
                 continue
             elif ld == a:  # other side changed
-                debug(s, "other changed, get", r)
+                debug(s, b"other changed, get", r)
                 wctx.sub(s).get(r, overwrite)
                 sm[s] = r
             elif ld[0] != r[0]:  # sources differ
-                prompts['lo'] = l[0]
-                prompts['ro'] = r[0]
+                prompts[b'lo'] = l[0]
+                prompts[b'ro'] = r[0]
                 if repo.ui.promptchoice(
                     _(
-                        ' subrepository sources for %(s)s differ\n'
-                        'you can use (l)ocal%(l)s source (%(lo)s)'
-                        ' or (r)emote%(o)s source (%(ro)s).\n'
-                        'what do you want to do?'
-                        '$$ &Local $$ &Remote'
+                        b' subrepository sources for %(s)s differ\n'
+                        b'you can use (l)ocal%(l)s source (%(lo)s)'
+                        b' or (r)emote%(o)s source (%(ro)s).\n'
+                        b'what do you want to do?'
+                        b'$$ &Local $$ &Remote'
                     )
                     % prompts,
                     0,
                 ):
-                    debug(s, "prompt changed, get", r)
+                    debug(s, b"prompt changed, get", r)
                     wctx.sub(s).get(r, overwrite)
                     sm[s] = r
             elif ld[1] == a[1]:  # local side is unchanged
-                debug(s, "other side changed, get", r)
+                debug(s, b"other side changed, get", r)
                 wctx.sub(s).get(r, overwrite)
                 sm[s] = r
             else:
-                debug(s, "both sides changed")
+                debug(s, b"both sides changed")
                 srepo = wctx.sub(s)
-                prompts['sl'] = srepo.shortid(l[1])
-                prompts['sr'] = srepo.shortid(r[1])
+                prompts[b'sl'] = srepo.shortid(l[1])
+                prompts[b'sr'] = srepo.shortid(r[1])
                 option = repo.ui.promptchoice(
                     _(
-                        ' subrepository %(s)s diverged (local revision: %(sl)s, '
-                        'remote revision: %(sr)s)\n'
-                        'you can (m)erge, keep (l)ocal%(l)s or keep '
-                        '(r)emote%(o)s.\n'
-                        'what do you want to do?'
-                        '$$ &Merge $$ &Local $$ &Remote'
+                        b' subrepository %(s)s diverged (local revision: %(sl)s, '
+                        b'remote revision: %(sr)s)\n'
+                        b'you can (m)erge, keep (l)ocal%(l)s or keep '
+                        b'(r)emote%(o)s.\n'
+                        b'what do you want to do?'
+                        b'$$ &Merge $$ &Local $$ &Remote'
                     )
                     % prompts,
                     0,
@@ -221,59 +221,59 @@
                 if option == 0:
                     wctx.sub(s).merge(r)
                     sm[s] = l
-                    debug(s, "merge with", r)
+                    debug(s, b"merge with", r)
                 elif option == 1:
                     sm[s] = l
-                    debug(s, "keep local subrepo revision", l)
+                    debug(s, b"keep local subrepo revision", l)
                 else:
                     wctx.sub(s).get(r, overwrite)
                     sm[s] = r
-                    debug(s, "get remote subrepo revision", r)
+                    debug(s, b"get remote subrepo revision", r)
         elif ld == a:  # remote removed, local unchanged
-            debug(s, "remote removed, remove")
+            debug(s, b"remote removed, remove")
             wctx.sub(s).remove()
         elif a == nullstate:  # not present in remote or ancestor
-            debug(s, "local added, keep")
+            debug(s, b"local added, keep")
             sm[s] = l
             continue
         else:
             if repo.ui.promptchoice(
                 _(
-                    ' local%(l)s changed subrepository %(s)s'
-                    ' which remote%(o)s removed\n'
-                    'use (c)hanged version or (d)elete?'
-                    '$$ &Changed $$ &Delete'
+                    b' local%(l)s changed subrepository %(s)s'
+                    b' which remote%(o)s removed\n'
+                    b'use (c)hanged version or (d)elete?'
+                    b'$$ &Changed $$ &Delete'
                 )
                 % prompts,
                 0,
             ):
-                debug(s, "prompt remove")
+                debug(s, b"prompt remove")
                 wctx.sub(s).remove()
 
     for s, r in sorted(s2.items()):
         if s in s1:
             continue
         elif s not in sa:
-            debug(s, "remote added, get", r)
+            debug(s, b"remote added, get", r)
             mctx.sub(s).get(r)
             sm[s] = r
         elif r != sa[s]:
             prompts = promptssrc.copy()
-            prompts['s'] = s
+            prompts[b's'] = s
             if (
                 repo.ui.promptchoice(
                     _(
-                        ' remote%(o)s changed subrepository %(s)s'
-                        ' which local%(l)s removed\n'
-                        'use (c)hanged version or (d)elete?'
-                        '$$ &Changed $$ &Delete'
+                        b' remote%(o)s changed subrepository %(s)s'
+                        b' which local%(l)s removed\n'
+                        b'use (c)hanged version or (d)elete?'
+                        b'$$ &Changed $$ &Delete'
                     )
                     % prompts,
                     0,
                 )
                 == 0
             ):
-                debug(s, "prompt recreate", r)
+                debug(s, b"prompt recreate", r)
                 mctx.sub(s).get(r)
                 sm[s] = r
 
@@ -297,11 +297,11 @@
     newstate = wctx.substate.copy()
 
     # only manage subrepos and .hgsubstate if .hgsub is present
-    if '.hgsub' in wctx:
+    if b'.hgsub' in wctx:
         # we'll decide whether to track this ourselves, thanks
         for c in status.modified, status.added, status.removed:
-            if '.hgsubstate' in c:
-                c.remove('.hgsubstate')
+            if b'.hgsubstate' in c:
+                c.remove(b'.hgsubstate')
 
         # compare current state to last committed state
         # build new substate based on last committed state
@@ -314,14 +314,14 @@
                     continue
                 if not force:
                     raise error.Abort(
-                        _("commit with new subrepo %s excluded") % s
+                        _(b"commit with new subrepo %s excluded") % s
                     )
             dirtyreason = wctx.sub(s).dirtyreason(True)
             if dirtyreason:
-                if not ui.configbool('ui', 'commitsubrepos'):
+                if not ui.configbool(b'ui', b'commitsubrepos'):
                     raise error.Abort(
                         dirtyreason,
-                        hint=_("use --subrepos for recursive commit"),
+                        hint=_(b"use --subrepos for recursive commit"),
                     )
                 subs.append(s)
                 commitsubs.add(s)
@@ -336,18 +336,18 @@
             r = [s for s in p.substate if s not in newstate]
             subs += [s for s in r if match(s)]
         if subs:
-            if not match('.hgsub') and '.hgsub' in (
+            if not match(b'.hgsub') and b'.hgsub' in (
                 wctx.modified() + wctx.added()
             ):
-                raise error.Abort(_("can't commit subrepos without .hgsub"))
-            status.modified.insert(0, '.hgsubstate')
+                raise error.Abort(_(b"can't commit subrepos without .hgsub"))
+            status.modified.insert(0, b'.hgsubstate')
 
-    elif '.hgsub' in status.removed:
+    elif b'.hgsub' in status.removed:
         # clean up .hgsubstate when .hgsub is removed
-        if '.hgsubstate' in wctx and '.hgsubstate' not in (
+        if b'.hgsubstate' in wctx and b'.hgsubstate' not in (
             status.modified + status.added + status.removed
         ):
-            status.removed.insert(0, '.hgsubstate')
+            status.removed.insert(0, b'.hgsubstate')
 
     return subs, commitsubs, newstate
 
@@ -355,7 +355,7 @@
 def reporelpath(repo):
     """return path to this (sub)repo as seen from outermost repo"""
     parent = repo
-    while util.safehasattr(parent, '_subparent'):
+    while util.safehasattr(parent, b'_subparent'):
         parent = parent._subparent
     return repo.root[len(pathutil.normasprefix(parent.root)) :]
 
@@ -368,7 +368,7 @@
 def _abssource(repo, push=False, abort=True):
     """return pull/push path of repo - either based on parent repo .hgsub info
     or on the top repo config. Abort or return None if no source found."""
-    if util.safehasattr(repo, '_subparent'):
+    if util.safehasattr(repo, b'_subparent'):
         source = util.url(repo._subsource)
         if source.isabs():
             return bytes(source)
@@ -376,17 +376,17 @@
         parent = _abssource(repo._subparent, push, abort=False)
         if parent:
             parent = util.url(util.pconvert(parent))
-            parent.path = posixpath.join(parent.path or '', source.path)
+            parent.path = posixpath.join(parent.path or b'', source.path)
             parent.path = posixpath.normpath(parent.path)
             return bytes(parent)
     else:  # recursion reached top repo
         path = None
-        if util.safehasattr(repo, '_subtoppath'):
+        if util.safehasattr(repo, b'_subtoppath'):
             path = repo._subtoppath
-        elif push and repo.ui.config('paths', 'default-push'):
-            path = repo.ui.config('paths', 'default-push')
-        elif repo.ui.config('paths', 'default'):
-            path = repo.ui.config('paths', 'default')
+        elif push and repo.ui.config(b'paths', b'default-push'):
+            path = repo.ui.config(b'paths', b'default-push')
+        elif repo.ui.config(b'paths', b'default'):
+            path = repo.ui.config(b'paths', b'default')
         elif repo.shared():
             # chop off the .hg component to get the default path form.  This has
             # already run through vfsmod.vfs(..., realpath=True), so it doesn't
@@ -410,7 +410,7 @@
             return path
 
     if abort:
-        raise error.Abort(_("default path for subrepository not found"))
+        raise error.Abort(_(b"default path for subrepository not found"))
 
 
 def newcommitphase(ui, ctx):
@@ -418,12 +418,12 @@
     substate = getattr(ctx, "substate", None)
     if not substate:
         return commitphase
-    check = ui.config('phases', 'checksubrepos')
-    if check not in ('ignore', 'follow', 'abort'):
+    check = ui.config(b'phases', b'checksubrepos')
+    if check not in (b'ignore', b'follow', b'abort'):
         raise error.Abort(
-            _('invalid phases.checksubrepos configuration: %s') % check
+            _(b'invalid phases.checksubrepos configuration: %s') % check
         )
-    if check == 'ignore':
+    if check == b'ignore':
         return commitphase
     maxphase = phases.public
     maxsub = None
@@ -434,11 +434,11 @@
             maxphase = subphase
             maxsub = s
     if commitphase < maxphase:
-        if check == 'abort':
+        if check == b'abort':
             raise error.Abort(
                 _(
-                    "can't commit in %s phase"
-                    " conflicting %s from subrepository %s"
+                    b"can't commit in %s phase"
+                    b" conflicting %s from subrepository %s"
                 )
                 % (
                     phases.phasenames[commitphase],
@@ -448,8 +448,8 @@
             )
         ui.warn(
             _(
-                "warning: changes are committed in"
-                " %s phase from subrepository %s\n"
+                b"warning: changes are committed in"
+                b" %s phase from subrepository %s\n"
             )
             % (phases.phasenames[maxphase], maxsub)
         )