Add TupleOfTuplesValue along with associated tests and updated documentation

This commit is contained in:
Christian Abbott 2014-12-18 07:15:20 -08:00
parent 5d1a8d7887
commit c4ba5ca559
3 changed files with 92 additions and 11 deletions

View file

@ -176,7 +176,16 @@ class ListValue(Value):
self.default = []
# initial conversion
if self.converter is not None:
self.default = [self.converter(value) for value in self.default]
self.default = self._convert(self.default)
def _convert(self, list_):
converted_values = []
for value in list_:
try:
converted_values.append(self.converter(value))
except (TypeError, ValueError):
raise ValueError(self.message.format(value, value))
return converted_values
def to_python(self, value):
split_value = [v.strip() for v in value.strip().split(self.separator)]
@ -184,14 +193,7 @@ class ListValue(Value):
value_list = filter(None, split_value)
if self.converter is None:
return list(value_list)
converted_values = []
for list_value in value_list:
try:
converted_values.append(self.converter(list_value))
except (TypeError, ValueError):
raise ValueError(self.message.format(list_value, value))
return converted_values
return self._convert(value_list)
class BackendsValue(ListValue):
@ -218,6 +220,33 @@ class TupleValue(ListValue):
return tuple(super(TupleValue, self).to_python(value))
class TupleOfTuplesValue(TupleValue):
def __init__(self, *args, **kwargs):
self.tuple_separator = kwargs.pop('tuple_separator', ';')
super(TupleOfTuplesValue, self).__init__(*args, **kwargs)
def _convert(self, items):
# This could receive either a bare tuple or tuple of tuples
if items and isinstance(items[0], tuple):
converted_tuples = []
for inner in items:
converted = super(TupleOfTuplesValue, self)._convert(inner)
converted_tuples.append(tuple(converted))
return tuple(converted_tuples)
return tuple(super(TupleOfTuplesValue, self)._convert(items))
def to_python(self, value):
split_value = [
v.strip() for v in value.strip().split(self.tuple_separator)
]
# Remove empty items
value_list = filter(None, split_value)
tuples = [
super(TupleOfTuplesValue, self).to_python(v) for v in value_list
]
return tuple(tuples)
class SetValue(ListValue):
message = 'Cannot interpret set item {0!r} in set {1!r}'

View file

@ -274,6 +274,27 @@ Type values
See the :class:`~ListValue` examples above.
.. class:: TupleOfTuplesValue(default, [tuple_separator=';', separator=',', converter=None])
A :class:`~TupleValue` subclass that handles tuple of tuples values.
:param tuple_separator: the separator to split each tuple with
:param separator: the separator to split the inner tuple contents with
:param converter: the optional converter callable to apply for each inner
tuple item
Useful for ADMINS, MANAGERS, and the like. For example::
ADMINS = TupleOfTuplesValue((
('John', 'jcleese@site.com'),
('Eric', 'eidle@site.com'),
))
Override using environment variables like this::
DJANGO_ADMINS=Terry,tjones@site.com;Graham,gchapman@site.com
.. class:: SetValue
A :class:`~Value` subclass that handles set values.

View file

@ -9,8 +9,8 @@ from mock import patch
from configurations.values import (Value, BooleanValue, IntegerValue,
FloatValue, DecimalValue, ListValue,
TupleValue, SetValue, DictValue,
URLValue, EmailValue, IPValue,
TupleValue, TupleOfTuplesValue, SetValue,
DictValue, URLValue, EmailValue, IPValue,
RegexValue, PathValue, SecretValue,
DatabaseURLValue, EmailURLValue,
CacheURLValue, BackendsValue,
@ -175,6 +175,37 @@ class ValueTests(TestCase):
with env(DJANGO_TEST=''):
self.assertEqual(value.setup('TEST'), ())
def test_tuple_of_tuples_values_default(self):
value = TupleOfTuplesValue()
with env(DJANGO_TEST='2,3;4,5'):
expected = (('2', '3'), ('4', '5'))
self.assertEqual(value.setup('TEST'), expected)
with env(DJANGO_TEST='2;3;4;5'):
expected = (('2',), ('3',), ('4',), ('5',))
self.assertEqual(value.setup('TEST'), expected)
with env(DJANGO_TEST='2,3,4,5'):
expected = (('2', '3', '4', '5'),)
self.assertEqual(value.setup('TEST'), expected)
with env(DJANGO_TEST='2, 3 , ; 4 , 5 ; '):
expected = (('2', '3'), ('4', '5'))
self.assertEqual(value.setup('TEST'), expected)
with env(DJANGO_TEST=''):
self.assertEqual(value.setup('TEST'), ())
def test_tuple_of_tuples_values_separator(self):
value = TupleOfTuplesValue(tuple_separator=':')
with env(DJANGO_TEST='2,3:4,5'):
self.assertEqual(value.setup('TEST'), (('2', '3'), ('4', '5')))
def test_tuple_of_tuples_values_converter(self):
value = TupleOfTuplesValue(converter=int)
with env(DJANGO_TEST='2,3;4,5'):
self.assertEqual(value.setup('TEST'), ((2, 3), (4, 5)))
def test_tuple_of_tuples_values_converter_default(self):
value = TupleOfTuplesValue((('2', '3'), ('4', '5')), converter=int)
self.assertEqual(value.value, ((2, 3), (4, 5)))
def test_set_values_default(self):
value = SetValue()
with env(DJANGO_TEST='2,2'):