Validator — validate_schema()
The validator module checks SDF data.json payloads against their schema.json and validates meta.json field structure. Validation is synchronous, offline, and raises no network requests.
Import
from sdf import validate_schema, validate_metavalidate_schema(data, schema)
Validates a data dict against a JSON Schema Draft 2020-12 schema.
validate_schema(data: dict, schema: dict) -> ValidationResult| Parameter | Type | Description |
|---|---|---|
data | dict | The data.json payload to validate |
schema | dict | JSON Schema Draft 2020-12 |
Returns: ValidationResult
Does not raise on validation failure — use the valid field on the returned object to check the result.
ValidationResult
@dataclassclass ValidationResult: valid: bool errors: list[ValidationError]@dataclassclass ValidationError: path: str # JSON pointer to the failing field message: str # Human-readable error message schema_path: str # Path within the schema that triggered the errorBasic usage
from sdf import validate_schema
schema = { "$schema": "https://json-schema.org/draft/2020-12/schema", "type": "object", "required": ["invoice_number", "total"], "properties": { "invoice_number": {"type": "string"}, "total": { "type": "object", "required": ["amount", "currency"], "properties": { "amount": {"type": "string"}, "currency": {"type": "string", "pattern": "^[A-Z]{3}$"}, }, }, },}
data = { "invoice_number": "INV-2026-001", "total": {"amount": "1250.00", "currency": "EUR"},}
result = validate_schema(data, schema)
if result.valid: print("Document is valid")else: for error in result.errors: print(f" {error.path}: {error.message}")Handling validation errors
from sdf import validate_schema
# Missing required field and wrong currency formatdata = { "total": {"amount": "1250.00", "currency": "eur"}, # lowercase — fails pattern}
result = validate_schema(data, schema)
print(result.valid) # Falseprint(len(result.errors)) # 2
for error in result.errors: print(f"Path: {error.path}") print(f" {error.message}")
# Path: /invoice_number# 'invoice_number' is a required property# Path: /total/currency# 'eur' does not match '^[A-Z]{3}$'Validating a parsed SDF document
After reading a document with parse_sdf(), validate data against the embedded schema:
from sdf import parse_sdf, validate_schemafrom sdf.errors import SDFError
with open("invoice.sdf", "rb") as f: result = parse_sdf(f.read())
validation = validate_schema(result.data, result.schema)
if not validation.valid: raise SDFError( "SDF_ERROR_SCHEMA_MISMATCH", f"Document data does not satisfy its embedded schema: " + "; ".join(f"{e.path}: {e.message}" for e in validation.errors), )
print("Document data is valid")validate_meta(meta)
Validates an SDFMeta object for required fields and correct value formats.
validate_meta(meta: SDFMeta) -> NoneRaises: SDFError with code SDF_ERROR_INVALID_META if any required field is missing or malformed.
from sdf import SDFMeta, validate_metafrom sdf.errors import SDFError
meta = SDFMeta( issuer="Acme Corp", issuer_id="DE123456789", document_type="invoice",)
try: validate_meta(meta) print("Meta is valid")except SDFError as e: print(f"Invalid meta: {e}")validate_meta() checks:
issueris non-emptydocument_typeis non-emptydocument_idis a valid UUID v4 (auto-generated bySDFMeta, so this will always pass unless manually overridden)sdf_versionis a supported version stringissued_atis a valid ISO 8601 datetime string (auto-generated, always passes unless manually overridden)
Offline operation
All validation uses the schema.json embedded inside the .sdf archive. External $ref URIs in schemas are not fetched. If a schema references an external URL, validation will fail with a schema compilation error — not silently succeed.
This is intentional: SDF documents must be fully self-validating. A document produced today must be validatable 20 years from now without any network access.