control: tags -1 +patch

> Reportbug is not designed to cope with arbitrary encodings of
> configuration files, but relies on the user to use consistent encoding
> in files and environment.

We can and should still prevent reportbug from simply crashing in such
cases.  So here is a patch.  It applies on top of the patch that I sent
to #695887.

Besides #877650, it should also fix #868022 and #883577.
>From c238cf242a8713ccd8bd9a36319e1bd1d8c72bb6 Mon Sep 17 00:00:00 2001
From: Nis Martensen <nis.marten...@web.de>
Date: Tue, 5 Dec 2017 21:40:03 +0100
Subject: [PATCH 2/2] Prevent Unicode(De|En)codeError with most open() calls

We are still getting new bugreports with
Unicode(De|En)codingError-Crashes. While users can often fix that by
fixing their locale setup, we should prevent crashes where we can.
---
 bin/reportbug           | 35 ++++++++++++++++++-----------------
 reportbug/debbugs.py    |  2 +-
 reportbug/submit.py     |  5 ++---
 reportbug/tempfiles.py  |  4 ++--
 reportbug/ui/gtk2_ui.py |  5 ++---
 reportbug/ui/text_ui.py |  4 ++--
 reportbug/utils.py      | 15 ++++++++-------
 7 files changed, 35 insertions(+), 35 deletions(-)

