Patchwork D1909: cmdutil: add a kludge to make bytes repr() the same on 2 and 3

login
register
mail settings
Submitter phabricator
Date Jan. 18, 2018, 6:17 p.m.
Message ID <differential-rev-PHID-DREV-isaqid5mrmpsi62m5c6z-req@phab.mercurial-scm.org>
Download mbox | patch
Permalink /patch/26920/
State Superseded
Headers show

Comments

phabricator - Jan. 18, 2018, 6:17 p.m.
durin42 created this revision.
Herald added a subscriber: mercurial-devel.
Herald added a reviewer: hg-reviewers.

REVISION SUMMARY
  This fixes the output formatting problems I see in debugobsolete. I
  still am seeing some effectflag differences, which we'll need to
  tackle separately.
  
  I'm not in love with this approach. There might be something better we
  could do, and I'd love it if someone else wanted to take a run at
  this.

REPOSITORY
  rHG Mercurial

REVISION DETAIL
  https://phab.mercurial-scm.org/D1909

AFFECTED FILES
  mercurial/cmdutil.py

CHANGE DETAILS




To: durin42, #hg-reviewers
Cc: mercurial-devel
phabricator - Jan. 19, 2018, 1:34 p.m.
yuja accepted this revision.
yuja added a comment.
This revision is now accepted and ready to land.


  This looks ugly, but seems okay. Since `sysstr()` decodes bytes as latin-1,
  8-bit characters will be escaped by `\x`, not by `\u`.

REPOSITORY
  rHG Mercurial

REVISION DETAIL
  https://phab.mercurial-scm.org/D1909

To: durin42, #hg-reviewers, yuja
Cc: yuja, mercurial-devel
phabricator - Jan. 27, 2018, 9:37 a.m.
yuja added a comment.


  I'm thinking of adding a couple of utility functions as this sort of hack
  is unavoidable around the codebase:
  
  - `pycompat.maybebytestr(x)`
  - make `repr(bytestr)` return `repr(bytes)[1:]`
  - `pycompat.rapply(f, xs)` to recursively apply `f = maybebytestr` to dict/list items

REPOSITORY
  rHG Mercurial

REVISION DETAIL
  https://phab.mercurial-scm.org/D1909

To: durin42, #hg-reviewers, yuja
Cc: yuja, mercurial-devel

Patch

diff --git a/mercurial/cmdutil.py b/mercurial/cmdutil.py
--- a/mercurial/cmdutil.py
+++ b/mercurial/cmdutil.py
@@ -1985,6 +1985,19 @@ 
 
     return changeset_templater(ui, repo, spec, match, opts, buffered)
 
+class _regrettablereprbytes(bytes):
+    """Bytes subclass that makes the repr the same on Python 3 as Python 2.
+
+    This is a huge hack.
+    """
+    def __repr__(self):
+        return repr(pycompat.sysstr(self))
+
+def _maybebytestr(v):
+    if pycompat.ispy3 and isinstance(v, bytes):
+        return _regrettablereprbytes(v)
+    return v
+
 def showmarker(fm, marker, index=None):
     """utility function to display obsolescence marker in a readable way
 
@@ -2003,7 +2016,8 @@ 
     fm.write('date', '(%s) ', fm.formatdate(marker.date()))
     meta = marker.metadata().copy()
     meta.pop('date', None)
-    fm.write('metadata', '{%s}', fm.formatdict(meta, fmt='%r: %r', sep=', '))
+    smeta = {_maybebytestr(k): _maybebytestr(v) for k, v in meta.iteritems()}
+    fm.write('metadata', '{%s}', fm.formatdict(smeta, fmt='%r: %r', sep=', '))
     fm.plain('\n')
 
 def finddate(ui, repo, date):