diff --git a/CHANGELOG.md b/CHANGELOG.md
index b35ad65e..4f4c40a3 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -5,6 +5,7 @@
 - Ring fence SQLAlchemy dependency to a facade and integration tests.
 - Add tests for examples.
 - Add _from_str_ and _to_str_ to complement _from_dict_ and _to_dict_ for de-serializing and serializing from JSON.
+- Ring fence jsonschema dependency into a facade.
 
 ## Version 0.12.1 - 2020-01-12
 
diff --git a/open_alchemy/facades/__init__.py b/open_alchemy/facades/__init__.py
index 2f7710ef..76fedf12 100644
--- a/open_alchemy/facades/__init__.py
+++ b/open_alchemy/facades/__init__.py
@@ -1,5 +1,6 @@
 """Facades for ringfenced modules."""
 # pylint: disable=useless-import-alias
 
+from . import jsonschema as jsonschema
 from . import models as models
 from . import sqlalchemy as sqlalchemy
diff --git a/open_alchemy/facades/jsonschema/__init__.py b/open_alchemy/facades/jsonschema/__init__.py
new file mode 100644
index 00000000..b1ac6e30
--- /dev/null
+++ b/open_alchemy/facades/jsonschema/__init__.py
@@ -0,0 +1,48 @@
+"""Facade for jsonschema."""
+
+import functools
+import json
+import typing
+
+import jsonschema
+
+# Re mapping values
+ValidationError = jsonschema.ValidationError
+validate = jsonschema.validate  # pylint: disable=invalid-name
+
+
+def _filename_to_dict(filename: str) -> typing.Dict:
+    """
+    Map filename for a JSON file to the de-serialized dictionary.
+
+    Args:
+        filename: The name of the JSON file.
+
+    Returns:
+        The de-serialized contents of the file as a dictionary.
+
+    """
+    with open(filename) as in_file:
+        json_dict = json.loads(in_file.read())
+    return json_dict
+
+
+def resolver(
+    *filenames: str,
+) -> typing.Tuple[
+    jsonschema.RefResolver, typing.Tuple[typing.Dict[str, typing.Any], ...]
+]:
+    """
+    Create resolver for references to schemas in another file.
+
+    Args:
+        filenames: The names for the files to add to the resolver.
+
+    Returns:
+        The resolver and the underlying schemas as a dictionary.
+
+    """
+    schema_dicts = tuple(map(_filename_to_dict, filenames))
+    initial: typing.Dict[str, typing.Any] = {}
+    merged_schema = functools.reduce(lambda x, y: {**x, **y}, schema_dicts, initial)
+    return jsonschema.RefResolver.from_schema(merged_schema), schema_dicts
diff --git a/open_alchemy/helpers/get_ext_prop/__init__.py b/open_alchemy/helpers/get_ext_prop/__init__.py
index 4ebb4523..382f678b 100644
--- a/open_alchemy/helpers/get_ext_prop/__init__.py
+++ b/open_alchemy/helpers/get_ext_prop/__init__.py
@@ -4,19 +4,14 @@ import json
 import os
 import typing
 
-import jsonschema
-
 from open_alchemy import exceptions
+from open_alchemy import facades
 
 _DIRECTORY = os.path.dirname(__file__)
 _SCHEMAS_FILE = os.path.join(_DIRECTORY, "extension-schemas.json")
-with open(_SCHEMAS_FILE) as in_file:
-    _SCHEMAS = json.load(in_file)
 _COMMON_SCHEMAS_FILE = os.path.join(_DIRECTORY, "common-schemas.json")
