Rev 5991: Proper error messages for config files with content in non-utf encoding or that cannot be parsed in file:///home/vila/src/bzr/bugs/799212-non-ascii-confs/

Vincent Ladeuil v.ladeuil+lp at free.fr
Mon Jun 20 13:51:21 UTC 2011


At file:///home/vila/src/bzr/bugs/799212-non-ascii-confs/

------------------------------------------------------------
revno: 5991
revision-id: v.ladeuil+lp at free.fr-20110620135121-etfu8raxgczra0cw
parent: v.ladeuil+lp at free.fr-20110620131531-6lozjugg9hwf5qp2
fixes bug(s): https://launchpad.net/bugs/502060 https://launchpad.net/bugs/688677
committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
branch nick: 799212-non-ascii-confs
timestamp: Mon 2011-06-20 15:51:21 +0200
message:
  Proper error messages for config files with content in non-utf encoding or that cannot be parsed
-------------- next part --------------
=== modified file 'bzrlib/config.py'
--- a/bzrlib/config.py	2011-06-20 13:15:31 +0000
+++ b/bzrlib/config.py	2011-06-20 13:51:21 +0000
@@ -692,6 +692,8 @@
             self._parser = ConfigObj(co_input, encoding='utf-8')
         except configobj.ConfigObjError, e:
             raise errors.ParseConfigError(e.errors, e.config.filename)
+        except UnicodeDecodeError:
+            raise errors.ConfigContentError(self.file_name)
         # Make sure self.reload() will use the right file name
         self._parser.filename = self.file_name
         for hook in OldConfigHooks['load']:
@@ -1697,7 +1699,7 @@
             self._config = ConfigObj(self._input, encoding='utf-8')
         except configobj.ConfigObjError, e:
             raise errors.ParseConfigError(e.errors, e.config.filename)
-        except UnicodeError, e:
+        except UnicodeError:
             raise errors.ConfigContentError(self._filename)
         return self._config
 
@@ -2180,12 +2182,21 @@
         except errors.NoSuchFile:
             return StringIO()
 
+    def _external_url(self):
+        return urlutils.join(self._transport.external_url(), self._filename)
+
     def _get_configobj(self):
         f = self._get_config_file()
         try:
-            return ConfigObj(f, encoding='utf-8')
+            try:
+                conf = ConfigObj(f, encoding='utf-8')
+            except configobj.ConfigObjError, e:
+                raise errors.ParseConfigError(e.errors, self._external_url())
+            except UnicodeDecodeError:
+                raise errors.ConfigContentError(self._external_url())
         finally:
             f.close()
+        return conf
 
     def _set_configobj(self, configobj):
         out_file = StringIO()
@@ -2387,6 +2398,8 @@
         except configobj.ConfigObjError, e:
             self._config_obj = None
             raise errors.ParseConfigError(e.errors, self.external_url())
+        except UnicodeDecodeError:
+            raise errors.ConfigContentError(self.external_url())
 
     def save(self):
         if not self.is_loaded():

=== modified file 'bzrlib/tests/test_config.py'
--- a/bzrlib/tests/test_config.py	2011-06-20 13:15:31 +0000
+++ b/bzrlib/tests/test_config.py	2011-06-20 13:51:21 +0000
@@ -1871,9 +1871,34 @@
 
 class TestTransportConfig(tests.TestCaseWithTransport):
 
+    def test_load_utf8(self):
+        """Ensure we can load an utf8-encoded file."""
+        t = self.get_transport()
+        unicode_user = u'b\N{Euro Sign}ar'
+        unicode_content = u'user=%s' % (unicode_user,)
+        utf8_content = unicode_content.encode('utf8')
+        # Store the raw content in the config file
+        t.put_bytes('foo.conf', utf8_content)
+        conf = config.TransportConfig(t, 'foo.conf')
+        self.assertEquals(unicode_user, conf.get_option('user'))
+
+    def test_load_non_ascii(self):
+        """Ensure we display a proper error on non-ascii, non utf-8 content."""
+        t = self.get_transport()
+        t.put_bytes('foo.conf', 'user=foo\n#\xff\n')
+        conf = config.TransportConfig(t, 'foo.conf')
+        self.assertRaises(errors.ConfigContentError, conf._get_configobj)
+
+    def test_load_erroneous_content(self):
+        """Ensure we display a proper error on content that can't be parsed."""
+        t = self.get_transport()
+        t.put_bytes('foo.conf', '[open_section\n')
+        conf = config.TransportConfig(t, 'foo.conf')
+        self.assertRaises(errors.ParseConfigError, conf._get_configobj)
+
     def test_get_value(self):
         """Test that retreiving a value from a section is possible"""
-        bzrdir_config = config.TransportConfig(transport.get_transport('.'),
+        bzrdir_config = config.TransportConfig(self.get_transport('.'),
                                                'control.conf')
         bzrdir_config.set_option('value', 'key', 'SECTION')
         bzrdir_config.set_option('value2', 'key2')
@@ -2358,7 +2383,7 @@
         t = self.get_transport()
         t.put_bytes('foo.conf', 'user=foo\n#%s\n' % (self.invalid_utf8_char,))
         store = config.IniFileStore(t, 'foo.conf')
-        self.assertRaises(errors.ParseConfigError, store.load)
+        self.assertRaises(errors.ConfigContentError, store.load)
 
     def test_load_erroneous_content(self):
         """Ensure we display a proper error on content that can't be parsed."""
@@ -2396,7 +2421,7 @@
         with open('foo.conf', 'wb') as f:
             f.write('user=foo\n#%s\n' % (self.invalid_utf8_char,))
         conf = config.IniBasedConfig(file_name='foo.conf')
-        self.assertRaises(errors.ParseConfigError, conf._get_parser)
+        self.assertRaises(errors.ConfigContentError, conf._get_parser)
 
     def test_load_erroneous_content(self):
         """Ensure we display a proper error on content that can't be parsed."""

=== modified file 'doc/en/release-notes/bzr-2.4.txt'
--- a/doc/en/release-notes/bzr-2.4.txt	2011-06-20 13:15:31 +0000
+++ b/doc/en/release-notes/bzr-2.4.txt	2011-06-20 13:51:21 +0000
@@ -29,8 +29,9 @@
 Bug Fixes
 *********
 
-* Display a proper error message when ``authentication.conf`` content cannot
-  be decoded as UTF-8. (Vincent Ladeuil, #792246)
+* Display a proper error message when a config file content cannot be
+  decoded as UTF-8 or when it cannot be parsed.
+  (Vincent Ladeuil, #502060, #688677, #792246)
 
 * Properly load utf8-encoded config files. (Vincent Ladeuil, #799212)
 



More information about the bazaar-commits mailing list