diff --git a/pipenv/vendor/cerberus/benchmarks/__init__.py b/pipenv/vendor/cerberus/benchmarks/__init__.py deleted file mode 100644 index 7cdc925f..00000000 --- a/pipenv/vendor/cerberus/benchmarks/__init__.py +++ /dev/null @@ -1,4 +0,0 @@ -from pathlib import Path - - -DOCUMENTS_PATH = Path(__file__).parent / "documents" diff --git a/pipenv/vendor/cerberus/benchmarks/test_overall_performance_1.py b/pipenv/vendor/cerberus/benchmarks/test_overall_performance_1.py deleted file mode 100644 index 1f9eeb1d..00000000 --- a/pipenv/vendor/cerberus/benchmarks/test_overall_performance_1.py +++ /dev/null @@ -1,212 +0,0 @@ -""" -some notes regarding this test suite: -- results are only comparable using the semantically equal schema against and - identical set of documents in the same execution environment -- the module can be executed to generate a new set of test documents -- it is intended to detect *significant* changes in validation time -- benchmarks should run with as few other processes running on the system as - possible (e.g. an Alpine Linux on bare metal w/o a Desktop environment) -""" - -import json -from collections import Counter -from pathlib import Path -from random import choice, randrange -from typing import Callable, List - -from pytest import mark - -from pipenv.vendor.cerberus import rules_set_registry, schema_registry, TypeDefinition, Validator -from pipenv.vendor.cerberus.benchmarks import DOCUMENTS_PATH - - -rules_set_registry.add("path_rules", {"coerce": Path, "type": "path"}) - - -schema_registry.add( - "field_3_schema", - { - # an outer rule requires all fields' values to be a list - "field_31": {"contains": 0, "empty": False}, - "field_32": { - "default": [None, None, None], - "items": [ - {"type": "integer"}, - {"type": "string"}, - {"type": ["integer", "string"]}, - ], - "schema": {"nullable": True}, - }, - }, -) - - -def schema_1_field_3_allow_unknown_check_with(field, value, error): - if len(value) > 9: - error(field, "Requires a smaller list.") - - -schema_1 = { - "field_1": { - "type": "dict", - "required": True, - "allow_unknown": True, - "keysrules": {"regex": r"field_1[12345]"}, - "minlength": 3, - "maxlength": 5, - "schema": { - "field_11": { - "type": "integer", - "allowed": list(range(100)), - "dependencies": {"field_12": 0, "^field_1.field_13": 0}, - }, - "field_12": { - "type": "integer", - "default_setter": lambda _: 1, - "forbidden": (1,), - }, - "field_13": {"type": "integer"}, - "field_14": {"rename": "field_13"}, - }, - }, - "field_2": { - "type": "dict", - "allow_unknown": False, - "schema": { - "field_21": { - "type": "integer", - "coerce": [str.strip, int], - "min": 9, - "max": 89, - "anyof": [{"dependencies": "field_22"}, {"dependencies": "field_23"}], - }, - "field_22": {"excludes": "field_23", "nullable": True}, - "field_23": {"nullable": True}, - }, - }, - "field_3": { - "allow_unknown": {"check_with": schema_1_field_3_allow_unknown_check_with}, - "valuesrules": {"type": "list"}, - "require_all": True, - "schema": "field_3_schema", - }, - "field_4": "path_rules", -} - - -def init_validator(): - class TestValidator(Validator): - types_mapping = { - **Validator.types_mapping, - "path": TypeDefinition("path", (Path,), ()), - } - - return TestValidator(schema_1, purge_unknown=True) - - -def load_documents(): - with (DOCUMENTS_PATH / "overall_documents_1.json").open() as f: - documents = json.load(f) - return documents - - -def validate_documents(init_validator: Callable, documents: List[dict]): - doc_count = failed_count = 0 - error_paths = Counter() - validator = init_validator() - - def count_errors(errors): - if errors is None: - return - for error in errors: - if error.is_group_error: - count_errors(error.child_errors) - else: - error_paths[error.schema_path] += 1 - - for document in documents: - if validator.validated(document) is None: - failed_count += 1 - count_errors(validator._errors) - doc_count += 1 - - print( - f"{failed_count} out of {doc_count} documents failed with " - f"{len(error_paths)} different error leafs." - ) - print("Top 3 errors, excluding container errors:") - for path, count in error_paths.most_common(3): - print(f"{count}: {path}") - - -@mark.benchmark(group="overall-1") -def test_overall_performance_1(benchmark): - benchmark.pedantic(validate_documents, (init_validator, load_documents()), rounds=5) - - -# - - -def generate_sample_document_1() -> dict: - result = {} - for i in (1, 2, 3, 4, 5): - if randrange(100): - result[f"field_{i}"] = globals()[f"generate_document_1_field_{i}"]() - return result - - -def generate_document_1_field_1() -> dict: - result = {"field_11": randrange(100), "field_13": 0} - if randrange(100): - result["field_12"] = 0 - if not randrange(100): - result["field_14"] = None - if randrange(100): - result["field_15"] = None - return result - - -def generate_document_1_field_2() -> dict: - x = "*" if not randrange(50) else " " - result = {"field_21": x + str(randrange(100)) + x} - - if randrange(100): - result["field_22"] = None - if "field_22" in result and not randrange(100): - result["field_23"] = None - - return result - - -def generate_document_1_field_3() -> dict: - result = {} - if randrange(100): - result["field_31"] = [randrange(2) for _ in range(randrange(20))] - else: - result["field_31"] = None - if randrange(100): - result["field_32"] = [ - choice((0, 0, 0, 0, 0, 0, 0, 0, "", None)), - choice(("", "", "", "", "", "", "", "", 0, None)), - choice((0, 0, 0, 0, "", "", "", "", None)), - ] - if not randrange(10): - result["3_unknown"] = [0] * (randrange(10) + 1) - return result - - -def generate_document_1_field_4(): - return "/foo/bar" if randrange(100) else 0 - - -def generate_document_1_field_5(): - return None - - -def write_sample_documents(): - with (DOCUMENTS_PATH / "overall_documents_1.json").open("wt") as f: - json.dump([generate_sample_document_1() for _ in range(10_000)], f) - - -if __name__ == "__main__": - write_sample_documents() diff --git a/pipenv/vendor/cerberus/benchmarks/test_overall_performance_2.py b/pipenv/vendor/cerberus/benchmarks/test_overall_performance_2.py deleted file mode 100644 index 227f81aa..00000000 --- a/pipenv/vendor/cerberus/benchmarks/test_overall_performance_2.py +++ /dev/null @@ -1,54 +0,0 @@ -import json -from collections import Counter -from typing import Callable, List -from typing import Counter as CounterType - -from pytest import mark - -from pipenv.vendor.cerberus import Validator -from pipenv.vendor.cerberus.benchmarks.schemas.overalll_schema_2 import product_schema -from pipenv.vendor.cerberus.benchmarks import DOCUMENTS_PATH - - -def init_validator(): - return Validator(product_schema, purge_unknown=True) - - -def load_documents(): - with (DOCUMENTS_PATH / "overall_documents_2.json").open() as f: - documents = json.load(f) - return documents - - -def validate_documents(init_validator: Callable, documents: List[dict]) -> None: - doc_count = failed_count = 0 - error_paths: CounterType[tuple] = Counter() - validator = init_validator() - - def count_errors(errors): - if errors is None: - return - for error in errors: - if error.is_group_error: - count_errors(error.child_errors) - else: - error_paths[error.schema_path] += 1 - - for document in documents: - if validator.validated(document) is None: - failed_count += 1 - count_errors(validator._errors) - doc_count += 1 - - print( - f"{failed_count} out of {doc_count} documents failed with " - f"{len(error_paths)} different error leafs." - ) - print("Top 3 errors, excluding container errors:") - for path, count in error_paths.most_common(3): - print(f"{count}: {path}") - - -@mark.benchmark(group="overall-2") -def test_overall_performance_2(benchmark): - benchmark.pedantic(validate_documents, (init_validator, load_documents()), rounds=5) diff --git a/pipenv/vendor/cerberus/tests/__init__.py b/pipenv/vendor/cerberus/tests/__init__.py deleted file mode 100644 index b5e66e06..00000000 --- a/pipenv/vendor/cerberus/tests/__init__.py +++ /dev/null @@ -1,159 +0,0 @@ -# -*- coding: utf-8 -*- - -import re - -import pytest - -from pipenv.vendor.cerberus import errors, Validator, SchemaError, DocumentError -from pipenv.vendor.cerberus.tests.conftest import sample_schema - - -def assert_exception(exception, document={}, schema=None, validator=None, msg=None): - """ - Tests whether a specific exception is raised. Optionally also tests whether the - exception message is as expected. - """ - if validator is None: - validator = Validator() - if msg is None: - with pytest.raises(exception): - validator(document, schema) - else: - with pytest.raises(exception, match=re.escape(msg)): - validator(document, schema) - - -def assert_schema_error(*args): - """Tests whether a validation raises an exception due to a malformed schema.""" - assert_exception(SchemaError, *args) - - -def assert_document_error(*args): - """Tests whether a validation raises an exception due to a malformed document.""" - assert_exception(DocumentError, *args) - - -def assert_fail( - document, - schema=None, - validator=None, - update=False, - error=None, - errors=None, - child_errors=None, -): - """Tests whether a validation fails.""" - if validator is None: - validator = Validator(sample_schema) - result = validator(document, schema, update) - assert isinstance(result, bool) - assert not result - - actual_errors = validator._errors - - assert not (error is not None and errors is not None) - assert not (errors is not None and child_errors is not None), ( - 'child_errors can only be tested in ' 'conjunction with the error parameter' - ) - assert not (child_errors is not None and error is None) - if error is not None: - assert len(actual_errors) == 1 - assert_has_error(actual_errors, *error) - - if child_errors is not None: - assert len(actual_errors[0].child_errors) == len(child_errors) - assert_has_errors(actual_errors[0].child_errors, child_errors) - - elif errors is not None: - assert len(actual_errors) == len(errors) - assert_has_errors(actual_errors, errors) - - return actual_errors - - -def assert_success(document, schema=None, validator=None, update=False): - """Tests whether a validation succeeds.""" - if validator is None: - validator = Validator(sample_schema) - result = validator(document, schema, update) - assert isinstance(result, bool) - if not result: - raise AssertionError(validator.errors) - - -def assert_has_error(_errors, d_path, s_path, error_def, constraint, info=()): - if not isinstance(d_path, tuple): - d_path = (d_path,) - if not isinstance(info, tuple): - info = (info,) - - assert isinstance(_errors, errors.ErrorList) - - for i, error in enumerate(_errors): - assert isinstance(error, errors.ValidationError) - try: - assert error.document_path == d_path - assert error.schema_path == s_path - assert error.code == error_def.code - assert error.rule == error_def.rule - assert error.constraint == constraint - if not error.is_group_error: - assert error.info == info - except AssertionError: - pass - except Exception: - raise - else: - break - else: - raise AssertionError( - """ - Error with properties: - document_path={doc_path} - schema_path={schema_path} - code={code} - constraint={constraint} - info={info} - not found in errors: - {errors} - """.format( - doc_path=d_path, - schema_path=s_path, - code=hex(error.code), - info=info, - constraint=constraint, - errors=_errors, - ) - ) - return i - - -def assert_has_errors(_errors, _exp_errors): - assert isinstance(_exp_errors, list) - for error in _exp_errors: - assert isinstance(error, tuple) - assert_has_error(_errors, *error) - - -def assert_not_has_error(_errors, *args, **kwargs): - try: - assert_has_error(_errors, *args, **kwargs) - except AssertionError: - pass - except Exception as e: - raise e - else: - raise AssertionError('An unexpected error occurred.') - - -def assert_bad_type(field, data_type, value): - assert_fail( - {field: value}, error=(field, (field, 'type'), errors.BAD_TYPE, data_type) - ) - - -def assert_normalized(document, expected, schema=None, validator=None): - if validator is None: - validator = Validator(sample_schema) - assert_success(document, schema, validator) - assert validator.document == expected diff --git a/pipenv/vendor/cerberus/tests/conftest.py b/pipenv/vendor/cerberus/tests/conftest.py deleted file mode 100644 index 6c701060..00000000 --- a/pipenv/vendor/cerberus/tests/conftest.py +++ /dev/null @@ -1,81 +0,0 @@ -# -*- coding: utf-8 -*- - -from copy import deepcopy - -import pytest - -from pipenv.vendor.cerberus import Validator - - -@pytest.fixture -def document(): - return deepcopy(sample_document) - - -@pytest.fixture -def schema(): - return deepcopy(sample_schema) - - -@pytest.fixture -def validator(): - return Validator(sample_schema) - - -sample_schema = { - 'a_string': {'type': 'string', 'minlength': 2, 'maxlength': 10}, - 'a_binary': {'type': 'binary', 'minlength': 2, 'maxlength': 10}, - 'a_nullable_integer': {'type': 'integer', 'nullable': True}, - 'an_integer': {'type': 'integer', 'min': 1, 'max': 100}, - 'a_restricted_integer': {'type': 'integer', 'allowed': [-1, 0, 1]}, - 'a_boolean': {'type': 'boolean', 'meta': 'can haz two distinct states'}, - 'a_datetime': {'type': 'datetime', 'meta': {'format': '%a, %d. %b %Y'}}, - 'a_float': {'type': 'float', 'min': 1, 'max': 100}, - 'a_number': {'type': 'number', 'min': 1, 'max': 100}, - 'a_set': {'type': 'set'}, - 'one_or_more_strings': {'type': ['string', 'list'], 'schema': {'type': 'string'}}, - 'a_regex_email': { - 'type': 'string', - 'regex': r'^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$', - }, - 'a_readonly_string': {'type': 'string', 'readonly': True}, - 'a_restricted_string': {'type': 'string', 'allowed': ['agent', 'client', 'vendor']}, - 'an_array': {'type': 'list', 'allowed': ['agent', 'client', 'vendor']}, - 'an_array_from_set': { - 'type': 'list', - 'allowed': set(['agent', 'client', 'vendor']), - }, - 'a_list_of_dicts': { - 'type': 'list', - 'schema': { - 'type': 'dict', - 'schema': { - 'sku': {'type': 'string'}, - 'price': {'type': 'integer', 'required': True}, - }, - }, - }, - 'a_list_of_values': { - 'type': 'list', - 'items': [{'type': 'string'}, {'type': 'integer'}], - }, - 'a_list_of_integers': {'type': 'list', 'schema': {'type': 'integer'}}, - 'a_dict': { - 'type': 'dict', - 'schema': { - 'address': {'type': 'string'}, - 'city': {'type': 'string', 'required': True}, - }, - }, - 'a_dict_with_valuesrules': {'type': 'dict', 'valuesrules': {'type': 'integer'}}, - 'a_list_length': { - 'type': 'list', - 'schema': {'type': 'integer'}, - 'minlength': 2, - 'maxlength': 5, - }, - 'a_nullable_field_without_type': {'nullable': True}, - 'a_not_nullable_field_without_type': {}, -} - -sample_document = {'name': 'john doe'} diff --git a/pipenv/vendor/cerberus/tests/test_assorted.py b/pipenv/vendor/cerberus/tests/test_assorted.py deleted file mode 100644 index 8f049ea5..00000000 --- a/pipenv/vendor/cerberus/tests/test_assorted.py +++ /dev/null @@ -1,111 +0,0 @@ -# -*- coding: utf-8 -*- - -from decimal import Decimal -from pipenv.patched.pip._vendor.pkg_resources import Distribution, DistributionNotFound - -from pytest import mark - -from pipenv.vendor.cerberus import TypeDefinition, Validator -from pipenv.vendor.cerberus.tests import assert_fail, assert_success -from pipenv.vendor.cerberus.utils import validator_factory -from pipenv.vendor.cerberus.validator import BareValidator -from pipenv.vendor.cerberus.platform import PYTHON_VERSION - - -if PYTHON_VERSION > 3 and PYTHON_VERSION < 3.4: - from imp import reload -elif PYTHON_VERSION >= 3.4: - from importlib import reload -else: - pass # Python 2.x - - -def test_pkgresources_version(monkeypatch): - def create_fake_distribution(name): - return Distribution(project_name="cerberus", version="1.2.3") - - with monkeypatch.context() as m: - cerberus = __import__("cerberus") - m.setattr("pkg_resources.get_distribution", create_fake_distribution) - reload(cerberus) - assert cerberus.__version__ == "1.2.3" - - -def test_version_not_found(monkeypatch): - def raise_distribution_not_found(name): - raise DistributionNotFound("pkg_resources cannot get distribution") - - with monkeypatch.context() as m: - cerberus = __import__("cerberus") - m.setattr("pkg_resources.get_distribution", raise_distribution_not_found) - reload(cerberus) - assert cerberus.__version__ == "unknown" - - -def test_clear_cache(validator): - assert len(validator._valid_schemas) > 0 - validator.clear_caches() - assert len(validator._valid_schemas) == 0 - - -def test_docstring(validator): - assert validator.__doc__ - - -# Test that testing with the sample schema works as expected -# as there might be rules with side-effects in it - - -@mark.parametrize( - "test,document", - ((assert_fail, {"an_integer": 60}), (assert_success, {"an_integer": 110})), -) -def test_that_test_fails(test, document): - try: - test(document) - except AssertionError: - pass - else: - raise AssertionError("test didn't fail") - - -def test_dynamic_types(): - decimal_type = TypeDefinition("decimal", (Decimal,), ()) - document = {"measurement": Decimal(0)} - schema = {"measurement": {"type": "decimal"}} - - validator = Validator() - validator.types_mapping["decimal"] = decimal_type - assert_success(document, schema, validator) - - class MyValidator(Validator): - types_mapping = Validator.types_mapping.copy() - types_mapping["decimal"] = decimal_type - - validator = MyValidator() - assert_success(document, schema, validator) - - -def test_mro(): - assert Validator.__mro__ == (Validator, BareValidator, object), Validator.__mro__ - - -def test_mixin_init(): - class Mixin(object): - def __init__(self, *args, **kwargs): - kwargs["test"] = True - super(Mixin, self).__init__(*args, **kwargs) - - MyValidator = validator_factory("MyValidator", Mixin) - validator = MyValidator() - assert validator._config["test"] - - -def test_sub_init(): - class MyValidator(Validator): - def __init__(self, *args, **kwargs): - kwargs["test"] = True - super(MyValidator, self).__init__(*args, **kwargs) - - validator = MyValidator() - assert validator._config["test"] diff --git a/pipenv/vendor/cerberus/tests/test_customization.py b/pipenv/vendor/cerberus/tests/test_customization.py deleted file mode 100644 index 4dcb8dd0..00000000 --- a/pipenv/vendor/cerberus/tests/test_customization.py +++ /dev/null @@ -1,101 +0,0 @@ -# -*- coding: utf-8 -*- - -from pytest import mark - -import pipenv.vendor.cerberus as cerberus -from pipenv.vendor.cerberus.tests import assert_fail, assert_success -from pipenv.vendor.cerberus.tests.conftest import sample_schema - - -def test_contextual_data_preservation(): - class InheritedValidator(cerberus.Validator): - def __init__(self, *args, **kwargs): - if 'working_dir' in kwargs: - self.working_dir = kwargs['working_dir'] - super(InheritedValidator, self).__init__(*args, **kwargs) - - def _validate_type_test(self, value): - if self.working_dir: - return True - - assert 'test' in InheritedValidator.types - v = InheritedValidator( - {'test': {'type': 'list', 'schema': {'type': 'test'}}}, working_dir='/tmp' - ) - assert_success({'test': ['foo']}, validator=v) - - -def test_docstring_parsing(): - class CustomValidator(cerberus.Validator): - def _validate_foo(self, argument, field, value): - """{'type': 'zap'}""" - pass - - def _validate_bar(self, value): - """ - Test the barreness of a value. - - The rule's arguments are validated against this schema: - {'type': 'boolean'} - """ - pass - - assert 'foo' in CustomValidator.validation_rules - assert 'bar' in CustomValidator.validation_rules - - -# TODO remove 'validator' as rule parameter with the next major release -@mark.parametrize('rule', ('check_with', 'validator')) -def test_check_with_method(rule): - # https://github.com/pyeve/cerberus/issues/265 - class MyValidator(cerberus.Validator): - def _check_with_oddity(self, field, value): - if not value & 1: - self._error(field, "Must be an odd number") - - v = MyValidator(schema={'amount': {rule: 'oddity'}}) - assert_success(document={'amount': 1}, validator=v) - assert_fail( - document={'amount': 2}, - validator=v, - error=('amount', (), cerberus.errors.CUSTOM, None, ('Must be an odd number',)), - ) - - -# TODO remove test with the next major release -@mark.parametrize('rule', ('check_with', 'validator')) -def test_validator_method(rule): - class MyValidator(cerberus.Validator): - def _validator_oddity(self, field, value): - if not value & 1: - self._error(field, "Must be an odd number") - - v = MyValidator(schema={'amount': {rule: 'oddity'}}) - assert_success(document={'amount': 1}, validator=v) - assert_fail( - document={'amount': 2}, - validator=v, - error=('amount', (), cerberus.errors.CUSTOM, None, ('Must be an odd number',)), - ) - - -def test_schema_validation_can_be_disabled_in_schema_setter(): - class NonvalidatingValidator(cerberus.Validator): - """ - Skips schema validation to speed up initialization - """ - - @cerberus.Validator.schema.setter - def schema(self, schema): - if schema is None: - self._schema = None - elif self.is_child: - self._schema = schema - elif isinstance(schema, cerberus.schema.DefinitionSchema): - self._schema = schema - else: - self._schema = cerberus.schema.UnvalidatedSchema(schema) - - v = NonvalidatingValidator(schema=sample_schema) - assert v.validate(document={'an_integer': 1}) - assert not v.validate(document={'an_integer': 'a'}) diff --git a/pipenv/vendor/cerberus/tests/test_errors.py b/pipenv/vendor/cerberus/tests/test_errors.py deleted file mode 100644 index 6d8ffd6c..00000000 --- a/pipenv/vendor/cerberus/tests/test_errors.py +++ /dev/null @@ -1,365 +0,0 @@ -# -*- coding: utf-8 -*- - -from pipenv.vendor.cerberus import Validator, errors -from pipenv.vendor.cerberus.tests import assert_fail - - -ValidationError = errors.ValidationError - - -def test__error_1(): - v = Validator(schema={'foo': {'type': 'string'}}) - v.document = {'foo': 42} - v._error('foo', errors.BAD_TYPE, 'string') - error = v._errors[0] - assert error.document_path == ('foo',) - assert error.schema_path == ('foo', 'type') - assert error.code == 0x24 - assert error.rule == 'type' - assert error.constraint == 'string' - assert error.value == 42 - assert error.info == ('string',) - assert not error.is_group_error - assert not error.is_logic_error - - -def test__error_2(): - v = Validator(schema={'foo': {'keysrules': {'type': 'integer'}}}) - v.document = {'foo': {'0': 'bar'}} - v._error('foo', errors.KEYSRULES, ()) - error = v._errors[0] - assert error.document_path == ('foo',) - assert error.schema_path == ('foo', 'keysrules') - assert error.code == 0x83 - assert error.rule == 'keysrules' - assert error.constraint == {'type': 'integer'} - assert error.value == {'0': 'bar'} - assert error.info == ((),) - assert error.is_group_error - assert not error.is_logic_error - - -def test__error_3(): - valids = [ - {'type': 'string', 'regex': '0x[0-9a-f]{2}'}, - {'type': 'integer', 'min': 0, 'max': 255}, - ] - v = Validator(schema={'foo': {'oneof': valids}}) - v.document = {'foo': '0x100'} - v._error('foo', errors.ONEOF, (), 0, 2) - error = v._errors[0] - assert error.document_path == ('foo',) - assert error.schema_path == ('foo', 'oneof') - assert error.code == 0x92 - assert error.rule == 'oneof' - assert error.constraint == valids - assert error.value == '0x100' - assert error.info == ((), 0, 2) - assert error.is_group_error - assert error.is_logic_error - - -def test_error_tree_from_subschema(validator): - schema = {'foo': {'schema': {'bar': {'type': 'string'}}}} - document = {'foo': {'bar': 0}} - assert_fail(document, schema, validator=validator) - d_error_tree = validator.document_error_tree - s_error_tree = validator.schema_error_tree - - assert 'foo' in d_error_tree - - assert len(d_error_tree['foo'].errors) == 1, d_error_tree['foo'] - assert d_error_tree['foo'].errors[0].code == errors.MAPPING_SCHEMA.code - assert 'bar' in d_error_tree['foo'] - assert d_error_tree['foo']['bar'].errors[0].value == 0 - assert d_error_tree.fetch_errors_from(('foo', 'bar'))[0].value == 0 - - assert 'foo' in s_error_tree - assert 'schema' in s_error_tree['foo'] - assert 'bar' in s_error_tree['foo']['schema'] - assert 'type' in s_error_tree['foo']['schema']['bar'] - assert s_error_tree['foo']['schema']['bar']['type'].errors[0].value == 0 - assert ( - s_error_tree.fetch_errors_from(('foo', 'schema', 'bar', 'type'))[0].value == 0 - ) - - -def test_error_tree_from_anyof(validator): - schema = {'foo': {'anyof': [{'type': 'string'}, {'type': 'integer'}]}} - document = {'foo': []} - assert_fail(document, schema, validator=validator) - d_error_tree = validator.document_error_tree - s_error_tree = validator.schema_error_tree - assert 'foo' in d_error_tree - assert d_error_tree['foo'].errors[0].value == [] - assert 'foo' in s_error_tree - assert 'anyof' in s_error_tree['foo'] - assert 0 in s_error_tree['foo']['anyof'] - assert 1 in s_error_tree['foo']['anyof'] - assert 'type' in s_error_tree['foo']['anyof'][0] - assert s_error_tree['foo']['anyof'][0]['type'].errors[0].value == [] - - -def test_nested_error_paths(validator): - # interpreters of the same version on some platforms showed different sort results - # over various runs: - def assert_has_all_errors(errors, *ref_errs): - for ref_err in ref_errs: - for error in errors: - if error == ref_err: - break - else: - raise AssertionError - - schema = { - 'a_dict': { - 'keysrules': {'type': 'integer'}, - 'valuesrules': {'regex': '[a-z]*'}, - }, - 'a_list': {'schema': {'type': 'string', 'oneof_regex': ['[a-z]*$', '[A-Z]*']}}, - } - document = { - 'a_dict': {0: 'abc', 'one': 'abc', 2: 'aBc', 'three': 'abC'}, - 'a_list': [0, 'abc', 'abC'], - } - assert_fail(document, schema, validator=validator) - - det = validator.document_error_tree - set = validator.schema_error_tree - - assert len(det.errors) == 0 - assert len(set.errors) == 0 - - assert len(det['a_dict'].errors) == 2 - assert len(set['a_dict'].errors) == 0 - - assert det['a_dict'][0] is None - assert len(det['a_dict']['one'].errors) == 1 - assert len(det['a_dict'][2].errors) == 1 - assert len(det['a_dict']['three'].errors) == 2 - - assert len(set['a_dict']['keysrules'].errors) == 1 - assert len(set['a_dict']['valuesrules'].errors) == 1 - - assert len(set['a_dict']['keysrules']['type'].errors) == 2 - assert len(set['a_dict']['valuesrules']['regex'].errors) == 2 - - ref_err1 = ValidationError( - ('a_dict', 'one'), - ('a_dict', 'keysrules', 'type'), - errors.BAD_TYPE.code, - 'type', - 'integer', - 'one', - (), - ) - - ref_err2 = ValidationError( - ('a_dict', 2), - ('a_dict', 'valuesrules', 'regex'), - errors.REGEX_MISMATCH.code, - 'regex', - '[a-z]*$', - 'aBc', - (), - ) - - ref_err3 = ValidationError( - ('a_dict', 'three'), - ('a_dict', 'keysrules', 'type'), - errors.BAD_TYPE.code, - 'type', - 'integer', - 'three', - (), - ) - ref_err4 = ValidationError( - ('a_dict', 'three'), - ('a_dict', 'valuesrules', 'regex'), - errors.REGEX_MISMATCH.code, - 'regex', - '[a-z]*$', - 'abC', - (), - ) - assert det['a_dict'][2].errors[0] == ref_err2 - assert det['a_dict']['one'].errors[0] == ref_err1 - assert_has_all_errors(det['a_dict']['three'].errors, ref_err3, ref_err4) - assert_has_all_errors(set['a_dict']['keysrules']['type'].errors, ref_err1, ref_err3) - assert_has_all_errors( - set['a_dict']['valuesrules']['regex'].errors, ref_err2, ref_err4 - ) - - assert len(det['a_list'].errors) == 1 - assert len(det['a_list'][0].errors) == 1 - assert det['a_list'][1] is None - assert len(det['a_list'][2].errors) == 3 - assert len(set['a_list'].errors) == 0 - assert len(set['a_list']['schema'].errors) == 1 - assert len(set['a_list']['schema']['type'].errors) == 1 - assert len(set['a_list']['schema']['oneof'][0]['regex'].errors) == 1 - assert len(set['a_list']['schema']['oneof'][1]['regex'].errors) == 1 - - ref_err5 = ValidationError( - ('a_list', 0), - ('a_list', 'schema', 'type'), - errors.BAD_TYPE.code, - 'type', - 'string', - 0, - (), - ) - ref_err6 = ValidationError( - ('a_list', 2), - ('a_list', 'schema', 'oneof'), - errors.ONEOF.code, - 'oneof', - 'irrelevant_at_this_point', - 'abC', - (), - ) - ref_err7 = ValidationError( - ('a_list', 2), - ('a_list', 'schema', 'oneof', 0, 'regex'), - errors.REGEX_MISMATCH.code, - 'regex', - '[a-z]*$', - 'abC', - (), - ) - ref_err8 = ValidationError( - ('a_list', 2), - ('a_list', 'schema', 'oneof', 1, 'regex'), - errors.REGEX_MISMATCH.code, - 'regex', - '[a-z]*$', - 'abC', - (), - ) - - assert det['a_list'][0].errors[0] == ref_err5 - assert_has_all_errors(det['a_list'][2].errors, ref_err6, ref_err7, ref_err8) - assert set['a_list']['schema']['oneof'].errors[0] == ref_err6 - assert set['a_list']['schema']['oneof'][0]['regex'].errors[0] == ref_err7 - assert set['a_list']['schema']['oneof'][1]['regex'].errors[0] == ref_err8 - assert set['a_list']['schema']['type'].errors[0] == ref_err5 - - -def test_path_resolution_for_registry_references(): - class CustomValidator(Validator): - def _normalize_coerce_custom(self, value): - raise Exception("Failed coerce") - - validator = CustomValidator() - validator.schema_registry.add( - "schema1", {"child": {"type": "boolean", "coerce": "custom"}} - ) - validator.schema = {"parent": {"schema": "schema1"}} - validator.validate({"parent": {"child": "["}}) - - expected = { - 'parent': [ - { - 'child': [ - "must be of boolean type", - "field 'child' cannot be coerced: Failed coerce", - ] - } - ] - } - assert validator.errors == expected - - -def test_queries(): - schema = {'foo': {'type': 'dict', 'schema': {'bar': {'type': 'number'}}}} - document = {'foo': {'bar': 'zero'}} - validator = Validator(schema) - validator(document) - - assert 'foo' in validator.document_error_tree - assert 'bar' in validator.document_error_tree['foo'] - assert 'foo' in validator.schema_error_tree - assert 'schema' in validator.schema_error_tree['foo'] - - assert errors.MAPPING_SCHEMA in validator.document_error_tree['foo'].errors - assert errors.MAPPING_SCHEMA in validator.document_error_tree['foo'] - assert errors.BAD_TYPE in validator.document_error_tree['foo']['bar'] - assert errors.MAPPING_SCHEMA in validator.schema_error_tree['foo']['schema'] - assert ( - errors.BAD_TYPE in validator.schema_error_tree['foo']['schema']['bar']['type'] - ) - - assert ( - validator.document_error_tree['foo'][errors.MAPPING_SCHEMA].child_errors[0].code - == errors.BAD_TYPE.code - ) - - -def test_basic_error_handler(): - handler = errors.BasicErrorHandler() - _errors, ref = [], {} - - _errors.append(ValidationError(['foo'], ['foo'], 0x63, 'readonly', True, None, ())) - ref.update({'foo': [handler.messages[0x63]]}) - assert handler(_errors) == ref - - _errors.append(ValidationError(['bar'], ['foo'], 0x42, 'min', 1, 2, ())) - ref.update({'bar': [handler.messages[0x42].format(constraint=1)]}) - assert handler(_errors) == ref - - _errors.append( - ValidationError( - ['zap', 'foo'], ['zap', 'schema', 'foo'], 0x24, 'type', 'string', True, () - ) - ) - ref.update({'zap': [{'foo': [handler.messages[0x24].format(constraint='string')]}]}) - assert handler(_errors) == ref - - _errors.append( - ValidationError( - ['zap', 'foo'], - ['zap', 'schema', 'foo'], - 0x41, - 'regex', - '^p[äe]ng$', - 'boom', - (), - ) - ) - ref['zap'][0]['foo'].append(handler.messages[0x41].format(constraint='^p[äe]ng$')) - assert handler(_errors) == ref - - -def test_basic_error_of_errors(validator): - schema = {'foo': {'oneof': [{'type': 'integer'}, {'type': 'string'}]}} - document = {'foo': 23.42} - error = ('foo', ('foo', 'oneof'), errors.ONEOF, schema['foo']['oneof'], ()) - child_errors = [ - (error[0], error[1] + (0, 'type'), errors.BAD_TYPE, 'integer'), - (error[0], error[1] + (1, 'type'), errors.BAD_TYPE, 'string'), - ] - assert_fail( - document, schema, validator=validator, error=error, child_errors=child_errors - ) - assert validator.errors == { - 'foo': [ - errors.BasicErrorHandler.messages[0x92], - { - 'oneof definition 0': ['must be of integer type'], - 'oneof definition 1': ['must be of string type'], - }, - ] - } - - -def test_wrong_amount_of_items(validator): - # https://github.com/pyeve/cerberus/issues/505 - validator.schema = { - 'test_list': { - 'type': 'list', - 'required': True, - 'items': [{'type': 'string'}, {'type': 'string'}], - } - } - validator({'test_list': ['test']}) - assert validator.errors == {'test_list': ["length of list should be 2, it is 1"]} diff --git a/pipenv/vendor/cerberus/tests/test_legacy.py b/pipenv/vendor/cerberus/tests/test_legacy.py deleted file mode 100644 index 59bd7b84..00000000 --- a/pipenv/vendor/cerberus/tests/test_legacy.py +++ /dev/null @@ -1,3 +0,0 @@ -# -*- coding: utf-8 -*- - -pass diff --git a/pipenv/vendor/cerberus/tests/test_normalization.py b/pipenv/vendor/cerberus/tests/test_normalization.py deleted file mode 100644 index 43191504..00000000 --- a/pipenv/vendor/cerberus/tests/test_normalization.py +++ /dev/null @@ -1,543 +0,0 @@ -# -*- coding: utf-8 -*- - -from copy import deepcopy -from tempfile import NamedTemporaryFile - -from pytest import mark - -from pipenv.vendor.cerberus import Validator, errors -from pipenv.vendor.cerberus.tests import ( - assert_fail, - assert_has_error, - assert_normalized, - assert_success, -) - - -def must_not_be_called(*args, **kwargs): - raise RuntimeError('This shall not be called.') - - -def test_coerce(): - schema = {'amount': {'coerce': int}} - document = {'amount': '1'} - expected = {'amount': 1} - assert_normalized(document, expected, schema) - - -def test_coerce_in_dictschema(): - schema = {'thing': {'type': 'dict', 'schema': {'amount': {'coerce': int}}}} - document = {'thing': {'amount': '2'}} - expected = {'thing': {'amount': 2}} - assert_normalized(document, expected, schema) - - -def test_coerce_in_listschema(): - schema = {'things': {'type': 'list', 'schema': {'coerce': int}}} - document = {'things': ['1', '2', '3']} - expected = {'things': [1, 2, 3]} - assert_normalized(document, expected, schema) - - -def test_coerce_in_listitems(): - schema = {'things': {'type': 'list', 'items': [{'coerce': int}, {'coerce': str}]}} - document = {'things': ['1', 2]} - expected = {'things': [1, '2']} - assert_normalized(document, expected, schema) - - validator = Validator(schema) - document['things'].append(3) - assert not validator(document) - assert validator.document['things'] == document['things'] - - -def test_coerce_in_dictschema_in_listschema(): - item_schema = {'type': 'dict', 'schema': {'amount': {'coerce': int}}} - schema = {'things': {'type': 'list', 'schema': item_schema}} - document = {'things': [{'amount': '2'}]} - expected = {'things': [{'amount': 2}]} - assert_normalized(document, expected, schema) - - -def test_coerce_not_destructive(): - schema = {'amount': {'coerce': int}} - v = Validator(schema) - doc = {'amount': '1'} - v.validate(doc) - assert v.document is not doc - - -def test_coerce_catches_ValueError(): - schema = {'amount': {'coerce': int}} - _errors = assert_fail({'amount': 'not_a_number'}, schema) - _errors[0].info = () # ignore exception message here - assert_has_error( - _errors, 'amount', ('amount', 'coerce'), errors.COERCION_FAILED, int - ) - - -def test_coerce_in_listitems_catches_ValueError(): - schema = {'things': {'type': 'list', 'items': [{'coerce': int}, {'coerce': str}]}} - document = {'things': ['not_a_number', 2]} - _errors = assert_fail(document, schema) - _errors[0].info = () # ignore exception message here - assert_has_error( - _errors, - ('things', 0), - ('things', 'items', 'coerce'), - errors.COERCION_FAILED, - int, - ) - - -def test_coerce_catches_TypeError(): - schema = {'name': {'coerce': str.lower}} - _errors = assert_fail({'name': 1234}, schema) - _errors[0].info = () # ignore exception message here - assert_has_error( - _errors, 'name', ('name', 'coerce'), errors.COERCION_FAILED, str.lower - ) - - -def test_coerce_in_listitems_catches_TypeError(): - schema = { - 'things': {'type': 'list', 'items': [{'coerce': int}, {'coerce': str.lower}]} - } - document = {'things': ['1', 2]} - _errors = assert_fail(document, schema) - _errors[0].info = () # ignore exception message here - assert_has_error( - _errors, - ('things', 1), - ('things', 'items', 'coerce'), - errors.COERCION_FAILED, - str.lower, - ) - - -def test_coerce_unknown(): - schema = {'foo': {'schema': {}, 'allow_unknown': {'coerce': int}}} - document = {'foo': {'bar': '0'}} - expected = {'foo': {'bar': 0}} - assert_normalized(document, expected, schema) - - -def test_custom_coerce_and_rename(): - class MyNormalizer(Validator): - def __init__(self, multiplier, *args, **kwargs): - super(MyNormalizer, self).__init__(*args, **kwargs) - self.multiplier = multiplier - - def _normalize_coerce_multiply(self, value): - return value * self.multiplier - - v = MyNormalizer(2, {'foo': {'coerce': 'multiply'}}) - assert v.normalized({'foo': 2})['foo'] == 4 - - v = MyNormalizer(3, allow_unknown={'rename_handler': 'multiply'}) - assert v.normalized({3: None}) == {9: None} - - -def test_coerce_chain(): - drop_prefix = lambda x: x[2:] # noqa: E731 - upper = lambda x: x.upper() # noqa: E731 - schema = {'foo': {'coerce': [hex, drop_prefix, upper]}} - assert_normalized({'foo': 15}, {'foo': 'F'}, schema) - - -def test_coerce_chain_aborts(validator): - def dont_do_me(value): - raise AssertionError('The coercion chain did not abort after an ' 'error.') - - schema = {'foo': {'coerce': [hex, dont_do_me]}} - validator({'foo': '0'}, schema) - assert errors.COERCION_FAILED in validator._errors - - -def test_coerce_non_digit_in_sequence(validator): - # https://github.com/pyeve/cerberus/issues/211 - schema = {'data': {'type': 'list', 'schema': {'type': 'integer', 'coerce': int}}} - document = {'data': ['q']} - assert validator.validated(document, schema) is None - assert ( - validator.validated(document, schema, always_return_document=True) == document - ) # noqa: W503 - - -def test_nullables_dont_fail_coerce(): - schema = {'foo': {'coerce': int, 'nullable': True, 'type': 'integer'}} - document = {'foo': None} - assert_normalized(document, document, schema) - - -def test_nullables_fail_coerce_on_non_null_values(validator): - def failing_coercion(value): - raise Exception("expected to fail") - - schema = {'foo': {'coerce': failing_coercion, 'nullable': True, 'type': 'integer'}} - document = {'foo': None} - assert_normalized(document, document, schema) - - validator({'foo': 2}, schema) - assert errors.COERCION_FAILED in validator._errors - - -def test_normalized(): - schema = {'amount': {'coerce': int}} - document = {'amount': '2'} - expected = {'amount': 2} - assert_normalized(document, expected, schema) - - -def test_rename(validator): - schema = {'foo': {'rename': 'bar'}} - document = {'foo': 0} - expected = {'bar': 0} - # We cannot use assertNormalized here since there is bug where - # Cerberus says that the renamed field is an unknown field: - # {'bar': 'unknown field'} - validator(document, schema, False) - assert validator.document == expected - - -def test_rename_handler(): - validator = Validator(allow_unknown={'rename_handler': int}) - schema = {} - document = {'0': 'foo'} - expected = {0: 'foo'} - assert_normalized(document, expected, schema, validator) - - -def test_purge_unknown(): - validator = Validator(purge_unknown=True) - schema = {'foo': {'type': 'string'}} - document = {'bar': 'foo'} - expected = {} - assert_normalized(document, expected, schema, validator) - - -def test_purge_unknown_in_subschema(): - schema = { - 'foo': { - 'type': 'dict', - 'schema': {'foo': {'type': 'string'}}, - 'purge_unknown': True, - } - } - document = {'foo': {'bar': ''}} - expected = {'foo': {}} - assert_normalized(document, expected, schema) - - -def test_issue_147_complex(): - schema = {'revision': {'coerce': int}} - document = {'revision': '5', 'file': NamedTemporaryFile(mode='w+')} - document['file'].write(r'foobar') - document['file'].seek(0) - normalized = Validator(schema, allow_unknown=True).normalized(document) - assert normalized['revision'] == 5 - assert normalized['file'].read() == 'foobar' - document['file'].close() - normalized['file'].close() - - -def test_issue_147_nested_dict(): - schema = {'thing': {'type': 'dict', 'schema': {'amount': {'coerce': int}}}} - ref_obj = '2' - document = {'thing': {'amount': ref_obj}} - normalized = Validator(schema).normalized(document) - assert document is not normalized - assert normalized['thing']['amount'] == 2 - assert ref_obj == '2' - assert document['thing']['amount'] is ref_obj - - -def test_coerce_in_valuesrules(): - # https://github.com/pyeve/cerberus/issues/155 - schema = { - 'thing': {'type': 'dict', 'valuesrules': {'coerce': int, 'type': 'integer'}} - } - document = {'thing': {'amount': '2'}} - expected = {'thing': {'amount': 2}} - assert_normalized(document, expected, schema) - - -def test_coerce_in_keysrules(): - # https://github.com/pyeve/cerberus/issues/155 - schema = { - 'thing': {'type': 'dict', 'keysrules': {'coerce': int, 'type': 'integer'}} - } - document = {'thing': {'5': 'foo'}} - expected = {'thing': {5: 'foo'}} - assert_normalized(document, expected, schema) - - -def test_coercion_of_sequence_items(validator): - # https://github.com/pyeve/cerberus/issues/161 - schema = {'a_list': {'type': 'list', 'schema': {'type': 'float', 'coerce': float}}} - document = {'a_list': [3, 4, 5]} - expected = {'a_list': [3.0, 4.0, 5.0]} - assert_normalized(document, expected, schema, validator) - for x in validator.document['a_list']: - assert isinstance(x, float) - - -@mark.parametrize( - 'default', ({'default': 'bar_value'}, {'default_setter': lambda doc: 'bar_value'}) -) -def test_default_missing(default): - bar_schema = {'type': 'string'} - bar_schema.update(default) - schema = {'foo': {'type': 'string'}, 'bar': bar_schema} - document = {'foo': 'foo_value'} - expected = {'foo': 'foo_value', 'bar': 'bar_value'} - assert_normalized(document, expected, schema) - - -@mark.parametrize( - 'default', ({'default': 'bar_value'}, {'default_setter': must_not_be_called}) -) -def test_default_existent(default): - bar_schema = {'type': 'string'} - bar_schema.update(default) - schema = {'foo': {'type': 'string'}, 'bar': bar_schema} - document = {'foo': 'foo_value', 'bar': 'non_default'} - assert_normalized(document, document.copy(), schema) - - -@mark.parametrize( - 'default', ({'default': 'bar_value'}, {'default_setter': must_not_be_called}) -) -def test_default_none_nullable(default): - bar_schema = {'type': 'string', 'nullable': True} - bar_schema.update(default) - schema = {'foo': {'type': 'string'}, 'bar': bar_schema} - document = {'foo': 'foo_value', 'bar': None} - assert_normalized(document, document.copy(), schema) - - -@mark.parametrize( - 'default', ({'default': 'bar_value'}, {'default_setter': lambda doc: 'bar_value'}) -) -def test_default_none_nonnullable(default): - bar_schema = {'type': 'string', 'nullable': False} - bar_schema.update(default) - schema = {'foo': {'type': 'string'}, 'bar': bar_schema} - document = {'foo': 'foo_value', 'bar': None} - expected = {'foo': 'foo_value', 'bar': 'bar_value'} - assert_normalized(document, expected, schema) - - -def test_default_none_default_value(): - schema = { - 'foo': {'type': 'string'}, - 'bar': {'type': 'string', 'nullable': True, 'default': None}, - } - document = {'foo': 'foo_value'} - expected = {'foo': 'foo_value', 'bar': None} - assert_normalized(document, expected, schema) - - -@mark.parametrize( - 'default', ({'default': 'bar_value'}, {'default_setter': lambda doc: 'bar_value'}) -) -def test_default_missing_in_subschema(default): - bar_schema = {'type': 'string'} - bar_schema.update(default) - schema = { - 'thing': { - 'type': 'dict', - 'schema': {'foo': {'type': 'string'}, 'bar': bar_schema}, - } - } - document = {'thing': {'foo': 'foo_value'}} - expected = {'thing': {'foo': 'foo_value', 'bar': 'bar_value'}} - assert_normalized(document, expected, schema) - - -def test_depending_default_setters(): - schema = { - 'a': {'type': 'integer'}, - 'b': {'type': 'integer', 'default_setter': lambda d: d['a'] + 1}, - 'c': {'type': 'integer', 'default_setter': lambda d: d['b'] * 2}, - 'd': {'type': 'integer', 'default_setter': lambda d: d['b'] + d['c']}, - } - document = {'a': 1} - expected = {'a': 1, 'b': 2, 'c': 4, 'd': 6} - assert_normalized(document, expected, schema) - - -def test_circular_depending_default_setters(validator): - schema = { - 'a': {'type': 'integer', 'default_setter': lambda d: d['b'] + 1}, - 'b': {'type': 'integer', 'default_setter': lambda d: d['a'] + 1}, - } - validator({}, schema) - assert errors.SETTING_DEFAULT_FAILED in validator._errors - - -def test_issue_250(): - # https://github.com/pyeve/cerberus/issues/250 - schema = { - 'list': { - 'type': 'list', - 'schema': { - 'type': 'dict', - 'allow_unknown': True, - 'schema': {'a': {'type': 'string'}}, - }, - } - } - document = {'list': {'is_a': 'mapping'}} - assert_fail( - document, - schema, - error=('list', ('list', 'type'), errors.BAD_TYPE, schema['list']['type']), - ) - - -def test_issue_250_no_type_pass_on_list(): - # https://github.com/pyeve/cerberus/issues/250 - schema = { - 'list': { - 'schema': { - 'allow_unknown': True, - 'type': 'dict', - 'schema': {'a': {'type': 'string'}}, - } - } - } - document = {'list': [{'a': 'known', 'b': 'unknown'}]} - assert_normalized(document, document, schema) - - -def test_issue_250_no_type_fail_on_dict(): - # https://github.com/pyeve/cerberus/issues/250 - schema = { - 'list': {'schema': {'allow_unknown': True, 'schema': {'a': {'type': 'string'}}}} - } - document = {'list': {'a': {'a': 'known'}}} - assert_fail( - document, - schema, - error=( - 'list', - ('list', 'schema'), - errors.BAD_TYPE_FOR_SCHEMA, - schema['list']['schema'], - ), - ) - - -def test_issue_250_no_type_fail_pass_on_other(): - # https://github.com/pyeve/cerberus/issues/250 - schema = { - 'list': {'schema': {'allow_unknown': True, 'schema': {'a': {'type': 'string'}}}} - } - document = {'list': 1} - assert_normalized(document, document, schema) - - -def test_allow_unknown_with_of_rules(): - # https://github.com/pyeve/cerberus/issues/251 - schema = { - 'test': { - 'oneof': [ - { - 'type': 'dict', - 'allow_unknown': True, - 'schema': {'known': {'type': 'string'}}, - }, - {'type': 'dict', 'schema': {'known': {'type': 'string'}}}, - ] - } - } - # check regression and that allow unknown does not cause any different - # than expected behaviour for one-of. - document = {'test': {'known': 's'}} - assert_fail( - document, - schema, - error=('test', ('test', 'oneof'), errors.ONEOF, schema['test']['oneof']), - ) - # check that allow_unknown is actually applied - document = {'test': {'known': 's', 'unknown': 'asd'}} - assert_success(document, schema) - - -def test_271_normalising_tuples(): - # https://github.com/pyeve/cerberus/issues/271 - schema = { - 'my_field': {'type': 'list', 'schema': {'type': ('string', 'number', 'dict')}} - } - document = {'my_field': ('foo', 'bar', 42, 'albert', 'kandinsky', {'items': 23})} - assert_success(document, schema) - - normalized = Validator(schema).normalized(document) - assert normalized['my_field'] == ( - 'foo', - 'bar', - 42, - 'albert', - 'kandinsky', - {'items': 23}, - ) - - -def test_allow_unknown_wo_schema(): - # https://github.com/pyeve/cerberus/issues/302 - v = Validator({'a': {'type': 'dict', 'allow_unknown': True}}) - v({'a': {}}) - - -def test_allow_unknown_with_purge_unknown(): - validator = Validator(purge_unknown=True) - schema = {'foo': {'type': 'dict', 'allow_unknown': True}} - document = {'foo': {'bar': True}, 'bar': 'foo'} - expected = {'foo': {'bar': True}} - assert_normalized(document, expected, schema, validator) - - -def test_allow_unknown_with_purge_unknown_subdocument(): - validator = Validator(purge_unknown=True) - schema = { - 'foo': { - 'type': 'dict', - 'schema': {'bar': {'type': 'string'}}, - 'allow_unknown': True, - } - } - document = {'foo': {'bar': 'baz', 'corge': False}, 'thud': 'xyzzy'} - expected = {'foo': {'bar': 'baz', 'corge': False}} - assert_normalized(document, expected, schema, validator) - - -def test_purge_readonly(): - schema = { - 'description': {'type': 'string', 'maxlength': 500}, - 'last_updated': {'readonly': True}, - } - validator = Validator(schema=schema, purge_readonly=True) - document = {'description': 'it is a thing'} - expected = deepcopy(document) - document['last_updated'] = 'future' - assert_normalized(document, expected, validator=validator) - - -def test_defaults_in_allow_unknown_schema(): - schema = {'meta': {'type': 'dict'}, 'version': {'type': 'string'}} - allow_unknown = { - 'type': 'dict', - 'schema': { - 'cfg_path': {'type': 'string', 'default': 'cfg.yaml'}, - 'package': {'type': 'string'}, - }, - } - validator = Validator(schema=schema, allow_unknown=allow_unknown) - - document = {'version': '1.2.3', 'plugin_foo': {'package': 'foo'}} - expected = { - 'version': '1.2.3', - 'plugin_foo': {'package': 'foo', 'cfg_path': 'cfg.yaml'}, - } - assert_normalized(document, expected, schema, validator) diff --git a/pipenv/vendor/cerberus/tests/test_registries.py b/pipenv/vendor/cerberus/tests/test_registries.py deleted file mode 100644 index 3cb3e6ef..00000000 --- a/pipenv/vendor/cerberus/tests/test_registries.py +++ /dev/null @@ -1,84 +0,0 @@ -# -*- coding: utf-8 -*- - -from pipenv.vendor.cerberus import schema_registry, rules_set_registry, Validator -from pipenv.vendor.cerberus.tests import ( - assert_fail, - assert_normalized, - assert_schema_error, - assert_success, -) - - -def test_schema_registry_simple(): - schema_registry.add('foo', {'bar': {'type': 'string'}}) - schema = {'a': {'schema': 'foo'}, 'b': {'schema': 'foo'}} - document = {'a': {'bar': 'a'}, 'b': {'bar': 'b'}} - assert_success(document, schema) - - -def test_top_level_reference(): - schema_registry.add('peng', {'foo': {'type': 'integer'}}) - document = {'foo': 42} - assert_success(document, 'peng') - - -def test_rules_set_simple(): - rules_set_registry.add('foo', {'type': 'integer'}) - assert_success({'bar': 1}, {'bar': 'foo'}) - assert_fail({'bar': 'one'}, {'bar': 'foo'}) - - -def test_allow_unknown_as_reference(): - rules_set_registry.add('foo', {'type': 'number'}) - v = Validator(allow_unknown='foo') - assert_success({0: 1}, {}, v) - assert_fail({0: 'one'}, {}, v) - - -def test_recursion(): - rules_set_registry.add('self', {'type': 'dict', 'allow_unknown': 'self'}) - v = Validator(allow_unknown='self') - assert_success({0: {1: {2: {}}}}, {}, v) - - -def test_references_remain_unresolved(validator): - rules_set_registry.extend( - (('boolean', {'type': 'boolean'}), ('booleans', {'valuesrules': 'boolean'})) - ) - validator.schema = {'foo': 'booleans'} - assert 'booleans' == validator.schema['foo'] - assert 'boolean' == rules_set_registry._storage['booleans']['valuesrules'] - - -def test_rules_registry_with_anyof_type(): - rules_set_registry.add('string_or_integer', {'anyof_type': ['string', 'integer']}) - schema = {'soi': 'string_or_integer'} - assert_success({'soi': 'hello'}, schema) - - -def test_schema_registry_with_anyof_type(): - schema_registry.add('soi_id', {'id': {'anyof_type': ['string', 'integer']}}) - schema = {'soi': {'schema': 'soi_id'}} - assert_success({'soi': {'id': 'hello'}}, schema) - - -def test_normalization_with_rules_set(): - # https://github.com/pyeve/cerberus/issues/283 - rules_set_registry.add('foo', {'default': 42}) - assert_normalized({}, {'bar': 42}, {'bar': 'foo'}) - rules_set_registry.add('foo', {'default_setter': lambda _: 42}) - assert_normalized({}, {'bar': 42}, {'bar': 'foo'}) - rules_set_registry.add('foo', {'type': 'integer', 'nullable': True}) - assert_success({'bar': None}, {'bar': 'foo'}) - - -def test_rules_set_with_dict_field(): - document = {'a_dict': {'foo': 1}} - schema = {'a_dict': {'type': 'dict', 'schema': {'foo': 'rule'}}} - - # the schema's not yet added to the valid ones, so test the faulty first - rules_set_registry.add('rule', {'tüpe': 'integer'}) - assert_schema_error(document, schema) - - rules_set_registry.add('rule', {'type': 'integer'}) - assert_success(document, schema) diff --git a/pipenv/vendor/cerberus/tests/test_schema.py b/pipenv/vendor/cerberus/tests/test_schema.py deleted file mode 100644 index a44a4042..00000000 --- a/pipenv/vendor/cerberus/tests/test_schema.py +++ /dev/null @@ -1,178 +0,0 @@ -# -*- coding: utf-8 -*- - -import re - -import pytest - -from pipenv.vendor.cerberus import Validator, errors, SchemaError -from pipenv.vendor.cerberus.schema import UnvalidatedSchema -from pipenv.vendor.cerberus.tests import assert_schema_error - - -def test_empty_schema(): - validator = Validator() - with pytest.raises(SchemaError, match=errors.SCHEMA_ERROR_MISSING): - validator({}, schema=None) - - -def test_bad_schema_type(validator): - schema = "this string should really be dict" - msg = errors.SCHEMA_ERROR_DEFINITION_TYPE.format(schema) - with pytest.raises(SchemaError, match=msg): - validator.schema = schema - - -def test_bad_schema_type_field(validator): - field = 'foo' - schema = {field: {'schema': {'bar': {'type': 'strong'}}}} - with pytest.raises(SchemaError): - validator.schema = schema - - -def test_unknown_rule(validator): - msg = "{'foo': [{'unknown': ['unknown rule']}]}" - with pytest.raises(SchemaError, match=re.escape(msg)): - validator.schema = {'foo': {'unknown': 'rule'}} - - -def test_unknown_type(validator): - msg = str({'foo': [{'type': ['Unsupported types: unknown']}]}) - with pytest.raises(SchemaError, match=re.escape(msg)): - validator.schema = {'foo': {'type': 'unknown'}} - - -def test_bad_schema_definition(validator): - field = 'name' - msg = str({field: ['must be of dict type']}) - with pytest.raises(SchemaError, match=re.escape(msg)): - validator.schema = {field: 'this should really be a dict'} - - -def test_bad_of_rules(): - schema = {'foo': {'anyof': {'type': 'string'}}} - assert_schema_error({}, schema) - - -def test_normalization_rules_are_invalid_in_of_rules(): - schema = {0: {'anyof': [{'coerce': lambda x: x}]}} - assert_schema_error({}, schema) - - -def test_anyof_allof_schema_validate(): - # make sure schema with 'anyof' and 'allof' constraints are checked - # correctly - schema = { - 'doc': {'type': 'dict', 'anyof': [{'schema': [{'param': {'type': 'number'}}]}]} - } - assert_schema_error({'doc': 'this is my document'}, schema) - - schema = { - 'doc': {'type': 'dict', 'allof': [{'schema': [{'param': {'type': 'number'}}]}]} - } - assert_schema_error({'doc': 'this is my document'}, schema) - - -def test_repr(): - v = Validator({'foo': {'type': 'string'}}) - assert repr(v.schema) == "{'foo': {'type': 'string'}}" - - -def test_validated_schema_cache(): - v = Validator({'foozifix': {'coerce': int}}) - cache_size = len(v._valid_schemas) - - v = Validator({'foozifix': {'type': 'integer'}}) - cache_size += 1 - assert len(v._valid_schemas) == cache_size - - v = Validator({'foozifix': {'coerce': int}}) - assert len(v._valid_schemas) == cache_size - - max_cache_size = 163 - assert cache_size <= max_cache_size, ( - "There's an unexpected high amount (%s) of cached valid " - "definition schemas. Unless you added further tests, " - "there are good chances that something is wrong. " - "If you added tests with new schemas, you can try to " - "adjust the variable `max_cache_size` according to " - "the added schemas." % cache_size - ) - - -def test_expansion_in_nested_schema(): - schema = {'detroit': {'schema': {'anyof_regex': ['^Aladdin', 'Sane$']}}} - v = Validator(schema) - assert v.schema['detroit']['schema'] == { - 'anyof': [{'regex': '^Aladdin'}, {'regex': 'Sane$'}] - } - - -def test_unvalidated_schema_can_be_copied(): - schema = UnvalidatedSchema() - schema_copy = schema.copy() - assert schema_copy == schema - - -# TODO remove with next major release -def test_deprecated_rule_names_in_valueschema(): - def check_with(field, value, error): - pass - - schema = { - "field_1": { - "type": "dict", - "valueschema": { - "type": "dict", - "keyschema": {"type": "string"}, - "valueschema": {"type": "string"}, - }, - }, - "field_2": { - "type": "list", - "items": [ - {"keyschema": {}}, - {"validator": check_with}, - {"valueschema": {}}, - ], - }, - } - - validator = Validator(schema) - - assert validator.schema == { - "field_1": { - "type": "dict", - "valuesrules": { - "type": "dict", - "keysrules": {"type": "string"}, - "valuesrules": {"type": "string"}, - }, - }, - "field_2": { - "type": "list", - "items": [ - {"keysrules": {}}, - {"check_with": check_with}, - {"valuesrules": {}}, - ], - }, - } - - -def test_anyof_check_with(): - def foo(field, value, error): - pass - - def bar(field, value, error): - pass - - schema = {'field': {'anyof_check_with': [foo, bar]}} - validator = Validator(schema) - - assert validator.schema == { - 'field': {'anyof': [{'check_with': foo}, {'check_with': bar}]} - } - - -def test_rulename_space_is_normalized(): - Validator(schema={"field": {"default setter": lambda x: x, "type": "string"}}) diff --git a/pipenv/vendor/cerberus/tests/test_utils.py b/pipenv/vendor/cerberus/tests/test_utils.py deleted file mode 100644 index f09cae6b..00000000 --- a/pipenv/vendor/cerberus/tests/test_utils.py +++ /dev/null @@ -1,11 +0,0 @@ -from pipenv.vendor.cerberus.utils import compare_paths_lt - - -def test_compare_paths(): - lesser = ('a_dict', 'keysrules') - greater = ('a_dict', 'valuesrules') - assert compare_paths_lt(lesser, greater) - - lesser += ('type',) - greater += ('regex',) - assert compare_paths_lt(lesser, greater) diff --git a/pipenv/vendor/cerberus/tests/test_validation.py b/pipenv/vendor/cerberus/tests/test_validation.py deleted file mode 100644 index 801bf6fa..00000000 --- a/pipenv/vendor/cerberus/tests/test_validation.py +++ /dev/null @@ -1,1975 +0,0 @@ -# -*- coding: utf-8 -*- - -import itertools -import re -import sys -from datetime import datetime, date -from random import choice -from string import ascii_lowercase - -from pytest import mark - -from pipenv.vendor.cerberus import errors, Validator -from pipenv.vendor.cerberus.tests import ( - assert_bad_type, - assert_document_error, - assert_fail, - assert_has_error, - assert_not_has_error, - assert_success, -) -from pipenv.vendor.cerberus.tests.conftest import sample_schema - - -def test_empty_document(): - assert_document_error(None, sample_schema, None, errors.DOCUMENT_MISSING) - - -def test_bad_document_type(): - document = "not a dict" - assert_document_error( - document, sample_schema, None, errors.DOCUMENT_FORMAT.format(document) - ) - - -def test_unknown_field(validator): - field = 'surname' - assert_fail( - {field: 'doe'}, - validator=validator, - error=(field, (), errors.UNKNOWN_FIELD, None), - ) - assert validator.errors == {field: ['unknown field']} - - -def test_empty_field_definition(document): - field = 'name' - schema = {field: {}} - assert_success(document, schema) - - -def test_required_field(schema): - field = 'a_required_string' - required_string_extension = { - 'a_required_string': { - 'type': 'string', - 'minlength': 2, - 'maxlength': 10, - 'required': True, - } - } - schema.update(required_string_extension) - assert_fail( - {'an_integer': 1}, - schema, - error=(field, (field, 'required'), errors.REQUIRED_FIELD, True), - ) - - -def test_nullable_field(): - assert_success({'a_nullable_integer': None}) - assert_success({'a_nullable_integer': 3}) - assert_success({'a_nullable_field_without_type': None}) - assert_fail({'a_nullable_integer': "foo"}) - assert_fail({'an_integer': None}) - assert_fail({'a_not_nullable_field_without_type': None}) - - -def test_nullable_skips_allowed(): - schema = {'role': {'allowed': ['agent', 'client', 'supplier'], 'nullable': True}} - assert_success({'role': None}, schema) - - -def test_readonly_field(): - field = 'a_readonly_string' - assert_fail( - {field: 'update me if you can'}, - error=(field, (field, 'readonly'), errors.READONLY_FIELD, True), - ) - - -def test_readonly_field_first_rule(): - # test that readonly rule is checked before any other rule, and blocks. - # See #63. - schema = {'a_readonly_number': {'type': 'integer', 'readonly': True, 'max': 1}} - v = Validator(schema) - v.validate({'a_readonly_number': 2}) - # it would be a list if there's more than one error; we get a dict - # instead. - assert 'read-only' in v.errors['a_readonly_number'][0] - - -def test_readonly_field_with_default_value(): - schema = { - 'created': {'type': 'string', 'readonly': True, 'default': 'today'}, - 'modified': { - 'type': 'string', - 'readonly': True, - 'default_setter': lambda d: d['created'], - }, - } - assert_success({}, schema) - expected_errors = [ - ( - 'created', - ('created', 'readonly'), - errors.READONLY_FIELD, - schema['created']['readonly'], - ), - ( - 'modified', - ('modified', 'readonly'), - errors.READONLY_FIELD, - schema['modified']['readonly'], - ), - ] - assert_fail( - {'created': 'tomorrow', 'modified': 'today'}, schema, errors=expected_errors - ) - assert_fail( - {'created': 'today', 'modified': 'today'}, schema, errors=expected_errors - ) - - -def test_nested_readonly_field_with_default_value(): - schema = { - 'some_field': { - 'type': 'dict', - 'schema': { - 'created': {'type': 'string', 'readonly': True, 'default': 'today'}, - 'modified': { - 'type': 'string', - 'readonly': True, - 'default_setter': lambda d: d['created'], - }, - }, - } - } - assert_success({'some_field': {}}, schema) - expected_errors = [ - ( - ('some_field', 'created'), - ('some_field', 'schema', 'created', 'readonly'), - errors.READONLY_FIELD, - schema['some_field']['schema']['created']['readonly'], - ), - ( - ('some_field', 'modified'), - ('some_field', 'schema', 'modified', 'readonly'), - errors.READONLY_FIELD, - schema['some_field']['schema']['modified']['readonly'], - ), - ] - assert_fail( - {'some_field': {'created': 'tomorrow', 'modified': 'now'}}, - schema, - errors=expected_errors, - ) - assert_fail( - {'some_field': {'created': 'today', 'modified': 'today'}}, - schema, - errors=expected_errors, - ) - - -def test_repeated_readonly(validator): - # https://github.com/pyeve/cerberus/issues/311 - validator.schema = {'id': {'readonly': True}} - assert_fail({'id': 0}, validator=validator) - assert_fail({'id': 0}, validator=validator) - - -def test_not_a_string(): - assert_bad_type('a_string', 'string', 1) - - -def test_not_a_binary(): - # 'u' literal prefix produces type `str` in Python 3 - assert_bad_type('a_binary', 'binary', u"i'm not a binary") - - -def test_not_a_integer(): - assert_bad_type('an_integer', 'integer', "i'm not an integer") - - -def test_not_a_boolean(): - assert_bad_type('a_boolean', 'boolean', "i'm not a boolean") - - -def test_not_a_datetime(): - assert_bad_type('a_datetime', 'datetime', "i'm not a datetime") - - -def test_not_a_float(): - assert_bad_type('a_float', 'float', "i'm not a float") - - -def test_not_a_number(): - assert_bad_type('a_number', 'number', "i'm not a number") - - -def test_not_a_list(): - assert_bad_type('a_list_of_values', 'list', "i'm not a list") - - -def test_not_a_dict(): - assert_bad_type('a_dict', 'dict', "i'm not a dict") - - -def test_bad_max_length(schema): - field = 'a_string' - max_length = schema[field]['maxlength'] - value = "".join(choice(ascii_lowercase) for i in range(max_length + 1)) - assert_fail( - {field: value}, - error=( - field, - (field, 'maxlength'), - errors.MAX_LENGTH, - max_length, - (len(value),), - ), - ) - - -def test_bad_max_length_binary(schema): - field = 'a_binary' - max_length = schema[field]['maxlength'] - value = b'\x00' * (max_length + 1) - assert_fail( - {field: value}, - error=( - field, - (field, 'maxlength'), - errors.MAX_LENGTH, - max_length, - (len(value),), - ), - ) - - -def test_bad_min_length(schema): - field = 'a_string' - min_length = schema[field]['minlength'] - value = "".join(choice(ascii_lowercase) for i in range(min_length - 1)) - assert_fail( - {field: value}, - error=( - field, - (field, 'minlength'), - errors.MIN_LENGTH, - min_length, - (len(value),), - ), - ) - - -def test_bad_min_length_binary(schema): - field = 'a_binary' - min_length = schema[field]['minlength'] - value = b'\x00' * (min_length - 1) - assert_fail( - {field: value}, - error=( - field, - (field, 'minlength'), - errors.MIN_LENGTH, - min_length, - (len(value),), - ), - ) - - -def test_bad_max_value(schema): - def assert_bad_max_value(field, inc): - max_value = schema[field]['max'] - value = max_value + inc - assert_fail( - {field: value}, error=(field, (field, 'max'), errors.MAX_VALUE, max_value) - ) - - field = 'an_integer' - assert_bad_max_value(field, 1) - field = 'a_float' - assert_bad_max_value(field, 1.0) - field = 'a_number' - assert_bad_max_value(field, 1) - - -def test_bad_min_value(schema): - def assert_bad_min_value(field, inc): - min_value = schema[field]['min'] - value = min_value - inc - assert_fail( - {field: value}, error=(field, (field, 'min'), errors.MIN_VALUE, min_value) - ) - - field = 'an_integer' - assert_bad_min_value(field, 1) - field = 'a_float' - assert_bad_min_value(field, 1.0) - field = 'a_number' - assert_bad_min_value(field, 1) - - -def test_bad_schema(): - field = 'a_dict' - subschema_field = 'address' - schema = { - field: { - 'type': 'dict', - 'schema': { - subschema_field: {'type': 'string'}, - 'city': {'type': 'string', 'required': True}, - }, - } - } - document = {field: {subschema_field: 34}} - validator = Validator(schema) - - assert_fail( - document, - validator=validator, - error=( - field, - (field, 'schema'), - errors.MAPPING_SCHEMA, - validator.schema['a_dict']['schema'], - ), - child_errors=[ - ( - (field, subschema_field), - (field, 'schema', subschema_field, 'type'), - errors.BAD_TYPE, - 'string', - ), - ( - (field, 'city'), - (field, 'schema', 'city', 'required'), - errors.REQUIRED_FIELD, - True, - ), - ], - ) - - handler = errors.BasicErrorHandler - assert field in validator.errors - assert subschema_field in validator.errors[field][-1] - assert ( - handler.messages[errors.BAD_TYPE.code].format(constraint='string') - in validator.errors[field][-1][subschema_field] - ) - assert 'city' in validator.errors[field][-1] - assert ( - handler.messages[errors.REQUIRED_FIELD.code] - in validator.errors[field][-1]['city'] - ) - - -def test_bad_valuesrules(): - field = 'a_dict_with_valuesrules' - schema_field = 'a_string' - value = {schema_field: 'not an integer'} - - exp_child_errors = [ - ( - (field, schema_field), - (field, 'valuesrules', 'type'), - errors.BAD_TYPE, - 'integer', - ) - ] - assert_fail( - {field: value}, - error=(field, (field, 'valuesrules'), errors.VALUESRULES, {'type': 'integer'}), - child_errors=exp_child_errors, - ) - - -def test_bad_list_of_values(validator): - field = 'a_list_of_values' - value = ['a string', 'not an integer'] - assert_fail( - {field: value}, - validator=validator, - error=( - field, - (field, 'items'), - errors.BAD_ITEMS, - [{'type': 'string'}, {'type': 'integer'}], - ), - child_errors=[ - ((field, 1), (field, 'items', 1, 'type'), errors.BAD_TYPE, 'integer') - ], - ) - - assert ( - errors.BasicErrorHandler.messages[errors.BAD_TYPE.code].format( - constraint='integer' - ) - in validator.errors[field][-1][1] - ) - - value = ['a string', 10, 'an extra item'] - assert_fail( - {field: value}, - error=( - field, - (field, 'items'), - errors.ITEMS_LENGTH, - [{'type': 'string'}, {'type': 'integer'}], - (2, 3), - ), - ) - - -def test_bad_list_of_integers(): - field = 'a_list_of_integers' - value = [34, 'not an integer'] - assert_fail({field: value}) - - -def test_bad_list_of_dicts(): - field = 'a_list_of_dicts' - map_schema = { - 'sku': {'type': 'string'}, - 'price': {'type': 'integer', 'required': True}, - } - seq_schema = {'type': 'dict', 'schema': map_schema} - schema = {field: {'type': 'list', 'schema': seq_schema}} - validator = Validator(schema) - value = [{'sku': 'KT123', 'price': '100'}] - document = {field: value} - - assert_fail( - document, - validator=validator, - error=(field, (field, 'schema'), errors.SEQUENCE_SCHEMA, seq_schema), - child_errors=[ - ((field, 0), (field, 'schema', 'schema'), errors.MAPPING_SCHEMA, map_schema) - ], - ) - - assert field in validator.errors - assert 0 in validator.errors[field][-1] - assert 'price' in validator.errors[field][-1][0][-1] - exp_msg = errors.BasicErrorHandler.messages[errors.BAD_TYPE.code].format( - constraint='integer' - ) - assert exp_msg in validator.errors[field][-1][0][-1]['price'] - - value = ["not a dict"] - exp_child_errors = [ - ((field, 0), (field, 'schema', 'type'), errors.BAD_TYPE, 'dict', ()) - ] - assert_fail( - {field: value}, - error=(field, (field, 'schema'), errors.SEQUENCE_SCHEMA, seq_schema), - child_errors=exp_child_errors, - ) - - -def test_array_unallowed(): - field = 'an_array' - value = ['agent', 'client', 'profit'] - assert_fail( - {field: value}, - error=( - field, - (field, 'allowed'), - errors.UNALLOWED_VALUES, - ['agent', 'client', 'vendor'], - (('profit',),), - ), - ) - - -def test_string_unallowed(): - field = 'a_restricted_string' - value = 'profit' - assert_fail( - {field: value}, - error=( - field, - (field, 'allowed'), - errors.UNALLOWED_VALUE, - ['agent', 'client', 'vendor'], - value, - ), - ) - - -def test_integer_unallowed(): - field = 'a_restricted_integer' - value = 2 - assert_fail( - {field: value}, - error=(field, (field, 'allowed'), errors.UNALLOWED_VALUE, [-1, 0, 1], value), - ) - - -def test_integer_allowed(): - assert_success({'a_restricted_integer': -1}) - - -def test_validate_update(): - assert_success( - { - 'an_integer': 100, - 'a_dict': {'address': 'adr'}, - 'a_list_of_dicts': [{'sku': 'let'}], - }, - update=True, - ) - - -def test_string(): - assert_success({'a_string': 'john doe'}) - - -def test_string_allowed(): - assert_success({'a_restricted_string': 'client'}) - - -def test_integer(): - assert_success({'an_integer': 50}) - - -def test_boolean(): - assert_success({'a_boolean': True}) - - -def test_datetime(): - assert_success({'a_datetime': datetime.now()}) - - -def test_float(): - assert_success({'a_float': 3.5}) - assert_success({'a_float': 1}) - - -def test_number(): - assert_success({'a_number': 3.5}) - assert_success({'a_number': 3}) - - -def test_array(): - assert_success({'an_array': ['agent', 'client']}) - - -def test_set(): - assert_success({'a_set': set(['hello', 1])}) - - -def test_one_of_two_types(validator): - field = 'one_or_more_strings' - assert_success({field: 'foo'}) - assert_success({field: ['foo', 'bar']}) - exp_child_errors = [ - ((field, 1), (field, 'schema', 'type'), errors.BAD_TYPE, 'string') - ] - assert_fail( - {field: ['foo', 23]}, - validator=validator, - error=(field, (field, 'schema'), errors.SEQUENCE_SCHEMA, {'type': 'string'}), - child_errors=exp_child_errors, - ) - assert_fail( - {field: 23}, - error=((field,), (field, 'type'), errors.BAD_TYPE, ['string', 'list']), - ) - assert validator.errors == {field: [{1: ['must be of string type']}]} - - -def test_regex(validator): - field = 'a_regex_email' - assert_success({field: 'valid.email@gmail.com'}, validator=validator) - assert_fail( - {field: 'invalid'}, - update=True, - error=( - field, - (field, 'regex'), - errors.REGEX_MISMATCH, - r'^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$', - ), - ) - - -def test_regex_with_flag(): - assert_success({"item": "hOly grAil"}, {"item": {"regex": "(?i)holy grail"}}) - assert_fail({"item": "hOly grAil"}, {"item": {"regex": "holy grail"}}) - - -def test_a_list_of_dicts(): - assert_success( - { - 'a_list_of_dicts': [ - {'sku': 'AK345', 'price': 100}, - {'sku': 'YZ069', 'price': 25}, - ] - } - ) - - -def test_a_list_of_values(): - assert_success({'a_list_of_values': ['hello', 100]}) - - -def test_an_array_from_set(): - assert_success({'an_array_from_set': ['agent', 'client']}) - - -def test_a_list_of_integers(): - assert_success({'a_list_of_integers': [99, 100]}) - - -def test_a_dict(schema): - assert_success({'a_dict': {'address': 'i live here', 'city': 'in my own town'}}) - assert_fail( - {'a_dict': {'address': 8545}}, - error=( - 'a_dict', - ('a_dict', 'schema'), - errors.MAPPING_SCHEMA, - schema['a_dict']['schema'], - ), - child_errors=[ - ( - ('a_dict', 'address'), - ('a_dict', 'schema', 'address', 'type'), - errors.BAD_TYPE, - 'string', - ), - ( - ('a_dict', 'city'), - ('a_dict', 'schema', 'city', 'required'), - errors.REQUIRED_FIELD, - True, - ), - ], - ) - - -def test_a_dict_with_valuesrules(validator): - assert_success( - {'a_dict_with_valuesrules': {'an integer': 99, 'another integer': 100}} - ) - - error = ( - 'a_dict_with_valuesrules', - ('a_dict_with_valuesrules', 'valuesrules'), - errors.VALUESRULES, - {'type': 'integer'}, - ) - child_errors = [ - ( - ('a_dict_with_valuesrules', 'a string'), - ('a_dict_with_valuesrules', 'valuesrules', 'type'), - errors.BAD_TYPE, - 'integer', - ) - ] - - assert_fail( - {'a_dict_with_valuesrules': {'a string': '99'}}, - validator=validator, - error=error, - child_errors=child_errors, - ) - - assert 'valuesrules' in validator.schema_error_tree['a_dict_with_valuesrules'] - v = validator.schema_error_tree - assert len(v['a_dict_with_valuesrules']['valuesrules'].descendants) == 1 - - -# TODO remove 'keyschema' as rule with the next major release -@mark.parametrize('rule', ('keysrules', 'keyschema')) -def test_keysrules(rule): - schema = { - 'a_dict_with_keysrules': { - 'type': 'dict', - rule: {'type': 'string', 'regex': '[a-z]+'}, - } - } - assert_success({'a_dict_with_keysrules': {'key': 'value'}}, schema=schema) - assert_fail({'a_dict_with_keysrules': {'KEY': 'value'}}, schema=schema) - - -def test_a_list_length(schema): - field = 'a_list_length' - min_length = schema[field]['minlength'] - max_length = schema[field]['maxlength'] - - assert_fail( - {field: [1] * (min_length - 1)}, - error=( - field, - (field, 'minlength'), - errors.MIN_LENGTH, - min_length, - (min_length - 1,), - ), - ) - - for i in range(min_length, max_length): - value = [1] * i - assert_success({field: value}) - - assert_fail( - {field: [1] * (max_length + 1)}, - error=( - field, - (field, 'maxlength'), - errors.MAX_LENGTH, - max_length, - (max_length + 1,), - ), - ) - - -def test_custom_datatype(): - class MyValidator(Validator): - def _validate_type_objectid(self, value): - if re.match('[a-f0-9]{24}', value): - return True - - schema = {'test_field': {'type': 'objectid'}} - validator = MyValidator(schema) - assert_success({'test_field': '50ad188438345b1049c88a28'}, validator=validator) - assert_fail( - {'test_field': 'hello'}, - validator=validator, - error=('test_field', ('test_field', 'type'), errors.BAD_TYPE, 'objectid'), - ) - - -def test_custom_datatype_rule(): - class MyValidator(Validator): - def _validate_min_number(self, min_number, field, value): - """{'type': 'number'}""" - if value < min_number: - self._error(field, 'Below the min') - - # TODO replace with TypeDefintion in next major release - def _validate_type_number(self, value): - if isinstance(value, int): - return True - - schema = {'test_field': {'min_number': 1, 'type': 'number'}} - validator = MyValidator(schema) - assert_fail( - {'test_field': '0'}, - validator=validator, - error=('test_field', ('test_field', 'type'), errors.BAD_TYPE, 'number'), - ) - assert_fail( - {'test_field': 0}, - validator=validator, - error=('test_field', (), errors.CUSTOM, None, ('Below the min',)), - ) - assert validator.errors == {'test_field': ['Below the min']} - - -def test_custom_validator(): - class MyValidator(Validator): - def _validate_isodd(self, isodd, field, value): - """{'type': 'boolean'}""" - if isodd and not bool(value & 1): - self._error(field, 'Not an odd number') - - schema = {'test_field': {'isodd': True}} - validator = MyValidator(schema) - assert_success({'test_field': 7}, validator=validator) - assert_fail( - {'test_field': 6}, - validator=validator, - error=('test_field', (), errors.CUSTOM, None, ('Not an odd number',)), - ) - assert validator.errors == {'test_field': ['Not an odd number']} - - -@mark.parametrize( - 'value, _type', (('', 'string'), ((), 'list'), ({}, 'dict'), ([], 'list')) -) -def test_empty_values(value, _type): - field = 'test' - schema = {field: {'type': _type}} - document = {field: value} - - assert_success(document, schema) - - schema[field]['empty'] = False - assert_fail( - document, - schema, - error=(field, (field, 'empty'), errors.EMPTY_NOT_ALLOWED, False), - ) - - schema[field]['empty'] = True - assert_success(document, schema) - - -def test_empty_skips_regex(validator): - schema = {'foo': {'empty': True, 'regex': r'\d?\d\.\d\d', 'type': 'string'}} - assert validator({'foo': ''}, schema) - - -def test_ignore_none_values(): - field = 'test' - schema = {field: {'type': 'string', 'empty': False, 'required': False}} - document = {field: None} - - # Test normal behaviour - validator = Validator(schema, ignore_none_values=False) - assert_fail(document, validator=validator) - validator.schema[field]['required'] = True - validator.schema.validate() - _errors = assert_fail(document, validator=validator) - assert_not_has_error( - _errors, field, (field, 'required'), errors.REQUIRED_FIELD, True - ) - - # Test ignore None behaviour - validator = Validator(schema, ignore_none_values=True) - validator.schema[field]['required'] = False - validator.schema.validate() - assert_success(document, validator=validator) - validator.schema[field]['required'] = True - _errors = assert_fail(schema=schema, document=document, validator=validator) - assert_has_error(_errors, field, (field, 'required'), errors.REQUIRED_FIELD, True) - assert_not_has_error(_errors, field, (field, 'type'), errors.BAD_TYPE, 'string') - - -def test_unknown_keys(): - schema = {} - - # test that unknown fields are allowed when allow_unknown is True. - v = Validator(allow_unknown=True, schema=schema) - assert_success({"unknown1": True, "unknown2": "yes"}, validator=v) - - # test that unknown fields are allowed only if they meet the - # allow_unknown schema when provided. - v.allow_unknown = {'type': 'string'} - assert_success(document={'name': 'mark'}, validator=v) - assert_fail({"name": 1}, validator=v) - - # test that unknown fields are not allowed if allow_unknown is False - v.allow_unknown = False - assert_fail({'name': 'mark'}, validator=v) - - -def test_unknown_key_dict(validator): - # https://github.com/pyeve/cerberus/issues/177 - validator.allow_unknown = True - document = {'a_dict': {'foo': 'foo_value', 'bar': 25}} - assert_success(document, {}, validator=validator) - - -def test_unknown_key_list(validator): - # https://github.com/pyeve/cerberus/issues/177 - validator.allow_unknown = True - document = {'a_dict': ['foo', 'bar']} - assert_success(document, {}, validator=validator) - - -def test_unknown_keys_list_of_dicts(validator): - # test that allow_unknown is honored even for subdicts in lists. - # https://github.com/pyeve/cerberus/issues/67. - validator.allow_unknown = True - document = {'a_list_of_dicts': [{'sku': 'YZ069', 'price': 25, 'extra': True}]} - assert_success(document, validator=validator) - - -def test_unknown_keys_retain_custom_rules(): - # test that allow_unknown schema respect custom validation rules. - # https://github.com/pyeve/cerberus/issues/#66. - class CustomValidator(Validator): - def _validate_type_foo(self, value): - if value == "foo": - return True - - validator = CustomValidator({}) - validator.allow_unknown = {"type": "foo"} - assert_success(document={"fred": "foo", "barney": "foo"}, validator=validator) - - -def test_nested_unknown_keys(): - schema = { - 'field1': { - 'type': 'dict', - 'allow_unknown': True, - 'schema': {'nested1': {'type': 'string'}}, - } - } - document = {'field1': {'nested1': 'foo', 'arb1': 'bar', 'arb2': 42}} - assert_success(document=document, schema=schema) - - schema['field1']['allow_unknown'] = {'type': 'string'} - assert_fail(document=document, schema=schema) - - -def test_novalidate_noerrors(validator): - """ - In v0.1.0 and below `self.errors` raised an exception if no - validation had been performed yet. - """ - assert validator.errors == {} - - -def test_callable_validator(): - """ - Validator instance is callable, functions as a shorthand - passthrough to validate() - """ - schema = {'test_field': {'type': 'string'}} - v = Validator(schema) - assert v.validate({'test_field': 'foo'}) - assert v({'test_field': 'foo'}) - assert not v.validate({'test_field': 1}) - assert not v({'test_field': 1}) - - -def test_dependencies_field(): - schema = {'test_field': {'dependencies': 'foo'}, 'foo': {'type': 'string'}} - assert_success({'test_field': 'foobar', 'foo': 'bar'}, schema) - assert_fail({'test_field': 'foobar'}, schema) - - -def test_dependencies_list(): - schema = { - 'test_field': {'dependencies': ['foo', 'bar']}, - 'foo': {'type': 'string'}, - 'bar': {'type': 'string'}, - } - assert_success({'test_field': 'foobar', 'foo': 'bar', 'bar': 'foo'}, schema) - assert_fail({'test_field': 'foobar', 'foo': 'bar'}, schema) - - -def test_dependencies_list_with_required_field(): - schema = { - 'test_field': {'required': True, 'dependencies': ['foo', 'bar']}, - 'foo': {'type': 'string'}, - 'bar': {'type': 'string'}, - } - # False: all dependencies missing - assert_fail({'test_field': 'foobar'}, schema) - # False: one of dependencies missing - assert_fail({'test_field': 'foobar', 'foo': 'bar'}, schema) - # False: one of dependencies missing - assert_fail({'test_field': 'foobar', 'bar': 'foo'}, schema) - # False: dependencies are validated and field is required - assert_fail({'foo': 'bar', 'bar': 'foo'}, schema) - # False: All dependencies are optional but field is still required - assert_fail({}, schema) - # True: dependency missing - assert_fail({'foo': 'bar'}, schema) - # True: dependencies are validated but field is not required - schema['test_field']['required'] = False - assert_success({'foo': 'bar', 'bar': 'foo'}, schema) - - -def test_dependencies_list_with_subodcuments_fields(): - schema = { - 'test_field': {'dependencies': ['a_dict.foo', 'a_dict.bar']}, - 'a_dict': { - 'type': 'dict', - 'schema': {'foo': {'type': 'string'}, 'bar': {'type': 'string'}}, - }, - } - assert_success( - {'test_field': 'foobar', 'a_dict': {'foo': 'foo', 'bar': 'bar'}}, schema - ) - assert_fail({'test_field': 'foobar', 'a_dict': {}}, schema) - assert_fail({'test_field': 'foobar', 'a_dict': {'foo': 'foo'}}, schema) - - -def test_dependencies_dict(): - schema = { - 'test_field': {'dependencies': {'foo': 'foo', 'bar': 'bar'}}, - 'foo': {'type': 'string'}, - 'bar': {'type': 'string'}, - } - assert_success({'test_field': 'foobar', 'foo': 'foo', 'bar': 'bar'}, schema) - assert_fail({'test_field': 'foobar', 'foo': 'foo'}, schema) - assert_fail({'test_field': 'foobar', 'foo': 'bar'}, schema) - assert_fail({'test_field': 'foobar', 'bar': 'bar'}, schema) - assert_fail({'test_field': 'foobar', 'bar': 'foo'}, schema) - assert_fail({'test_field': 'foobar'}, schema) - - -def test_dependencies_dict_with_required_field(): - schema = { - 'test_field': {'required': True, 'dependencies': {'foo': 'foo', 'bar': 'bar'}}, - 'foo': {'type': 'string'}, - 'bar': {'type': 'string'}, - } - # False: all dependencies missing - assert_fail({'test_field': 'foobar'}, schema) - # False: one of dependencies missing - assert_fail({'test_field': 'foobar', 'foo': 'foo'}, schema) - assert_fail({'test_field': 'foobar', 'bar': 'bar'}, schema) - # False: dependencies are validated and field is required - assert_fail({'foo': 'foo', 'bar': 'bar'}, schema) - # False: All dependencies are optional, but field is still required - assert_fail({}, schema) - # False: dependency missing - assert_fail({'foo': 'bar'}, schema) - - assert_success({'test_field': 'foobar', 'foo': 'foo', 'bar': 'bar'}, schema) - - # True: dependencies are validated but field is not required - schema['test_field']['required'] = False - assert_success({'foo': 'bar', 'bar': 'foo'}, schema) - - -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_field_with_mutually_dependent_nullable_fields(): - # https://github.com/pyeve/cerberus/pull/306 - schema = { - 'foo': {'dependencies': 'bar', 'nullable': True}, - 'bar': {'dependencies': 'foo', 'nullable': True}, - } - assert_success({'foo': None, 'bar': None}, schema) - assert_success({'foo': 1, 'bar': 1}, schema) - assert_success({'foo': None, 'bar': 1}, schema) - assert_fail({'foo': None}, schema) - assert_fail({'foo': 1}, schema) - - -def test_dependencies_dict_with_subdocuments_fields(): - schema = { - 'test_field': { - 'dependencies': {'a_dict.foo': ['foo', 'bar'], 'a_dict.bar': 'bar'} - }, - 'a_dict': { - 'type': 'dict', - 'schema': {'foo': {'type': 'string'}, 'bar': {'type': 'string'}}, - }, - } - assert_success( - {'test_field': 'foobar', 'a_dict': {'foo': 'foo', 'bar': 'bar'}}, schema - ) - assert_success( - {'test_field': 'foobar', 'a_dict': {'foo': 'bar', 'bar': 'bar'}}, schema - ) - assert_fail({'test_field': 'foobar', 'a_dict': {}}, schema) - assert_fail( - {'test_field': 'foobar', 'a_dict': {'foo': 'foo', 'bar': 'foo'}}, schema - ) - assert_fail({'test_field': 'foobar', 'a_dict': {'bar': 'foo'}}, schema) - assert_fail({'test_field': 'foobar', 'a_dict': {'bar': 'bar'}}, schema) - - -def test_root_relative_dependencies(): - # https://github.com/pyeve/cerberus/issues/288 - subschema = {'version': {'dependencies': '^repo'}} - schema = {'package': {'allow_unknown': True, 'schema': subschema}, 'repo': {}} - assert_fail( - {'package': {'repo': 'somewhere', 'version': 0}}, - schema, - error=('package', ('package', 'schema'), errors.MAPPING_SCHEMA, subschema), - child_errors=[ - ( - ('package', 'version'), - ('package', 'schema', 'version', 'dependencies'), - errors.DEPENDENCIES_FIELD, - '^repo', - ('^repo',), - ) - ], - ) - assert_success({'repo': 'somewhere', 'package': {'version': 1}}, schema) - - -def test_dependencies_errors(): - v = Validator( - { - 'field1': {'required': False}, - 'field2': {'required': True, 'dependencies': {'field1': ['one', 'two']}}, - } - ) - assert_fail( - {'field1': 'three', 'field2': 7}, - validator=v, - error=( - 'field2', - ('field2', 'dependencies'), - errors.DEPENDENCIES_FIELD_VALUE, - {'field1': ['one', 'two']}, - ({'field1': 'three'},), - ), - ) - - -def test_options_passed_to_nested_validators(validator): - validator.schema = { - 'sub_dict': {'type': 'dict', 'schema': {'foo': {'type': 'string'}}} - } - validator.allow_unknown = True - assert_success({'sub_dict': {'foo': 'bar', 'unknown': True}}, validator=validator) - - -def test_self_root_document(): - """ - Make sure self.root_document is always the root document. See: - * https://github.com/pyeve/cerberus/pull/42 - * https://github.com/pyeve/eve/issues/295 - """ - - class MyValidator(Validator): - def _validate_root_doc(self, root_doc, field, value): - """{'type': 'boolean'}""" - if 'sub' not in self.root_document or len(self.root_document['sub']) != 2: - self._error(field, 'self.context is not the root doc!') - - schema = { - 'sub': { - 'type': 'list', - 'root_doc': True, - 'schema': { - 'type': 'dict', - 'schema': {'foo': {'type': 'string', 'root_doc': True}}, - }, - } - } - assert_success( - {'sub': [{'foo': 'bar'}, {'foo': 'baz'}]}, validator=MyValidator(schema) - ) - - -def test_validator_rule(validator): - def validate_name(field, value, error): - if not value.islower(): - error(field, 'must be lowercase') - - validator.schema = { - 'name': {'validator': validate_name}, - 'age': {'type': 'integer'}, - } - - assert_fail( - {'name': 'ItsMe', 'age': 2}, - validator=validator, - error=('name', (), errors.CUSTOM, None, ('must be lowercase',)), - ) - assert validator.errors == {'name': ['must be lowercase']} - assert_success({'name': 'itsme', 'age': 2}, validator=validator) - - -def test_validated(validator): - validator.schema = {'property': {'type': 'string'}} - document = {'property': 'string'} - assert validator.validated(document) == document - document = {'property': 0} - assert validator.validated(document) is None - - -def test_anyof(): - # prop1 must be either a number between 0 and 10 - schema = {'prop1': {'min': 0, 'max': 10}} - doc = {'prop1': 5} - - assert_success(doc, schema) - - # prop1 must be either a number between 0 and 10 or 100 and 110 - schema = {'prop1': {'anyof': [{'min': 0, 'max': 10}, {'min': 100, 'max': 110}]}} - doc = {'prop1': 105} - - assert_success(doc, schema) - - # prop1 must be either a number between 0 and 10 or 100 and 110 - schema = {'prop1': {'anyof': [{'min': 0, 'max': 10}, {'min': 100, 'max': 110}]}} - doc = {'prop1': 50} - - assert_fail(doc, schema) - - # prop1 must be an integer that is either be - # greater than or equal to 0, or greater than or equal to 10 - schema = {'prop1': {'type': 'integer', 'anyof': [{'min': 0}, {'min': 10}]}} - assert_success({'prop1': 10}, schema) - # test that intermediate schemas do not sustain - assert 'type' not in schema['prop1']['anyof'][0] - assert 'type' not in schema['prop1']['anyof'][1] - assert 'allow_unknown' not in schema['prop1']['anyof'][0] - assert 'allow_unknown' not in schema['prop1']['anyof'][1] - assert_success({'prop1': 5}, schema) - - exp_child_errors = [ - (('prop1',), ('prop1', 'anyof', 0, 'min'), errors.MIN_VALUE, 0), - (('prop1',), ('prop1', 'anyof', 1, 'min'), errors.MIN_VALUE, 10), - ] - assert_fail( - {'prop1': -1}, - schema, - error=(('prop1',), ('prop1', 'anyof'), errors.ANYOF, [{'min': 0}, {'min': 10}]), - child_errors=exp_child_errors, - ) - doc = {'prop1': 5.5} - assert_fail(doc, schema) - doc = {'prop1': '5.5'} - assert_fail(doc, schema) - - -def test_allof(): - # prop1 has to be a float between 0 and 10 - schema = {'prop1': {'allof': [{'type': 'float'}, {'min': 0}, {'max': 10}]}} - doc = {'prop1': -1} - assert_fail(doc, schema) - doc = {'prop1': 5} - assert_success(doc, schema) - doc = {'prop1': 11} - assert_fail(doc, schema) - - # prop1 has to be a float and an integer - schema = {'prop1': {'allof': [{'type': 'float'}, {'type': 'integer'}]}} - doc = {'prop1': 11} - assert_success(doc, schema) - doc = {'prop1': 11.5} - assert_fail(doc, schema) - doc = {'prop1': '11'} - assert_fail(doc, schema) - - -def test_unicode_allowed(): - # issue 280 - doc = {'letters': u'♄εℓł☺'} - - schema = {'letters': {'type': 'string', 'allowed': ['a', 'b', 'c']}} - assert_fail(doc, schema) - - schema = {'letters': {'type': 'string', 'allowed': [u'♄εℓł☺']}} - assert_success(doc, schema) - - schema = {'letters': {'type': 'string', 'allowed': ['♄εℓł☺']}} - doc = {'letters': '♄εℓł☺'} - assert_success(doc, schema) - - -@mark.skipif(sys.version_info[0] < 3, reason='requires python 3.x') -def test_unicode_allowed_py3(): - """ - All strings are unicode in Python 3.x. Input doc and schema have equal strings and - validation yield success. - """ - - # issue 280 - doc = {'letters': u'♄εℓł☺'} - schema = {'letters': {'type': 'string', 'allowed': ['♄εℓł☺']}} - assert_success(doc, schema) - - -@mark.skipif(sys.version_info[0] > 2, reason='requires python 2.x') -def test_unicode_allowed_py2(): - """ - Python 2.x encodes value of allowed using default encoding if the string includes - characters outside ASCII range. Produced string does not match input which is an - unicode string. - """ - - # issue 280 - doc = {'letters': u'♄εℓł☺'} - schema = {'letters': {'type': 'string', 'allowed': ['♄εℓł☺']}} - assert_fail(doc, schema) - - -def test_oneof(): - # prop1 can only only be: - # - greater than 10 - # - greater than 0 - # - equal to -5, 5, or 15 - - schema = { - 'prop1': { - 'type': 'integer', - 'oneof': [{'min': 0}, {'min': 10}, {'allowed': [-5, 5, 15]}], - } - } - - # document is not valid - # prop1 not greater than 0, 10 or equal to -5 - doc = {'prop1': -1} - assert_fail(doc, schema) - - # document is valid - # prop1 is less then 0, but is -5 - doc = {'prop1': -5} - assert_success(doc, schema) - - # document is valid - # prop1 greater than 0 - doc = {'prop1': 1} - assert_success(doc, schema) - - # document is not valid - # prop1 is greater than 0 - # and equal to 5 - doc = {'prop1': 5} - assert_fail(doc, schema) - - # document is not valid - # prop1 is greater than 0 - # and greater than 10 - doc = {'prop1': 11} - assert_fail(doc, schema) - - # document is not valid - # prop1 is greater than 0 - # and greater than 10 - # and equal to 15 - doc = {'prop1': 15} - assert_fail(doc, schema) - - -def test_noneof(): - # prop1 can not be: - # - greater than 10 - # - greater than 0 - # - equal to -5, 5, or 15 - - schema = { - 'prop1': { - 'type': 'integer', - 'noneof': [{'min': 0}, {'min': 10}, {'allowed': [-5, 5, 15]}], - } - } - - # document is valid - doc = {'prop1': -1} - assert_success(doc, schema) - - # document is not valid - # prop1 is equal to -5 - doc = {'prop1': -5} - assert_fail(doc, schema) - - # document is not valid - # prop1 greater than 0 - doc = {'prop1': 1} - assert_fail(doc, schema) - - # document is not valid - doc = {'prop1': 5} - assert_fail(doc, schema) - - # document is not valid - doc = {'prop1': 11} - assert_fail(doc, schema) - - # document is not valid - # and equal to 15 - doc = {'prop1': 15} - assert_fail(doc, schema) - - -def test_anyof_allof(): - # prop1 can be any number outside of [0-10] - schema = { - 'prop1': { - 'allof': [ - {'anyof': [{'type': 'float'}, {'type': 'integer'}]}, - {'anyof': [{'min': 10}, {'max': 0}]}, - ] - } - } - - doc = {'prop1': 11} - assert_success(doc, schema) - doc = {'prop1': -1} - assert_success(doc, schema) - doc = {'prop1': 5} - assert_fail(doc, schema) - - doc = {'prop1': 11.5} - assert_success(doc, schema) - doc = {'prop1': -1.5} - assert_success(doc, schema) - doc = {'prop1': 5.5} - assert_fail(doc, schema) - - doc = {'prop1': '5.5'} - assert_fail(doc, schema) - - -def test_anyof_schema(validator): - # test that a list of schemas can be specified. - - valid_parts = [ - {'schema': {'model number': {'type': 'string'}, 'count': {'type': 'integer'}}}, - {'schema': {'serial number': {'type': 'string'}, 'count': {'type': 'integer'}}}, - ] - valid_item = {'type': ['dict', 'string'], 'anyof': valid_parts} - schema = {'parts': {'type': 'list', 'schema': valid_item}} - document = { - 'parts': [ - {'model number': 'MX-009', 'count': 100}, - {'serial number': '898-001'}, - 'misc', - ] - } - - # document is valid. each entry in 'parts' matches a type or schema - assert_success(document, schema, validator=validator) - - document['parts'].append({'product name': "Monitors", 'count': 18}) - # document is invalid. 'product name' does not match any valid schemas - assert_fail(document, schema, validator=validator) - - document['parts'].pop() - # document is valid again - assert_success(document, schema, validator=validator) - - document['parts'].append({'product name': "Monitors", 'count': 18}) - document['parts'].append(10) - # and invalid. numbers are not allowed. - - exp_child_errors = [ - (('parts', 3), ('parts', 'schema', 'anyof'), errors.ANYOF, valid_parts), - ( - ('parts', 4), - ('parts', 'schema', 'type'), - errors.BAD_TYPE, - ['dict', 'string'], - ), - ] - - _errors = assert_fail( - document, - schema, - validator=validator, - error=('parts', ('parts', 'schema'), errors.SEQUENCE_SCHEMA, valid_item), - child_errors=exp_child_errors, - ) - assert_not_has_error( - _errors, ('parts', 4), ('parts', 'schema', 'anyof'), errors.ANYOF, valid_parts - ) - - # tests errors.BasicErrorHandler's tree representation - v_errors = validator.errors - assert 'parts' in v_errors - assert 3 in v_errors['parts'][-1] - assert v_errors['parts'][-1][3][0] == "no definitions validate" - scope = v_errors['parts'][-1][3][-1] - assert 'anyof definition 0' in scope - assert 'anyof definition 1' in scope - assert scope['anyof definition 0'] == [{"product name": ["unknown field"]}] - assert scope['anyof definition 1'] == [{"product name": ["unknown field"]}] - assert v_errors['parts'][-1][4] == ["must be of ['dict', 'string'] type"] - - -def test_anyof_2(): - # these two schema should be the same - schema1 = { - 'prop': { - 'anyof': [ - {'type': 'dict', 'schema': {'val': {'type': 'integer'}}}, - {'type': 'dict', 'schema': {'val': {'type': 'string'}}}, - ] - } - } - schema2 = { - 'prop': { - 'type': 'dict', - 'anyof': [ - {'schema': {'val': {'type': 'integer'}}}, - {'schema': {'val': {'type': 'string'}}}, - ], - } - } - - doc = {'prop': {'val': 0}} - assert_success(doc, schema1) - assert_success(doc, schema2) - - doc = {'prop': {'val': '0'}} - assert_success(doc, schema1) - assert_success(doc, schema2) - - doc = {'prop': {'val': 1.1}} - assert_fail(doc, schema1) - assert_fail(doc, schema2) - - -def test_anyof_type(): - schema = {'anyof_type': {'anyof_type': ['string', 'integer']}} - assert_success({'anyof_type': 'bar'}, schema) - assert_success({'anyof_type': 23}, schema) - - -def test_oneof_schema(): - schema = { - 'oneof_schema': { - 'type': 'dict', - 'oneof_schema': [ - {'digits': {'type': 'integer', 'min': 0, 'max': 99}}, - {'text': {'type': 'string', 'regex': '^[0-9]{2}$'}}, - ], - } - } - assert_success({'oneof_schema': {'digits': 19}}, schema) - assert_success({'oneof_schema': {'text': '84'}}, schema) - assert_fail({'oneof_schema': {'digits': 19, 'text': '84'}}, schema) - - -def test_nested_oneof_type(): - schema = { - 'nested_oneof_type': {'valuesrules': {'oneof_type': ['string', 'integer']}} - } - assert_success({'nested_oneof_type': {'foo': 'a'}}, schema) - assert_success({'nested_oneof_type': {'bar': 3}}, schema) - - -def test_nested_oneofs(validator): - validator.schema = { - 'abc': { - 'type': 'dict', - 'oneof_schema': [ - { - 'foo': { - 'type': 'dict', - 'schema': {'bar': {'oneof_type': ['integer', 'float']}}, - } - }, - {'baz': {'type': 'string'}}, - ], - } - } - - document = {'abc': {'foo': {'bar': 'bad'}}} - - expected_errors = { - 'abc': [ - 'none or more than one rule validate', - { - 'oneof definition 0': [ - { - 'foo': [ - { - 'bar': [ - 'none or more than one rule validate', - { - 'oneof definition 0': [ - 'must be of integer type' - ], - 'oneof definition 1': ['must be of float type'], - }, - ] - } - ] - } - ], - 'oneof definition 1': [{'foo': ['unknown field']}], - }, - ] - } - - assert_fail(document, validator=validator) - assert validator.errors == expected_errors - - -def test_no_of_validation_if_type_fails(validator): - valid_parts = [ - {'schema': {'model number': {'type': 'string'}, 'count': {'type': 'integer'}}}, - {'schema': {'serial number': {'type': 'string'}, 'count': {'type': 'integer'}}}, - ] - validator.schema = {'part': {'type': ['dict', 'string'], 'anyof': valid_parts}} - document = {'part': 10} - _errors = assert_fail(document, validator=validator) - assert len(_errors) == 1 - - -def test_issue_107(validator): - schema = { - 'info': { - 'type': 'dict', - 'schema': {'name': {'type': 'string', 'required': True}}, - } - } - document = {'info': {'name': 'my name'}} - assert_success(document, schema, validator=validator) - - v = Validator(schema) - assert_success(document, schema, v) - # it once was observed that this behaves other than the previous line - assert v.validate(document) - - -def test_dont_type_validate_nulled_values(validator): - assert_fail({'an_integer': None}, validator=validator) - assert validator.errors == {'an_integer': ['null value not allowed']} - - -def test_dependencies_error(validator): - schema = { - 'field1': {'required': False}, - 'field2': {'required': True, 'dependencies': {'field1': ['one', 'two']}}, - } - validator.validate({'field2': 7}, schema) - exp_msg = errors.BasicErrorHandler.messages[ - errors.DEPENDENCIES_FIELD_VALUE.code - ].format(field='field2', constraint={'field1': ['one', 'two']}) - assert validator.errors == {'field2': [exp_msg]} - - -def test_dependencies_on_boolean_field_with_one_value(): - # https://github.com/pyeve/cerberus/issues/138 - schema = { - 'deleted': {'type': 'boolean'}, - 'text': {'dependencies': {'deleted': False}}, - } - try: - assert_success({'text': 'foo', 'deleted': False}, schema) - assert_fail({'text': 'foo', 'deleted': True}, schema) - assert_fail({'text': 'foo'}, schema) - except TypeError as e: - if str(e) == "argument of type 'bool' is not iterable": - raise AssertionError( - "Bug #138 still exists, couldn't use boolean in dependency " - "without putting it in a list.\n" - "'some_field': True vs 'some_field: [True]" - ) - else: - raise - - -def test_dependencies_on_boolean_field_with_value_in_list(): - # https://github.com/pyeve/cerberus/issues/138 - schema = { - 'deleted': {'type': 'boolean'}, - 'text': {'dependencies': {'deleted': [False]}}, - } - - assert_success({'text': 'foo', 'deleted': False}, schema) - assert_fail({'text': 'foo', 'deleted': True}, schema) - assert_fail({'text': 'foo'}, schema) - - -def test_document_path(): - class DocumentPathTester(Validator): - def _validate_trail(self, constraint, field, value): - """{'type': 'boolean'}""" - test_doc = self.root_document - for crumb in self.document_path: - test_doc = test_doc[crumb] - assert test_doc == self.document - - v = DocumentPathTester() - schema = {'foo': {'schema': {'bar': {'trail': True}}}} - document = {'foo': {'bar': {}}} - assert_success(document, schema, validator=v) - - -def test_excludes(): - schema = { - 'this_field': {'type': 'dict', 'excludes': 'that_field'}, - 'that_field': {'type': 'dict'}, - } - assert_success({'this_field': {}}, schema) - assert_success({'that_field': {}}, schema) - assert_success({}, schema) - assert_fail({'that_field': {}, 'this_field': {}}, schema) - - -def test_mutual_excludes(): - schema = { - 'this_field': {'type': 'dict', 'excludes': 'that_field'}, - 'that_field': {'type': 'dict', 'excludes': 'this_field'}, - } - assert_success({'this_field': {}}, schema) - assert_success({'that_field': {}}, schema) - assert_success({}, schema) - assert_fail({'that_field': {}, 'this_field': {}}, schema) - - -def test_required_excludes(): - schema = { - 'this_field': {'type': 'dict', 'excludes': 'that_field', 'required': True}, - 'that_field': {'type': 'dict', 'excludes': 'this_field', 'required': True}, - } - assert_success({'this_field': {}}, schema, update=False) - assert_success({'that_field': {}}, schema, update=False) - assert_fail({}, schema) - assert_fail({'that_field': {}, 'this_field': {}}, schema) - - -def test_multiples_exclusions(): - schema = { - 'this_field': {'type': 'dict', 'excludes': ['that_field', 'bazo_field']}, - 'that_field': {'type': 'dict', 'excludes': 'this_field'}, - 'bazo_field': {'type': 'dict'}, - } - assert_success({'this_field': {}}, schema) - assert_success({'that_field': {}}, schema) - assert_fail({'this_field': {}, 'that_field': {}}, schema) - assert_fail({'this_field': {}, 'bazo_field': {}}, schema) - assert_fail({'that_field': {}, 'this_field': {}, 'bazo_field': {}}, schema) - assert_success({'that_field': {}, 'bazo_field': {}}, schema) - - -def test_bad_excludes_fields(validator): - validator.schema = { - 'this_field': { - 'type': 'dict', - 'excludes': ['that_field', 'bazo_field'], - 'required': True, - }, - 'that_field': {'type': 'dict', 'excludes': 'this_field', 'required': True}, - } - assert_fail({'that_field': {}, 'this_field': {}}, validator=validator) - handler = errors.BasicErrorHandler - assert validator.errors == { - 'that_field': [ - handler.messages[errors.EXCLUDES_FIELD.code].format( - "'this_field'", field="that_field" - ) - ], - 'this_field': [ - handler.messages[errors.EXCLUDES_FIELD.code].format( - "'that_field', 'bazo_field'", field="this_field" - ) - ], - } - - -def test_boolean_is_not_a_number(): - # https://github.com/pyeve/cerberus/issues/144 - assert_fail({'value': True}, {'value': {'type': 'number'}}) - - -def test_min_max_date(): - schema = {'date': {'min': date(1900, 1, 1), 'max': date(1999, 12, 31)}} - assert_success({'date': date(1945, 5, 8)}, schema) - assert_fail({'date': date(1871, 5, 10)}, schema) - - -def test_dict_length(): - schema = {'dict': {'minlength': 1}} - assert_fail({'dict': {}}, schema) - assert_success({'dict': {'foo': 'bar'}}, schema) - - -def test_forbidden(): - schema = {'user': {'forbidden': ['root', 'admin']}} - assert_fail({'user': 'admin'}, schema) - assert_success({'user': 'alice'}, schema) - - -def test_forbidden_number(): - schema = {'amount': {'forbidden': (0, 0.0)}} - assert_fail({'amount': 0}, schema) - assert_fail({'amount': 0.0}, schema) - - -def test_mapping_with_sequence_schema(): - schema = {'list': {'schema': {'allowed': ['a', 'b', 'c']}}} - document = {'list': {'is_a': 'mapping'}} - assert_fail( - document, - schema, - error=( - 'list', - ('list', 'schema'), - errors.BAD_TYPE_FOR_SCHEMA, - schema['list']['schema'], - ), - ) - - -def test_sequence_with_mapping_schema(): - schema = {'list': {'schema': {'foo': {'allowed': ['a', 'b', 'c']}}, 'type': 'dict'}} - document = {'list': ['a', 'b', 'c']} - assert_fail(document, schema) - - -def test_type_error_aborts_validation(): - schema = {'foo': {'type': 'string', 'allowed': ['a']}} - document = {'foo': 0} - assert_fail( - document, schema, error=('foo', ('foo', 'type'), errors.BAD_TYPE, 'string') - ) - - -def test_dependencies_in_oneof(): - # https://github.com/pyeve/cerberus/issues/241 - schema = { - 'a': { - 'type': 'integer', - 'oneof': [ - {'allowed': [1], 'dependencies': 'b'}, - {'allowed': [2], 'dependencies': 'c'}, - ], - }, - 'b': {}, - 'c': {}, - } - assert_success({'a': 1, 'b': 'foo'}, schema) - assert_success({'a': 2, 'c': 'bar'}, schema) - assert_fail({'a': 1, 'c': 'foo'}, schema) - assert_fail({'a': 2, 'b': 'bar'}, schema) - - -def test_allow_unknown_with_oneof_rules(validator): - # https://github.com/pyeve/cerberus/issues/251 - schema = { - 'test': { - 'oneof': [ - { - 'type': 'dict', - 'allow_unknown': True, - 'schema': {'known': {'type': 'string'}}, - }, - {'type': 'dict', 'schema': {'known': {'type': 'string'}}}, - ] - } - } - # check regression and that allow unknown does not cause any different - # than expected behaviour for one-of. - document = {'test': {'known': 's'}} - validator(document, schema) - _errors = validator._errors - assert len(_errors) == 1 - assert_has_error( - _errors, 'test', ('test', 'oneof'), errors.ONEOF, schema['test']['oneof'] - ) - assert len(_errors[0].child_errors) == 0 - # check that allow_unknown is actually applied - document = {'test': {'known': 's', 'unknown': 'asd'}} - assert_success(document, validator=validator) - - -@mark.parametrize('constraint', (('Graham Chapman', 'Eric Idle'), 'Terry Gilliam')) -def test_contains(constraint): - validator = Validator({'actors': {'contains': constraint}}) - - document = {'actors': ('Graham Chapman', 'Eric Idle', 'Terry Gilliam')} - assert validator(document) - - document = {'actors': ('Eric idle', 'Terry Jones', 'John Cleese', 'Michael Palin')} - assert not validator(document) - assert errors.MISSING_MEMBERS in validator.document_error_tree['actors'] - missing_actors = validator.document_error_tree['actors'][ - errors.MISSING_MEMBERS - ].info[0] - assert any(x in missing_actors for x in ('Eric Idle', 'Terry Gilliam')) - - -def test_require_all_simple(): - schema = {'foo': {'type': 'string'}} - validator = Validator(require_all=True) - assert_fail( - {}, - schema, - validator, - error=('foo', '__require_all__', errors.REQUIRED_FIELD, True), - ) - assert_success({'foo': 'bar'}, schema, validator) - validator.require_all = False - assert_success({}, schema, validator) - assert_success({'foo': 'bar'}, schema, validator) - - -def test_require_all_override_by_required(): - schema = {'foo': {'type': 'string', 'required': False}} - validator = Validator(require_all=True) - assert_success({}, schema, validator) - assert_success({'foo': 'bar'}, schema, validator) - validator.require_all = False - assert_success({}, schema, validator) - assert_success({'foo': 'bar'}, schema, validator) - - schema = {'foo': {'type': 'string', 'required': True}} - validator.require_all = True - assert_fail( - {}, - schema, - validator, - error=('foo', ('foo', 'required'), errors.REQUIRED_FIELD, True), - ) - assert_success({'foo': 'bar'}, schema, validator) - validator.require_all = False - assert_fail( - {}, - schema, - validator, - error=('foo', ('foo', 'required'), errors.REQUIRED_FIELD, True), - ) - assert_success({'foo': 'bar'}, schema, validator) - - -@mark.parametrize( - "validator_require_all, sub_doc_require_all", - list(itertools.product([True, False], repeat=2)), -) -def test_require_all_override_by_subdoc_require_all( - validator_require_all, sub_doc_require_all -): - sub_schema = {"bar": {"type": "string"}} - schema = { - "foo": { - "type": "dict", - "require_all": sub_doc_require_all, - "schema": sub_schema, - } - } - validator = Validator(require_all=validator_require_all) - - assert_success({"foo": {"bar": "baz"}}, schema, validator) - if validator_require_all: - assert_fail({}, schema, validator) - else: - assert_success({}, schema, validator) - if sub_doc_require_all: - assert_fail({"foo": {}}, schema, validator) - else: - assert_success({"foo": {}}, schema, validator) - - -def test_require_all_and_exclude(): - schema = { - 'foo': {'type': 'string', 'excludes': 'bar'}, - 'bar': {'type': 'string', 'excludes': 'foo'}, - } - validator = Validator(require_all=True) - assert_fail( - {}, - schema, - validator, - errors=[ - ('foo', '__require_all__', errors.REQUIRED_FIELD, True), - ('bar', '__require_all__', errors.REQUIRED_FIELD, True), - ], - ) - assert_success({'foo': 'value'}, schema, validator) - assert_success({'bar': 'value'}, schema, validator) - assert_fail({'foo': 'value', 'bar': 'value'}, schema, validator) - validator.require_all = False - assert_success({}, schema, validator) - assert_success({'foo': 'value'}, schema, validator) - assert_success({'bar': 'value'}, schema, validator) - assert_fail({'foo': 'value', 'bar': 'value'}, schema, validator) - - -def test_allowed_when_passing_list_of_dicts(): - # https://github.com/pyeve/cerberus/issues/524 - doc = {'letters': [{'some': 'dict'}]} - schema = {'letters': {'type': 'list', 'allowed': ['a', 'b', 'c']}} - - assert_fail( - doc, - schema, - error=( - 'letters', - ('letters', 'allowed'), - errors.UNALLOWED_VALUES, - ['a', 'b', 'c'], - (({'some': 'dict'},),), - ), - ) diff --git a/tasks/vendoring/__init__.py b/tasks/vendoring/__init__.py index 4ec47b10..8facc5bf 100644 --- a/tasks/vendoring/__init__.py +++ b/tasks/vendoring/__init__.py @@ -315,6 +315,9 @@ def post_install_cleanup(ctx, vendor_dir): drop_dir(vendor_dir / "bin") drop_dir(vendor_dir / "tests") drop_dir(vendor_dir / "shutil_backports") + drop_dir(vendor_dir / "cerberus" / "tests") + drop_dir(vendor_dir / "cerberus" / "benchmarks") + remove_all(vendor_dir.glob("toml.py"))