From 3c48ef9e1e7bcb0211e58d35d2fc46bda0feca22 Mon Sep 17 00:00:00 2001 From: Julien Danjou Date: Thu, 5 Jul 2018 17:37:31 +0200 Subject: [PATCH] Include path in AnyInvalid errors Fixes #347 --- voluptuous/tests/tests.py | 47 +++++++++++++++++++++++++++++++++++++++ voluptuous/validators.py | 8 ++++--- 2 files changed, 52 insertions(+), 3 deletions(-) diff --git a/voluptuous/tests/tests.py b/voluptuous/tests/tests.py index 2b1ab92..3d195ac 100644 --- a/voluptuous/tests/tests.py +++ b/voluptuous/tests/tests.py @@ -1085,6 +1085,53 @@ def test_self_validation(): schema({"follow": {"follow": {"number": 123456}}}) +def test_any_error_has_path(): + """https://github.com/alecthomas/voluptuous/issues/347""" + s = Schema({ + Optional('q'): int, + Required('q2'): Any(int, msg='toto') + }) + try: + s({'q': 'str', 'q2': 'tata'}) + except MultipleInvalid as exc: + assert ( + (exc.errors[0].path == ['q'] and exc.errors[1].path == ['q2']) or + (exc.errors[1].path == ['q'] and exc.errors[0].path == ['q2']) + ) + else: + assert False, "Did not raise AnyInvalid" + + +def test_all_error_has_path(): + """https://github.com/alecthomas/voluptuous/issues/347""" + s = Schema({ + Optional('q'): int, + Required('q2'): All([str, Length(min=10)], msg='toto'), + }) + try: + s({'q': 'str', 'q2': 12}) + except MultipleInvalid as exc: + assert ( + (exc.errors[0].path == ['q'] and exc.errors[1].path == ['q2']) or + (exc.errors[1].path == ['q'] and exc.errors[0].path == ['q2']) + ) + else: + assert False, "Did not raise AllInvalid" + + +def test_match_error_has_path(): + """https://github.com/alecthomas/voluptuous/issues/347""" + s = Schema({ + Required('q2'): Match("a"), + }) + try: + s({'q2': 12}) + except MultipleInvalid as exc: + assert exc.errors[0].path == ['q2'] + else: + assert False, "Did not raise MatchInvalid" + + def test_self_any(): schema = Schema({"number": int, "follow": Any(Self, "stop")}) diff --git a/voluptuous/validators.py b/voluptuous/validators.py index e39461c..687d83b 100644 --- a/voluptuous/validators.py +++ b/voluptuous/validators.py @@ -252,8 +252,10 @@ def _exec(self, funcs, v, path=None): error = e else: if error: - raise error if self.msg is None else AnyInvalid(self.msg) - raise AnyInvalid(self.msg or 'no valid value found') + raise error if self.msg is None else AnyInvalid( + self.msg, path=path) + raise AnyInvalid(self.msg or 'no valid value found', + path=path) # Convenience alias @@ -281,7 +283,7 @@ def _exec(self, funcs, v, path=None): else: v = func(path, v) except Invalid as e: - raise e if self.msg is None else AllInvalid(self.msg) + raise e if self.msg is None else AllInvalid(self.msg, path=path) return v