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:58:54 UTC 2011
At file:///home/vila/src/bzr/bugs/799212-non-ascii-confs/
------------------------------------------------------------
revno: 5991
revision-id: v.ladeuil+lp at free.fr-20110620135854-venf3fbpk7ggqbc9
parent: v.ladeuil+lp at free.fr-20110620135814-t4d3iz9zu82vpvhl
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:58:54 +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:58:14 +0000
+++ b/bzrlib/config.py 2011-06-20 13:58:54 +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:58:14 +0000
+++ b/bzrlib/tests/test_config.py 2011-06-20 13:58:54 +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:58:14 +0000
+++ b/doc/en/release-notes/bzr-2.4.txt 2011-06-20 13:58:54 +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