From 90ea77961987da03188f5b9972631f89d20c4798 Mon Sep 17 00:00:00 2001 From: Julian Berman Date: Wed, 12 Jul 2023 11:38:44 +0200 Subject: [PATCH] Fix a regression with RefResolver-based resolution in newly created drafts We need a bit more state management to serve `RefResolver` until it's fully removed :/ (The handler here is simply to avoid needing to hit some remote reference.) Refs: https://github.com/python-jsonschema/jsonschema/issues/1061#issuecomment-1624266555 --- CHANGELOG.rst | 5 +++++ jsonschema/tests/test_validators.py | 22 ++++++++++++++++++++++ jsonschema/validators.py | 5 +++++ 3 files changed, 32 insertions(+) diff --git a/CHANGELOG.rst b/CHANGELOG.rst index e4a22946..5bae3bee 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -1,3 +1,8 @@ +v4.18.1 +======= + +* Fix a regression with ``jsonschema.RefResolver`` based resolution when used in combination with a custom validation dialect (via ``jsonschema.validators.create``). + v4.18.0 ======= diff --git a/jsonschema/tests/test_validators.py b/jsonschema/tests/test_validators.py index f7f54146..5a4f87f3 100644 --- a/jsonschema/tests/test_validators.py +++ b/jsonschema/tests/test_validators.py @@ -2373,6 +2373,28 @@ def test_pointer_within_schema_with_different_id(self): validator = validators.Draft7Validator(another, resolver=two) self.assertFalse(validator.is_valid({"maxLength": "foo"})) + def test_newly_created_validator_with_ref_resolver(self): + """ + See https://github.com/python-jsonschema/jsonschema/issues/1061#issuecomment-1624266555. + """ # noqa: E501 + + def handle(uri): + self.assertEqual(uri, "http://example.com/foo") + return {"type": "integer"} + + resolver = validators._RefResolver("", {}, handlers={"http": handle}) + Validator = validators.create( + meta_schema={}, + validators=validators.Draft4Validator.VALIDATORS, + ) + schema = {"$id": "http://example.com/bar", "$ref": "foo"} + validator = Validator(schema, resolver=resolver) + self.assertEqual( + (validator.is_valid({}), validator.is_valid(37)), + (False, True), + ) + + def sorted_errors(errors): def key(error): diff --git a/jsonschema/validators.py b/jsonschema/validators.py index bed919e2..b8a9c141 100644 --- a/jsonschema/validators.py +++ b/jsonschema/validators.py @@ -275,6 +275,11 @@ def __attrs_post_init__(self): resource = specification.create_resource(self.schema) self._resolver = registry.resolver_with_root(resource) + # REMOVEME: Legacy ref resolution state management. + push_scope = getattr(self._ref_resolver, "push_scope", None) + if push_scope is not None: + push_scope(id_of(self.schema)) + @classmethod def check_schema(cls, schema, format_checker=_UNSET): Validator = validator_for(cls.META_SCHEMA, default=cls)