conftypes: Various bugfixes/cleanups/tests.
This commit is contained in:
parent
7c54c20808
commit
963fb40961
@ -126,9 +126,10 @@ class BaseType:
|
||||
Return:
|
||||
The transformed value.
|
||||
"""
|
||||
if self.none_ok and not value:
|
||||
if not value:
|
||||
return None
|
||||
return value
|
||||
else:
|
||||
return value
|
||||
|
||||
def validate(self, value):
|
||||
"""Validate value against possible values.
|
||||
@ -259,7 +260,8 @@ class Bool(BaseType):
|
||||
def transform(self, value):
|
||||
if not value:
|
||||
return None
|
||||
return Bool._BOOLEAN_STATES[value.lower()]
|
||||
else:
|
||||
return Bool._BOOLEAN_STATES[value.lower()]
|
||||
|
||||
def validate(self, value):
|
||||
if not value:
|
||||
@ -294,9 +296,10 @@ class Int(BaseType):
|
||||
self.maxval = maxval
|
||||
|
||||
def transform(self, value):
|
||||
if self.none_ok and not value:
|
||||
if not value:
|
||||
return None
|
||||
return int(value)
|
||||
else:
|
||||
return int(value)
|
||||
|
||||
def validate(self, value):
|
||||
if not value:
|
||||
@ -328,9 +331,12 @@ class IntList(List):
|
||||
|
||||
def validate(self, value):
|
||||
try:
|
||||
self.transform(value)
|
||||
vals = self.transform(value)
|
||||
except ValueError:
|
||||
raise ValidationError(value, "must be a list of integers!")
|
||||
for v in vals:
|
||||
if v is None and not self.none_ok:
|
||||
raise ValidationError(value, "items may not be empty!")
|
||||
|
||||
|
||||
class Float(BaseType):
|
||||
@ -353,9 +359,10 @@ class Float(BaseType):
|
||||
self.maxval = maxval
|
||||
|
||||
def transform(self, value):
|
||||
if self.none_ok and not value:
|
||||
if not value:
|
||||
return None
|
||||
return float(value)
|
||||
else:
|
||||
return float(value)
|
||||
|
||||
def validate(self, value):
|
||||
if not value:
|
||||
@ -395,9 +402,10 @@ class Perc(BaseType):
|
||||
self.maxval = maxval
|
||||
|
||||
def transform(self, value):
|
||||
if self.none_ok and not value:
|
||||
if not value:
|
||||
return
|
||||
return int(value[:-1])
|
||||
else:
|
||||
return int(value[:-1])
|
||||
|
||||
def validate(self, value):
|
||||
if not value:
|
||||
@ -440,7 +448,7 @@ class PercList(List):
|
||||
|
||||
def transform(self, value):
|
||||
vals = super().transform(value)
|
||||
return [int(val[:-1]) for val in vals]
|
||||
return [int(v[:-1]) if v is not None else None for v in vals]
|
||||
|
||||
def validate(self, value):
|
||||
vals = super().transform(value)
|
||||
@ -556,12 +564,13 @@ class ColorSystem(BaseType):
|
||||
def transform(self, value):
|
||||
if not value:
|
||||
return None
|
||||
mapping = {
|
||||
'rgb': QColor.Rgb,
|
||||
'hsv': QColor.Hsv,
|
||||
'hsl': QColor.Hsl,
|
||||
}
|
||||
return mapping[value.lower()]
|
||||
else:
|
||||
mapping = {
|
||||
'rgb': QColor.Rgb,
|
||||
'hsv': QColor.Hsv,
|
||||
'hsl': QColor.Hsl,
|
||||
}
|
||||
return mapping[value.lower()]
|
||||
|
||||
|
||||
class QtColor(BaseType):
|
||||
@ -582,7 +591,10 @@ class QtColor(BaseType):
|
||||
raise ValidationError(value, "must be a valid color")
|
||||
|
||||
def transform(self, value):
|
||||
return QColor(value)
|
||||
if not value:
|
||||
return None
|
||||
else:
|
||||
return QColor(value)
|
||||
|
||||
|
||||
class CssColor(BaseType):
|
||||
@ -654,6 +666,8 @@ class QtFont(Font):
|
||||
"""A Font which gets converted to q QFont."""
|
||||
|
||||
def transform(self, value):
|
||||
if not value:
|
||||
return None
|
||||
style_map = {
|
||||
'normal': QFont.StyleNormal,
|
||||
'italic': QFont.StyleItalic,
|
||||
@ -708,7 +722,10 @@ class Regex(BaseType):
|
||||
raise ValidationError(value, "must be a valid regex - " + str(e))
|
||||
|
||||
def transform(self, value):
|
||||
return re.compile(value, self.flags)
|
||||
if not value:
|
||||
return None
|
||||
else:
|
||||
return re.compile(value, self.flags)
|
||||
|
||||
|
||||
class RegexList(List):
|
||||
@ -723,7 +740,8 @@ class RegexList(List):
|
||||
|
||||
def transform(self, value):
|
||||
vals = super().transform(value)
|
||||
return [re.compile(pattern, self.flags) for pattern in vals]
|
||||
return [re.compile(v, self.flags) if v is not None else None
|
||||
for v in vals]
|
||||
|
||||
def validate(self, value):
|
||||
try:
|
||||
@ -752,6 +770,8 @@ class File(BaseType):
|
||||
raise ValidationError(value, "must be an absolute path!")
|
||||
|
||||
def transform(self, value):
|
||||
if not value:
|
||||
return None
|
||||
return os.path.expanduser(value)
|
||||
|
||||
|
||||
@ -824,7 +844,7 @@ class WebKitBytes(BaseType):
|
||||
def transform(self, value):
|
||||
if not value:
|
||||
return None
|
||||
if any(value.lower().endswith(c) for c in self.SUFFIXES):
|
||||
elif any(value.lower().endswith(c) for c in self.SUFFIXES):
|
||||
suffix = value[-1].lower()
|
||||
val = value[:-1]
|
||||
multiplicator = self.SUFFIXES[suffix]
|
||||
@ -853,8 +873,9 @@ class WebKitBytesList(List):
|
||||
def transform(self, value):
|
||||
if value == '':
|
||||
return None
|
||||
vals = super().transform(value)
|
||||
return [self.bytestype.transform(val) for val in vals]
|
||||
else:
|
||||
vals = super().transform(value)
|
||||
return [self.bytestype.transform(val) for val in vals]
|
||||
|
||||
def validate(self, value):
|
||||
if not value:
|
||||
@ -894,7 +915,10 @@ class ShellCommand(String):
|
||||
raise ValidationError(value, "needs to contain a {}-placeholder.")
|
||||
|
||||
def transform(self, value):
|
||||
return shlex.split(value)
|
||||
if not value:
|
||||
return None
|
||||
else:
|
||||
return shlex.split(value)
|
||||
|
||||
|
||||
class ZoomPerc(Perc):
|
||||
@ -962,7 +986,9 @@ class Proxy(BaseType):
|
||||
return out
|
||||
|
||||
def transform(self, value):
|
||||
if value == 'system':
|
||||
if not value:
|
||||
return None
|
||||
elif value == 'system':
|
||||
return None
|
||||
elif value == 'none':
|
||||
return QNetworkProxy(QNetworkProxy.NoProxy)
|
||||
@ -1011,7 +1037,11 @@ class KeyBindingName(BaseType):
|
||||
"""The name (keys) of a keybinding."""
|
||||
|
||||
def validate(self, value):
|
||||
pass
|
||||
if not value:
|
||||
if self.none_ok:
|
||||
return
|
||||
else:
|
||||
raise ValidationError(value, "may not be empty!")
|
||||
|
||||
|
||||
class KeyBinding(Command):
|
||||
@ -1046,13 +1076,20 @@ class AutoSearch(BaseType):
|
||||
('false', "Never search automatically."))
|
||||
|
||||
def validate(self, value):
|
||||
if not value:
|
||||
if self.none_ok:
|
||||
return
|
||||
else:
|
||||
raise ValidationError(value, "may not be empty!")
|
||||
if value.lower() in ('naive', 'dns'):
|
||||
pass
|
||||
else:
|
||||
Bool.validate(self, value)
|
||||
|
||||
def transform(self, value):
|
||||
if value.lower() in ('naive', 'dns'):
|
||||
if not value:
|
||||
return None
|
||||
elif value.lower() in ('naive', 'dns'):
|
||||
return value.lower()
|
||||
elif super().transform(value):
|
||||
# boolean true is an alias for naive matching
|
||||
|
@ -20,6 +20,9 @@
|
||||
import unittest
|
||||
|
||||
import qutebrowser.config.conftypes as conftypes
|
||||
from qutebrowser.test.stubs import FakeCmdUtils, FakeCommand
|
||||
|
||||
from PyQt5.QtGui import QColor, QFont
|
||||
|
||||
|
||||
class ValidValuesTest(unittest.TestCase):
|
||||
@ -87,13 +90,8 @@ class BaseTypeTests(unittest.TestCase):
|
||||
self.assertEqual(self.t.transform("foobar"), "foobar")
|
||||
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with none_ok = False and an empty value."""
|
||||
self.assertEqual(self.t.transform(''), '')
|
||||
|
||||
def test_transform_empty_none_ok(self):
|
||||
"""Test transform with none_ok = True and an empty value."""
|
||||
t = conftypes.BaseType(none_ok=True)
|
||||
self.assertIsNone(t.transform(''))
|
||||
"""Test transform with an empty value."""
|
||||
self.assertIsNone(self.t.transform(''))
|
||||
|
||||
def test_validate_not_implemented(self):
|
||||
"""Test validate without valid_values set."""
|
||||
@ -166,7 +164,8 @@ class StringTests(unittest.TestCase):
|
||||
def test_validate_empty(self):
|
||||
"""Test validate with empty string and none_ok = False."""
|
||||
t = conftypes.String()
|
||||
t.validate("")
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate("")
|
||||
|
||||
def test_validate_empty_none_ok(self):
|
||||
"""Test validate with empty string and none_ok = True."""
|
||||
@ -249,7 +248,7 @@ class ListTests(unittest.TestCase):
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with an empty value."""
|
||||
self.assertEqual(self.t.transform('foo,,baz'),
|
||||
['foo', '', 'baz'])
|
||||
['foo', None, 'baz'])
|
||||
|
||||
def test_transform_empty_none_ok(self):
|
||||
"""Test transform with an empty value and none_ok = True."""
|
||||
@ -271,7 +270,11 @@ class BoolTests(unittest.TestCase):
|
||||
"""Test transform with all values."""
|
||||
for out, inputs in self.TESTS.items():
|
||||
for inp in inputs:
|
||||
self.assertEqual(self.t.transform(inp), out)
|
||||
self.assertEqual(self.t.transform(inp), out, inp)
|
||||
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with none_ok = False and an empty value."""
|
||||
self.assertIsNone(self.t.transform(''))
|
||||
|
||||
def test_validate_valid(self):
|
||||
"""Test validate with valid values."""
|
||||
@ -285,6 +288,18 @@ class BoolTests(unittest.TestCase):
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
self.t.validate(val)
|
||||
|
||||
def test_validate_empty(self):
|
||||
"""Test validate with empty string and none_ok = False."""
|
||||
t = conftypes.Bool()
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('')
|
||||
|
||||
def test_validate_empty_none_ok(self):
|
||||
"""Test validate with empty string and none_ok = True."""
|
||||
t = conftypes.Int(none_ok=True)
|
||||
t.validate('')
|
||||
|
||||
|
||||
|
||||
class IntTests(unittest.TestCase):
|
||||
|
||||
@ -397,10 +412,9 @@ class IntListTests(unittest.TestCase):
|
||||
self.assertEqual(self.t.transform('23,42,1337'),
|
||||
[23, 42, 1337])
|
||||
|
||||
def test_transform_empty_none_ok(self):
|
||||
"""Test transform with an empty value and none_ok = True."""
|
||||
t = conftypes.IntList(none_ok=True)
|
||||
self.assertEqual(t.transform('23,,42'), [23, None, 42])
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with an empty value."""
|
||||
self.assertEqual(self.t.transform('23,,42'), [23, None, 42])
|
||||
|
||||
|
||||
class FloatTests(unittest.TestCase):
|
||||
@ -481,9 +495,9 @@ class FloatTests(unittest.TestCase):
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('3.01')
|
||||
|
||||
def test_transform_none(self):
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with an empty value."""
|
||||
t = conftypes.Float(none_ok=True)
|
||||
t = conftypes.Float()
|
||||
self.assertIsNone(t.transform(''))
|
||||
|
||||
def test_transform_float(self):
|
||||
@ -501,6 +515,9 @@ class PercTests(unittest.TestCase):
|
||||
|
||||
"""Test Perc."""
|
||||
|
||||
def setUp(self):
|
||||
self.t = conftypes.Perc()
|
||||
|
||||
def test_minval_gt_maxval(self):
|
||||
"""Test __init__ with a minval bigger than the maxval."""
|
||||
with self.assertRaises(ValueError):
|
||||
@ -508,26 +525,22 @@ class PercTests(unittest.TestCase):
|
||||
|
||||
def test_validate_int(self):
|
||||
"""Test validate with a normal int (not a percentage)."""
|
||||
t = conftypes.Perc()
|
||||
with self.assertRaises(ValueError):
|
||||
t.validate('1337')
|
||||
self.t.validate('1337')
|
||||
|
||||
def test_validate_string(self):
|
||||
"""Test validate with something which isn't a percentage."""
|
||||
t = conftypes.Perc()
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('1337%%')
|
||||
self.t.validate('1337%%')
|
||||
|
||||
def test_validate_perc(self):
|
||||
"""Test validate with a percentage."""
|
||||
t = conftypes.Perc()
|
||||
t.validate('1337%')
|
||||
self.t.validate('1337%')
|
||||
|
||||
def test_validate_empty(self):
|
||||
"""Test validate with empty string and none_ok = False."""
|
||||
t = conftypes.Perc()
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('')
|
||||
self.t.validate('')
|
||||
|
||||
def test_validate_empty_none_ok(self):
|
||||
"""Test validate with empty string and none_ok = True."""
|
||||
@ -570,15 +583,13 @@ class PercTests(unittest.TestCase):
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('4%')
|
||||
|
||||
def test_transform_none(self):
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with an empty value."""
|
||||
t = conftypes.Perc(none_ok=True)
|
||||
self.assertIsNone(t.transform(''))
|
||||
self.assertIsNone(self.t.transform(''))
|
||||
|
||||
def test_transform_perc(self):
|
||||
"""Test transform with a percentage."""
|
||||
t = conftypes.Perc()
|
||||
self.assertEqual(t.transform('1337%'), 1337)
|
||||
self.assertEqual(self.t.transform('1337%'), 1337)
|
||||
|
||||
|
||||
class PercListTests(unittest.TestCase):
|
||||
@ -663,6 +674,9 @@ class PercOrIntTests(unittest.TestCase):
|
||||
|
||||
"""Test PercOrInt."""
|
||||
|
||||
def setUp(self):
|
||||
self.t = conftypes.PercOrInt()
|
||||
|
||||
def test_minint_gt_maxint(self):
|
||||
"""Test __init__ with a minint bigger than the maxint."""
|
||||
with self.assertRaises(ValueError):
|
||||
@ -675,25 +689,21 @@ class PercOrIntTests(unittest.TestCase):
|
||||
|
||||
def test_validate_string(self):
|
||||
"""Test validate with something which isn't a percentage."""
|
||||
t = conftypes.PercOrInt()
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('1337%%')
|
||||
self.t.validate('1337%%')
|
||||
|
||||
def test_validate_perc(self):
|
||||
"""Test validate with a percentage."""
|
||||
t = conftypes.PercOrInt()
|
||||
t.validate('1337%')
|
||||
self.t.validate('1337%')
|
||||
|
||||
def test_validate_int(self):
|
||||
"""Test validate with a normal int."""
|
||||
t = conftypes.PercOrInt()
|
||||
t.validate('1337')
|
||||
self.t.validate('1337')
|
||||
|
||||
def test_validate_empty(self):
|
||||
"""Test validate with empty string and none_ok = False."""
|
||||
t = conftypes.PercOrInt()
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
t.validate('')
|
||||
self.t.validate('')
|
||||
|
||||
def test_validate_empty_none_ok(self):
|
||||
"""Test validate with empty string and none_ok = True."""
|
||||
@ -786,21 +796,125 @@ class PercOrIntTests(unittest.TestCase):
|
||||
|
||||
def test_transform_none(self):
|
||||
"""Test transform with an empty value."""
|
||||
t = conftypes.PercOrInt(none_ok=True)
|
||||
self.assertIsNone(t.transform(''))
|
||||
self.assertIsNone(self.t.transform(''))
|
||||
|
||||
def test_transform_perc(self):
|
||||
"""Test transform with a percentage."""
|
||||
t = conftypes.PercOrInt()
|
||||
self.assertEqual(t.transform('1337%'), '1337%')
|
||||
self.assertEqual(self.t.transform('1337%'), '1337%')
|
||||
|
||||
def test_transform_int(self):
|
||||
"""Test transform with an int."""
|
||||
t = conftypes.PercOrInt()
|
||||
self.assertEqual(t.transform('1337'), '1337')
|
||||
self.assertEqual(self.t.transform('1337'), '1337')
|
||||
|
||||
|
||||
class CommandTests(unittest.TestCase):
|
||||
|
||||
"""Test Command."""
|
||||
|
||||
def setUp(self):
|
||||
self.old_cmdutils = conftypes.cmdutils
|
||||
commands = {
|
||||
'cmd1': FakeCommand("desc 1"),
|
||||
'cmd2': FakeCommand("desc 2"),
|
||||
}
|
||||
conftypes.cmdutils = FakeCmdUtils(commands)
|
||||
self.t = conftypes.Command()
|
||||
|
||||
def tearDown(self):
|
||||
conftypes.cmdutils = self.old_cmdutils
|
||||
|
||||
def test_validate_empty(self):
|
||||
"""Test validate with an empty string."""
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
self.t.validate('')
|
||||
|
||||
def test_validate_empty_none_ok(self):
|
||||
"""Test validate with an empty string and none_ok=True."""
|
||||
t = conftypes.Command(none_ok=True)
|
||||
t.validate('')
|
||||
|
||||
def test_validate_command(self):
|
||||
"""Test validate with a command."""
|
||||
self.t.validate('cmd1')
|
||||
self.t.validate('cmd2')
|
||||
|
||||
def test_validate_command_args(self):
|
||||
"""Test validate with a command and arguments."""
|
||||
self.t.validate('cmd1 foo bar')
|
||||
self.t.validate('cmd2 baz fish')
|
||||
|
||||
def test_validate_invalid_command(self):
|
||||
"""Test validate with an invalid command."""
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
self.t.validate('cmd3')
|
||||
|
||||
def test_validate_invalid_command_args(self):
|
||||
"""Test validate with an invalid command and arguments."""
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
self.t.validate('cmd3 foo bar')
|
||||
|
||||
def test_transform(self):
|
||||
"""Make sure transform doesn't alter values."""
|
||||
self.assertEqual(self.t.transform('foo bar'), 'foo bar')
|
||||
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with an empty value."""
|
||||
self.assertIsNone(self.t.transform(''))
|
||||
|
||||
def test_complete(self):
|
||||
"""Test complete."""
|
||||
items = self.t.complete()
|
||||
self.assertEqual(len(items), 2)
|
||||
self.assertIn(('cmd1', "desc 1"), items)
|
||||
self.assertIn(('cmd2', "desc 2"), items)
|
||||
|
||||
|
||||
class ColorSystemTests(unittest.TestCase):
|
||||
|
||||
"""Test ColorSystem."""
|
||||
|
||||
TESTS = {
|
||||
'RGB': QColor.Rgb,
|
||||
'rgb': QColor.Rgb,
|
||||
'HSV': QColor.Hsv,
|
||||
'hsv': QColor.Hsv,
|
||||
'HSL': QColor.Hsl,
|
||||
'hsl': QColor.Hsl,
|
||||
}
|
||||
INVALID = ['RRGB', 'HSV ']
|
||||
|
||||
def setUp(self):
|
||||
self.t = conftypes.ColorSystem()
|
||||
|
||||
def test_validate_empty(self):
|
||||
"""Test validate with an empty string."""
|
||||
with self.assertRaises(conftypes.ValidationError):
|
||||
self.t.validate('')
|
||||
|
||||
def test_validate_empty_none_ok(self):
|
||||
"""Test validate with an empty string and none_ok=True."""
|
||||
t = conftypes.ColorSystem(none_ok=True)
|
||||
t.validate('')
|
||||
|
||||
def test_validate_valid(self):
|
||||
"""Test validate with valid values."""
|
||||
for val in self.TESTS:
|
||||
self.t.validate(val)
|
||||
|
||||
def test_validate_invalid(self):
|
||||
"""Test validate with invalid values."""
|
||||
for val in self.INVALID:
|
||||
with self.assertRaises(conftypes.ValidationError, msg=val):
|
||||
self.t.validate(val)
|
||||
|
||||
def test_transform(self):
|
||||
"""Test transform."""
|
||||
for k, v in self.TESTS.items():
|
||||
self.assertEqual(self.t.transform(k), v, k)
|
||||
|
||||
def test_transform_empty(self):
|
||||
"""Test transform with an empty value."""
|
||||
self.assertIsNone(self.t.transform(''))
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
||||
|
@ -279,3 +279,19 @@ class FakeSignal:
|
||||
|
||||
def __init__(self, name='fake'):
|
||||
self.signal = '2{}(int, int)'.format(name)
|
||||
|
||||
|
||||
class FakeCmdUtils:
|
||||
|
||||
"""Stub for cmdutils which provides a cmd_dict."""
|
||||
|
||||
def __init__(self, commands):
|
||||
self.cmd_dict = commands
|
||||
|
||||
|
||||
class FakeCommand:
|
||||
|
||||
"""A simple command stub which has a description."""
|
||||
|
||||
def __init__(self, desc):
|
||||
self.desc = desc
|
||||
|
Loading…
Reference in New Issue
Block a user