diff options
author | Louie Lu <git@louie.lu> | 2017-07-12 18:05:32 (GMT) |
---|---|---|
committer | terryjreedy <tjreedy@udel.edu> | 2017-07-12 18:05:32 (GMT) |
commit | 50c9435c9b73b39fcf79cc3e58edc58bb943d0ed (patch) | |
tree | 19f695e2fb995e613378bf7fee064cff01c4d6f9 /Lib/idlelib/idle_test | |
parent | d1cc037d1442cc35d1b194ec8e50901514360949 (diff) | |
download | cpython-50c9435c9b73b39fcf79cc3e58edc58bb943d0ed.zip cpython-50c9435c9b73b39fcf79cc3e58edc58bb943d0ed.tar.gz cpython-50c9435c9b73b39fcf79cc3e58edc58bb943d0ed.tar.bz2 |
bpo-30899: Add unittests, 100% coverage, for IDLE's two ConfigParser subclasses. (#2662)
Patch by Louie Lu.
Diffstat (limited to 'Lib/idlelib/idle_test')
-rw-r--r-- | Lib/idlelib/idle_test/test_config.py | 169 |
1 files changed, 165 insertions, 4 deletions
diff --git a/Lib/idlelib/idle_test/test_config.py b/Lib/idlelib/idle_test/test_config.py index a8e3a3b..f5a609f 100644 --- a/Lib/idlelib/idle_test/test_config.py +++ b/Lib/idlelib/idle_test/test_config.py @@ -1,9 +1,13 @@ '''Test idlelib.config. -Much is tested by opening config dialog live or in test_configdialog. -Coverage: 27% +Coverage: 46% (100% for IdleConfParser, IdleUserConfParser*, ConfigChanges). +* Except is OSError clause in Save method. +Much of IdleConf is exercised by ConfigDialog and test_configdialog, +but it should be tested here. ''' -from test.support import captured_stderr +import os +import tempfile +from test.support import captured_stderr, findfile import unittest from idlelib import config @@ -26,6 +30,161 @@ def tearDownModule(): idleConf.userCfg = usercfg +class IdleConfParserTest(unittest.TestCase): + """Test that IdleConfParser works""" + + config = """ + [one] + one = false + two = true + three = 10 + + [two] + one = a string + two = true + three = false + """ + + def test_get(self): + parser = config.IdleConfParser('') + parser.read_string(self.config) + eq = self.assertEqual + + # Test with type argument. + self.assertIs(parser.Get('one', 'one', type='bool'), False) + self.assertIs(parser.Get('one', 'two', type='bool'), True) + eq(parser.Get('one', 'three', type='int'), 10) + eq(parser.Get('two', 'one'), 'a string') + self.assertIs(parser.Get('two', 'two', type='bool'), True) + self.assertIs(parser.Get('two', 'three', type='bool'), False) + + # Test without type should fallback to string. + eq(parser.Get('two', 'two'), 'true') + eq(parser.Get('two', 'three'), 'false') + + # If option not exist, should return None, or default. + self.assertIsNone(parser.Get('not', 'exist')) + eq(parser.Get('not', 'exist', default='DEFAULT'), 'DEFAULT') + + def test_get_option_list(self): + parser = config.IdleConfParser('') + parser.read_string(self.config) + get_list = parser.GetOptionList + self.assertCountEqual(get_list('one'), ['one', 'two', 'three']) + self.assertCountEqual(get_list('two'), ['one', 'two', 'three']) + self.assertEqual(get_list('not exist'), []) + + def test_load_nothing(self): + parser = config.IdleConfParser('') + parser.Load() + self.assertEqual(parser.sections(), []) + + def test_load_file(self): + # Borrow test/cfgparser.1 from test_configparser. + config_path = findfile('cfgparser.1') + parser = config.IdleConfParser(config_path) + parser.Load() + + self.assertEqual(parser.Get('Foo Bar', 'foo'), 'newbar') + self.assertEqual(parser.GetOptionList('Foo Bar'), ['foo']) + + +class IdleUserConfParserTest(unittest.TestCase): + """Test that IdleUserConfParser works""" + + def new_parser(self, path=''): + return config.IdleUserConfParser(path) + + def test_set_option(self): + parser = self.new_parser() + parser.add_section('Foo') + # Setting new option in existing section should return True. + self.assertTrue(parser.SetOption('Foo', 'bar', 'true')) + # Setting existing option with same value should return False. + self.assertFalse(parser.SetOption('Foo', 'bar', 'true')) + # Setting exiting option with new value should return True. + self.assertTrue(parser.SetOption('Foo', 'bar', 'false')) + self.assertEqual(parser.Get('Foo', 'bar'), 'false') + + # Setting option in new section should create section and return True. + self.assertTrue(parser.SetOption('Bar', 'bar', 'true')) + self.assertCountEqual(parser.sections(), ['Bar', 'Foo']) + self.assertEqual(parser.Get('Bar', 'bar'), 'true') + + def test_remove_option(self): + parser = self.new_parser() + parser.AddSection('Foo') + parser.SetOption('Foo', 'bar', 'true') + + self.assertTrue(parser.RemoveOption('Foo', 'bar')) + self.assertFalse(parser.RemoveOption('Foo', 'bar')) + self.assertFalse(parser.RemoveOption('Not', 'Exist')) + + def test_add_section(self): + parser = self.new_parser() + self.assertEqual(parser.sections(), []) + + # Should not add duplicate section. + # Configparser raises DuplicateError, IdleParser not. + parser.AddSection('Foo') + parser.AddSection('Foo') + parser.AddSection('Bar') + self.assertCountEqual(parser.sections(), ['Bar', 'Foo']) + + def test_remove_empty_sections(self): + parser = self.new_parser() + + parser.AddSection('Foo') + parser.AddSection('Bar') + parser.SetOption('Idle', 'name', 'val') + self.assertCountEqual(parser.sections(), ['Bar', 'Foo', 'Idle']) + parser.RemoveEmptySections() + self.assertEqual(parser.sections(), ['Idle']) + + def test_is_empty(self): + parser = self.new_parser() + + parser.AddSection('Foo') + parser.AddSection('Bar') + self.assertTrue(parser.IsEmpty()) + self.assertEqual(parser.sections(), []) + + parser.SetOption('Foo', 'bar', 'false') + parser.AddSection('Bar') + self.assertFalse(parser.IsEmpty()) + self.assertCountEqual(parser.sections(), ['Foo']) + + def test_remove_file(self): + with tempfile.TemporaryDirectory() as tdir: + path = os.path.join(tdir, 'test.cfg') + parser = self.new_parser(path) + parser.RemoveFile() # Should not raise exception. + + parser.AddSection('Foo') + parser.SetOption('Foo', 'bar', 'true') + parser.Save() + self.assertTrue(os.path.exists(path)) + parser.RemoveFile() + self.assertFalse(os.path.exists(path)) + + def test_save(self): + with tempfile.TemporaryDirectory() as tdir: + path = os.path.join(tdir, 'test.cfg') + parser = self.new_parser(path) + parser.AddSection('Foo') + parser.SetOption('Foo', 'bar', 'true') + + # Should save to path when config is not empty. + self.assertFalse(os.path.exists(path)) + parser.Save() + self.assertTrue(os.path.exists(path)) + + # Should remove the file from disk when config is empty. + parser.remove_section('Foo') + parser.Save() + self.assertFalse(os.path.exists(path)) + + class CurrentColorKeysTest(unittest.TestCase): """ Test colorkeys function with user config [Theme] and [Keys] patterns. @@ -179,10 +338,12 @@ class ChangesTest(unittest.TestCase): def test_save_added(self): changes = self.load() - changes.save_all() + self.assertTrue(changes.save_all()) self.assertEqual(usermain['Msec']['mitem'], 'mval') self.assertEqual(userhigh['Hsec']['hitem'], 'hval') self.assertEqual(userkeys['Ksec']['kitem'], 'kval') + changes.add_option('main', 'Msec', 'mitem', 'mval') + self.assertFalse(changes.save_all()) usermain.remove_section('Msec') userhigh.remove_section('Hsec') userkeys.remove_section('Ksec') |