Preflight
Problem
Tombi does not currently resolve an embedded schema resource by its canonical $id within a JSON Schema Compound Schema Document.
Shoko uses two different resource identifiers for a package:
shoko://<namespace>/<name> is a versionless dependency alias generated from a lockfile.
shoko://<namespace>/<name>/versions/<version>/schema.json is the immutable canonical $id of a published schema.
When a Compound Schema Document contains both resources, Tombi should resolve the versionless alias to the locked, versioned embedded resource. It currently attempts to load a shoko:// reference as an external document instead.
This prevents standards-based, offline distribution of resolved schema dependency graphs. A direct JSON Pointer such as #/$defs/dependency works, but it couples references to the generated bundle layout instead of preserving each resource's canonical identity.
Proposal
Implement JSON Schema resource indexing and reference resolution for Compound Schema Documents, following Draft 2020-12 URI and scope semantics.
Minimal version-resolved example:
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"$ref": "shoko://python/pyproject",
"$defs": {
"python-pyproject-alias": {
"$id": "shoko://python/pyproject",
"$ref": "shoko://python/pyproject/versions/1.0.0/schema.json"
},
"python-pyproject-1.0.0": {
"$schema": "https://json-schema.org/draft/2020-12/schema",
"$id": "shoko://python/pyproject/versions/1.0.0/schema.json",
"type": "object",
"properties": {
"tool": {
"type": "object",
"properties": {
"tombi": {
"$ref": "shoko://tombi-toml/tombi"
}
},
"required": ["tombi"]
}
},
"required": ["tool"]
},
"tombi-alias": {
"$id": "shoko://tombi-toml/tombi",
"$ref": "shoko://tombi-toml/tombi/versions/1.2.3/schema.json"
},
"tombi-1.2.3": {
"$schema": "https://json-schema.org/draft/2020-12/schema",
"$id": "shoko://tombi-toml/tombi/versions/1.2.3/schema.json",
"type": "object",
"properties": {
"strict": {
"type": "boolean",
"description": "Enable strict validation."
}
},
"required": ["strict"],
"additionalProperties": false
}
}
}
For this TOML:
Tombi should resolve this chain entirely inside the loaded document:
shoko://python/pyproject
-> shoko://python/pyproject/versions/1.0.0/schema.json
-> shoko://tombi-toml/tombi
-> shoko://tombi-toml/tombi/versions/1.2.3/schema.json
It should report that strict must be a boolean without performing any external shoko:// fetch. No Shoko-specific URI handler should be required: these URIs are opaque canonical identifiers once their resources are present in the loaded Compound Schema Document.
Required behavior
- Discover schema resources introduced by non-fragment
$id values throughout a loaded schema document.
- Resolve each resource's canonical URI against the correct enclosing base URI.
- Consult the loaded document's embedded-resource index before attempting an external fetch.
- Maintain independent dialect, base URI, and anchor scopes for each embedded resource.
- Support nested embedded resources and references between sibling or transitive embedded resources.
- Resolve
$anchor, $dynamicAnchor, $ref, and $dynamicRef using their correct resource and dynamic scopes.
- Reject duplicate canonical resource URIs deterministically instead of silently choosing one.
- Use the same resolution model for validation, completion, hover, go-to-definition, and document links.
- Preserve normal external
file, http, and https resolution when a referenced resource is not embedded.
- Work offline when every referenced resource is present in the Compound Schema Document.
Acceptance criteria
- The example above reports that
tool.tombi.strict = 42 is not a boolean.
- No fetcher is called for either the versionless or versioned embedded
shoko:// resources.
- Validation, completion, hover, go-to-definition, and document links have regression tests using an embedded resource.
- Tests cover:
- absolute and relative
$id;
- versionless alias resources pointing to immutable versioned resources;
- sibling and nested embedded resources;
- references from an embedded resource back to another resource;
- mixed dialect resources with an explicit
$schema;
$anchor and $dynamicRef/$dynamicAnchor scope;
- duplicate canonical resource IDs;
- offline operation;
- fallback to an external resource when no embedded resource matches.
- Existing direct JSON Pointer references such as
#/$defs/name continue to work.
Alternatives
Shoko could rewrite every dependency reference to a generated #/$defs/... JSON Pointer or introduce a resolver-specific file format. That would work with Tombi today, but it would create a non-standard coupling between schema identity and generated bundle layout. Supporting Compound Schema Documents keeps the resolved artifact entirely within JSON Schema semantics.
Additional context
- JSON Schema 2020-12 guidance: Bundling
- JSON Schema 2020-12 Core specification: Schema Resources
- VS Code's JSON language service added embedded-resource indexing in microsoft/vscode-json-languageservice@24c3800.
- Verified compatibility boundary from the Shoko investigation:
- VS Code JSON /
vscode-json-languageservice >= 6.0.0-next.2: supported.
yaml-language-server >= 1.23.0: supported.
- The corrected versionless-alias-to-versioned-resource example was tested successfully with
vscode-json-languageservice 6.0.0-next.3 and yaml-language-server 1.24.0.
- Tombi currently resolves
#/$defs/... but not an absolute $id for an embedded resource.
Preflight
Problem
Tombi does not currently resolve an embedded schema resource by its canonical
$idwithin a JSON Schema Compound Schema Document.Shoko uses two different resource identifiers for a package:
shoko://<namespace>/<name>is a versionless dependency alias generated from a lockfile.shoko://<namespace>/<name>/versions/<version>/schema.jsonis the immutable canonical$idof a published schema.When a Compound Schema Document contains both resources, Tombi should resolve the versionless alias to the locked, versioned embedded resource. It currently attempts to load a
shoko://reference as an external document instead.This prevents standards-based, offline distribution of resolved schema dependency graphs. A direct JSON Pointer such as
#/$defs/dependencyworks, but it couples references to the generated bundle layout instead of preserving each resource's canonical identity.Proposal
Implement JSON Schema resource indexing and reference resolution for Compound Schema Documents, following Draft 2020-12 URI and scope semantics.
Minimal version-resolved example:
{ "$schema": "https://json-schema.org/draft/2020-12/schema", "$ref": "shoko://python/pyproject", "$defs": { "python-pyproject-alias": { "$id": "shoko://python/pyproject", "$ref": "shoko://python/pyproject/versions/1.0.0/schema.json" }, "python-pyproject-1.0.0": { "$schema": "https://json-schema.org/draft/2020-12/schema", "$id": "shoko://python/pyproject/versions/1.0.0/schema.json", "type": "object", "properties": { "tool": { "type": "object", "properties": { "tombi": { "$ref": "shoko://tombi-toml/tombi" } }, "required": ["tombi"] } }, "required": ["tool"] }, "tombi-alias": { "$id": "shoko://tombi-toml/tombi", "$ref": "shoko://tombi-toml/tombi/versions/1.2.3/schema.json" }, "tombi-1.2.3": { "$schema": "https://json-schema.org/draft/2020-12/schema", "$id": "shoko://tombi-toml/tombi/versions/1.2.3/schema.json", "type": "object", "properties": { "strict": { "type": "boolean", "description": "Enable strict validation." } }, "required": ["strict"], "additionalProperties": false } } }For this TOML:
Tombi should resolve this chain entirely inside the loaded document:
It should report that
strictmust be a boolean without performing any externalshoko://fetch. No Shoko-specific URI handler should be required: these URIs are opaque canonical identifiers once their resources are present in the loaded Compound Schema Document.Required behavior
$idvalues throughout a loaded schema document.$anchor,$dynamicAnchor,$ref, and$dynamicRefusing their correct resource and dynamic scopes.file,http, andhttpsresolution when a referenced resource is not embedded.Acceptance criteria
tool.tombi.strict = 42is not a boolean.shoko://resources.$id;$schema;$anchorand$dynamicRef/$dynamicAnchorscope;#/$defs/namecontinue to work.Alternatives
Shoko could rewrite every dependency reference to a generated
#/$defs/...JSON Pointer or introduce a resolver-specific file format. That would work with Tombi today, but it would create a non-standard coupling between schema identity and generated bundle layout. Supporting Compound Schema Documents keeps the resolved artifact entirely within JSON Schema semantics.Additional context
vscode-json-languageservice >= 6.0.0-next.2: supported.yaml-language-server >= 1.23.0: supported.vscode-json-languageservice 6.0.0-next.3andyaml-language-server 1.24.0.#/$defs/...but not an absolute$idfor an embedded resource.