@githolon/dsl 0.61.0 → 0.61.1
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/package.json +1 -1
- package/src/codegen_proof.ts +48 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@githolon/dsl",
|
|
3
|
-
"version": "0.61.
|
|
3
|
+
"version": "0.61.1",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Nomos 2 domain-authoring DSL: aggregates + directives in TS, executed and encoded to the Rust kernel's wire shapes.",
|
|
6
6
|
"license": "SEE LICENSE IN LICENSE.md",
|
package/src/codegen_proof.ts
CHANGED
|
@@ -116,6 +116,41 @@ const SUBJECT_CANDIDATES: readonly string[] = [`user:${ZERO_UUID}`, `key:${HEX64
|
|
|
116
116
|
* schema and return the first that validates. If none fits an exotic constraint, fall back to the
|
|
117
117
|
* readable placeholder (behaviour unchanged from before — that directive is proven by hand).
|
|
118
118
|
*/
|
|
119
|
+
/** BIRTHS ISOLATION (multi-`.births()` parent): a parent with SEVERAL birth legs (co2:
|
|
120
|
+
* birthCatalogueWorkspace + birthEstateWorkspace) synthesizes the SAME readable `sample-<field>` payloads,
|
|
121
|
+
* so each leg's plan DERIVES THE SAME child workspace name and the second birth collides on an
|
|
122
|
+
* already-born name. Give each leg a distinct child by suffixing its `sample-`-prefixed string values with
|
|
123
|
+
* a per-leg discriminator — but ONLY when the suffixed payload STILL satisfies the directive's own schema
|
|
124
|
+
* (a constrained field is left untouched, never broken). A single-birth parent is unaffected (no suffix). */
|
|
125
|
+
function uniquifyBirthPayload(
|
|
126
|
+
payload: Record<string, unknown>,
|
|
127
|
+
disc: string,
|
|
128
|
+
schema: z.ZodTypeAny | undefined,
|
|
129
|
+
): Record<string, unknown> {
|
|
130
|
+
const suffixed: Record<string, unknown> = {};
|
|
131
|
+
let changed = false;
|
|
132
|
+
for (const [k, v] of Object.entries(payload)) {
|
|
133
|
+
if (typeof v === "string" && v.startsWith("sample-")) { suffixed[k] = `${v}-${disc}`; changed = true; }
|
|
134
|
+
else suffixed[k] = v;
|
|
135
|
+
}
|
|
136
|
+
if (!changed) return payload;
|
|
137
|
+
// Re-validate PER FIELD (the birthPayload has its framework/law-hash fields deleted — they are injected at
|
|
138
|
+
// runtime — so a whole-payload parse would spuriously fail on the missing required fields). For a
|
|
139
|
+
// ZodObject we check each suffixed value against ITS OWN field schema; a field whose schema rejects the
|
|
140
|
+
// suffix (a length/regex bound) is reverted to its original value (never break a constrained field).
|
|
141
|
+
const shape =
|
|
142
|
+
schema !== undefined && typeof (schema as { shape?: unknown }).shape === "object"
|
|
143
|
+
? ((schema as unknown as { shape: Record<string, z.ZodTypeAny> }).shape)
|
|
144
|
+
: undefined;
|
|
145
|
+
for (const [k, v] of Object.entries(suffixed)) {
|
|
146
|
+
const orig = payload[k];
|
|
147
|
+
if (v === orig) continue;
|
|
148
|
+
const fieldSchema = shape?.[k];
|
|
149
|
+
if (fieldSchema !== undefined && !fieldSchema.safeParse(v).success) suffixed[k] = orig; // revert the constrained field
|
|
150
|
+
}
|
|
151
|
+
return suffixed;
|
|
152
|
+
}
|
|
153
|
+
|
|
119
154
|
function sampleString(zt: z.ZodTypeAny, field: string): string {
|
|
120
155
|
const readable = `sample-${field}`;
|
|
121
156
|
if (zt.safeParse(readable).success) return readable;
|
|
@@ -2071,8 +2106,20 @@ export function legsForDomain(mod: DomainModule, modules: readonly DomainModule[
|
|
|
2071
2106
|
// The child-birth legs (one per `.births()` directive) — discovered by running each plan. A parent
|
|
2072
2107
|
// with SEVERAL births (co2: birthCatalogueWorkspace + birthEstateWorkspace) keeps EVERY leg; keeping
|
|
2073
2108
|
// only the first left the other children compile-valid-only (unprovable through their birth).
|
|
2074
|
-
const
|
|
2109
|
+
const parentBirths = allBirths.filter((b) => b.parentDomain === domain);
|
|
2110
|
+
const childBirths = parentBirths.map((b) => {
|
|
2075
2111
|
const withParent = attachParentSetup(b, allBirths);
|
|
2112
|
+
// BIRTHS ISOLATION: with >1 birth leg, uniquify each leg's synthesized child so the legs don't collide
|
|
2113
|
+
// on one generated child workspace name (the discriminator = the birth directive id, unique per leg).
|
|
2114
|
+
if (parentBirths.length > 1) {
|
|
2115
|
+
const birthDir = (mod.directives as Directive<unknown>[]).find((d) => d?.id === b.birthDirectiveId);
|
|
2116
|
+
const schema = birthDir?.payloadSchema as z.ZodTypeAny | undefined;
|
|
2117
|
+
const disc = b.birthDirectiveId;
|
|
2118
|
+
const uniq = uniquifyBirthPayload(withParent.birthPayload, disc, schema);
|
|
2119
|
+
if (uniq !== withParent.birthPayload) {
|
|
2120
|
+
return { ...withParent, birthPayload: uniq };
|
|
2121
|
+
}
|
|
2122
|
+
}
|
|
2076
2123
|
// A GATED birth with no parent-birth authority path: seat its relation via the SAME granter/seed
|
|
2077
2124
|
// discovery the relation-bootstrap leg uses (the law's own authority path, e.g. co2's
|
|
2078
2125
|
// seedPlatformFounder → seedPlatformAdmin → grantCo2EstateCreator → birthEstateWorkspace).
|