@hyperscale0/hsx 1.0.0-rc.1 → 2.0.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/CHANGELOG.md +32 -4
- package/README.md +58 -36
- package/bin/hsx.ts +2 -0
- package/dist/bin/hsx.js +2 -0
- package/dist/bin/hsx.js.map +1 -1
- package/dist/src/ast.d.ts +10 -2
- package/dist/src/ast.d.ts.map +1 -1
- package/dist/src/ast.js +24 -0
- package/dist/src/ast.js.map +1 -1
- package/dist/src/cli.d.ts +3 -1
- package/dist/src/cli.d.ts.map +1 -1
- package/dist/src/cli.js +25 -5
- package/dist/src/cli.js.map +1 -1
- package/dist/src/compile.d.ts +9 -5
- package/dist/src/compile.d.ts.map +1 -1
- package/dist/src/compile.js +9 -3
- package/dist/src/compile.js.map +1 -1
- package/dist/src/cost.d.ts +3 -1
- package/dist/src/cost.d.ts.map +1 -1
- package/dist/src/cost.js +124 -94
- package/dist/src/cost.js.map +1 -1
- package/dist/src/diagnostics.d.ts.map +1 -1
- package/dist/src/diagnostics.js +89 -5
- package/dist/src/diagnostics.js.map +1 -1
- package/dist/src/emit.d.ts +4 -3
- package/dist/src/emit.d.ts.map +1 -1
- package/dist/src/emit.js +28 -233
- package/dist/src/emit.js.map +1 -1
- package/dist/src/format.js.map +1 -1
- package/dist/src/index.d.ts +4 -3
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +3 -1
- package/dist/src/index.js.map +1 -1
- package/dist/src/ir.d.ts.map +1 -1
- package/dist/src/lex.d.ts.map +1 -1
- package/dist/src/lsp/server.d.ts +32 -0
- package/dist/src/lsp/server.d.ts.map +1 -0
- package/dist/src/lsp/server.js +391 -0
- package/dist/src/lsp/server.js.map +1 -0
- package/dist/src/modules.d.ts +2 -0
- package/dist/src/modules.d.ts.map +1 -1
- package/dist/src/modules.js +14 -14
- package/dist/src/modules.js.map +1 -1
- package/dist/src/parse.js +3 -3
- package/dist/src/parse.js.map +1 -1
- package/dist/src/std-bundle.d.ts +2 -0
- package/dist/src/std-bundle.d.ts.map +1 -0
- package/dist/src/std-bundle.js +88 -0
- package/dist/src/std-bundle.js.map +1 -0
- package/dist/src/std-library.d.ts +5 -0
- package/dist/src/std-library.d.ts.map +1 -0
- package/dist/src/std-library.js +9 -0
- package/dist/src/std-library.js.map +1 -0
- package/dist/src/typecheck.d.ts.map +1 -1
- package/dist/src/typecheck.js +859 -156
- package/dist/src/typecheck.js.map +1 -1
- package/dist/src/version.d.ts +1 -1
- package/dist/src/version.d.ts.map +1 -1
- package/dist/src/version.js +1 -1
- package/dist/src/version.js.map +1 -1
- package/docs/README.md +12 -0
- package/docs/assets/hsx.svg +18 -0
- package/docs/guide/01-first-program.md +2 -2
- package/docs/guide/02-money.md +1 -1
- package/docs/guide/03-instruments.md +44 -3
- package/docs/guide/04-lifecycles.md +18 -3
- package/docs/guide/05-fees-and-splits.md +2 -2
- package/docs/guide/06-schedules.md +1 -1
- package/docs/guide/07-composition.md +8 -2
- package/docs/guide/08-writing-a-module.md +13 -2
- package/docs/guide/09-cost.md +3 -3
- package/docs/guide/10-diagnostics.md +1 -1
- package/docs/llms-full.txt +458 -194
- package/docs/llms.txt +2 -2
- package/docs/playground.md +55 -0
- package/docs/reference/cli.md +5 -3
- package/docs/reference/diagnostics.md +223 -37
- package/docs/reference/grammar.md +2 -2
- package/docs/reference/std/advance.md +2 -2
- package/docs/reference/std/cancellable_booking.md +10 -10
- package/docs/reference/std/captured_payment.md +14 -14
- package/docs/reference/std/conditional_disbursement.md +3 -3
- package/docs/reference/std/credit_facility.md +2 -2
- package/docs/reference/std/held_payment.md +37 -33
- package/docs/reference/std/instant_transfer.md +8 -8
- package/docs/reference/std/metered.md +2 -2
- package/docs/reference/std/pooled_split.md +2 -2
- package/docs/reference/std/premium_forward.md +13 -13
- package/docs/reference/std/reconciled_payout.md +2 -2
- package/docs/reference/std/recurring_collection.md +2 -2
- package/docs/reference/std/rotating_pool.md +2 -2
- package/docs/reference/std/scheduled.md +18 -18
- package/docs/reference/std/security_deposit.md +14 -14
- package/docs/reference/std/settlement_batch.md +2 -2
- package/docs/reference/std/swap.md +18 -18
- package/docs/reference/std/threshold_pool.md +2 -2
- package/docs/reference/std/weighted_distribution.md +2 -2
- package/docs/reference/types.md +1 -1
- package/docs/reference/udl-output.md +2 -3
- package/examples/01-first-program/README.md +1 -1
- package/examples/01-first-program/tip-jar.hsx +1 -1
- package/examples/02-imports-and-archetypes/README.md +1 -4
- package/examples/02-imports-and-archetypes/photo-booth.hsx +1 -1
- package/examples/03-diagnostics/corner-shop-fixed.hsx +1 -1
- package/examples/03-diagnostics/corner-shop.hsx +1 -1
- package/examples/04-complete-product/README.md +0 -3
- package/examples/04-complete-product/study-hall.hsx +1 -1
- package/examples/05-watch-club/README.md +0 -3
- package/examples/05-watch-club/watch-club.hsx +1 -1
- package/examples/README.md +35 -4
- package/examples/advance/advance.hsx +1 -1
- package/examples/advance/advance.udl +10 -5
- package/examples/cancellable_booking/cancellable_booking.hsx +1 -1
- package/examples/cancellable_booking/cancellable_booking.udl +3 -1
- package/examples/captured_payment/captured_payment.hsx +1 -1
- package/examples/captured_payment/captured_payment.udl +4 -1
- package/examples/conditional_disbursement/conditional_disbursement.hsx +1 -1
- package/examples/conditional_disbursement/conditional_disbursement.udl +5 -3
- package/examples/cost-table.json +1602 -382
- package/examples/credit_facility/credit_facility.hsx +1 -1
- package/examples/credit_facility/credit_facility.udl +16 -9
- package/examples/held_payment/held_payment.hsx +1 -1
- package/examples/held_payment/held_payment.udl +38 -3
- package/examples/instant_transfer/instant_transfer.hsx +1 -1
- package/examples/instant_transfer/instant_transfer.udl +11 -5
- package/examples/metered/metered.hsx +1 -1
- package/examples/metered/metered.udl +4 -2
- package/examples/pooled_split/pooled_split.hsx +1 -1
- package/examples/pooled_split/pooled_split.udl +6 -3
- package/examples/premium_forward/premium_forward.hsx +1 -1
- package/examples/premium_forward/premium_forward.udl +10 -4
- package/examples/reconciled_payout/reconciled_payout.hsx +1 -1
- package/examples/reconciled_payout/reconciled_payout.udl +4 -2
- package/examples/recurring_collection/recurring_collection.hsx +1 -1
- package/examples/recurring_collection/recurring_collection.udl +12 -7
- package/examples/rotating_pool/rotating_pool.hsx +1 -1
- package/examples/rotating_pool/rotating_pool.udl +14 -4
- package/examples/scheduled/scheduled.hsx +1 -1
- package/examples/scheduled/scheduled.udl +9 -4
- package/examples/security_deposit/security_deposit.hsx +1 -1
- package/examples/security_deposit/security_deposit.udl +17 -3
- package/examples/settlement_batch/settlement_batch.hsx +1 -1
- package/examples/swap/swap.hsx +1 -1
- package/examples/swap/swap.udl +12 -6
- package/examples/threshold_pool/threshold_pool.hsx +1 -1
- package/examples/threshold_pool/threshold_pool.udl +4 -2
- package/examples/weighted_distribution/weighted_distribution.hsx +1 -1
- package/examples/weighted_distribution/weighted_distribution.udl +4 -2
- package/package.json +15 -6
- package/skills/hsx/SKILL.md +26 -26
- package/src/ast.ts +34 -2
- package/src/cli.ts +32 -13
- package/src/compile.ts +15 -7
- package/src/cost.ts +176 -104
- package/src/diagnostics.ts +89 -4
- package/src/emit.ts +34 -266
- package/src/index.ts +10 -7
- package/src/lsp/server.ts +460 -0
- package/src/modules.ts +21 -13
- package/src/parse.ts +3 -3
- package/src/std-bundle.ts +91 -0
- package/src/std-library.ts +12 -0
- package/src/typecheck.ts +1147 -235
- package/src/version.ts +1 -1
- package/std/SEMANTICS.md +12 -3
- package/std/{settlements → money_flows}/advance.hsx +1 -1
- package/std/{settlements → money_flows}/cancellable_booking.hsx +4 -3
- package/std/{settlements → money_flows}/captured_payment.hsx +35 -6
- package/std/{settlements → money_flows}/conditional_disbursement.hsx +17 -16
- package/std/{settlements → money_flows}/credit_facility.hsx +1 -2
- package/std/{settlements → money_flows}/held_payment.hsx +59 -25
- package/std/money_flows/index.hsx +3 -0
- package/std/{settlements → money_flows}/instant_transfer.hsx +2 -3
- package/std/{settlements → money_flows}/metered.hsx +1 -1
- package/std/{settlements → money_flows}/pooled_split.hsx +3 -3
- package/std/{settlements → money_flows}/premium_forward.hsx +22 -23
- package/std/{settlements → money_flows}/reconciled_payout.hsx +3 -3
- package/std/{settlements → money_flows}/recurring_collection.hsx +1 -1
- package/std/{settlements → money_flows}/rotating_pool.hsx +8 -6
- package/std/{settlements → money_flows}/scheduled.hsx +22 -27
- package/std/{settlements → money_flows}/security_deposit.hsx +38 -14
- package/std/{settlements → money_flows}/settlement_batch.hsx +3 -3
- package/std/{settlements → money_flows}/swap.hsx +41 -16
- package/std/{settlements → money_flows}/threshold_pool.hsx +5 -5
- package/std/{settlements → money_flows}/weighted_distribution.hsx +6 -6
- package/docs/sessions/2026-09-02-two-instruments.hsx +0 -21
- package/docs/sessions/2026-09-02-two-instruments.md +0 -41
- package/std/settlements/index.hsx +0 -3
package/src/emit.ts
CHANGED
|
@@ -1,10 +1,9 @@
|
|
|
1
1
|
import {
|
|
2
|
-
serializeUdl,
|
|
3
2
|
validateUdl,
|
|
4
3
|
type UdlDocument,
|
|
5
4
|
type UdlIssueCode,
|
|
6
5
|
} from "@hyperscale0/udl";
|
|
7
|
-
import type {
|
|
6
|
+
import type { TypedInstrument, TypedProgram } from "./ir.ts";
|
|
8
7
|
|
|
9
8
|
export interface OriginMapEntry {
|
|
10
9
|
readonly path: string;
|
|
@@ -25,9 +24,7 @@ export type GeneralLowerResult =
|
|
|
25
24
|
| {
|
|
26
25
|
readonly ok: true;
|
|
27
26
|
readonly value: {
|
|
28
|
-
readonly canonicalUdl: string;
|
|
29
27
|
readonly document: UdlDocument;
|
|
30
|
-
readonly frame: Record<string, JsonValue>;
|
|
31
28
|
readonly originMap: readonly OriginMapEntry[];
|
|
32
29
|
};
|
|
33
30
|
};
|
|
@@ -58,11 +55,7 @@ export function lowerGeneralProgram(program: TypedProgram): GeneralLowerResult {
|
|
|
58
55
|
udl: 1,
|
|
59
56
|
version: 1,
|
|
60
57
|
};
|
|
61
|
-
const
|
|
62
|
-
const unresolved = [
|
|
63
|
-
...unresolvedCompilerMarkers(candidate),
|
|
64
|
-
...unresolvedCompilerMarkers(frame, "$.frame"),
|
|
65
|
-
];
|
|
58
|
+
const unresolved = unresolvedCompilerMarkers(candidate);
|
|
66
59
|
if (unresolved.length > 0) {
|
|
67
60
|
const origins = originMapFor(program);
|
|
68
61
|
return {
|
|
@@ -77,7 +70,9 @@ export function lowerGeneralProgram(program: TypedProgram): GeneralLowerResult {
|
|
|
77
70
|
ok: false,
|
|
78
71
|
};
|
|
79
72
|
}
|
|
80
|
-
const validation = validateUdl(candidate
|
|
73
|
+
const validation = validateUdl(candidate, {
|
|
74
|
+
requireDecisionPartyBindings: true,
|
|
75
|
+
});
|
|
81
76
|
if (!validation.ok) {
|
|
82
77
|
const origins = originMapFor(program);
|
|
83
78
|
return {
|
|
@@ -99,9 +94,7 @@ export function lowerGeneralProgram(program: TypedProgram): GeneralLowerResult {
|
|
|
99
94
|
return {
|
|
100
95
|
ok: true,
|
|
101
96
|
value: {
|
|
102
|
-
canonicalUdl: serializeUdl(document),
|
|
103
97
|
document,
|
|
104
|
-
frame,
|
|
105
98
|
originMap: originMapFor(program),
|
|
106
99
|
},
|
|
107
100
|
};
|
|
@@ -135,21 +128,36 @@ function unresolvedCompilerMarkers(
|
|
|
135
128
|
});
|
|
136
129
|
}
|
|
137
130
|
|
|
138
|
-
function originForUdlPath(
|
|
131
|
+
export function originForUdlPath<T extends { readonly path: string }>(
|
|
139
132
|
path: string,
|
|
140
|
-
origins: readonly
|
|
141
|
-
):
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
133
|
+
origins: readonly T[],
|
|
134
|
+
): T | undefined {
|
|
135
|
+
let longestMatch: T | undefined;
|
|
136
|
+
let longestLength = -1;
|
|
137
|
+
let rootFallback: T | undefined;
|
|
138
|
+
|
|
139
|
+
for (let i = 0; i < origins.length; i += 1) {
|
|
140
|
+
const entry = origins[i]!;
|
|
141
|
+
const entryPath = entry.path;
|
|
142
|
+
if (rootFallback === undefined && entryPath === "$") {
|
|
143
|
+
rootFallback = entry;
|
|
144
|
+
}
|
|
145
|
+
const entryLen = entryPath.length;
|
|
146
|
+
if (
|
|
147
|
+
path === entryPath ||
|
|
148
|
+
(path.length > entryLen &&
|
|
149
|
+
(path.charCodeAt(entryLen) === 46 ||
|
|
150
|
+
path.charCodeAt(entryLen) === 91) &&
|
|
151
|
+
path.startsWith(entryPath))
|
|
152
|
+
) {
|
|
153
|
+
if (entryLen > longestLength) {
|
|
154
|
+
longestMatch = entry;
|
|
155
|
+
longestLength = entryLen;
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
return longestMatch ?? rootFallback;
|
|
153
161
|
}
|
|
154
162
|
|
|
155
163
|
export function requiredFields(instrument: TypedInstrument): string[] {
|
|
@@ -182,240 +190,6 @@ export function requiredFields(instrument: TypedInstrument): string[] {
|
|
|
182
190
|
];
|
|
183
191
|
}
|
|
184
192
|
|
|
185
|
-
function frameFor(program: TypedProgram): Record<string, JsonValue> {
|
|
186
|
-
const actors = new Map<string, Record<string, JsonValue>>();
|
|
187
|
-
const moneyEvents: Record<string, JsonValue>[] = [];
|
|
188
|
-
const design: string[] = [];
|
|
189
|
-
const fees: Record<string, JsonValue>[] = [];
|
|
190
|
-
const mechanics = new Set<string>();
|
|
191
|
-
const eventKeys = new Set<string>();
|
|
192
|
-
const ensureActor = (rawKey: string, role: string): string => {
|
|
193
|
-
const key = frameKey(rawKey);
|
|
194
|
-
if (!actors.has(key)) {
|
|
195
|
-
actors.set(key, {
|
|
196
|
-
key,
|
|
197
|
-
label: titleize(key),
|
|
198
|
-
maxCount: 1,
|
|
199
|
-
minCount: 1,
|
|
200
|
-
role,
|
|
201
|
-
});
|
|
202
|
-
}
|
|
203
|
-
return key;
|
|
204
|
-
};
|
|
205
|
-
const uniqueEventKey = (raw: string): string => {
|
|
206
|
-
const base = frameKey(raw);
|
|
207
|
-
let key = base;
|
|
208
|
-
let ordinal = 2;
|
|
209
|
-
while (eventKeys.has(key)) {
|
|
210
|
-
const suffix = `_${ordinal}`;
|
|
211
|
-
key = `${base.slice(0, 40 - suffix.length)}${suffix}`;
|
|
212
|
-
ordinal += 1;
|
|
213
|
-
}
|
|
214
|
-
eventKeys.add(key);
|
|
215
|
-
return key;
|
|
216
|
-
};
|
|
217
|
-
for (const instrument of program.instruments) {
|
|
218
|
-
const actorByField = new Map<string, string>();
|
|
219
|
-
const parties = instrument.slots.parties;
|
|
220
|
-
if (parties && typeof parties === "object" && !Array.isArray(parties)) {
|
|
221
|
-
for (const [role, value] of Object.entries(parties)) {
|
|
222
|
-
if (typeof value !== "string") continue;
|
|
223
|
-
const actor = ensureActor(role, frameActorRole(role, "source"));
|
|
224
|
-
actorByField.set(value, actor);
|
|
225
|
-
}
|
|
226
|
-
}
|
|
227
|
-
for (const action of instrument.actions) {
|
|
228
|
-
if (action.slots.due) mechanics.add("recurring_billing");
|
|
229
|
-
const moves = action.slots.moves;
|
|
230
|
-
if (!Array.isArray(moves)) continue;
|
|
231
|
-
moves.forEach((move, index) => {
|
|
232
|
-
if (moneyEvents.length >= 20) return;
|
|
233
|
-
if (!move || typeof move !== "object" || Array.isArray(move)) return;
|
|
234
|
-
const bind =
|
|
235
|
-
move.bind &&
|
|
236
|
-
typeof move.bind === "object" &&
|
|
237
|
-
!Array.isArray(move.bind)
|
|
238
|
-
? move.bind
|
|
239
|
-
: {};
|
|
240
|
-
const source = frameActorForBinding(
|
|
241
|
-
bind.sourceAccountId,
|
|
242
|
-
actorByField,
|
|
243
|
-
"source",
|
|
244
|
-
ensureActor,
|
|
245
|
-
);
|
|
246
|
-
const destination = frameActorForBinding(
|
|
247
|
-
bind.destinationAccountId,
|
|
248
|
-
actorByField,
|
|
249
|
-
"destination",
|
|
250
|
-
ensureActor,
|
|
251
|
-
);
|
|
252
|
-
const operation =
|
|
253
|
-
typeof move.operation === "string" ? move.operation : "transfer";
|
|
254
|
-
if (source === "escrow" || destination === "escrow") {
|
|
255
|
-
mechanics.add("escrow");
|
|
256
|
-
}
|
|
257
|
-
moneyEvents.push({
|
|
258
|
-
allocationTotalBps: 0,
|
|
259
|
-
amount: bindingWords(bind.amount) || "the declared amount",
|
|
260
|
-
amountDependencies: [],
|
|
261
|
-
amountMode: "fixed",
|
|
262
|
-
amountSchedule: [],
|
|
263
|
-
distribution: "single",
|
|
264
|
-
fromActor: source,
|
|
265
|
-
key: uniqueEventKey(
|
|
266
|
-
typeof move.key === "string"
|
|
267
|
-
? move.key
|
|
268
|
-
: `${instrument.id}_${action.name}_${index + 1}`,
|
|
269
|
-
),
|
|
270
|
-
kind: frameEventKind(operation, source, destination),
|
|
271
|
-
label: `${titleize(action.name)} movement`,
|
|
272
|
-
occurrence: action.slots.due ? "repeatable" : "once",
|
|
273
|
-
timing: action.name === "create" ? "on_create" : "on_lifecycle",
|
|
274
|
-
toActor: destination,
|
|
275
|
-
trigger: `when ${action.name.replaceAll("_", " ")} runs`,
|
|
276
|
-
});
|
|
277
|
-
});
|
|
278
|
-
}
|
|
279
|
-
if (design.length < 10) {
|
|
280
|
-
design.push(
|
|
281
|
-
`${instrument.id}: ${instrument.fields.length} fields and ${instrument.actions.length} actions`,
|
|
282
|
-
);
|
|
283
|
-
}
|
|
284
|
-
const feeRules = instrument.slots.feeRules;
|
|
285
|
-
if (Array.isArray(feeRules)) {
|
|
286
|
-
feeRules.forEach((fee, index) => {
|
|
287
|
-
if (fees.length >= 4) return;
|
|
288
|
-
if (!fee || typeof fee !== "object" || Array.isArray(fee)) return;
|
|
289
|
-
fees.push({
|
|
290
|
-
label: `${titleize(instrument.id)} fee ${index + 1}`,
|
|
291
|
-
on:
|
|
292
|
-
typeof fee.baseField === "string"
|
|
293
|
-
? fee.baseField
|
|
294
|
-
: `${instrument.id} movement`,
|
|
295
|
-
structure:
|
|
296
|
-
typeof fee.position === "string"
|
|
297
|
-
? `${fee.position.replaceAll("_", " ")} fee`
|
|
298
|
-
: "declared fee",
|
|
299
|
-
});
|
|
300
|
-
});
|
|
301
|
-
}
|
|
302
|
-
}
|
|
303
|
-
if (actors.size === 0) ensureActor("platform", "platform");
|
|
304
|
-
if (moneyEvents.length === 0) {
|
|
305
|
-
const actor = actors.keys().next().value ?? "platform";
|
|
306
|
-
moneyEvents.push({
|
|
307
|
-
allocationTotalBps: 0,
|
|
308
|
-
amount: "the declared settlement amount",
|
|
309
|
-
amountDependencies: [],
|
|
310
|
-
amountMode: "fixed",
|
|
311
|
-
amountSchedule: [],
|
|
312
|
-
distribution: "single",
|
|
313
|
-
fromActor: actor,
|
|
314
|
-
key: uniqueEventKey(`${program.name}_create`),
|
|
315
|
-
kind: "charge",
|
|
316
|
-
label: `${program.title} movement`,
|
|
317
|
-
occurrence: "once",
|
|
318
|
-
timing: "on_create",
|
|
319
|
-
toActor: actor,
|
|
320
|
-
trigger: "when the settlement is created",
|
|
321
|
-
});
|
|
322
|
-
}
|
|
323
|
-
if (mechanics.size === 0) mechanics.add("escrow");
|
|
324
|
-
return {
|
|
325
|
-
actors: [...actors.values()],
|
|
326
|
-
confidence: "high",
|
|
327
|
-
conservationGroups: [],
|
|
328
|
-
design,
|
|
329
|
-
feePolicy: fees.length > 0 ? "defined" : "none",
|
|
330
|
-
fees,
|
|
331
|
-
headline: program.title,
|
|
332
|
-
mechanics: [...mechanics],
|
|
333
|
-
moneyEvents,
|
|
334
|
-
offPlatform: [],
|
|
335
|
-
openQuestions: [],
|
|
336
|
-
rules: [],
|
|
337
|
-
subjects: program.subjects.map((subject) => ({
|
|
338
|
-
kind: subject.kind,
|
|
339
|
-
title: subject.title,
|
|
340
|
-
})),
|
|
341
|
-
summary: `${program.title} compiles ${program.instruments.length} financial instrument${program.instruments.length === 1 ? "" : "s"}.`,
|
|
342
|
-
};
|
|
343
|
-
}
|
|
344
|
-
|
|
345
|
-
function frameActorForBinding(
|
|
346
|
-
value: JsonValue | undefined,
|
|
347
|
-
actorByField: ReadonlyMap<string, string>,
|
|
348
|
-
direction: "destination" | "source",
|
|
349
|
-
ensureActor: (key: string, role: string) => string,
|
|
350
|
-
): string {
|
|
351
|
-
const path = bindingWords(value);
|
|
352
|
-
if (path.includes("escrowAccountId")) return "escrow";
|
|
353
|
-
const field = path.startsWith("fields.")
|
|
354
|
-
? path.slice("fields.".length)
|
|
355
|
-
: path;
|
|
356
|
-
const declared = actorByField.get(field);
|
|
357
|
-
if (declared) return declared;
|
|
358
|
-
if (field.toLowerCase().includes("platform")) {
|
|
359
|
-
return ensureActor("platform", "platform");
|
|
360
|
-
}
|
|
361
|
-
return ensureActor(
|
|
362
|
-
direction === "source" ? "payer" : "beneficiary",
|
|
363
|
-
direction === "source" ? "payer" : "beneficiary",
|
|
364
|
-
);
|
|
365
|
-
}
|
|
366
|
-
|
|
367
|
-
function frameActorRole(
|
|
368
|
-
role: string,
|
|
369
|
-
direction: "destination" | "source",
|
|
370
|
-
): string {
|
|
371
|
-
return [
|
|
372
|
-
"payer",
|
|
373
|
-
"beneficiary",
|
|
374
|
-
"platform",
|
|
375
|
-
"provider",
|
|
376
|
-
"guardian",
|
|
377
|
-
"holder",
|
|
378
|
-
].includes(role)
|
|
379
|
-
? role
|
|
380
|
-
: direction === "source"
|
|
381
|
-
? "payer"
|
|
382
|
-
: "beneficiary";
|
|
383
|
-
}
|
|
384
|
-
|
|
385
|
-
function frameEventKind(
|
|
386
|
-
operation: string,
|
|
387
|
-
source: string,
|
|
388
|
-
destination: string,
|
|
389
|
-
): string {
|
|
390
|
-
if (operation.endsWith(".reserve")) return "hold";
|
|
391
|
-
if (operation.endsWith(".void") || operation.endsWith(".return")) {
|
|
392
|
-
return "refund";
|
|
393
|
-
}
|
|
394
|
-
if (operation.startsWith("payout.")) return "payout";
|
|
395
|
-
if (source === "escrow" || destination === "escrow") return "release";
|
|
396
|
-
return "charge";
|
|
397
|
-
}
|
|
398
|
-
|
|
399
|
-
function frameKey(value: string): string {
|
|
400
|
-
const snake = value
|
|
401
|
-
.replace(/([a-z0-9])([A-Z])/g, "$1_$2")
|
|
402
|
-
.replace(/[^A-Za-z0-9]+/g, "_")
|
|
403
|
-
.replace(/^_+|_+$/g, "")
|
|
404
|
-
.toLowerCase();
|
|
405
|
-
const leading = /^[a-z]/.test(snake) ? snake : `event_${snake}`;
|
|
406
|
-
return leading.slice(0, 40) || "event";
|
|
407
|
-
}
|
|
408
|
-
|
|
409
|
-
function bindingWords(value: JsonValue | undefined): string {
|
|
410
|
-
if (typeof value === "string") return value;
|
|
411
|
-
if (!value || typeof value !== "object" || Array.isArray(value)) return "";
|
|
412
|
-
const binding = value as Readonly<Record<string, JsonValue>>;
|
|
413
|
-
if (binding.from === "const" && typeof binding.value === "string")
|
|
414
|
-
return binding.value;
|
|
415
|
-
if (typeof binding.path === "string") return binding.path;
|
|
416
|
-
return "";
|
|
417
|
-
}
|
|
418
|
-
|
|
419
193
|
function originMapFor(program: TypedProgram): OriginMapEntry[] {
|
|
420
194
|
const entries: OriginMapEntry[] = [{ path: "$", span: program.origin }];
|
|
421
195
|
program.subjects.forEach((subject, index) => {
|
|
@@ -439,9 +213,3 @@ function originMapFor(program: TypedProgram): OriginMapEntry[] {
|
|
|
439
213
|
});
|
|
440
214
|
return entries;
|
|
441
215
|
}
|
|
442
|
-
|
|
443
|
-
function titleize(value: string): string {
|
|
444
|
-
return value
|
|
445
|
-
.replaceAll("_", " ")
|
|
446
|
-
.replace(/\b[a-z]/g, (letter) => letter.toUpperCase());
|
|
447
|
-
}
|
package/src/index.ts
CHANGED
|
@@ -12,6 +12,7 @@ export {
|
|
|
12
12
|
type HsxEffectKind,
|
|
13
13
|
type UdlCostManifest,
|
|
14
14
|
type UdlCostTable,
|
|
15
|
+
type UdlCostTables,
|
|
15
16
|
} from "./cost.ts";
|
|
16
17
|
export {
|
|
17
18
|
hsxDiagnostics,
|
|
@@ -27,13 +28,15 @@ export {
|
|
|
27
28
|
type ProgramEntryOverrideValue,
|
|
28
29
|
} from "./entry-overrides.ts";
|
|
29
30
|
export { type OriginMapEntry } from "./emit.ts";
|
|
30
|
-
export { lowerGeneralProgram } from "./emit.ts";
|
|
31
|
+
export { lowerGeneralProgram, originForUdlPath } from "./emit.ts";
|
|
31
32
|
export { parseProgram } from "./parse.ts";
|
|
32
33
|
export { checkGeneralProgram, type GeneralCheckOptions } from "./typecheck.ts";
|
|
33
|
-
export
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
34
|
+
export {
|
|
35
|
+
byteOffsetToCodeUnit,
|
|
36
|
+
type BlockExpr,
|
|
37
|
+
type ExposeDecl,
|
|
38
|
+
type Program,
|
|
39
|
+
type ProgramDecl,
|
|
40
|
+
type UseDecl,
|
|
39
41
|
} from "./ast.ts";
|
|
42
|
+
export { bundledStandardLibrary, type StandardLibrary } from "./std-library.ts";
|