Merged `parser.clean()` fix (issue #16820) from 3.2 through 3.3.

This commit is contained in:
Łukasz Langa 2012-12-31 03:43:37 +01:00
commit 1dce0003a6
4 changed files with 48 additions and 1 deletions

View File

@ -389,7 +389,13 @@ However, there are a few differences that should be taken into account:
the default value to be visible again. Trying to delete a default value the default value to be visible again. Trying to delete a default value
causes a ``KeyError``. causes a ``KeyError``.
* Trying to delete the ``DEFAULTSECT`` raises ``ValueError``. * ``DEFAULTSECT`` cannot be removed from the parser:
* trying to delete it raises ``ValueError``,
* ``parser.clear()`` leaves it intact,
* ``parser.popitem()`` never returns it.
* ``parser.get(section, option, **kwargs)`` - the second argument is **not** * ``parser.get(section, option, **kwargs)`` - the second argument is **not**
a fallback value. Note however that the section-level ``get()`` methods are a fallback value. Note however that the section-level ``get()`` methods are

View File

@ -852,6 +852,19 @@ class RawConfigParser(MutableMapping):
value_getter = lambda option: d[option] value_getter = lambda option: d[option]
return [(option, value_getter(option)) for option in d.keys()] return [(option, value_getter(option)) for option in d.keys()]
def popitem(self):
"""Remove a section from the parser and return it as
a (section_name, section_proxy) tuple. If no section is present, raise
KeyError.
The section DEFAULT is never returned because it cannot be removed.
"""
for key in self.sections():
value = self[key]
del self[key]
return key, value
raise KeyError
def optionxform(self, optionstr): def optionxform(self, optionstr):
return optionstr.lower() return optionstr.lower()

View File

@ -770,6 +770,33 @@ boolean {0[0]} NO
with self.assertRaises(configparser.NoSectionError): with self.assertRaises(configparser.NoSectionError):
cf.items("no such section") cf.items("no such section")
def test_popitem(self):
cf = self.fromstring("""
[section1]
name1 {0[0]} value1
[section2]
name2 {0[0]} value2
[section3]
name3 {0[0]} value3
""".format(self.delimiters), defaults={"default": "<default>"})
self.assertEqual(cf.popitem()[0], 'section1')
self.assertEqual(cf.popitem()[0], 'section2')
self.assertEqual(cf.popitem()[0], 'section3')
with self.assertRaises(KeyError):
cf.popitem()
def test_clear(self):
cf = self.newconfig({"foo": "Bar"})
self.assertEqual(
cf.get(self.default_section, "Foo"), "Bar",
"could not locate option, expecting case-insensitive option names")
cf['zing'] = {'option1': 'value1', 'option2': 'value2'}
self.assertEqual(cf.sections(), ['zing'])
self.assertEqual(set(cf['zing'].keys()), {'option1', 'option2', 'foo'})
cf.clear()
self.assertEqual(set(cf.sections()), set())
self.assertEqual(set(cf[self.default_section].keys()), {'foo'})
class StrictTestCase(BasicTestCase): class StrictTestCase(BasicTestCase):
config_class = configparser.RawConfigParser config_class = configparser.RawConfigParser

View File

@ -1057,6 +1057,7 @@ Michael Scharf
Andreas Schawo Andreas Schawo
Neil Schemenauer Neil Schemenauer
David Scherer David Scherer
Wolfgang Scherer
Hynek Schlawack Hynek Schlawack
Bob Schmertz Bob Schmertz
Gregor Schmid Gregor Schmid