From 8c9edd5a2c37d9e80446e8ada0a99c59206348af Mon Sep 17 00:00:00 2001 From: Julian Berman Date: Mon, 14 Jan 2019 09:09:41 -0500 Subject: Split out dependencies for draft 3. Draft 3 allowed simple string dependencies, but no later draft does. This also lets us use the same fix for boolean schema nonsense as we just did for items. --- jsonschema/_legacy_validators.py | 25 +++++++++++++++++++++++++ jsonschema/_validators.py | 20 ++++++-------------- jsonschema/tests/test_validators.py | 28 ++++++++++++++++++++++++++-- jsonschema/validators.py | 2 +- 4 files changed, 58 insertions(+), 17 deletions(-) diff --git a/jsonschema/_legacy_validators.py b/jsonschema/_legacy_validators.py index 4e01727..f439714 100644 --- a/jsonschema/_legacy_validators.py +++ b/jsonschema/_legacy_validators.py @@ -47,6 +47,31 @@ def oneOf_draft4(validator, oneOf, instance, schema): ) +def dependencies_draft3(validator, dependencies, instance, schema): + if not validator.is_type(instance, "object"): + return + + for property, dependency in iteritems(dependencies): + if property not in instance: + continue + + if validator.is_type(dependency, "object"): + for error in validator.descend( + instance, dependency, schema_path=property, + ): + yield error + elif validator.is_type(dependency, "string"): + if dependency not in instance: + yield ValidationError( + "%r is a dependency of %r" % (dependency, property) + ) + else: + for each in dependency: + if each not in instance: + message = "%r is a dependency of %r" + yield ValidationError(message % (each, property)) + + def disallow_draft3(validator, disallow, instance, schema): for disallowed in _utils.ensure_list(disallow): if validator.is_valid(instance, {"type": [disallowed]}): diff --git a/jsonschema/_validators.py b/jsonschema/_validators.py index bb91643..8837d39 100644 --- a/jsonschema/_validators.py +++ b/jsonschema/_validators.py @@ -220,24 +220,16 @@ def dependencies(validator, dependencies, instance, schema): if property not in instance: continue - # FIXME - if dependency is True: - dependency = {} - elif dependency is False: - dependency = {"not": {}} - - if validator.is_type(dependency, "object"): + if validator.is_type(dependency, "array"): + for each in dependency: + if each not in instance: + message = "%r is a dependency of %r" + yield ValidationError(message % (each, property)) + else: for error in validator.descend( instance, dependency, schema_path=property, ): yield error - else: - dependencies = _utils.ensure_list(dependency) - for dependency in dependencies: - if dependency not in instance: - yield ValidationError( - "%r is a dependency of %r" % (dependency, property) - ) def enum(validator, enums, instance, schema): diff --git a/jsonschema/tests/test_validators.py b/jsonschema/tests/test_validators.py index eff7aeb..5bbcc02 100644 --- a/jsonschema/tests/test_validators.py +++ b/jsonschema/tests/test_validators.py @@ -373,10 +373,34 @@ class TestValidationErrorMessages(TestCase): message = self.message_for(instance=1, schema={"maximum": 0}) self.assertEqual(message, "1 is greater than the maximum of 0") - def test_dependencies_failure_has_single_element_not_list(self): + def test_dependencies_single_element(self): depend, on = "bar", "foo" schema = {u"dependencies": {depend: on}} - message = self.message_for(instance={"bar": 2}, schema=schema) + message = self.message_for( + instance={"bar": 2}, + schema=schema, + cls=validators.Draft3Validator, + ) + self.assertEqual(message, "%r is a dependency of %r" % (on, depend)) + + def test_dependencies_list_draft3(self): + depend, on = "bar", "foo" + schema = {u"dependencies": {depend: [on]}} + message = self.message_for( + instance={"bar": 2}, + schema=schema, + cls=validators.Draft3Validator, + ) + self.assertEqual(message, "%r is a dependency of %r" % (on, depend)) + + def test_dependencies_list_draft7(self): + depend, on = "bar", "foo" + schema = {u"dependencies": {depend: [on]}} + message = self.message_for( + instance={"bar": 2}, + schema=schema, + cls=validators.Draft7Validator, + ) self.assertEqual(message, "%r is a dependency of %r" % (on, depend)) def test_additionalItems_single_failure(self): diff --git a/jsonschema/validators.py b/jsonschema/validators.py index d0a2da9..b70a1d5 100644 --- a/jsonschema/validators.py +++ b/jsonschema/validators.py @@ -409,7 +409,7 @@ Draft3Validator = create( u"$ref": _validators.ref, u"additionalItems": _validators.additionalItems, u"additionalProperties": _validators.additionalProperties, - u"dependencies": _validators.dependencies, + u"dependencies": _legacy_validators.dependencies_draft3, u"disallow": _legacy_validators.disallow_draft3, u"divisibleBy": _validators.multipleOf, u"enum": _validators.enum, -- cgit v1.2.1