From 939754e6c3435d5489d57aef0d2bdd49c6edc3fc Mon Sep 17 00:00:00 2001 From: mvdbeek Date: Sun, 27 Oct 2019 10:12:42 +0100 Subject: [PATCH 1/3] Fix unicodify on exceptions with non-utf bytestring args --- lib/galaxy/util/__init__.py | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/lib/galaxy/util/__init__.py b/lib/galaxy/util/__init__.py index cf5125a6af9..c09214c1a32 100644 --- a/lib/galaxy/util/__init__.py +++ b/lib/galaxy/util/__init__.py @@ -1018,10 +1018,15 @@ def unicodify(value, encoding=DEFAULT_ENCODING, error='replace', strip_null=Fals >>> s = u'lâtín strìñg'; assert unicodify(s.encode('latin-1'), 'latin-1') == s >>> s = u'lâtín strìñg'; assert unicodify(s.encode('latin-1')) == u'l\ufffdt\ufffdn str\ufffd\ufffdg' >>> s = u'lâtín strìñg'; assert unicodify(s.encode('latin-1'), error='ignore') == u'ltn strg' + >>> assert unicodify(Exception(u'¼ cup of flour'.encode('latin-1')), error='ignore') == ' cup of flour' """ if value is None: return value try: + if isinstance(value, Exception): + # This is for backwards compatibility for python 2, but works on python 3 as well + if value.args: + value = value.args[0] if isinstance(value, bytearray): value = bytes(value) elif not isinstance(value, string_types) and not isinstance(value, binary_type): From 89d1f97f05ae226180a62e3368cf7978b3913dd4 Mon Sep 17 00:00:00 2001 From: Marius van den Beek Date: Sun, 27 Oct 2019 16:15:10 +0100 Subject: [PATCH 2/3] Only use value.args[0] if exception has a single argument. Co-Authored-By: Nicola Soranzo --- lib/galaxy/util/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/galaxy/util/__init__.py b/lib/galaxy/util/__init__.py index c09214c1a32..365bc41aa18 100644 --- a/lib/galaxy/util/__init__.py +++ b/lib/galaxy/util/__init__.py @@ -1025,7 +1025,7 @@ def unicodify(value, encoding=DEFAULT_ENCODING, error='replace', strip_null=Fals try: if isinstance(value, Exception): # This is for backwards compatibility for python 2, but works on python 3 as well - if value.args: + if len(value.args) == 1: value = value.args[0] if isinstance(value, bytearray): value = bytes(value) From 9c3be80a7cdec8e9b44717c0abb60eb71c2168f8 Mon Sep 17 00:00:00 2001 From: Nicola Soranzo Date: Mon, 28 Oct 2019 12:19:23 +0000 Subject: [PATCH 3/3] Safer fix for ``unicodify`` on exceptions with bytestring message Follow-up on https://github.com/galaxyproject/galaxy/pull/8891 . Should be safer for `Exception` subclasses that override `__str__()` / ` __unicode__()` methods. --- lib/galaxy/util/__init__.py | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/lib/galaxy/util/__init__.py b/lib/galaxy/util/__init__.py index 365bc41aa18..9961a518cc1 100644 --- a/lib/galaxy/util/__init__.py +++ b/lib/galaxy/util/__init__.py @@ -1018,21 +1018,20 @@ def unicodify(value, encoding=DEFAULT_ENCODING, error='replace', strip_null=Fals >>> s = u'lâtín strìñg'; assert unicodify(s.encode('latin-1'), 'latin-1') == s >>> s = u'lâtín strìñg'; assert unicodify(s.encode('latin-1')) == u'l\ufffdt\ufffdn str\ufffd\ufffdg' >>> s = u'lâtín strìñg'; assert unicodify(s.encode('latin-1'), error='ignore') == u'ltn strg' - >>> assert unicodify(Exception(u'¼ cup of flour'.encode('latin-1')), error='ignore') == ' cup of flour' + >>> if PY2: assert unicodify(Exception(u'¼ cup of flour'.encode('latin-1')), error='ignore') == ' cup of flour' """ if value is None: return value try: - if isinstance(value, Exception): - # This is for backwards compatibility for python 2, but works on python 3 as well - if len(value.args) == 1: - value = value.args[0] if isinstance(value, bytearray): value = bytes(value) elif not isinstance(value, string_types) and not isinstance(value, binary_type): # In Python 2, value is not an instance of basestring (i.e. str or unicode) # In Python 3, value is not an instance of bytes or str - value = text_type(value) + try: + value = text_type(value) + except Exception: + value = str(value) # Now in Python 2, value is an instance of basestring, but may be not unicode # Now in Python 3, value is an instance of bytes or str if not isinstance(value, text_type):