diff --git a/bin/reportbug b/bin/reportbug
index 6a554b6..dff93c2 100755
--- a/bin/reportbug
+++ b/bin/reportbug
@@ -142,11 +142,10 @@ def include_file_in_report(message, message_filename,
         """
     if inline:
         try:
-            fp = open(include_filename)
-            message += '\n*** %s\n%s' % (
-                include_filename,
-                fp.read())
-            fp.close()
+            with open(include_filename, errors='backslashreplace') as fp:
+                message += '\n*** {}\n{}'.format(
+                    include_filename,
+                    fp.read())
             fp, temp_filename = TempFile(
                 prefix=tempfile_prefix(package_name), dir=draftpath)
             fp.write(message)
@@ -192,7 +191,8 @@ def handle_editing(filename, dmessage, options, sendto, attachments, package,
                     stopmsg(filename)
                     sys.exit(1)
 
-            message = open(filename).read()
+            with open(filename, errors='backslashreplace') as f:
+                message = f.read()
             changed = True
 
         prompt = 'Submit this report on %s (e to edit)' % package
@@ -365,7 +365,8 @@ def handle_editing(filename, dmessage, options, sendto, attachments, package,
                 if 'patch' in newtaglist:
                     patch = True
                 message = message.replace(oldtags, newtags)
-                open(filename, 'w').write(message)
+                with open(filename, 'w', errors='backslashreplace') as f:
+                    f.write(message)
         elif x == 's':
             skip_editing = True
             ccemail = ui.get_string(
@@ -391,7 +392,7 @@ def handle_editing(filename, dmessage, options, sendto, attachments, package,
             else:
                 break
 
-    return open(filename).read(), patch, justsave
+    return open(filename, errors='backslashreplace').read(), patch, justsave
 
 
 def find_package_for(filename, notatty=False, pathonly=False):
@@ -670,7 +671,7 @@ def offer_configuration(options):
               'home directory.  Please fix this before using '
               'reportbug again.\n', utils.USERFILE)
 
-    fp = os.fdopen(fd, 'w')
+    fp = os.fdopen(fd, 'w', errors='backslashreplace')
     print('# reportbug preferences file', file=fp)
     print('# character encoding: %s' % charset, file=fp)
     print('# Version of reportbug this preferences file was written by', file=fp)
@@ -1168,7 +1169,8 @@ class UI(object):
                           'reduce its size else the report cannot be sent' % (
                               self.options.bodyfile, self.options.max_attachment_size))
                     raise Exception
-                body = open(self.options.bodyfile).read()
+                with open(self.options.bodyfile, errors='backslashreplace') as bf:
+                    body = bf.read()
             except:
                 efail('Unable to read body from file %s.\n', self.options.bodyfile)
 
@@ -1351,11 +1353,8 @@ class UI(object):
         if self.options.include:
             for f in self.options.include:
                 if os.path.exists(f):
-                    fp = open(f)
-                    incfiles = '%s\n*** %s\n%s' % (
-                        incfiles, f,
-                        fp.read())
-                    fp.close()
+                    with open(f, errors='backslashreplace') as fp:
+                        incfiles += '\n*** {}\n{}'.format(f, fp.read())
                 else:
                     ewrite("Can't find %s to include!\n", f)
                     sys.exit(1)
@@ -1864,7 +1863,8 @@ For more details, please see: http://www.debian.org/devel/wnpp/''')
         ewrite('\n')
         prompted = False
         if interactive and not (self.options.kudos or exinfo) and presubj:
-            ui.display_report(open(presubj).read() + '\n', presubj=True)
+            with open(presubj, errors='backslashreplace') as f:
+                ui.display_report(f.read() + '\n', presubj=True)
 
         if self.options.kudos:
             subject = subject or ('Thanks for packaging %s!' % package)
@@ -2094,7 +2094,8 @@ For more details, please see: http://www.debian.org/devel/wnpp/''')
             if not mua:
                 SIGFILE = os.path.join(HOMEDIR, '.signature')
                 try:
-                    message = "\n\n-- \n" + open(SIGFILE).read()
+                    with open(SIGFILE, errors='backslashreplace') as sf:
+                        message = "\n\n-- \n" + sf.read()
                 except IOError:
                     pass
         else:
diff --git a/reportbug/debbugs.py b/reportbug/debbugs.py
index 1c65075..a8d24eb 100644
--- a/reportbug/debbugs.py
+++ b/reportbug/debbugs.py
@@ -930,7 +930,7 @@ def parse_bts_url(url):
 # Dynamically add any additional systems found
 for origin in glob.glob('/etc/dpkg/origins/*'):
     try:
-        fp = open(origin)
+        fp = open(origin, errors='backslashreplace')
         system = os.path.basename(origin)
         SYSTEMS[system] = SYSTEMS.get(system, {'otherpkgs': {},
                                                'query-dpkg': True,
diff --git a/reportbug/submit.py b/reportbug/submit.py
index ea613cb..7454188 100644
--- a/reportbug/submit.py
+++ b/reportbug/submit.py
@@ -88,9 +88,8 @@ def sign_message(body, fromaddr, package='x', pgp_addr=None, sign='gpg', draftpa
 
     try:
         os.system(signcmd)
-        x = open(file2, 'r')
-        signedbody = x.read()
-        x.close()
+        with open(file2, 'r', errors='backslashreplace') as x:
+            signedbody = x.read()
 
         if os.path.exists(file1):
             os.unlink(file1)
diff --git a/reportbug/tempfiles.py b/reportbug/tempfiles.py
index bfa1208..7ca6622 100644
--- a/reportbug/tempfiles.py
+++ b/reportbug/tempfiles.py
@@ -61,7 +61,7 @@ def open_write_safe(filename, mode='w+b', bufsize=-1):
         fd = os.open(filename, _text_openflags, 0o600)
 
     try:
-        return os.fdopen(fd, mode, bufsize)
+        return os.fdopen(fd, mode, bufsize, errors='backslashreplace')
     except:
         os.close(fd)
         raise
@@ -72,7 +72,7 @@ def open_write_safe(filename, mode='w+b', bufsize=-1):
 def TempFile(suffix="", prefix=template, dir=None, text=True,
              mode="w+", bufsize=-1):
     fh, filename = tempfile.mkstemp(suffix, prefix, dir, text)
-    fd = os.fdopen(fh, mode, bufsize)
+    fd = os.fdopen(fh, mode, bufsize, errors='backslashreplace')
     return (fd, filename)
 
 
diff --git a/reportbug/ui/gtk2_ui.py b/reportbug/ui/gtk2_ui.py
index fe97201..80b7d3d 100644
--- a/reportbug/ui/gtk2_ui.py
+++ b/reportbug/ui/gtk2_ui.py
@@ -1350,9 +1350,8 @@ class EditorPage(Page):
         global report_message
         _assert_context(ui_context)
         report_message = self.get_value()[0]
-        f = open(self.filename, "w")
-        f.write(report_message)
-        f.close()
+        with open(self.filename, "w", errors='backslashreplace') as f:
+            f.write(report_message)
 
     def connect_signals(self):
         _assert_context(ui_context)
diff --git a/reportbug/ui/text_ui.py b/reportbug/ui/text_ui.py
index 4a60ff8..eeaae63 100644
--- a/reportbug/ui/text_ui.py
+++ b/reportbug/ui/text_ui.py
@@ -1023,7 +1023,7 @@ def spawn_editor(message, filename, editor, charset='utf-8'):
 
     # Move the cursor for lazy buggers like me; add your editor here...
     ourline = 0
-    with open(filename) as f:
+    with open(filename, errors='backslashreplace') as f:
         for (lineno, line) in enumerate(f):
             if line == '\n' and not ourline:
                 ourline = lineno + 2
@@ -1062,7 +1062,7 @@ def spawn_editor(message, filename, editor, charset='utf-8'):
     if '&' in editor:
         return (None, 1)
 
-    with open(filename) as f:
+    with open(filename, errors='backslashreplace') as f:
         newmessage = f.read()
 
     if newmessage == message:
diff --git a/reportbug/utils.py b/reportbug/utils.py
index 8139668..450673d 100644
--- a/reportbug/utils.py
+++ b/reportbug/utils.py
@@ -246,7 +246,7 @@ def find_rewritten(username):
     for filename in ['/etc/email-addresses']:
         if os.path.exists(filename):
             try:
-                fp = open(filename)
+                fp = open(filename, errors='backslashreplace')
             except IOError:
                 continue
             for line in fp:
@@ -714,7 +714,7 @@ def get_changed_config_files(conffiles, nocompress=False):
     changed = []
     for (filename, md5sum) in conffiles:
         try:
-            fp = open(filename)
+            fp = open(filename, errors='backslashreplace')
         except IOError as msg:
             confinfo[filename] = msg
             continue
@@ -769,9 +769,8 @@ def get_debian_release_info():
             debvers = dists[0][1]
 
     try:
-        fob = open('/etc/debian_version')
-        verfile = fob.readline().strip()
-        fob.close()
+        with open('/etc/debian_version', errors='backslashreplace') as fob:
+            verfile = fob.readline().strip()
     except IOError:
         print('Unable to open /etc/debian_version', file=sys.stderr)
 
@@ -961,7 +960,9 @@ def mua_exists(mua):
     output = '/dev/null'
     if os.path.exists(output):
         try:
-            returnvalue = subprocess.call(MUAVERSION[mua_tmp], stdout=open(output, 'w'), stderr=subprocess.STDOUT,
+            returnvalue = subprocess.call(MUAVERSION[mua_tmp],
+                                          stdout=open(output, 'w', errors='backslashreplace'),
+                                          stderr=subprocess.STDOUT,
                                           shell=True)
         except (IOError, OSError):
             returnvalue = subprocess.call(MUAVERSION[mua_tmp], shell=True)
@@ -1084,7 +1085,7 @@ def parse_bug_control_file(filename):
     submitas = submitto = None
     reportwith = []
     supplemental = []
-    fh = open(filename)
+    fh = open(filename, errors='backslashreplace')
     for line in fh:
         line = line.strip()
         parts = line.split(': ')
-- 
2.11.0

_______________________________________________
Reportbug-maint mailing list
Reportbug-maint@lists.alioth.debian.org
http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/reportbug-maint

Reply via email to