@vizejs/marquette 0.323.0 → 0.327.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +16 -0
- package/dist/adapter.d.mts +16 -1
- package/dist/adapter.d.mts.map +1 -1
- package/dist/adapter.mjs +29 -1
- package/dist/adapter.mjs.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -129,6 +129,22 @@ mutate their inputs. Compatibility reports expose validation diagnostics for
|
|
|
129
129
|
both manifests and omit changes when either input is invalid. The published manifest schema is available from
|
|
130
130
|
`@vizejs/marquette/adapter/schema`.
|
|
131
131
|
|
|
132
|
+
Native rendering adapters share one closed version-one baseline for rendering,
|
|
133
|
+
events, layout, text, images, animation, accessibility, and lifecycle:
|
|
134
|
+
|
|
135
|
+
```ts
|
|
136
|
+
import { nativeEngineCapabilityProfile } from "@vizejs/marquette/adapter";
|
|
137
|
+
|
|
138
|
+
const nativeAdapter = {
|
|
139
|
+
adapter: "native.example",
|
|
140
|
+
capabilities: nativeEngineCapabilityProfile(),
|
|
141
|
+
};
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
The canonical identifiers use the `native.*` namespace and are emitted in a
|
|
145
|
+
stable order. The helper returns fresh values so an adapter may add private
|
|
146
|
+
capabilities without changing the baseline used by another consumer.
|
|
147
|
+
|
|
132
148
|
## Test-run evidence
|
|
133
149
|
|
|
134
150
|
Release-bound test-run evidence records live in their own lazy entries so
|
package/dist/adapter.d.mts
CHANGED
|
@@ -87,6 +87,21 @@ interface AdapterCapabilityCompatibilityReport {
|
|
|
87
87
|
readonly changes: readonly AdapterCapabilityCompatibilityChange[];
|
|
88
88
|
}
|
|
89
89
|
//#endregion
|
|
90
|
+
//#region src/adapter-native-profile.d.ts
|
|
91
|
+
/** Current contract version shared by the native-engine capability profile. */
|
|
92
|
+
declare const NATIVE_ENGINE_CAPABILITY_VERSION: 1;
|
|
93
|
+
/** Closed set of capability identifiers required from a native rendering engine. */
|
|
94
|
+
declare const NATIVE_ENGINE_CAPABILITY_IDS: readonly ["native.rendering", "native.events", "native.layout", "native.text", "native.images", "native.animation", "native.accessibility", "native.lifecycle"];
|
|
95
|
+
/** One identifier from the canonical native-engine capability profile. */
|
|
96
|
+
type NativeEngineCapabilityId = (typeof NATIVE_ENGINE_CAPABILITY_IDS)[number];
|
|
97
|
+
/**
|
|
98
|
+
* Creates the canonical version-one native-engine capability profile.
|
|
99
|
+
*
|
|
100
|
+
* A fresh list is returned so an adapter can extend its manifest without
|
|
101
|
+
* mutating the shared profile seen by another consumer.
|
|
102
|
+
*/
|
|
103
|
+
declare function nativeEngineCapabilityProfile(): readonly AdapterCapabilitySupport[];
|
|
104
|
+
//#endregion
|
|
90
105
|
//#region src/adapter-compatibility.d.ts
|
|
91
106
|
/**
|
|
92
107
|
* Compares adapter capability support from older to newer.
|
|
@@ -118,5 +133,5 @@ declare function validateAdapterCapabilityManifest(manifest: AdapterCapabilityMa
|
|
|
118
133
|
*/
|
|
119
134
|
declare function parseAdapterCapabilityManifest(value: unknown): AdapterCapabilityManifest;
|
|
120
135
|
//#endregion
|
|
121
|
-
export { ADAPTER_CAPABILITY_FORMAT_VERSION, type AdapterCapabilityCompatibilityChange, type AdapterCapabilityCompatibilityReport, type AdapterCapabilityDiagnostic, type AdapterCapabilityDiagnosticCode, type AdapterCapabilityManifest, type AdapterCapabilityMismatch, type AdapterCapabilityMismatchCode, type AdapterCapabilityNegotiation, type AdapterCapabilitySupport, type CompatibilityChangeKind, compareAdapterCapabilities, negotiateAdapterCapabilities, parseAdapterCapabilityManifest, validateAdapterCapabilityManifest };
|
|
136
|
+
export { ADAPTER_CAPABILITY_FORMAT_VERSION, type AdapterCapabilityCompatibilityChange, type AdapterCapabilityCompatibilityReport, type AdapterCapabilityDiagnostic, type AdapterCapabilityDiagnosticCode, type AdapterCapabilityManifest, type AdapterCapabilityMismatch, type AdapterCapabilityMismatchCode, type AdapterCapabilityNegotiation, type AdapterCapabilitySupport, type CompatibilityChangeKind, NATIVE_ENGINE_CAPABILITY_IDS, NATIVE_ENGINE_CAPABILITY_VERSION, type NativeEngineCapabilityId, compareAdapterCapabilities, nativeEngineCapabilityProfile, negotiateAdapterCapabilities, parseAdapterCapabilityManifest, validateAdapterCapabilityManifest };
|
|
122
137
|
//# sourceMappingURL=adapter.d.mts.map
|
package/dist/adapter.d.mts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"adapter.d.mts","names":[],"sources":["../src/adapter-model.ts","../src/adapter-compatibility.ts","../src/adapter-negotiate.ts","../src/adapter-validate.ts"],"mappings":";;;;cACa,iCAAA;;UAGI,wBAAA;EAH0C;EAAA,SAKhD,EAAA;EALgD;EAAA,SAOhD,UAAA;EAJM;EAAA,SAMN,UAAA;AAAA;;UAIM,yBAAA;EANN;;;;AAMX;EANW,SAYA,aAAA,UAAuB,iCAAA;;WAEvB,OAAA;EAFA;;;;;EAAA,SAQA,YAAA,YAAwB,wBAAA;AAAA;AAInC;AAAA,KAAY,+BAAA;;UASK,2BAAA;EAT0B;EAAA,SAWhC,IAAA,EAAM,+BAAA;EAF2B;EAAA,SAIjC,IAAA;EAFqC;EAAA,SAIrC,OAAA;AAAA;;KAIC,6BAAA;;UAOK,yBAAA;EAPL;EAAA,SASD,IAAA,EAAM,6BAAA;;WAEN,UAAA;EAX8B;EAAA,SAa9B,eAAA;EAN+B;EAAA,SAQ/B,UAAA;EANmC;EAAA,SAQnC,UAAA;AAAA;;UAIM,4BAAA;EANN;EAAA,SAQA,OAAA;EANU;EAAA,SAQV,UAAA;EAJM;EAAA,SAMN,WAAA,WAAsB,2BAAA;;WAEtB,UAAA,WAAqB,yBAAA;AAAA;;KAIpB,uBAAA;;UAGK,oCAAA;EAPe;EAAA,SASrB,IAAA,EAAM,uBAAA;EATwC;EAAA,SAW9C,IAAA;EAPwB;EAAA,SASxB,OAAA;AAAA;;UAIM,oCAAA;EAVoC;EAAA,SAY1C,mBAAA,WAA8B,2BAAA;EAVD;EAAA,SAY7B,eAAA,WAA0B,2BAAA;EAZpB;EAAA,SAcN,OAAA,WAAkB,oCAAA;AAAA;;;;;
|
|
1
|
+
{"version":3,"file":"adapter.d.mts","names":[],"sources":["../src/adapter-model.ts","../src/adapter-native-profile.ts","../src/adapter-compatibility.ts","../src/adapter-negotiate.ts","../src/adapter-validate.ts"],"mappings":";;;;cACa,iCAAA;;UAGI,wBAAA;EAH0C;EAAA,SAKhD,EAAA;EALgD;EAAA,SAOhD,UAAA;EAJM;EAAA,SAMN,UAAA;AAAA;;UAIM,yBAAA;EANN;;;;AAMX;EANW,SAYA,aAAA,UAAuB,iCAAA;;WAEvB,OAAA;EAFA;;;;;EAAA,SAQA,YAAA,YAAwB,wBAAA;AAAA;AAInC;AAAA,KAAY,+BAAA;;UASK,2BAAA;EAT0B;EAAA,SAWhC,IAAA,EAAM,+BAAA;EAF2B;EAAA,SAIjC,IAAA;EAFqC;EAAA,SAIrC,OAAA;AAAA;;KAIC,6BAAA;;UAOK,yBAAA;EAPL;EAAA,SASD,IAAA,EAAM,6BAAA;;WAEN,UAAA;EAX8B;EAAA,SAa9B,eAAA;EAN+B;EAAA,SAQ/B,UAAA;EANmC;EAAA,SAQnC,UAAA;AAAA;;UAIM,4BAAA;EANN;EAAA,SAQA,OAAA;EANU;EAAA,SAQV,UAAA;EAJM;EAAA,SAMN,WAAA,WAAsB,2BAAA;;WAEtB,UAAA,WAAqB,yBAAA;AAAA;;KAIpB,uBAAA;;UAGK,oCAAA;EAPe;EAAA,SASrB,IAAA,EAAM,uBAAA;EATwC;EAAA,SAW9C,IAAA;EAPwB;EAAA,SASxB,OAAA;AAAA;;UAIM,oCAAA;EAVoC;EAAA,SAY1C,mBAAA,WAA8B,2BAAA;EAVD;EAAA,SAY7B,eAAA,WAA0B,2BAAA;EAZpB;EAAA,SAcN,OAAA,WAAkB,oCAAA;AAAA;;;;cCpGhB,gCAAA;ADFb;AAAA,cCKa,4BAAA;;KAYD,wBAAA,WAAmC,4BAAA;;ADd/C;;;;;iBCsBgB,6BAAA,CAAA,YAA0C,wBAAA;;;;;ADzB1D;;;;iBEcgB,0BAAA,CACd,QAAA,EAAU,yBAAA,EACV,IAAA,EAAM,yBAAA,GACL,oCAAA;;;;AFjBH;;;;;AAGA;iBGagB,4BAAA,CACd,SAAA,EAAW,oBAAA,EACX,oBAAA,qBACA,QAAA,EAAU,yBAAA,GACT,4BAAA;;;;iBCHa,iCAAA,CACd,QAAA,EAAU,yBAAA,GACT,2BAAA;AJnBH;;;;;AAGA;;AAHA,iBI0GgB,8BAAA,CAA+B,KAAA,YAAiB,yBAAA"}
|
package/dist/adapter.mjs
CHANGED
|
@@ -2,6 +2,34 @@
|
|
|
2
2
|
/** Current serialized adapter-capability manifest format. */
|
|
3
3
|
const ADAPTER_CAPABILITY_FORMAT_VERSION = 1;
|
|
4
4
|
//#endregion
|
|
5
|
+
//#region src/adapter-native-profile.ts
|
|
6
|
+
/** Current contract version shared by the native-engine capability profile. */
|
|
7
|
+
const NATIVE_ENGINE_CAPABILITY_VERSION = 1;
|
|
8
|
+
/** Closed set of capability identifiers required from a native rendering engine. */
|
|
9
|
+
const NATIVE_ENGINE_CAPABILITY_IDS = [
|
|
10
|
+
"native.rendering",
|
|
11
|
+
"native.events",
|
|
12
|
+
"native.layout",
|
|
13
|
+
"native.text",
|
|
14
|
+
"native.images",
|
|
15
|
+
"native.animation",
|
|
16
|
+
"native.accessibility",
|
|
17
|
+
"native.lifecycle"
|
|
18
|
+
];
|
|
19
|
+
/**
|
|
20
|
+
* Creates the canonical version-one native-engine capability profile.
|
|
21
|
+
*
|
|
22
|
+
* A fresh list is returned so an adapter can extend its manifest without
|
|
23
|
+
* mutating the shared profile seen by another consumer.
|
|
24
|
+
*/
|
|
25
|
+
function nativeEngineCapabilityProfile() {
|
|
26
|
+
return NATIVE_ENGINE_CAPABILITY_IDS.map((id) => ({
|
|
27
|
+
id,
|
|
28
|
+
minVersion: 1,
|
|
29
|
+
maxVersion: 1
|
|
30
|
+
}));
|
|
31
|
+
}
|
|
32
|
+
//#endregion
|
|
5
33
|
//#region src/adapter-validate.ts
|
|
6
34
|
const IDENTIFIER = /^[a-z0-9][a-z0-9._-]*$/;
|
|
7
35
|
const DIAGNOSTIC_ORDER = {
|
|
@@ -170,6 +198,6 @@ function problem(code, capability, requiredVersion, support) {
|
|
|
170
198
|
};
|
|
171
199
|
}
|
|
172
200
|
//#endregion
|
|
173
|
-
export { ADAPTER_CAPABILITY_FORMAT_VERSION, compareAdapterCapabilities, negotiateAdapterCapabilities, parseAdapterCapabilityManifest, validateAdapterCapabilityManifest };
|
|
201
|
+
export { ADAPTER_CAPABILITY_FORMAT_VERSION, NATIVE_ENGINE_CAPABILITY_IDS, NATIVE_ENGINE_CAPABILITY_VERSION, compareAdapterCapabilities, nativeEngineCapabilityProfile, negotiateAdapterCapabilities, parseAdapterCapabilityManifest, validateAdapterCapabilityManifest };
|
|
174
202
|
|
|
175
203
|
//# sourceMappingURL=adapter.mjs.map
|
package/dist/adapter.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"adapter.mjs","names":["compareText"],"sources":["../src/adapter-model.ts","../src/adapter-validate.ts","../src/adapter-compatibility.ts","../src/adapter-negotiate.ts"],"sourcesContent":["/** Current serialized adapter-capability manifest format. */\nexport const ADAPTER_CAPABILITY_FORMAT_VERSION = 1 as const;\n\n/** Inclusive version range supported for one capability contract. */\nexport interface AdapterCapabilitySupport {\n /** Stable capability identifier from an application marquette. */\n readonly id: string;\n /** Oldest supported capability contract version, inclusive. */\n readonly minVersion: number;\n /** Newest supported capability contract version, inclusive. */\n readonly maxVersion: number;\n}\n\n/** Versioned, language-neutral capabilities offered by one adapter. */\nexport interface AdapterCapabilityManifest {\n /**\n * Serialized manifest format.\n *\n * @default 1\n */\n readonly formatVersion?: typeof ADAPTER_CAPABILITY_FORMAT_VERSION;\n /** Stable adapter identifier shown in diagnostics and reports. */\n readonly adapter: string;\n /**\n * Supported capability ranges.\n *\n * @default []\n */\n readonly capabilities?: readonly AdapterCapabilitySupport[];\n}\n\n/** Stable validation code for an adapter capability manifest. */\nexport type AdapterCapabilityDiagnosticCode =\n | \"invalid-format-version\"\n | \"invalid-adapter-id\"\n | \"invalid-capability-id\"\n | \"invalid-version\"\n | \"invalid-version-range\"\n | \"duplicate-capability\";\n\n/** Deterministic validation diagnostic for an adapter capability manifest. */\nexport interface AdapterCapabilityDiagnostic {\n /** Stable machine-readable diagnostic code. */\n readonly code: AdapterCapabilityDiagnosticCode;\n /** JSON-style path of the invalid value. */\n readonly path: string;\n /** Human-readable explanation. */\n readonly message: string;\n}\n\n/** Stable incompatibility code emitted during capability negotiation. */\nexport type AdapterCapabilityMismatchCode =\n | \"unknown-requirement\"\n | \"missing-capability\"\n | \"version-below-minimum\"\n | \"version-above-maximum\";\n\n/** One failed adapter capability requirement. */\nexport interface AdapterCapabilityMismatch {\n /** Stable machine-readable mismatch code. */\n readonly code: AdapterCapabilityMismatchCode;\n /** Required capability identifier. */\n readonly capability: string;\n /** Required contract version when the capability is declared. */\n readonly requiredVersion?: number;\n /** Adapter minimum when support exists. */\n readonly minVersion?: number;\n /** Adapter maximum when support exists. */\n readonly maxVersion?: number;\n}\n\n/** Deterministic result of negotiating requirements with one adapter. */\nexport interface AdapterCapabilityNegotiation {\n /** Adapter whose support was inspected. */\n readonly adapter: string;\n /** Whether the manifest is valid and every requirement is supported. */\n readonly compatible: boolean;\n /** Manifest validation failures, in stable path order. */\n readonly diagnostics: readonly AdapterCapabilityDiagnostic[];\n /** Unsupported or unknown requirements, in stable capability order. */\n readonly mismatches: readonly AdapterCapabilityMismatch[];\n}\n\n/** Compatibility classification for one adapter capability change. */\nexport type CompatibilityChangeKind = \"additive\" | \"breaking\";\n\n/** One stable adapter capability compatibility change. */\nexport interface AdapterCapabilityCompatibilityChange {\n /** Compatibility classification. */\n readonly kind: CompatibilityChangeKind;\n /** JSON-style path of the changed capability support. */\n readonly path: string;\n /** Human-readable summary. */\n readonly message: string;\n}\n\n/** Deterministic compatibility report between two adapter manifests. */\nexport interface AdapterCapabilityCompatibilityReport {\n /** Validation failures in the previous manifest. */\n readonly previousDiagnostics: readonly AdapterCapabilityDiagnostic[];\n /** Validation failures in the next manifest. */\n readonly nextDiagnostics: readonly AdapterCapabilityDiagnostic[];\n /** All changes in stable path order. */\n readonly changes: readonly AdapterCapabilityCompatibilityChange[];\n}\n","import {\n ADAPTER_CAPABILITY_FORMAT_VERSION,\n type AdapterCapabilityDiagnostic,\n type AdapterCapabilityDiagnosticCode,\n type AdapterCapabilityManifest,\n} from \"./adapter-model.js\";\n\nconst IDENTIFIER = /^[a-z0-9][a-z0-9._-]*$/;\nconst DIAGNOSTIC_ORDER: Record<AdapterCapabilityDiagnosticCode, number> = {\n \"invalid-format-version\": 0,\n \"invalid-adapter-id\": 1,\n \"invalid-capability-id\": 2,\n \"invalid-version\": 3,\n \"invalid-version-range\": 4,\n \"duplicate-capability\": 5,\n};\n\n/** Validates an adapter capability manifest without mutating it. */\nexport function validateAdapterCapabilityManifest(\n manifest: AdapterCapabilityManifest,\n): AdapterCapabilityDiagnostic[] {\n const diagnostics: AdapterCapabilityDiagnostic[] = [];\n if ((manifest.formatVersion ?? 1) !== ADAPTER_CAPABILITY_FORMAT_VERSION) {\n diagnostics.push(\n diagnostic(\n \"invalid-format-version\",\n \"formatVersion\",\n \"unsupported adapter capability manifest format version\",\n ),\n );\n }\n if (!IDENTIFIER.test(manifest.adapter)) {\n diagnostics.push(\n diagnostic(\n \"invalid-adapter-id\",\n \"adapter\",\n \"adapter must be a lowercase portable identifier\",\n ),\n );\n }\n\n const seen = new Set<string>();\n for (const [index, capability] of (manifest.capabilities ?? []).entries()) {\n const path = `capabilities.${index}`;\n if (!IDENTIFIER.test(capability.id)) {\n diagnostics.push(\n diagnostic(\n \"invalid-capability-id\",\n `${path}.id`,\n \"capability id must be a lowercase portable identifier\",\n ),\n );\n }\n if (seen.has(capability.id)) {\n diagnostics.push(\n diagnostic(\n \"duplicate-capability\",\n `${path}.id`,\n \"capability id must be unique within the adapter manifest\",\n ),\n );\n }\n seen.add(capability.id);\n if (capability.minVersion <= 0) {\n diagnostics.push(\n diagnostic(\n \"invalid-version\",\n `${path}.minVersion`,\n \"minimum supported version must be greater than zero\",\n ),\n );\n }\n if (capability.maxVersion <= 0) {\n diagnostics.push(\n diagnostic(\n \"invalid-version\",\n `${path}.maxVersion`,\n \"maximum supported version must be greater than zero\",\n ),\n );\n }\n if (capability.minVersion > capability.maxVersion) {\n diagnostics.push(\n diagnostic(\n \"invalid-version-range\",\n path,\n \"minimum supported version must not exceed maximum supported version\",\n ),\n );\n }\n }\n\n return diagnostics.sort(\n (left, right) =>\n compareText(left.path, right.path) ||\n DIAGNOSTIC_ORDER[left.code] - DIAGNOSTIC_ORDER[right.code] ||\n compareText(left.message, right.message),\n );\n}\n\n/**\n * Parses an untrusted manifest with strict field and primitive checks.\n *\n * Unknown fields, missing required fields, and mismatched primitive types\n * throw before negotiation. Semantic range errors remain available from\n * {@link validateAdapterCapabilityManifest}.\n */\nexport function parseAdapterCapabilityManifest(value: unknown): AdapterCapabilityManifest {\n assertRecord(value, \"manifest\");\n assertKnownFields(value, [\"formatVersion\", \"adapter\", \"capabilities\"], \"manifest\");\n if (value.formatVersion !== undefined && typeof value.formatVersion !== \"number\") {\n throw new TypeError(\"formatVersion must be a number\");\n }\n if (typeof value.adapter !== \"string\") {\n throw new TypeError(\"adapter must be a string\");\n }\n if (value.capabilities !== undefined) {\n if (!Array.isArray(value.capabilities)) {\n throw new TypeError(\"capabilities must be an array\");\n }\n for (const [index, capability] of value.capabilities.entries()) {\n const path = `capabilities.${index}`;\n assertRecord(capability, path);\n assertKnownFields(capability, [\"id\", \"minVersion\", \"maxVersion\"], path);\n if (typeof capability.id !== \"string\") throw new TypeError(`${path}.id must be a string`);\n if (\n typeof capability.minVersion !== \"number\" ||\n !Number.isSafeInteger(capability.minVersion) ||\n capability.minVersion < 0\n ) {\n throw new TypeError(`${path}.minVersion must be a safe integer`);\n }\n if (\n typeof capability.maxVersion !== \"number\" ||\n !Number.isSafeInteger(capability.maxVersion) ||\n capability.maxVersion < 0\n ) {\n throw new TypeError(`${path}.maxVersion must be a safe integer`);\n }\n }\n }\n return value as unknown as AdapterCapabilityManifest;\n}\n\nfunction diagnostic(\n code: AdapterCapabilityDiagnosticCode,\n path: string,\n message: string,\n): AdapterCapabilityDiagnostic {\n return { code, path, message };\n}\n\nfunction assertRecord(value: unknown, path: string): asserts value is Record<string, unknown> {\n if (value == null || typeof value !== \"object\" || Array.isArray(value)) {\n throw new TypeError(`${path} must be an object`);\n }\n}\n\nfunction assertKnownFields(\n value: Record<string, unknown>,\n expected: readonly string[],\n path: string,\n): void {\n const known = new Set(expected);\n const unknown = Object.keys(value).find((field) => !known.has(field));\n if (unknown !== undefined) throw new TypeError(`${path} has unknown field ${unknown}`);\n}\n\nfunction compareText(left: string, right: string): number {\n return left < right ? -1 : left > right ? 1 : 0;\n}\n","import type {\n AdapterCapabilityCompatibilityChange,\n AdapterCapabilityCompatibilityReport,\n AdapterCapabilityManifest,\n AdapterCapabilitySupport,\n CompatibilityChangeKind,\n} from \"./adapter-model.js\";\nimport { validateAdapterCapabilityManifest } from \"./adapter-validate.js\";\n\n/**\n * Compares adapter capability support from older to newer.\n *\n * Adding support or widening an inclusive version range is additive.\n * Removing support or narrowing either bound is breaking.\n */\nexport function compareAdapterCapabilities(\n previous: AdapterCapabilityManifest,\n next: AdapterCapabilityManifest,\n): AdapterCapabilityCompatibilityReport {\n const previousDiagnostics = validateAdapterCapabilityManifest(previous);\n const nextDiagnostics = validateAdapterCapabilityManifest(next);\n if (previousDiagnostics.length > 0 || nextDiagnostics.length > 0) {\n return { previousDiagnostics, nextDiagnostics, changes: [] };\n }\n\n const changes: AdapterCapabilityCompatibilityChange[] = [];\n if (previous.adapter !== next.adapter) {\n changes.push(change(\"breaking\", \"adapter\", \"adapter identity changed\"));\n }\n\n const oldSupport = byId(previous);\n const newSupport = byId(next);\n for (const id of [...oldSupport.keys()].filter((id) => !newSupport.has(id)).sort()) {\n changes.push(change(\"breaking\", `capabilities.${id}`, \"capability support was removed\"));\n }\n for (const id of [...newSupport.keys()].filter((id) => !oldSupport.has(id)).sort()) {\n changes.push(change(\"additive\", `capabilities.${id}`, \"capability support was added\"));\n }\n for (const [id, old] of oldSupport) {\n const current = newSupport.get(id);\n if (current === undefined) continue;\n if (old.minVersion !== current.minVersion) {\n changes.push(\n change(\n current.minVersion < old.minVersion ? \"additive\" : \"breaking\",\n `capabilities.${id}.minVersion`,\n current.minVersion < old.minVersion\n ? \"minimum supported version decreased\"\n : \"minimum supported version increased\",\n ),\n );\n }\n if (old.maxVersion !== current.maxVersion) {\n changes.push(\n change(\n current.maxVersion > old.maxVersion ? \"additive\" : \"breaking\",\n `capabilities.${id}.maxVersion`,\n current.maxVersion > old.maxVersion\n ? \"maximum supported version increased\"\n : \"maximum supported version decreased\",\n ),\n );\n }\n }\n\n changes.sort(\n (left, right) => compareText(left.path, right.path) || compareText(left.kind, right.kind),\n );\n return { previousDiagnostics, nextDiagnostics, changes };\n}\n\nfunction byId(manifest: AdapterCapabilityManifest): Map<string, AdapterCapabilitySupport> {\n return new Map((manifest.capabilities ?? []).map((value) => [value.id, value] as const));\n}\n\nfunction change(\n kind: CompatibilityChangeKind,\n path: string,\n message: string,\n): AdapterCapabilityCompatibilityChange {\n return { kind, path, message };\n}\n\nfunction compareText(left: string, right: string): number {\n return left < right ? -1 : left > right ? 1 : 0;\n}\n","import type { ApplicationMarquette } from \"./model.js\";\nimport type {\n AdapterCapabilityManifest,\n AdapterCapabilityMismatch,\n AdapterCapabilityMismatchCode,\n AdapterCapabilityNegotiation,\n AdapterCapabilitySupport,\n} from \"./adapter-model.js\";\nimport { validateAdapterCapabilityManifest } from \"./adapter-validate.js\";\n\n/**\n * Negotiates application capability requirements against one adapter.\n *\n * Requirement identifiers are deduplicated and sorted. Unknown application\n * capability identifiers fail closed instead of being treated as adapter\n * omissions. An invalid manifest never produces a compatible result.\n */\nexport function negotiateAdapterCapabilities(\n marquette: ApplicationMarquette,\n requiredCapabilities: readonly string[],\n manifest: AdapterCapabilityManifest,\n): AdapterCapabilityNegotiation {\n const diagnostics = validateAdapterCapabilityManifest(manifest);\n const support = new Map(\n (manifest.capabilities ?? []).map((capability) => [capability.id, capability] as const),\n );\n const mismatches = [...new Set(requiredCapabilities)]\n .sort()\n .flatMap((id) => mismatch(marquette, id, support.get(id), diagnostics.length === 0));\n\n return {\n adapter: manifest.adapter,\n compatible: diagnostics.length === 0 && mismatches.length === 0,\n diagnostics,\n mismatches,\n };\n}\n\nfunction mismatch(\n marquette: ApplicationMarquette,\n id: string,\n support: AdapterCapabilitySupport | undefined,\n manifestIsValid: boolean,\n): AdapterCapabilityMismatch[] {\n const requirement = marquette.capabilities?.[id];\n if (requirement === undefined) return [problem(\"unknown-requirement\", id)];\n if (!manifestIsValid) return [];\n\n const requiredVersion = requirement.version ?? 1;\n if (support === undefined) return [problem(\"missing-capability\", id, requiredVersion)];\n if (requiredVersion < support.minVersion) {\n return [problem(\"version-below-minimum\", id, requiredVersion, support)];\n }\n if (requiredVersion > support.maxVersion) {\n return [problem(\"version-above-maximum\", id, requiredVersion, support)];\n }\n return [];\n}\n\nfunction problem(\n code: AdapterCapabilityMismatchCode,\n capability: string,\n requiredVersion?: number,\n support?: AdapterCapabilitySupport,\n): AdapterCapabilityMismatch {\n return {\n code,\n capability,\n ...(requiredVersion === undefined ? {} : { requiredVersion }),\n ...(support === undefined\n ? {}\n : { minVersion: support.minVersion, maxVersion: support.maxVersion }),\n };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"adapter.mjs","names":["compareText"],"sources":["../src/adapter-model.ts","../src/adapter-native-profile.ts","../src/adapter-validate.ts","../src/adapter-compatibility.ts","../src/adapter-negotiate.ts"],"sourcesContent":["/** Current serialized adapter-capability manifest format. */\nexport const ADAPTER_CAPABILITY_FORMAT_VERSION = 1 as const;\n\n/** Inclusive version range supported for one capability contract. */\nexport interface AdapterCapabilitySupport {\n /** Stable capability identifier from an application marquette. */\n readonly id: string;\n /** Oldest supported capability contract version, inclusive. */\n readonly minVersion: number;\n /** Newest supported capability contract version, inclusive. */\n readonly maxVersion: number;\n}\n\n/** Versioned, language-neutral capabilities offered by one adapter. */\nexport interface AdapterCapabilityManifest {\n /**\n * Serialized manifest format.\n *\n * @default 1\n */\n readonly formatVersion?: typeof ADAPTER_CAPABILITY_FORMAT_VERSION;\n /** Stable adapter identifier shown in diagnostics and reports. */\n readonly adapter: string;\n /**\n * Supported capability ranges.\n *\n * @default []\n */\n readonly capabilities?: readonly AdapterCapabilitySupport[];\n}\n\n/** Stable validation code for an adapter capability manifest. */\nexport type AdapterCapabilityDiagnosticCode =\n | \"invalid-format-version\"\n | \"invalid-adapter-id\"\n | \"invalid-capability-id\"\n | \"invalid-version\"\n | \"invalid-version-range\"\n | \"duplicate-capability\";\n\n/** Deterministic validation diagnostic for an adapter capability manifest. */\nexport interface AdapterCapabilityDiagnostic {\n /** Stable machine-readable diagnostic code. */\n readonly code: AdapterCapabilityDiagnosticCode;\n /** JSON-style path of the invalid value. */\n readonly path: string;\n /** Human-readable explanation. */\n readonly message: string;\n}\n\n/** Stable incompatibility code emitted during capability negotiation. */\nexport type AdapterCapabilityMismatchCode =\n | \"unknown-requirement\"\n | \"missing-capability\"\n | \"version-below-minimum\"\n | \"version-above-maximum\";\n\n/** One failed adapter capability requirement. */\nexport interface AdapterCapabilityMismatch {\n /** Stable machine-readable mismatch code. */\n readonly code: AdapterCapabilityMismatchCode;\n /** Required capability identifier. */\n readonly capability: string;\n /** Required contract version when the capability is declared. */\n readonly requiredVersion?: number;\n /** Adapter minimum when support exists. */\n readonly minVersion?: number;\n /** Adapter maximum when support exists. */\n readonly maxVersion?: number;\n}\n\n/** Deterministic result of negotiating requirements with one adapter. */\nexport interface AdapterCapabilityNegotiation {\n /** Adapter whose support was inspected. */\n readonly adapter: string;\n /** Whether the manifest is valid and every requirement is supported. */\n readonly compatible: boolean;\n /** Manifest validation failures, in stable path order. */\n readonly diagnostics: readonly AdapterCapabilityDiagnostic[];\n /** Unsupported or unknown requirements, in stable capability order. */\n readonly mismatches: readonly AdapterCapabilityMismatch[];\n}\n\n/** Compatibility classification for one adapter capability change. */\nexport type CompatibilityChangeKind = \"additive\" | \"breaking\";\n\n/** One stable adapter capability compatibility change. */\nexport interface AdapterCapabilityCompatibilityChange {\n /** Compatibility classification. */\n readonly kind: CompatibilityChangeKind;\n /** JSON-style path of the changed capability support. */\n readonly path: string;\n /** Human-readable summary. */\n readonly message: string;\n}\n\n/** Deterministic compatibility report between two adapter manifests. */\nexport interface AdapterCapabilityCompatibilityReport {\n /** Validation failures in the previous manifest. */\n readonly previousDiagnostics: readonly AdapterCapabilityDiagnostic[];\n /** Validation failures in the next manifest. */\n readonly nextDiagnostics: readonly AdapterCapabilityDiagnostic[];\n /** All changes in stable path order. */\n readonly changes: readonly AdapterCapabilityCompatibilityChange[];\n}\n","import type { AdapterCapabilitySupport } from \"./adapter-model.js\";\n\n/** Current contract version shared by the native-engine capability profile. */\nexport const NATIVE_ENGINE_CAPABILITY_VERSION = 1 as const;\n\n/** Closed set of capability identifiers required from a native rendering engine. */\nexport const NATIVE_ENGINE_CAPABILITY_IDS = [\n \"native.rendering\",\n \"native.events\",\n \"native.layout\",\n \"native.text\",\n \"native.images\",\n \"native.animation\",\n \"native.accessibility\",\n \"native.lifecycle\",\n] as const;\n\n/** One identifier from the canonical native-engine capability profile. */\nexport type NativeEngineCapabilityId = (typeof NATIVE_ENGINE_CAPABILITY_IDS)[number];\n\n/**\n * Creates the canonical version-one native-engine capability profile.\n *\n * A fresh list is returned so an adapter can extend its manifest without\n * mutating the shared profile seen by another consumer.\n */\nexport function nativeEngineCapabilityProfile(): readonly AdapterCapabilitySupport[] {\n return NATIVE_ENGINE_CAPABILITY_IDS.map((id) => ({\n id,\n minVersion: NATIVE_ENGINE_CAPABILITY_VERSION,\n maxVersion: NATIVE_ENGINE_CAPABILITY_VERSION,\n }));\n}\n","import {\n ADAPTER_CAPABILITY_FORMAT_VERSION,\n type AdapterCapabilityDiagnostic,\n type AdapterCapabilityDiagnosticCode,\n type AdapterCapabilityManifest,\n} from \"./adapter-model.js\";\n\nconst IDENTIFIER = /^[a-z0-9][a-z0-9._-]*$/;\nconst DIAGNOSTIC_ORDER: Record<AdapterCapabilityDiagnosticCode, number> = {\n \"invalid-format-version\": 0,\n \"invalid-adapter-id\": 1,\n \"invalid-capability-id\": 2,\n \"invalid-version\": 3,\n \"invalid-version-range\": 4,\n \"duplicate-capability\": 5,\n};\n\n/** Validates an adapter capability manifest without mutating it. */\nexport function validateAdapterCapabilityManifest(\n manifest: AdapterCapabilityManifest,\n): AdapterCapabilityDiagnostic[] {\n const diagnostics: AdapterCapabilityDiagnostic[] = [];\n if ((manifest.formatVersion ?? 1) !== ADAPTER_CAPABILITY_FORMAT_VERSION) {\n diagnostics.push(\n diagnostic(\n \"invalid-format-version\",\n \"formatVersion\",\n \"unsupported adapter capability manifest format version\",\n ),\n );\n }\n if (!IDENTIFIER.test(manifest.adapter)) {\n diagnostics.push(\n diagnostic(\n \"invalid-adapter-id\",\n \"adapter\",\n \"adapter must be a lowercase portable identifier\",\n ),\n );\n }\n\n const seen = new Set<string>();\n for (const [index, capability] of (manifest.capabilities ?? []).entries()) {\n const path = `capabilities.${index}`;\n if (!IDENTIFIER.test(capability.id)) {\n diagnostics.push(\n diagnostic(\n \"invalid-capability-id\",\n `${path}.id`,\n \"capability id must be a lowercase portable identifier\",\n ),\n );\n }\n if (seen.has(capability.id)) {\n diagnostics.push(\n diagnostic(\n \"duplicate-capability\",\n `${path}.id`,\n \"capability id must be unique within the adapter manifest\",\n ),\n );\n }\n seen.add(capability.id);\n if (capability.minVersion <= 0) {\n diagnostics.push(\n diagnostic(\n \"invalid-version\",\n `${path}.minVersion`,\n \"minimum supported version must be greater than zero\",\n ),\n );\n }\n if (capability.maxVersion <= 0) {\n diagnostics.push(\n diagnostic(\n \"invalid-version\",\n `${path}.maxVersion`,\n \"maximum supported version must be greater than zero\",\n ),\n );\n }\n if (capability.minVersion > capability.maxVersion) {\n diagnostics.push(\n diagnostic(\n \"invalid-version-range\",\n path,\n \"minimum supported version must not exceed maximum supported version\",\n ),\n );\n }\n }\n\n return diagnostics.sort(\n (left, right) =>\n compareText(left.path, right.path) ||\n DIAGNOSTIC_ORDER[left.code] - DIAGNOSTIC_ORDER[right.code] ||\n compareText(left.message, right.message),\n );\n}\n\n/**\n * Parses an untrusted manifest with strict field and primitive checks.\n *\n * Unknown fields, missing required fields, and mismatched primitive types\n * throw before negotiation. Semantic range errors remain available from\n * {@link validateAdapterCapabilityManifest}.\n */\nexport function parseAdapterCapabilityManifest(value: unknown): AdapterCapabilityManifest {\n assertRecord(value, \"manifest\");\n assertKnownFields(value, [\"formatVersion\", \"adapter\", \"capabilities\"], \"manifest\");\n if (value.formatVersion !== undefined && typeof value.formatVersion !== \"number\") {\n throw new TypeError(\"formatVersion must be a number\");\n }\n if (typeof value.adapter !== \"string\") {\n throw new TypeError(\"adapter must be a string\");\n }\n if (value.capabilities !== undefined) {\n if (!Array.isArray(value.capabilities)) {\n throw new TypeError(\"capabilities must be an array\");\n }\n for (const [index, capability] of value.capabilities.entries()) {\n const path = `capabilities.${index}`;\n assertRecord(capability, path);\n assertKnownFields(capability, [\"id\", \"minVersion\", \"maxVersion\"], path);\n if (typeof capability.id !== \"string\") throw new TypeError(`${path}.id must be a string`);\n if (\n typeof capability.minVersion !== \"number\" ||\n !Number.isSafeInteger(capability.minVersion) ||\n capability.minVersion < 0\n ) {\n throw new TypeError(`${path}.minVersion must be a safe integer`);\n }\n if (\n typeof capability.maxVersion !== \"number\" ||\n !Number.isSafeInteger(capability.maxVersion) ||\n capability.maxVersion < 0\n ) {\n throw new TypeError(`${path}.maxVersion must be a safe integer`);\n }\n }\n }\n return value as unknown as AdapterCapabilityManifest;\n}\n\nfunction diagnostic(\n code: AdapterCapabilityDiagnosticCode,\n path: string,\n message: string,\n): AdapterCapabilityDiagnostic {\n return { code, path, message };\n}\n\nfunction assertRecord(value: unknown, path: string): asserts value is Record<string, unknown> {\n if (value == null || typeof value !== \"object\" || Array.isArray(value)) {\n throw new TypeError(`${path} must be an object`);\n }\n}\n\nfunction assertKnownFields(\n value: Record<string, unknown>,\n expected: readonly string[],\n path: string,\n): void {\n const known = new Set(expected);\n const unknown = Object.keys(value).find((field) => !known.has(field));\n if (unknown !== undefined) throw new TypeError(`${path} has unknown field ${unknown}`);\n}\n\nfunction compareText(left: string, right: string): number {\n return left < right ? -1 : left > right ? 1 : 0;\n}\n","import type {\n AdapterCapabilityCompatibilityChange,\n AdapterCapabilityCompatibilityReport,\n AdapterCapabilityManifest,\n AdapterCapabilitySupport,\n CompatibilityChangeKind,\n} from \"./adapter-model.js\";\nimport { validateAdapterCapabilityManifest } from \"./adapter-validate.js\";\n\n/**\n * Compares adapter capability support from older to newer.\n *\n * Adding support or widening an inclusive version range is additive.\n * Removing support or narrowing either bound is breaking.\n */\nexport function compareAdapterCapabilities(\n previous: AdapterCapabilityManifest,\n next: AdapterCapabilityManifest,\n): AdapterCapabilityCompatibilityReport {\n const previousDiagnostics = validateAdapterCapabilityManifest(previous);\n const nextDiagnostics = validateAdapterCapabilityManifest(next);\n if (previousDiagnostics.length > 0 || nextDiagnostics.length > 0) {\n return { previousDiagnostics, nextDiagnostics, changes: [] };\n }\n\n const changes: AdapterCapabilityCompatibilityChange[] = [];\n if (previous.adapter !== next.adapter) {\n changes.push(change(\"breaking\", \"adapter\", \"adapter identity changed\"));\n }\n\n const oldSupport = byId(previous);\n const newSupport = byId(next);\n for (const id of [...oldSupport.keys()].filter((id) => !newSupport.has(id)).sort()) {\n changes.push(change(\"breaking\", `capabilities.${id}`, \"capability support was removed\"));\n }\n for (const id of [...newSupport.keys()].filter((id) => !oldSupport.has(id)).sort()) {\n changes.push(change(\"additive\", `capabilities.${id}`, \"capability support was added\"));\n }\n for (const [id, old] of oldSupport) {\n const current = newSupport.get(id);\n if (current === undefined) continue;\n if (old.minVersion !== current.minVersion) {\n changes.push(\n change(\n current.minVersion < old.minVersion ? \"additive\" : \"breaking\",\n `capabilities.${id}.minVersion`,\n current.minVersion < old.minVersion\n ? \"minimum supported version decreased\"\n : \"minimum supported version increased\",\n ),\n );\n }\n if (old.maxVersion !== current.maxVersion) {\n changes.push(\n change(\n current.maxVersion > old.maxVersion ? \"additive\" : \"breaking\",\n `capabilities.${id}.maxVersion`,\n current.maxVersion > old.maxVersion\n ? \"maximum supported version increased\"\n : \"maximum supported version decreased\",\n ),\n );\n }\n }\n\n changes.sort(\n (left, right) => compareText(left.path, right.path) || compareText(left.kind, right.kind),\n );\n return { previousDiagnostics, nextDiagnostics, changes };\n}\n\nfunction byId(manifest: AdapterCapabilityManifest): Map<string, AdapterCapabilitySupport> {\n return new Map((manifest.capabilities ?? []).map((value) => [value.id, value] as const));\n}\n\nfunction change(\n kind: CompatibilityChangeKind,\n path: string,\n message: string,\n): AdapterCapabilityCompatibilityChange {\n return { kind, path, message };\n}\n\nfunction compareText(left: string, right: string): number {\n return left < right ? -1 : left > right ? 1 : 0;\n}\n","import type { ApplicationMarquette } from \"./model.js\";\nimport type {\n AdapterCapabilityManifest,\n AdapterCapabilityMismatch,\n AdapterCapabilityMismatchCode,\n AdapterCapabilityNegotiation,\n AdapterCapabilitySupport,\n} from \"./adapter-model.js\";\nimport { validateAdapterCapabilityManifest } from \"./adapter-validate.js\";\n\n/**\n * Negotiates application capability requirements against one adapter.\n *\n * Requirement identifiers are deduplicated and sorted. Unknown application\n * capability identifiers fail closed instead of being treated as adapter\n * omissions. An invalid manifest never produces a compatible result.\n */\nexport function negotiateAdapterCapabilities(\n marquette: ApplicationMarquette,\n requiredCapabilities: readonly string[],\n manifest: AdapterCapabilityManifest,\n): AdapterCapabilityNegotiation {\n const diagnostics = validateAdapterCapabilityManifest(manifest);\n const support = new Map(\n (manifest.capabilities ?? []).map((capability) => [capability.id, capability] as const),\n );\n const mismatches = [...new Set(requiredCapabilities)]\n .sort()\n .flatMap((id) => mismatch(marquette, id, support.get(id), diagnostics.length === 0));\n\n return {\n adapter: manifest.adapter,\n compatible: diagnostics.length === 0 && mismatches.length === 0,\n diagnostics,\n mismatches,\n };\n}\n\nfunction mismatch(\n marquette: ApplicationMarquette,\n id: string,\n support: AdapterCapabilitySupport | undefined,\n manifestIsValid: boolean,\n): AdapterCapabilityMismatch[] {\n const requirement = marquette.capabilities?.[id];\n if (requirement === undefined) return [problem(\"unknown-requirement\", id)];\n if (!manifestIsValid) return [];\n\n const requiredVersion = requirement.version ?? 1;\n if (support === undefined) return [problem(\"missing-capability\", id, requiredVersion)];\n if (requiredVersion < support.minVersion) {\n return [problem(\"version-below-minimum\", id, requiredVersion, support)];\n }\n if (requiredVersion > support.maxVersion) {\n return [problem(\"version-above-maximum\", id, requiredVersion, support)];\n }\n return [];\n}\n\nfunction problem(\n code: AdapterCapabilityMismatchCode,\n capability: string,\n requiredVersion?: number,\n support?: AdapterCapabilitySupport,\n): AdapterCapabilityMismatch {\n return {\n code,\n capability,\n ...(requiredVersion === undefined ? {} : { requiredVersion }),\n ...(support === undefined\n ? {}\n : { minVersion: support.minVersion, maxVersion: support.maxVersion }),\n };\n}\n"],"mappings":"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"}
|