py3: convert encoding name and mode to str
authorYuya Nishihara <yuya@tcha.org>
Wed, 28 Sep 2016 20:39:06 +0900
changeset 30033 02dbfaa6df0b
parent 30032 2219f4f82ede
child 30034 e4a6b439acc5
py3: convert encoding name and mode to str Otherwise tolocal() and fromlocal() wouldn't work on Python 3. Still tolocal() can't make a valid localstr object because localstr inherits str, but it can return some object without raising exceptions. Since Py3 bytes() behaves much like bytearray() than str() of Py2, we can't simply do s/str/bytes/g. I have no good idea to handle str/bytes divergence.
mercurial/encoding.py
--- a/mercurial/encoding.py	Wed Sep 28 22:32:09 2016 +0900
+++ b/mercurial/encoding.py	Wed Sep 28 20:39:06 2016 +0900
@@ -17,6 +17,8 @@
     pycompat,
 )
 
+_sysstr = pycompat.sysstr
+
 if pycompat.ispy3:
     unichr = chr
 
@@ -136,23 +138,24 @@
             if encoding == 'UTF-8':
                 # fast path
                 return s
-            r = u.encode(encoding, "replace")
-            if u == r.decode(encoding):
+            r = u.encode(_sysstr(encoding), u"replace")
+            if u == r.decode(_sysstr(encoding)):
                 # r is a safe, non-lossy encoding of s
                 return r
             return localstr(s, r)
         except UnicodeDecodeError:
             # we should only get here if we're looking at an ancient changeset
             try:
-                u = s.decode(fallbackencoding)
-                r = u.encode(encoding, "replace")
-                if u == r.decode(encoding):
+                u = s.decode(_sysstr(fallbackencoding))
+                r = u.encode(_sysstr(encoding), u"replace")
+                if u == r.decode(_sysstr(encoding)):
                     # r is a safe, non-lossy encoding of s
                     return r
                 return localstr(u.encode('UTF-8'), r)
             except UnicodeDecodeError:
                 u = s.decode("utf-8", "replace") # last ditch
-                return u.encode(encoding, "replace") # can't round-trip
+                # can't round-trip
+                return u.encode(_sysstr(encoding), u"replace")
     except LookupError as k:
         raise error.Abort(k, hint="please check your locale settings")
 
@@ -172,7 +175,8 @@
         return s._utf8
 
     try:
-        return s.decode(encoding, encodingmode).encode("utf-8")
+        u = s.decode(_sysstr(encoding), _sysstr(encodingmode))
+        return u.encode("utf-8")
     except UnicodeDecodeError as inst:
         sub = s[max(0, inst.start - 10):inst.start + 10]
         raise error.Abort("decoding near '%s': %s!" % (sub, inst))
@@ -185,7 +189,7 @@
 
 def colwidth(s):
     "Find the column width of a string for display in the local encoding"
-    return ucolwidth(s.decode(encoding, 'replace'))
+    return ucolwidth(s.decode(_sysstr(encoding), u'replace'))
 
 def ucolwidth(d):
     "Find the column width of a Unicode string for display"
@@ -265,7 +269,7 @@
     +
     """
     try:
-        u = s.decode(encoding)
+        u = s.decode(_sysstr(encoding))
     except UnicodeDecodeError:
         if len(s) <= width: # trimming is not needed
             return s
@@ -292,7 +296,7 @@
     for i in xrange(1, len(u)):
         usub = uslice(i)
         if ucolwidth(usub) <= width:
-            return concat(usub.encode(encoding))
+            return concat(usub.encode(_sysstr(encoding)))
     return ellipsis # no enough room for multi-column characters
 
 def _asciilower(s):
@@ -337,12 +341,12 @@
         if isinstance(s, localstr):
             u = s._utf8.decode("utf-8")
         else:
-            u = s.decode(encoding, encodingmode)
+            u = s.decode(_sysstr(encoding), _sysstr(encodingmode))
 
         lu = u.lower()
         if u == lu:
             return s # preserve localstring
-        return lu.encode(encoding)
+        return lu.encode(_sysstr(encoding))
     except UnicodeError:
         return s.lower() # we don't know how to fold this except in ASCII
     except LookupError as k:
@@ -360,12 +364,12 @@
         if isinstance(s, localstr):
             u = s._utf8.decode("utf-8")
         else:
-            u = s.decode(encoding, encodingmode)
+            u = s.decode(_sysstr(encoding), _sysstr(encodingmode))
 
         uu = u.upper()
         if u == uu:
             return s # preserve localstring
-        return uu.encode(encoding)
+        return uu.encode(_sysstr(encoding))
     except UnicodeError:
         return s.upper() # we don't know how to fold this except in ASCII
     except LookupError as k: