Skip to content

Commit

Permalink
Fixes the lookup for dependency fields.
Browse files Browse the repository at this point in the history
Before that a document field with None as value
was considered to be absent in the document.
Also gets the nullable rule's constraint from
Validator.ignore_none_values in case that one may
not be the default. Amended docs to clarify that.

Fixes pyeve#305
  • Loading branch information
funkyfuture committed Apr 17, 2017
1 parent b8f2842 commit 1cbaeff
Show file tree
Hide file tree
Showing 3 changed files with 23 additions and 10 deletions.
14 changes: 13 additions & 1 deletion cerberus/tests/test_validation.py
Original file line number Diff line number Diff line change
Expand Up @@ -808,7 +808,19 @@ def test_dependencies_dict_with_required_field():
assert_success({'foo': 'bar', 'bar': 'foo'}, schema)


def test_dependencies_dict_with_subodcuments_fields():
def test_dependencies_field_satisfy_nullable_field():
# https://github.com/pyeve/cerberus/issues/305
schema = {
'foo': {'nullable': True},
'bar': {'dependencies': 'foo'}
}

assert_success({'foo': None, 'bar': 1}, schema)
assert_success({'foo': None}, schema)
assert_fail({'bar': 1}, schema)


def test_dependencies_dict_with_subdocuments_fields():
schema = {
'test_field': {'dependencies': {'a_dict.foo': ['foo', 'bar'],
'a_dict.bar': 'bar'}},
Expand Down
11 changes: 6 additions & 5 deletions cerberus/validator.py
Original file line number Diff line number Diff line change
Expand Up @@ -240,7 +240,8 @@ def _error(self, *args):
else:
field_definitions = self._resolve_rules_set(self.schema[field])
if rule == 'nullable':
constraint = field_definitions.get(rule, False)
constraint = field_definitions.get(rule,
self.ignore_none_values)
else:
constraint = field_definitions[rule]

Expand Down Expand Up @@ -347,9 +348,9 @@ def _lookup_field(self, path):

parts = path.split('.')
for part in parts:
context = context.get(part)
if context is None:
if part not in context:
return None, None
context = context.get(part)

return parts[-1], context

Expand Down Expand Up @@ -842,7 +843,7 @@ def __validate_unknown_fields(self, field):
else:
self._error(field, errors.UNKNOWN_FIELD)

# Remember to keep the validations method below this line
# Remember to keep the validation methods below this line
# sorted alphabetically

def __validate_definitions(self, definitions, field):
Expand Down Expand Up @@ -892,7 +893,7 @@ def _validate_allowed(self, allowed_values, field, value):
def _validate_dependencies(self, dependencies, field, value):
""" {'type': ['dict', 'hashable', 'hashables']} """
if isinstance(dependencies, _str_type):
dependencies = [dependencies]
dependencies = (dependencies,)

if isinstance(dependencies, Sequence):
self.__validate_dependencies_sequence(dependencies, field)
Expand Down
8 changes: 4 additions & 4 deletions docs/validation-rules.rst
Original file line number Diff line number Diff line change
Expand Up @@ -355,10 +355,10 @@ Validates if *none* of the provided constraints validates the field. See `\*of-r

nullable
--------
If ``True`` the field value can be set to :obj:`None`. It is essentially the
functionality of the :attr:`~cerberus.Validator.ignore_none_values` property
of a :class:`~cerberus.Validator` instance, but allowing for more fine grained
control down to the field level.
If ``True`` the field value is allowed to be :obj:`None`. The rule will be
checked on every field, regardless it's defined or not. The rule's constraint
defaults to the :attr:`~cerberus.Validator.ignore_none_values` property of a
:class:`~cerberus.Validator` instance if not defined in the schema.

.. doctest::

Expand Down

0 comments on commit 1cbaeff

Please sign in to comment.