@hyperscale0/udl 4.0.0 → 4.2.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 +11 -0
- package/dist/diagnostics.d.ts +7 -1
- package/dist/diagnostics.d.ts.map +1 -1
- package/dist/diagnostics.js +1 -3
- package/dist/diagnostics.js.map +1 -1
- package/dist/finance.d.ts +6 -0
- package/dist/finance.d.ts.map +1 -1
- package/dist/finance.js +33 -2
- package/dist/finance.js.map +1 -1
- package/dist/object-contract.d.ts +8 -13
- package/dist/object-contract.d.ts.map +1 -1
- package/dist/object-contract.js +11 -29
- package/dist/object-contract.js.map +1 -1
- package/dist/reporting.d.ts +0 -1
- package/dist/reporting.d.ts.map +1 -1
- package/dist/reporting.js +0 -1
- package/dist/reporting.js.map +1 -1
- package/dist/schema.d.ts +3 -119
- package/dist/schema.d.ts.map +1 -1
- package/dist/schema.js +1 -21
- package/dist/schema.js.map +1 -1
- package/dist/validation.d.ts.map +1 -1
- package/dist/validation.js +4 -38
- package/dist/validation.js.map +1 -1
- package/docs/README.md +5 -8
- package/package.json +2 -2
- package/spec/README.md +5 -8
- package/spec/udl.schema.json +4 -95
- package/src/diagnostics.ts +7 -7
- package/src/finance.ts +45 -4
- package/src/object-contract.ts +14 -35
- package/src/reporting.ts +0 -1
- package/src/schema.ts +1 -21
- package/src/validation.ts +4 -81
package/src/object-contract.ts
CHANGED
|
@@ -2,7 +2,6 @@ import * as z from "zod";
|
|
|
2
2
|
import {
|
|
3
3
|
udlExternalIdSchema,
|
|
4
4
|
udlObjectIdSchema,
|
|
5
|
-
udlPartyNameSchema,
|
|
6
5
|
type UdlDocument,
|
|
7
6
|
type UdlField,
|
|
8
7
|
type UdlObjectField,
|
|
@@ -30,19 +29,11 @@ export const requestAttributionSchema = z.union([
|
|
|
30
29
|
]);
|
|
31
30
|
export type RequestAttribution = z.infer<typeof requestAttributionSchema>;
|
|
32
31
|
|
|
33
|
-
export const objectApprovalRequirementSchema = z.strictObject({
|
|
34
|
-
target: z.string().min(1),
|
|
35
|
-
action: udlPartyNameSchema,
|
|
36
|
-
party: udlPartyNameSchema,
|
|
37
|
-
role: udlPartyNameSchema,
|
|
38
|
-
decision: z.enum(["approved", "declined"]),
|
|
39
|
-
protectedRequest: z.string().min(1),
|
|
40
|
-
differentFromInitiator: z.boolean(),
|
|
41
|
-
});
|
|
42
|
-
|
|
43
32
|
export type JsonSchemaDocument = z.core.JSONSchema.BaseSchema;
|
|
44
33
|
|
|
45
34
|
export interface ObjectKindDiscovery {
|
|
35
|
+
productBuildId: string;
|
|
36
|
+
digest: string;
|
|
46
37
|
creation: true;
|
|
47
38
|
kind: string;
|
|
48
39
|
title: string;
|
|
@@ -61,9 +52,7 @@ export interface ObjectActionContext {
|
|
|
61
52
|
target: ObjectActionTarget;
|
|
62
53
|
}
|
|
63
54
|
export interface ObjectActionDiscovery extends ObjectActionContext {
|
|
64
|
-
|
|
65
|
-
typeof objectApprovalRequirementSchema
|
|
66
|
-
>[];
|
|
55
|
+
summary: string;
|
|
67
56
|
name: string;
|
|
68
57
|
title: string;
|
|
69
58
|
instrument: string;
|
|
@@ -111,6 +100,7 @@ export type RetainedObjectKind = Pick<
|
|
|
111
100
|
creation: false;
|
|
112
101
|
};
|
|
113
102
|
export interface ObjectDiscovery {
|
|
103
|
+
navigation: readonly { kind: string; title: string; creation: boolean }[];
|
|
114
104
|
retainedKinds: readonly RetainedObjectKind[];
|
|
115
105
|
productBuildId: string;
|
|
116
106
|
digest: string;
|
|
@@ -248,8 +238,14 @@ export function projectObjectDiscovery(
|
|
|
248
238
|
): ObjectDiscovery {
|
|
249
239
|
return {
|
|
250
240
|
...build,
|
|
241
|
+
navigation: document.objects.map((kind) => ({
|
|
242
|
+
kind: kind.id,
|
|
243
|
+
title: kind.title,
|
|
244
|
+
creation: true,
|
|
245
|
+
})),
|
|
251
246
|
retainedKinds: [],
|
|
252
247
|
kinds: document.objects.map((kind) => ({
|
|
248
|
+
...build,
|
|
253
249
|
creation: true,
|
|
254
250
|
kind: kind.id,
|
|
255
251
|
title: kind.title,
|
|
@@ -337,29 +333,12 @@ export function projectObjectDiscovery(
|
|
|
337
333
|
)!.name,
|
|
338
334
|
},
|
|
339
335
|
name: action.publicAction,
|
|
340
|
-
title: action.
|
|
336
|
+
title: action.publicAction
|
|
337
|
+
.replace(/_/g, " ")
|
|
338
|
+
.replace(/^./, (letter) => letter.toUpperCase()),
|
|
339
|
+
summary: action.summary,
|
|
341
340
|
instrument: instrument.id,
|
|
342
341
|
action: name,
|
|
343
|
-
approvalRequirements: action.requires.flatMap((rule) => {
|
|
344
|
-
if (rule.kind !== "approval") return [];
|
|
345
|
-
const party = document.parties[rule.party];
|
|
346
|
-
if (party?.kind !== "staff" || !party.role)
|
|
347
|
-
throw new Error(
|
|
348
|
-
`Approval party ${rule.party} has no staff authority`,
|
|
349
|
-
);
|
|
350
|
-
return [
|
|
351
|
-
{
|
|
352
|
-
target: rule.target ?? "self",
|
|
353
|
-
action: rule.action ?? name,
|
|
354
|
-
party: rule.party,
|
|
355
|
-
role: party.role,
|
|
356
|
-
decision: rule.decision,
|
|
357
|
-
protectedRequest: rule.protectedRequest ?? "self",
|
|
358
|
-
differentFromInitiator:
|
|
359
|
-
rule.differentFromInitiator === true,
|
|
360
|
-
},
|
|
361
|
-
];
|
|
362
|
-
}),
|
|
363
342
|
requirements: mergedReqs.map(
|
|
364
343
|
(requirement) =>
|
|
365
344
|
({
|
package/src/reporting.ts
CHANGED
|
@@ -171,7 +171,6 @@ export const reportDefinitionSchema = z.strictObject({
|
|
|
171
171
|
request: z.array(name).min(1).max(64),
|
|
172
172
|
read: z.array(name).min(1).max(64),
|
|
173
173
|
release: z.array(name).max(64),
|
|
174
|
-
independentApproval: z.literal(true),
|
|
175
174
|
retention: z.strictObject({ policy: name, years: integer.min(1).max(100) }),
|
|
176
175
|
}),
|
|
177
176
|
});
|
package/src/schema.ts
CHANGED
|
@@ -328,15 +328,6 @@ export const udlRequirementSchema = z.discriminatedUnion("kind", [
|
|
|
328
328
|
operator: z.enum(["==", "<=", ">=", "<", ">"]),
|
|
329
329
|
value,
|
|
330
330
|
}),
|
|
331
|
-
z.strictObject({
|
|
332
|
-
kind: z.literal("approval"),
|
|
333
|
-
target: path.default("self"),
|
|
334
|
-
party: name,
|
|
335
|
-
action: name.optional(),
|
|
336
|
-
decision: z.enum(["approved", "declined"]),
|
|
337
|
-
differentFromInitiator: z.literal(true).optional(),
|
|
338
|
-
protectedRequest: path.default("self"),
|
|
339
|
-
}),
|
|
340
331
|
z.strictObject({
|
|
341
332
|
kind: z.literal("evidence"),
|
|
342
333
|
instruction: path.optional(),
|
|
@@ -398,10 +389,10 @@ const clock = z.strictObject({
|
|
|
398
389
|
.optional(),
|
|
399
390
|
});
|
|
400
391
|
export const udlActionSchema = z.strictObject({
|
|
392
|
+
allowZero: z.literal(true).optional(),
|
|
401
393
|
summary: text,
|
|
402
394
|
publicAction: name.optional(),
|
|
403
395
|
expansionLimit: z.literal(8192).optional(),
|
|
404
|
-
humanApproval: z.literal("distinct_member").optional(),
|
|
405
396
|
reminder: z
|
|
406
397
|
.strictObject({
|
|
407
398
|
installment: path,
|
|
@@ -466,17 +457,6 @@ export const udlActionSchema = z.strictObject({
|
|
|
466
457
|
)
|
|
467
458
|
.max(16)
|
|
468
459
|
.optional(),
|
|
469
|
-
approval: z
|
|
470
|
-
.strictObject({
|
|
471
|
-
protectedRequest: path.default("self"),
|
|
472
|
-
target: path,
|
|
473
|
-
action: name,
|
|
474
|
-
party: name,
|
|
475
|
-
expires: path,
|
|
476
|
-
input: z.record(name, value),
|
|
477
|
-
decision: z.enum(["approved", "declined"]),
|
|
478
|
-
})
|
|
479
|
-
.optional(),
|
|
480
460
|
});
|
|
481
461
|
export const udlLifecycleSchema = z.strictObject({
|
|
482
462
|
states: z.array(name).min(1).max(64),
|
package/src/validation.ts
CHANGED
|
@@ -61,10 +61,6 @@ function moneyParty(
|
|
|
61
61
|
(!instrument?.subject && document.parties[name]?.kind === "person"))
|
|
62
62
|
);
|
|
63
63
|
}
|
|
64
|
-
function approvalParty(document: UdlDocument, name: string): boolean {
|
|
65
|
-
const party = document.parties[name];
|
|
66
|
-
return party?.kind === "staff" && !!party.role;
|
|
67
|
-
}
|
|
68
64
|
|
|
69
65
|
export type UdlValidationResult =
|
|
70
66
|
| { ok: true; value: UdlDocument }
|
|
@@ -1039,38 +1035,6 @@ export function validateUdl(value: unknown): UdlValidationResult {
|
|
|
1039
1035
|
for (const p of req.fields)
|
|
1040
1036
|
if (!field(p, input, act))
|
|
1041
1037
|
add(where, `unknown identity field ${p}`);
|
|
1042
|
-
} else if (req.kind === "approval") {
|
|
1043
|
-
const request = expect(
|
|
1044
|
-
req.protectedRequest,
|
|
1045
|
-
"ref",
|
|
1046
|
-
where,
|
|
1047
|
-
input,
|
|
1048
|
-
act,
|
|
1049
|
-
);
|
|
1050
|
-
if (request?.type === "ref" && request.targetKind !== "instrument")
|
|
1051
|
-
add(
|
|
1052
|
-
where,
|
|
1053
|
-
"protectedRequest must reference an instrument",
|
|
1054
|
-
"UDL5001",
|
|
1055
|
-
);
|
|
1056
|
-
const target = expect(req.target, "ref", where, input, act);
|
|
1057
|
-
if (!approvalParty(document, req.party))
|
|
1058
|
-
add(
|
|
1059
|
-
where,
|
|
1060
|
-
`approval requires staff with a role: ${req.party}`,
|
|
1061
|
-
hasParty(document, inst, req.party)
|
|
1062
|
-
? "party_kind_mismatch"
|
|
1063
|
-
: "subject_party_unbound",
|
|
1064
|
-
);
|
|
1065
|
-
if (
|
|
1066
|
-
req.action &&
|
|
1067
|
-
target?.type === "ref" &&
|
|
1068
|
-
target.targetKind === "instrument" &&
|
|
1069
|
-
targetIds(target.target).some(
|
|
1070
|
-
(id) => !byId.get(id)?.actions[req.action!],
|
|
1071
|
-
)
|
|
1072
|
-
)
|
|
1073
|
-
add(where, `unknown approved action ${req.action}`);
|
|
1074
1038
|
} else if (req.kind === "evidence") {
|
|
1075
1039
|
if (req.instruction) {
|
|
1076
1040
|
expect(req.instruction, "text", where, input, act);
|
|
@@ -1376,48 +1340,6 @@ export function validateUdl(value: unknown): UdlValidationResult {
|
|
|
1376
1340
|
}
|
|
1377
1341
|
}
|
|
1378
1342
|
};
|
|
1379
|
-
if (action.approval) {
|
|
1380
|
-
const request = expect(
|
|
1381
|
-
action.approval.protectedRequest,
|
|
1382
|
-
"ref",
|
|
1383
|
-
where,
|
|
1384
|
-
action.input,
|
|
1385
|
-
action,
|
|
1386
|
-
);
|
|
1387
|
-
if (request?.type === "ref" && request.targetKind !== "instrument")
|
|
1388
|
-
add(
|
|
1389
|
-
where,
|
|
1390
|
-
"protectedRequest must reference an instrument",
|
|
1391
|
-
"UDL5001",
|
|
1392
|
-
);
|
|
1393
|
-
const reference = expect(
|
|
1394
|
-
action.approval.target,
|
|
1395
|
-
"ref",
|
|
1396
|
-
where,
|
|
1397
|
-
action.input,
|
|
1398
|
-
action,
|
|
1399
|
-
);
|
|
1400
|
-
if (
|
|
1401
|
-
reference?.type === "ref" &&
|
|
1402
|
-
reference.targetKind === "instrument" &&
|
|
1403
|
-
targetIds(reference.target).some(
|
|
1404
|
-
(id) => !byId.get(id)?.actions[action.approval!.action],
|
|
1405
|
-
)
|
|
1406
|
-
)
|
|
1407
|
-
add(where, "approval target action does not exist");
|
|
1408
|
-
if (reference?.type === "ref" && reference.targetKind === "instrument")
|
|
1409
|
-
for (const id of targetIds(reference.target))
|
|
1410
|
-
checkArguments(id, action.approval.action, action.approval.input);
|
|
1411
|
-
expect(action.approval.expires, "date", where, action.input, action);
|
|
1412
|
-
if (!approvalParty(document, action.approval.party))
|
|
1413
|
-
add(
|
|
1414
|
-
where,
|
|
1415
|
-
"approval requires staff with a role",
|
|
1416
|
-
hasParty(document, inst, action.approval.party)
|
|
1417
|
-
? "party_kind_mismatch"
|
|
1418
|
-
: "subject_party_unbound",
|
|
1419
|
-
);
|
|
1420
|
-
}
|
|
1421
1343
|
const targets: { targets: string[]; count: number }[] = [];
|
|
1422
1344
|
for (const call of action.invoke ?? []) {
|
|
1423
1345
|
if (call.guard)
|
|
@@ -1502,9 +1424,10 @@ export function validateUdl(value: unknown): UdlValidationResult {
|
|
|
1502
1424
|
}
|
|
1503
1425
|
if (!issues.some((i) => i.path.startsWith(base)))
|
|
1504
1426
|
issues.push(
|
|
1505
|
-
...analyzeInstrumentFinance(inst, document).map((i) =>
|
|
1506
|
-
issue("UDL4001", base + i.path, i.message),
|
|
1507
|
-
|
|
1427
|
+
...analyzeInstrumentFinance(inst, document).map((i) => ({
|
|
1428
|
+
...issue("UDL4001", base + i.path, i.message),
|
|
1429
|
+
...(i.stranded ? { stranded: i.stranded } : {}),
|
|
1430
|
+
})),
|
|
1508
1431
|
);
|
|
1509
1432
|
}
|
|
1510
1433
|
const active = new Set<string>();
|