-with open(_COMMON_SCHEMAS_FILE) as in_file:
-    _COMMON_SCHEMAS = json.load(in_file)
-_resolver = jsonschema.RefResolver.from_schema(  # pylint: disable=invalid-name
-    {**_COMMON_SCHEMAS, **_SCHEMAS}
+_resolver, (_SCHEMAS, _) = facades.jsonschema.resolver(  # pylint: disable=invalid-name
+    _SCHEMAS_FILE, _COMMON_SCHEMAS_FILE
 )
 
 
@@ -49,8 +44,8 @@ def get_ext_prop(
 
     schema = _SCHEMAS.get(name)
     try:
-        jsonschema.validate(instance=value, schema=schema, resolver=_resolver)
-    except jsonschema.ValidationError:
+        facades.jsonschema.validate(instance=value, schema=schema, resolver=_resolver)
+    except facades.jsonschema.ValidationError:
         raise exceptions.MalformedExtensionPropertyError(
             f"The value of the {json.dumps(name)} extension property is not "
             "valid. "
diff --git a/open_alchemy/table_args/factory.py b/open_alchemy/table_args/factory.py
index 19703d6b..eaef2338 100644
--- a/open_alchemy/table_args/factory.py
+++ b/open_alchemy/table_args/factory.py
@@ -5,20 +5,19 @@ import json
 import os
 import typing
 
-import jsonschema
 from sqlalchemy import schema
 
 from open_alchemy import exceptions
+from open_alchemy import facades
 from open_alchemy import types
 
 _DIRECTORY = os.path.dirname(__file__)
 _PATHS = ("..", "helpers", "get_ext_prop")
 _COMMON_SCHEMAS_FILE = os.path.join(_DIRECTORY, *_PATHS, "common-schemas.json")
-with open(_COMMON_SCHEMAS_FILE) as in_file:
-    _COMMON_SCHEMAS = json.load(in_file)
-_resolver = jsonschema.RefResolver.from_schema(  # pylint: disable=invalid-name
-    _COMMON_SCHEMAS
-)
+(
+    _resolver,  # pylint: disable=invalid-name
+    (_COMMON_SCHEMAS,),
+) = facades.jsonschema.resolver(_COMMON_SCHEMAS_FILE)
 
 
 def _spec_to_schema_name(
@@ -39,15 +38,15 @@ def _spec_to_schema_name(
 
     """
     if schema_names is None:
-        schema_names = _COMMON_SCHEMAS.keys()
+        schema_names = list(_COMMON_SCHEMAS.keys())
 
     for name in schema_names:
         try:
-            jsonschema.validate(
+            facades.jsonschema.validate(
                 instance=spec, schema=_COMMON_SCHEMAS[name], resolver=_resolver
             )
             return name
-        except jsonschema.ValidationError:
+        except facades.jsonschema.ValidationError:
             continue
     raise exceptions.SchemaNotFoundError("Specification did not match any schemas.")
 
diff --git a/open_alchemy/utility_base.py b/open_alchemy/utility_base.py
index adaadc52..afa5552e 100644
--- a/open_alchemy/utility_base.py
+++ b/open_alchemy/utility_base.py
@@ -6,8 +6,6 @@ import json
 import sys
 import typing
 
-import jsonschema
-
 from . import exceptions
 from . import facades
 from . import helpers
@@ -134,8 +132,8 @@ class UtilityBase:
         # Check dictionary
         schema = cls._get_schema()
         try:
-            jsonschema.validate(instance=kwargs, schema=schema)
-        except jsonschema.ValidationError:
+            facades.jsonschema.validate(instance=kwargs, schema=schema)
+        except facades.jsonschema.ValidationError:
             raise exceptions.MalformedModelDictionaryError(
                 "The dictionary passed to from_dict is not a valid instance of the "
                 "model schema. "

Ring fence jsonschema
As a developer I want to have a shallow dependency on jsonschema so that it can be switched out for something else in the future.

At the moment jsonschema is deep linked into the code. There should be a module with an interface that abstracts away jasonschema behind an interface so that something else could be used in the future.
diff --git a/tests/open_alchemy/facades/test_jsonschema.py b/tests/open_alchemy/facades/test_jsonschema.py
new file mode 100644
index 00000000..93b1fd0e
--- /dev/null
+++ b/tests/open_alchemy/facades/test_jsonschema.py
@@ -0,0 +1,79 @@
+"""Tests for jsonschema facade."""
+
+import jsonschema
+import pytest
+
+from open_alchemy import facades
+
+
+@pytest.mark.facade
+def test_filename_to_dict(tmp_path):
+    """
+    GIVEN file with JSON contents
+    WHEN _filename_to_dict is called with the name of the file
+    THEN the dictionary contents of the file are returned.
+    """
+    # pylint: disable=protected-access
+    # Create file
+    directory = tmp_path / "json"
+    directory.mkdir()
+    json_file = directory / "dict.json"
+    json_file.write_text('{"key": "value"}')
+
+    returned_dict = facades.jsonschema._filename_to_dict(str(json_file))
+
+    assert returned_dict == {"key": "value"}
+
+
+@pytest.mark.facade
+def test_resolver_single(tmp_path):
+    """
+    GIVEN single file with schema, schema that references that schema and instance of
+        the schema
+    WHEN resolver is created and used to validate the instance
+    THEN no exceptions are raised and the referenced schema is returned as a dictionary.
+    """
+    # Create file
+    directory = tmp_path / "json"
+    directory.mkdir()
+    json_file = directory / "dict.json"
+    json_file.write_text('{"RefSchema": {"type": "string"}}')
+    schema = {"$ref": "#/RefSchema"}
+    instance = "test"
+
+    resolver, (schema_dict,) = facades.jsonschema.resolver(str(json_file))
+    jsonschema.validate(instance, schema, resolver=resolver)
+    assert schema_dict == {"RefSchema": {"type": "string"}}
+
+
+@pytest.mark.facade
+def test_resolver_multiple(tmp_path):
+    """
+    GIVEN multiple files with schema, schema that references those schemas and instance
+        of the schema
+    WHEN resolver is created and used to validate the instance
+    THEN no exceptions are raised and the referenced schemas are returned as
+        dictionaries.
+    """
+    # Create file
+    directory = tmp_path / "json"
+    directory.mkdir()
+    json_file1 = directory / "dict1.json"
+    json_file1.write_text('{"RefSchema1": {"type": "string"}}')
+    json_file2 = directory / "dict2.json"
+    json_file2.write_text('{"RefSchema2": {"type": "integer"}}')
+    schema = {
+        "type": "object",
+        "properties": {
+            "key1": {"$ref": "#/RefSchema1"},
+            "key2": {"$ref": "#/RefSchema2"},
+        },
+    }
+    instance = {"key1": "value 1", "key2": 1}
+
+    resolver, (schema1_dict, schema2_dict) = facades.jsonschema.resolver(
+        str(json_file1), str(json_file2)
+    )
+    jsonschema.validate(instance, schema, resolver=resolver)
+    assert schema1_dict == {"RefSchema1": {"type": "string"}}
+    assert schema2_dict == {"RefSchema2": {"type": "integer"}}

pip install -e .[dev,test]
parse_log_pytest
pytest
pytest pytest-cov
3.8.0
pytest --no-header -rA --tb=line --color=no -p no:cacheprovider -W ignore::DeprecationWarning
alabaster==0.7.13
alembic==1.14.1
anyio==4.5.2
asgiref==3.8.1
astroid==3.2.4
attrs==25.3.0
babel==2.17.0
bandit==1.7.10
black==24.8.0
blinker==1.8.2
cachetools==5.5.2
certifi==2025.1.31
cfgv==3.4.0
chardet==5.2.0
charset-normalizer==3.4.1
click==8.1.8
colorama==0.4.6
connexion==3.2.0
coverage==7.6.1
dill==0.3.9
distlib==0.3.9
doc8==1.1.2
docutils==0.20.1
exceptiongroup @ file:///croot/exceptiongroup_1706031385326/work
filelock==3.16.1
flake8==5.0.4
Flask==3.0.3
Flask-SQLAlchemy==3.1.1
greenlet==3.1.1
h11==0.14.0
httpcore==1.0.7
httpx==0.28.1
identify==2.6.1
idna==3.10
imagesize==1.4.1
importlib-resources==5.13.0
importlib_metadata==8.5.0
inflection==0.5.1
iniconfig @ file:///home/linux1/recipes/ci/iniconfig_1610983019677/work
isort==5.13.2
itsdangerous==2.2.0
Jinja2==3.1.6
jsonschema==4.23.0
jsonschema-specifications==2023.12.1
Mako==1.3.9
markdown-it-py==3.0.0
MarkupSafe==2.1.5
mccabe==0.7.0
mdurl==0.1.2
mypy==1.14.1
mypy-extensions==1.0.0
nodeenv==1.9.1
-e git+https://github.com/jdkandersson/OpenAlchemy.git@1172530614fe0c92ffb350d7ea6773b46057b4b8#egg=OpenAlchemy
packaging==24.2
pathspec==0.12.1
pbr==6.1.1
pkgutil_resolve_name==1.3.10
platformdirs==4.3.6
pluggy==1.5.0
pre-commit==3.5.0
pycodestyle==2.9.1
pydocstyle==6.3.0
pyflakes==2.5.0
Pygments==2.19.1
pylint==3.2.7
pyproject-api==1.8.0
pytest @ file:///croot/pytest_1717793244625/work
pytest-bandit==0.6.1
pytest-cov==5.0.0
pytest-flake8==1.2.2
pytest-flask==1.3.0
pytest-flask-sqlalchemy==1.1.0
pytest-mock==3.14.0
pytest-randomly==3.15.0
python-multipart==0.0.20
pytz==2025.2
PyYAML==6.0.2
referencing==0.35.1
requests==2.32.3
restructuredtext_lint==1.4.0
rich==14.0.0
rpds-py==0.20.1
sniffio==1.3.1
snowballstemmer==2.2.0
Sphinx==7.1.2
sphinxcontrib-applehelp==1.0.4
sphinxcontrib-devhelp==1.0.2
sphinxcontrib-htmlhelp==2.0.1
sphinxcontrib-jsmath==1.0.1
sphinxcontrib-qthelp==1.0.3
sphinxcontrib-serializinghtml==1.1.5
SQLAlchemy==2.0.40
starlette==0.44.0
stevedore==5.3.0
swagger_ui_bundle==1.1.0
tomli==2.2.1
tomlkit==0.13.2
tox==4.25.0
tox-pyenv==1.1.0
typeguard==4.4.0
typing_extensions==4.13.0
urllib3==2.2.3
virtualenv==20.29.3
Werkzeug==3.0.6
zipp==3.20.2

name: OpenAlchemy
channels:
  - defaults
  - https://repo.anaconda.com/pkgs/main
  - https://repo.anaconda.com/pkgs/r
  - conda-forge
dependencies:
  - _libgcc_mutex=0.1=main
  - _openmp_mutex=5.1=1_gnu
  - ca-certificates=2025.2.25=h06a4308_0
  - exceptiongroup=1.2.0=py38h06a4308_0
  - iniconfig=1.1.1=pyhd3eb1b0_0
  - libedit=3.1.20230828=h5eee18b_0
  - libffi=3.2.1=hf484d3e_1007
  - libgcc-ng=11.2.0=h1234567_1
  - libgomp=11.2.0=h1234567_1
  - libstdcxx-ng=11.2.0=h1234567_1
  - ncurses=6.4=h6a678d5_0
  - openssl=1.1.1w=h7f8727e_0
  - pip=24.2=py38h06a4308_0
  - pytest=7.4.4=py38h06a4308_0
  - python=3.8.0=h0371630_2
  - readline=7.0=h7b6447c_5
  - setuptools=75.1.0=py38h06a4308_0
  - sqlite=3.33.0=h62c20be_0
  - tk=8.6.14=h39e8969_0
  - wheel=0.44.0=py38h06a4308_0
  - xz=5.6.4=h5eee18b_1
  - zlib=1.2.13=h5eee18b_1
  - pip:
      - alabaster==0.7.13
      - alembic==1.14.1
      - anyio==4.5.2
      - asgiref==3.8.1
      - astroid==3.2.4
      - attrs==25.3.0
      - babel==2.17.0
      - bandit==1.7.10
      - black==24.8.0
      - blinker==1.8.2
      - cachetools==5.5.2
      - certifi==2025.1.31
      - cfgv==3.4.0
      - chardet==5.2.0
      - charset-normalizer==3.4.1
      - click==8.1.8
      - colorama==0.4.6
      - connexion==3.2.0
      - coverage==7.6.1
      - dill==0.3.9
      - distlib==0.3.9
      - doc8==1.1.2
      - docutils==0.20.1
      - filelock==3.16.1
      - flake8==5.0.4
      - flask==3.0.3
      - flask-sqlalchemy==3.1.1
      - greenlet==3.1.1
      - h11==0.14.0
      - httpcore==1.0.7
      - httpx==0.28.1
      - identify==2.6.1
      - idna==3.10
      - imagesize==1.4.1
      - importlib-metadata==8.5.0
      - importlib-resources==5.13.0
      - inflection==0.5.1
      - isort==5.13.2
      - itsdangerous==2.2.0
      - jinja2==3.1.6
      - jsonschema==4.23.0
      - jsonschema-specifications==2023.12.1
      - mako==1.3.9
      - markdown-it-py==3.0.0
      - markupsafe==2.1.5
      - mccabe==0.7.0
      - mdurl==0.1.2
      - mypy==1.14.1
      - mypy-extensions==1.0.0
      - nodeenv==1.9.1
      - packaging==24.2
      - pathspec==0.12.1
      - pbr==6.1.1
      - pkgutil-resolve-name==1.3.10
      - platformdirs==4.3.6
      - pluggy==1.5.0
      - pre-commit==3.5.0
      - pycodestyle==2.9.1
      - pydocstyle==6.3.0
      - pyflakes==2.5.0
      - pygments==2.19.1
      - pylint==3.2.7
      - pyproject-api==1.8.0
      - pytest-bandit==0.6.1
      - pytest-cov==5.0.0
      - pytest-flake8==1.2.2
      - pytest-flask==1.3.0
      - pytest-flask-sqlalchemy==1.1.0
      - pytest-mock==3.14.0
      - pytest-randomly==3.15.0
      - python-multipart==0.0.20
      - pytz==2025.2
      - pyyaml==6.0.2
      - referencing==0.35.1
      - requests==2.32.3
      - restructuredtext-lint==1.4.0
      - rich==14.0.0
      - rpds-py==0.20.1
      - sniffio==1.3.1
      - snowballstemmer==2.2.0
      - sphinx==7.1.2
      - sphinxcontrib-applehelp==1.0.4
      - sphinxcontrib-devhelp==1.0.2
      - sphinxcontrib-htmlhelp==2.0.1
      - sphinxcontrib-jsmath==1.0.1
      - sphinxcontrib-qthelp==1.0.3
      - sphinxcontrib-serializinghtml==1.1.5
      - sqlalchemy==2.0.40
      - starlette==0.44.0
      - stevedore==5.3.0
      - swagger-ui-bundle==1.1.0
      - tomli==2.2.1
      - tomlkit==0.13.2
      - tox==4.25.0
      - tox-pyenv==1.1.0
      - typeguard==4.4.0
      - typing-extensions==4.13.0
      - urllib3==2.2.3
      - virtualenv==20.29.3
      - werkzeug==3.0.6
      - zipp==3.20.2
prefix: /opt/conda/envs/OpenAlchemy

tests/open_alchemy/facades/test_jsonschema.py::test_filename_to_dict tests/open_alchemy/facades/test_jsonschema.py::test_resolver_multiple tests/open_alchemy/facades/test_jsonschema.py::test_resolver_single
tests/open_alchemy/facades/test_jsonschema.py::flake-8::FLAKE8
CHANGELOG.md open_alchemy/table_args/factory.py open_alchemy/helpers/get_ext_prop/__init__.py open_alchemy/utility_base.py open_alchemy/facades/__init__.py open_alchemy/facades/jsonschema/__init__.py
CHANGELOG.md open_alchemy/table_args/factory.py open_alchemy/helpers/get_ext_prop/__init__.py open_alchemy/utility_base.py open_alchemy/facades/__init__.py open_alchemy/facades/jsonschema/__init__.py