@kalada/host 0.1.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 ADDED
@@ -0,0 +1,101 @@
1
+ # `@kalada/host`
2
+
3
+ `@kalada/host` defines immutable, schema-neutral environment descriptors and a synchronous
4
+ parse/compile/link/prepared execution pipeline for Kalada.
5
+
6
+ ## Authority separation
7
+
8
+ Every binding declares `semanticType` as the syntax-owned `KaladaSyntaxStaticType`. That field is the
9
+ only semantic projection. Editor shape, metadata, validators, codecs, and provider-owned tags never
10
+ infer or fabricate a `KaladaType`. In particular, a metadata property named `$type` is ordinary data;
11
+ only a future provider adapter with explicit trusted provenance may interpret its own tags.
12
+
13
+ Editor shape is normalized into an ordered `kalada-editor-graph-v1` node table. Roots, definitions,
14
+ properties, tuple items, union variants, paths, unresolved references, unknown constructs, and cycle
15
+ edges retain input order. Graph construction, roots, definitions, reference resolution, and traversal
16
+ are bounded, with limit evidence retained in the graph. Node IDs such as `n0` are
17
+ deterministic traversal identities scoped only to that normalized document (`nodeIdScope` is
18
+ `document-local`); they are not hashes, cache keys, or cross-document fingerprints.
19
+
20
+ The schema-neutral graph can also retain literal, enum, never, unconstrained, opaque, record,
21
+ intersection, wrapper, relation, additional-property, presence, source-ID, annotation, and
22
+ constraint evidence. These constructs carry editor/provider evidence only; they do not infer the
23
+ binding's semantic type. `readSemanticType` is the public bounded reader for generic adapter-owned
24
+ type declarations.
25
+ New normalized evidence fields on pre-existing public node/property interfaces are optional for
26
+ source compatibility; host-produced normalized graphs always populate deterministic relation,
27
+ presence, and required-name values.
28
+
29
+ Normalized environments contain only recursively frozen serializable data. Validator and codec
30
+ callbacks are held separately in the returned, instance-scoped `capabilitySnapshot`. There is no
31
+ global provider registry, ambient lookup, cache, or import-time registration.
32
+
33
+ ## Manual provider
34
+
35
+ ```ts
36
+ import { createManualProvider, describeEnvironment } from "@kalada/host";
37
+
38
+ const provider = createManualProvider({
39
+ mode: "sync",
40
+ providerId: "example.manual",
41
+ providerVersion: "1",
42
+ configurationDigest: "sha256:configuration-owned-by-the-host",
43
+ bindings: [
44
+ {
45
+ id: "customer",
46
+ name: "customer",
47
+ path: ["customer"],
48
+ semanticType: "dynamic",
49
+ editorShape: {
50
+ root: {
51
+ kind: "object",
52
+ properties: [
53
+ { name: "name", required: true, shape: { kind: "scalar", name: "string" } },
54
+ ],
55
+ },
56
+ },
57
+ metadata: { description: "A customer record" },
58
+ },
59
+ ],
60
+ });
61
+
62
+ const described = describeEnvironment(provider);
63
+ if (!described.ok) throw new Error(described.diagnostics[0]?.code);
64
+ ```
65
+
66
+ Capability declarations and the provider explicitly state `mode: "sync" | "async"`; synchronous
67
+ execution rejects async declarations before callback invocation and offers no asynchronous API. A
68
+ capability is referenced from a binding by its declared handle. The normalized declaration is
69
+ data-only while the matching `decode` or `convert` function exists only in `capabilitySnapshot`.
70
+
71
+ Reusable cacheability requires all three provider fields (`providerId`, `providerVersion`, and
72
+ `configurationDigest`) and all three capability fields (`capabilityId`, `capabilityVersion`, and
73
+ `configurationDigest`). `cacheable: false` explicitly opts out. Any missing identity makes the
74
+ environment explicitly non-cacheable; this package emits no link fingerprint.
75
+
76
+ All failures use a frozen `phase: "environment"` diagnostic with a stable code and fixed message.
77
+ Diagnostics may include a copied binding path and allow-listed provenance strings, but never include
78
+ input values, callback/provider objects, exception messages, stacks, source text, or secrets.
79
+ The public `HostDiagnostic` envelope covers parse, lower, compile, link, bind, and evaluate phases,
80
+ UTF-16 sources, and immutable syntax/core causes.
81
+
82
+ ## Prepared execution
83
+
84
+ ```ts
85
+ import { evaluateExpression, prepareExpression } from "@kalada/host";
86
+
87
+ const prepared = prepareExpression("customerTotal + shipping", provider, {
88
+ parse: { sourceUri: "memory:///checkout.kalada" },
89
+ });
90
+ if (prepared.ok) {
91
+ const first = prepared.value.evaluate({ customerTotal: 10, shipping: 2 });
92
+ const second = prepared.value.evaluate({ customerTotal: 20, shipping: 3 });
93
+ }
94
+ const oneShot = evaluateExpression("customerTotal + shipping", provider, values);
95
+ ```
96
+
97
+ `prepareExpression` composes environment description, `parseExpression`, `compileExpression`, and
98
+ `linkExpression`. A prepared evaluation repeats own-data-property lookup, synchronous validation,
99
+ explicit conversion, canonical semantic validation, freezing, binding, and core evaluation. It does
100
+ not repeat source or link phases. Non-cacheable providers remain executable but omit
101
+ `linkFingerprint`; the package owns no hidden cache.