Skip to main content

PyPI version shields.io PyPI pyversions Ruff Checked with mypy

GHGA JSON Subschema

Note: This is a fork of IBM/jsonsubschema maintained by the German Human Genome-Phenome Archive (GHGA). It was created to bring in necessary fixes, updates, and functionality required by GHGA-related projects.

ghga-jsonsubschema checks if one JSON schema is a subschema (subtype) of another.

For any two JSON schemas s1 and s2, s1 <: s2 (reads s1 is subschema/subtype of s2) if every JSON document instance that validates against s1 also validates against s2.

jsonsubschema is very useful in analysing schema evolution and ensuring that newer schema versions are backward compatible. jsonsubschema also enables static type checking on different components of a system that uses JSON schema to describe data interfaces among the system's different components.

For a practical overview of the architecture, purpose, and usage of this library, please see DETAILS.md. For the formal foundations and deep technical details, please refer to the ISSTA 2021 paper by Andrew Habib, Avraham Shinnar, Martin Hirzel, and Michael Pradel, the original authors of this library.

Installation

Requirements

  • Python 3.11+

Install from PyPI

pip install ghga-jsonsubschema

Install from source

The unreleased version can be installed straight from the monorepo, without cloning it:

pip install "git+https://github.com/ghga-de/ghga.git#subdirectory=libs/ghga-jsonsubschema"

Running subschema

JSON subschema provides two usage interfaces:

CLI interface

First, create two JSON schema examples by executing the following:

echo '{"type": ["null", "string"]}' > s1.json
echo '{"type": ["string", "null"], "not": {"enum": [""]}}' > s2.json

Then, invoke the CLI by executing:

python -m jsonsubschema s2.json s1.json

Python API

from jsonsubschema import is_subschema


def main():
    s1 = {"type": "integer"}
    s2 = {"type": ["integer", "string"]}

    print(f"LHS <: RHS {is_subschema(s1, s2)}")


if __name__ == "__main__":
    main()

Development

This package is developed in the GHGA monorepo, where it lives in libs/ghga-jsonsubschema. Clone that repository and work inside this package's directory:

git clone https://github.com/ghga-de/ghga.git
cd ghga/libs/ghga-jsonsubschema
uv sync --extra dev
uv run pre-commit install

All further commands should be run from this directory as well.

Run the test suite:

uv run pytest tests/

Run the test suite with coverage:

uv run pytest --cov tests/

Note that uv sync uses the monorepo's shared environment and lockfile at the repository root, but installs only this package and its dependencies. To work on the monorepo as a whole, with all of its packages installed, run just sync from the repository root; its README describes the available tasks.

Changes made by GHGA

This fork is based on version 0.0.8 of IBM/jsonsubschema and introduces additional changes:

  • Public API names have been changed to align with PEP 8.
  • The minimum required Python version is now 3.11.
  • Packaging uses more modern conventions.
  • Tests have been converted from unittest to pytest.
  • An empty enum is now treated as an uninhabited schema.
  • Bugs inherited from upstream have been fixed: negating a numeric schema now respects exclusiveMinimum/exclusiveMaximum, intersecting numeric schemas no longer drops exclusive bounds, nested anyOf unions are now fully flattened (previously, adjacent nested unions could make two equivalent schemas compare as unrelated), and arrays with at most one item are now recognized as satisfying uniqueItems.
  • The dependencies keyword (which upstream silently ignores) now raises exceptions.UnsupportedDependencies instead of potentially returning unsound verdicts.
  • Negating an integer schema (e.g. {"not": {"type": "integer", "minimum": 10, "maximum": 20}}) now yields the exact complement — including the non-integer numbers, represented internally as {"type": "number", "not": {"multipleOf": 1}} — where upstream silently computes a too-small complement that can yield unsound verdicts. Only negating a numeric schema with a non-trivial multipleOf (whose complement would contain the non-multiples) raises exceptions.UnsupportedNegatedNumeric instead of returning potentially wrong results.
  • Uninhabited numeric schemas whose multipleOf has no multiple within the schema's bounds are now recognized as such, and subtype checks of numeric schemas admitting a single value are now exact (e.g. {"type": "integer"} is now a subschema of {"type": "number", "multipleOf": 0.5}).

License

This repository is distributed under the terms of the Apache 2.0 License, see LICENSE.txt.

Metadata

Release files for ghga-jsonsubschema 0.2.1

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for ghga-jsonsubschema 0.2.1
File Size Uploaded
ghga_jsonsubschema-0.2.1.tar.gz 55.3 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for ghga-jsonsubschema 0.2.1
File Interpreter ABI Platform
ghga_jsonsubschema-0.2.1-py3-none-any.whl Python 3 none any Details

Total release size: 91.6 kB

Release files / ghga_jsonsubschema-0.2.1.tar.gz

Download URL ghga_jsonsubschema-0.2.1.tar.gz
Size 55.3 kB
Tags Source
SHA-256 checksum
How to use checksums
56fbde2bb86ff5dfc3718974c5fb079e3dd0cbd6901bdd375f53d2cee3666724
BLAKE2b-256 checksum
How to use checksums
55f4bf6792afb9fad86b89c25a8242a8c2bbaec10aa88f55d31462279c34c046
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via uv/0.12.21 {"installer":{"name":"uv","version":"0.12.21","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release files / ghga_jsonsubschema-0.2.1-py3-none-any.whl

Download URL ghga_jsonsubschema-0.2.1-py3-none-any.whl
Size 36.3 kB
Tags Python 3
SHA-256 checksum
How to use checksums
041afc1d60f2ea9c8d344129af7874f3a2144028d2a4b81dcd1ef097a6379bb5
BLAKE2b-256 checksum
How to use checksums
b6fe8af7008f6ff22ceae7fb2b38828794ea6b62fd35f8bdcd066f22a6cfd548
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via uv/0.12.21 {"installer":{"name":"uv","version":"0.12.21","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release history Release notifications | RSS feed

This release

0.2.1 This release

2 release files

0.2.0

2 release files

0.1.2

2 release files

0.1.1

2 release files

0.1.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page