@distrohelena/canton-typescript-sdk 0.1.22 → 0.1.25
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 +7 -3
- package/dist/daml-interface/analysis/analyzed-choice.d.ts +5 -5
- package/dist/daml-interface/analysis/analyzed-daml-type-definition.d.ts +6 -0
- package/dist/daml-interface/analysis/analyzed-daml-type-definition.js +1 -0
- package/dist/daml-interface/analysis/analyzed-daml-type.d.ts +55 -0
- package/dist/daml-interface/analysis/analyzed-daml-type.js +1 -0
- package/dist/daml-interface/analysis/analyzed-template.d.ts +3 -3
- package/dist/daml-interface/analysis/daml-interface-analyzer.d.ts +3 -1
- package/dist/daml-interface/analysis/daml-interface-analyzer.js +183 -19
- package/dist/daml-interface/emission/named-type-emitter.d.ts +41 -0
- package/dist/daml-interface/emission/named-type-emitter.js +445 -0
- package/dist/daml-interface/emission/project-emitter.d.ts +5 -1
- package/dist/daml-interface/emission/project-emitter.js +20 -3
- package/dist/daml-interface/emission/registry-emitter.d.ts +1 -0
- package/dist/daml-interface/emission/registry-emitter.js +15 -8
- package/dist/daml-interface/emission/support-file-emitter.d.ts +16 -1
- package/dist/daml-interface/emission/support-file-emitter.js +206 -6
- package/dist/daml-interface/emission/template-binding-emitter.d.ts +25 -1
- package/dist/daml-interface/emission/template-binding-emitter.js +371 -72
- package/dist/daml-interface/emission/type-script-name-resolver.d.ts +50 -3
- package/dist/daml-interface/emission/type-script-name-resolver.js +369 -11
- package/dist/daml-interface/emission-model/generated-choice-binding.d.ts +7 -0
- package/dist/daml-interface/emission-model/generated-choice-binding.js +6 -0
- package/dist/daml-interface/emission-model/generated-daml-interface-project.d.ts +3 -0
- package/dist/daml-interface/emission-model/generated-daml-interface-project.js +2 -0
- package/dist/daml-interface/emission-model/generated-named-type-file.d.ts +23 -0
- package/dist/daml-interface/emission-model/generated-named-type-file.js +23 -0
- package/dist/daml-interface/emission-model/generated-template-binding.d.ts +9 -0
- package/dist/daml-interface/emission-model/generated-template-binding.js +8 -0
- package/dist/daml-interface/index.d.ts +12 -0
- package/dist/daml-interface/index.js +9 -0
- package/dist/daml-interface/runtime/daml-event-source-normalizer.d.ts +52 -0
- package/dist/daml-interface/runtime/daml-event-source-normalizer.js +364 -0
- package/dist/daml-interface/runtime/daml-materialization-error.d.ts +5 -0
- package/dist/daml-interface/runtime/daml-materialization-error.js +9 -0
- package/dist/daml-interface/runtime/daml-template.d.ts +6 -0
- package/dist/daml-interface/runtime/daml-template.js +10 -0
- package/dist/daml-interface/runtime/daml-type-descriptor.d.ts +71 -0
- package/dist/daml-interface/runtime/daml-type-descriptor.js +1 -0
- package/dist/daml-interface/runtime/daml-value-converter.d.ts +7 -0
- package/dist/daml-interface/runtime/daml-value-converter.js +370 -0
- package/dist/daml-interface/runtime/daml-value-materializer.d.ts +3 -0
- package/dist/daml-interface/runtime/daml-value-materializer.js +23 -0
- package/dist/daml-interface/writing/daml-interface-writer.js +1 -0
- package/dist/daml-lf/daml-lf-compilation.d.ts +1 -0
- package/dist/daml-lf/daml-lf-compilation.js +17 -3
- package/dist/daml-lf/model/daml-lf-builtin-type.d.ts +9 -0
- package/dist/daml-lf/model/daml-lf-builtin-type.js +9 -0
- package/dist/daml-lf/model/daml-lf-data-type.d.ts +18 -1
- package/dist/daml-lf/model/daml-lf-data-type.js +8 -1
- package/dist/daml-lf/model/daml-lf-type.d.ts +2 -0
- package/dist/daml-lf/model/daml-lf-type.js +2 -0
- package/dist/daml-lf/model/lf-2-model-mapper.d.ts +1 -0
- package/dist/daml-lf/model/lf-2-model-mapper.js +81 -25
- package/dist/daml-lf/semantics/daml-lf-semantic-model.d.ts +3 -0
- package/dist/daml-lf/semantics/daml-lf-semantic-model.js +5 -1
- package/dist/query/pqs/pqs-query-client.js +15 -0
- package/dist/query/pqs/pqs-sql-compiler.js +35 -7
- package/node/.generated/start-local/additional-config.extra-participants.conf +107 -0
- package/node/.generated/start-local/additional-config.extra-validators.conf +85 -0
- package/node/.generated/start-local/compose-extra-participants.yaml +312 -0
- package/node/.generated/start-local/extra-participants.env +58 -0
- package/node/start-local.sh +69 -29
- package/node/test-start-local.sh +49 -8
- package/package.json +1 -1
|
@@ -0,0 +1,370 @@
|
|
|
1
|
+
import { DamlDate, DamlEnum, DamlGenMap, DamlRecord, DamlTextMap, DamlTimestamp, DamlUnit, DamlVariant, } from "../../core/types/daml-values.js";
|
|
2
|
+
import { DamlNumeric } from "../../core/types/daml-numeric.js";
|
|
3
|
+
import { DamlParty } from "../../core/types/daml-party.js";
|
|
4
|
+
import { DamlMaterializationError } from "./daml-materialization-error.js";
|
|
5
|
+
const DAML_MIN_DATE_DAYS_SINCE_EPOCH = -719162;
|
|
6
|
+
const DAML_MAX_DATE_DAYS_SINCE_EPOCH = 2932896;
|
|
7
|
+
const DAML_MIN_TIMESTAMP_MICROSECONDS = -62135596800000000n;
|
|
8
|
+
const DAML_MAX_TIMESTAMP_MICROSECONDS = 253402300799999999n;
|
|
9
|
+
const DAML_MIN_INT64 = -9223372036854775808n;
|
|
10
|
+
const DAML_MAX_INT64 = 9223372036854775807n;
|
|
11
|
+
/** Decodes a protobuf or JSON/PQS DAML value according to its generated descriptor. */
|
|
12
|
+
export function decodeDamlValue(source, descriptor, registry, path) {
|
|
13
|
+
if (descriptor.kind === "namedReference") {
|
|
14
|
+
const factory = registry.resolve(descriptor.identity);
|
|
15
|
+
if (factory === undefined) {
|
|
16
|
+
throw materializationError(path, "named type descriptor is not registered");
|
|
17
|
+
}
|
|
18
|
+
return decodeDamlValue(source, factory(), registry, path);
|
|
19
|
+
}
|
|
20
|
+
else if (source.kind === "protobuf") {
|
|
21
|
+
return decodeProtobufValue(source.value, descriptor, registry, path);
|
|
22
|
+
}
|
|
23
|
+
return decodeJsonValue(source.value, descriptor, registry, path);
|
|
24
|
+
}
|
|
25
|
+
function decodeProtobufValue(value, descriptor, registry, path) {
|
|
26
|
+
switch (value.sum.oneofKind) {
|
|
27
|
+
case undefined:
|
|
28
|
+
throw materializationError(path, "value is absent");
|
|
29
|
+
case "unit":
|
|
30
|
+
requirePrimitiveDescriptor(descriptor, "unit", path);
|
|
31
|
+
return new DamlUnit();
|
|
32
|
+
case "bool":
|
|
33
|
+
requirePrimitiveDescriptor(descriptor, "bool", path);
|
|
34
|
+
return value.sum.bool;
|
|
35
|
+
case "int64":
|
|
36
|
+
requirePrimitiveDescriptor(descriptor, "int64", path);
|
|
37
|
+
return decodeInt64(value.sum.int64, path);
|
|
38
|
+
case "date":
|
|
39
|
+
requirePrimitiveDescriptor(descriptor, "date", path);
|
|
40
|
+
return decodeDate(value.sum.date, path);
|
|
41
|
+
case "timestamp":
|
|
42
|
+
requirePrimitiveDescriptor(descriptor, "timestamp", path);
|
|
43
|
+
return decodeTimestamp(value.sum.timestamp, path);
|
|
44
|
+
case "numeric":
|
|
45
|
+
requirePrimitiveDescriptor(descriptor, "numeric", path);
|
|
46
|
+
return decodeNumeric(value.sum.numeric, descriptor.numericScale, path);
|
|
47
|
+
case "party":
|
|
48
|
+
requirePrimitiveDescriptor(descriptor, "party", path);
|
|
49
|
+
return decodeParty(value.sum.party, path);
|
|
50
|
+
case "text":
|
|
51
|
+
requirePrimitiveDescriptor(descriptor, "text", path);
|
|
52
|
+
return value.sum.text;
|
|
53
|
+
case "contractId":
|
|
54
|
+
requireDescriptorKind(descriptor, "contractId", path, "contractId");
|
|
55
|
+
return value.sum.contractId;
|
|
56
|
+
case "optional":
|
|
57
|
+
requireDescriptorKind(descriptor, "optional", path, "optional");
|
|
58
|
+
return value.sum.optional.value === undefined
|
|
59
|
+
? undefined
|
|
60
|
+
: decodeDamlValue({ kind: "protobuf", value: value.sum.optional.value }, descriptor.element, registry, path);
|
|
61
|
+
case "list":
|
|
62
|
+
requireDescriptorKind(descriptor, "list", path, "list");
|
|
63
|
+
return value.sum.list.elements.map((element, index) => decodeDamlValue({ kind: "protobuf", value: element }, descriptor.element, registry, indexedPath(path, index)));
|
|
64
|
+
case "textMap":
|
|
65
|
+
requireDescriptorKind(descriptor, "textMap", path, "textMap");
|
|
66
|
+
return new DamlTextMap(value.sum.textMap.entries.map((entry, index) => [
|
|
67
|
+
entry.key,
|
|
68
|
+
decodeRequiredProtobufValue(entry.value, descriptor.value, registry, `${indexedPath(path, index)}.${entry.key}`),
|
|
69
|
+
]));
|
|
70
|
+
case "genMap":
|
|
71
|
+
requireDescriptorKind(descriptor, "genMap", path, "genMap");
|
|
72
|
+
return new DamlGenMap(value.sum.genMap.entries.map((entry, index) => [
|
|
73
|
+
decodeRequiredProtobufValue(entry.key, descriptor.key, registry, `${indexedPath(path, index)}.key`),
|
|
74
|
+
decodeRequiredProtobufValue(entry.value, descriptor.value, registry, `${indexedPath(path, index)}.value`),
|
|
75
|
+
]));
|
|
76
|
+
case "record":
|
|
77
|
+
requireDescriptorKind(descriptor, "record", path, "record");
|
|
78
|
+
return decodeProtobufRecord(value.sum.record, descriptor, registry, path);
|
|
79
|
+
case "variant": {
|
|
80
|
+
requireDescriptorKind(descriptor, "variant", path, "variant");
|
|
81
|
+
const variant = value.sum.variant;
|
|
82
|
+
const constructor = descriptor.constructors.find((candidate) => candidate.constructor === variant.constructor);
|
|
83
|
+
if (constructor === undefined) {
|
|
84
|
+
throw materializationError(path, `unknown variant constructor ${variant.constructor}`);
|
|
85
|
+
}
|
|
86
|
+
return new DamlVariant(variant.constructor, decodeRequiredProtobufValue(variant.value, constructor.payload, registry, `${path}.${variant.constructor}`));
|
|
87
|
+
}
|
|
88
|
+
case "enum":
|
|
89
|
+
requireDescriptorKind(descriptor, "enum", path, "enum");
|
|
90
|
+
if (!descriptor.constructors.includes(value.sum.enum.constructor)) {
|
|
91
|
+
throw materializationError(path, `unknown enum constructor ${value.sum.enum.constructor}`);
|
|
92
|
+
}
|
|
93
|
+
return new DamlEnum(value.sum.enum.constructor);
|
|
94
|
+
default:
|
|
95
|
+
return rejectUnknownProtobufKind(path, value.sum);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
function decodeProtobufRecord(record, descriptor, registry, path) {
|
|
99
|
+
const fields = record.fields;
|
|
100
|
+
const labelsPresent = fields.every((field) => field.label.length > 0);
|
|
101
|
+
const labelsAbsent = fields.every((field) => field.label.length === 0);
|
|
102
|
+
if (!labelsPresent && !labelsAbsent) {
|
|
103
|
+
throw materializationError(path, "record fields mix labelled and positional encodings");
|
|
104
|
+
}
|
|
105
|
+
const output = Object.create(null);
|
|
106
|
+
if (labelsPresent) {
|
|
107
|
+
if (new Set(fields.map((field) => field.label)).size !== fields.length) {
|
|
108
|
+
throw materializationError(path, "record contains duplicate field labels");
|
|
109
|
+
}
|
|
110
|
+
for (const field of descriptor.fields) {
|
|
111
|
+
const sourceField = fields.find((candidate) => candidate.label === field.damlLabel);
|
|
112
|
+
if (sourceField === undefined) {
|
|
113
|
+
throw materializationError(fieldPath(path, field.propertyName), "required record field is absent");
|
|
114
|
+
}
|
|
115
|
+
output[field.propertyName] = decodeRequiredProtobufValue(sourceField.value, field.type, registry, fieldPath(path, field.propertyName));
|
|
116
|
+
}
|
|
117
|
+
if (fields.length !== descriptor.fields.length) {
|
|
118
|
+
throw materializationError(path, "record contains an unexpected field");
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
if (fields.length !== descriptor.fields.length) {
|
|
123
|
+
throw materializationError(path, "record has the wrong number of positional fields");
|
|
124
|
+
}
|
|
125
|
+
descriptor.fields.forEach((field, index) => {
|
|
126
|
+
output[field.propertyName] = decodeRequiredProtobufValue(fields[index]?.value, field.type, registry, fieldPath(path, field.propertyName));
|
|
127
|
+
});
|
|
128
|
+
}
|
|
129
|
+
return new DamlRecord(output);
|
|
130
|
+
}
|
|
131
|
+
function decodeJsonValue(value, descriptor, registry, path) {
|
|
132
|
+
switch (descriptor.kind) {
|
|
133
|
+
case "primitive":
|
|
134
|
+
return decodeJsonPrimitive(value, descriptor, path);
|
|
135
|
+
case "contractId":
|
|
136
|
+
return requireString(value, path, "contract ID");
|
|
137
|
+
case "optional":
|
|
138
|
+
return value === null ? undefined : decodeDamlValue({ kind: "json", value }, descriptor.element, registry, path);
|
|
139
|
+
case "list":
|
|
140
|
+
return requireArray(value, path, "list").map((element, index) => decodeDamlValue({ kind: "json", value: element }, descriptor.element, registry, indexedPath(path, index)));
|
|
141
|
+
case "textMap":
|
|
142
|
+
return decodeJsonTextMap(value, descriptor, registry, path);
|
|
143
|
+
case "genMap":
|
|
144
|
+
return new DamlGenMap(requireArray(value, path, "generic map").map((entry, index) => {
|
|
145
|
+
const pair = requireArray(entry, indexedPath(path, index), "generic map entry");
|
|
146
|
+
if (pair.length !== 2) {
|
|
147
|
+
throw materializationError(indexedPath(path, index), "generic map entries must contain key and value");
|
|
148
|
+
}
|
|
149
|
+
return [
|
|
150
|
+
decodeDamlValue({ kind: "json", value: pair[0] }, descriptor.key, registry, `${indexedPath(path, index)}.key`),
|
|
151
|
+
decodeDamlValue({ kind: "json", value: pair[1] }, descriptor.value, registry, `${indexedPath(path, index)}.value`),
|
|
152
|
+
];
|
|
153
|
+
}));
|
|
154
|
+
case "record":
|
|
155
|
+
return decodeJsonRecord(value, descriptor, registry, path);
|
|
156
|
+
case "variant":
|
|
157
|
+
return decodeJsonVariant(value, descriptor, registry, path);
|
|
158
|
+
case "enum": {
|
|
159
|
+
const constructor = requireString(value, path, "enum constructor");
|
|
160
|
+
if (!descriptor.constructors.includes(constructor)) {
|
|
161
|
+
throw materializationError(path, `unknown enum constructor ${constructor}`);
|
|
162
|
+
}
|
|
163
|
+
return new DamlEnum(constructor);
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
function decodeJsonPrimitive(value, descriptor, path) {
|
|
168
|
+
switch (descriptor.primitive) {
|
|
169
|
+
case "unit": {
|
|
170
|
+
const record = requireObject(value, path, "unit");
|
|
171
|
+
if (Object.keys(record).length !== 0) {
|
|
172
|
+
throw materializationError(path, "unit must be an empty object");
|
|
173
|
+
}
|
|
174
|
+
return new DamlUnit();
|
|
175
|
+
}
|
|
176
|
+
case "bool":
|
|
177
|
+
if (typeof value !== "boolean") {
|
|
178
|
+
throw materializationError(path, "expected boolean");
|
|
179
|
+
}
|
|
180
|
+
return value;
|
|
181
|
+
case "int64":
|
|
182
|
+
return decodeInt64(requireString(value, path, "int64"), path);
|
|
183
|
+
case "date":
|
|
184
|
+
return decodeDate(value, path);
|
|
185
|
+
case "timestamp":
|
|
186
|
+
return decodeTimestamp(value, path);
|
|
187
|
+
case "numeric":
|
|
188
|
+
return decodeNumeric(requireString(value, path, "numeric"), descriptor.numericScale, path);
|
|
189
|
+
case "party":
|
|
190
|
+
return decodeParty(requireString(value, path, "party"), path);
|
|
191
|
+
case "text":
|
|
192
|
+
return requireString(value, path, "text");
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
function decodeJsonTextMap(value, descriptor, registry, path) {
|
|
196
|
+
const record = requireObject(value, path, "text map");
|
|
197
|
+
return new DamlTextMap(objectEntries(record).map(([key, entryValue]) => [
|
|
198
|
+
key,
|
|
199
|
+
decodeDamlValue({ kind: "json", value: entryValue }, descriptor.value, registry, fieldPath(path, key)),
|
|
200
|
+
]));
|
|
201
|
+
}
|
|
202
|
+
function decodeJsonRecord(value, descriptor, registry, path) {
|
|
203
|
+
const output = Object.create(null);
|
|
204
|
+
if (Array.isArray(value)) {
|
|
205
|
+
if (value.length !== descriptor.fields.length) {
|
|
206
|
+
throw materializationError(path, "record has the wrong number of positional fields");
|
|
207
|
+
}
|
|
208
|
+
descriptor.fields.forEach((field, index) => {
|
|
209
|
+
output[field.propertyName] = decodeDamlValue({ kind: "json", value: value[index] }, field.type, registry, fieldPath(path, field.propertyName));
|
|
210
|
+
});
|
|
211
|
+
return new DamlRecord(output);
|
|
212
|
+
}
|
|
213
|
+
const record = requireObject(value, path, "record");
|
|
214
|
+
const expectedLabels = new Set(descriptor.fields.map((field) => field.damlLabel));
|
|
215
|
+
for (const [label] of objectEntries(record)) {
|
|
216
|
+
if (!expectedLabels.has(label)) {
|
|
217
|
+
throw materializationError(path, `record contains unexpected field ${label}`);
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
for (const field of descriptor.fields) {
|
|
221
|
+
if (!Object.hasOwn(record, field.damlLabel)) {
|
|
222
|
+
throw materializationError(fieldPath(path, field.propertyName), "required record field is absent");
|
|
223
|
+
}
|
|
224
|
+
output[field.propertyName] = decodeDamlValue({ kind: "json", value: Reflect.get(record, field.damlLabel) }, field.type, registry, fieldPath(path, field.propertyName));
|
|
225
|
+
}
|
|
226
|
+
return new DamlRecord(output);
|
|
227
|
+
}
|
|
228
|
+
function decodeJsonVariant(value, descriptor, registry, path) {
|
|
229
|
+
const envelope = requireObject(value, path, "variant");
|
|
230
|
+
const tag = requireString(Reflect.get(envelope, "tag"), path, "variant tag");
|
|
231
|
+
const constructor = descriptor.constructors.find((candidate) => candidate.constructor === tag);
|
|
232
|
+
if (constructor === undefined) {
|
|
233
|
+
throw materializationError(path, `unknown variant constructor ${tag}`);
|
|
234
|
+
}
|
|
235
|
+
else if (!Object.hasOwn(envelope, "value")) {
|
|
236
|
+
throw materializationError(path, "variant value is absent");
|
|
237
|
+
}
|
|
238
|
+
return new DamlVariant(tag, decodeDamlValue({ kind: "json", value: Reflect.get(envelope, "value") }, constructor.payload, registry, `${path}.${tag}`));
|
|
239
|
+
}
|
|
240
|
+
function decodeRequiredProtobufValue(value, descriptor, registry, path) {
|
|
241
|
+
if (value === undefined) {
|
|
242
|
+
throw materializationError(path, "required value is absent");
|
|
243
|
+
}
|
|
244
|
+
return decodeDamlValue({ kind: "protobuf", value }, descriptor, registry, path);
|
|
245
|
+
}
|
|
246
|
+
function requirePrimitiveDescriptor(descriptor, primitive, path) {
|
|
247
|
+
if (descriptor.kind !== "primitive" || descriptor.primitive !== primitive) {
|
|
248
|
+
throw materializationError(path, `expected ${descriptor.kind} but received ${primitive}`);
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
function requireDescriptorKind(descriptor, expected, path, received) {
|
|
252
|
+
if (descriptor.kind !== expected) {
|
|
253
|
+
throw materializationError(path, `expected ${descriptor.kind} but received ${received}`);
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
function rejectUnknownProtobufKind(path, _value) {
|
|
257
|
+
throw materializationError(path, "value has an unknown protobuf oneof kind");
|
|
258
|
+
}
|
|
259
|
+
function requireArray(value, path, description) {
|
|
260
|
+
if (!Array.isArray(value)) {
|
|
261
|
+
throw materializationError(path, `expected ${description} array`);
|
|
262
|
+
}
|
|
263
|
+
return value;
|
|
264
|
+
}
|
|
265
|
+
function requireObject(value, path, description) {
|
|
266
|
+
if (typeof value !== "object" || value === null || Array.isArray(value)) {
|
|
267
|
+
throw materializationError(path, `expected ${description} object`);
|
|
268
|
+
}
|
|
269
|
+
return value;
|
|
270
|
+
}
|
|
271
|
+
function requireString(value, path, description) {
|
|
272
|
+
if (typeof value !== "string") {
|
|
273
|
+
throw materializationError(path, `expected ${description} string`);
|
|
274
|
+
}
|
|
275
|
+
return value;
|
|
276
|
+
}
|
|
277
|
+
function requireIntegerString(value, path, description) {
|
|
278
|
+
const result = requireString(value, path, description);
|
|
279
|
+
if (!/^-?(?:0|[1-9]\d*)$/.test(result)) {
|
|
280
|
+
throw materializationError(path, `expected ${description} integer string`);
|
|
281
|
+
}
|
|
282
|
+
return result;
|
|
283
|
+
}
|
|
284
|
+
function decodeInt64(value, path) {
|
|
285
|
+
const integer = requireIntegerString(value, path, "int64");
|
|
286
|
+
let int64;
|
|
287
|
+
try {
|
|
288
|
+
int64 = BigInt(integer);
|
|
289
|
+
}
|
|
290
|
+
catch {
|
|
291
|
+
throw materializationError(path, "invalid int64");
|
|
292
|
+
}
|
|
293
|
+
if (int64 < DAML_MIN_INT64 || int64 > DAML_MAX_INT64) {
|
|
294
|
+
throw materializationError(path, "int64 is outside the DAML ledger range");
|
|
295
|
+
}
|
|
296
|
+
return int64;
|
|
297
|
+
}
|
|
298
|
+
function decodeDate(value, path) {
|
|
299
|
+
if (typeof value !== "number" || !Number.isSafeInteger(value)) {
|
|
300
|
+
throw materializationError(path, "expected integer date");
|
|
301
|
+
}
|
|
302
|
+
else if (value < DAML_MIN_DATE_DAYS_SINCE_EPOCH || value > DAML_MAX_DATE_DAYS_SINCE_EPOCH) {
|
|
303
|
+
throw materializationError(path, "date is outside the DAML ledger range");
|
|
304
|
+
}
|
|
305
|
+
return new DamlDate(value);
|
|
306
|
+
}
|
|
307
|
+
function decodeTimestamp(value, path) {
|
|
308
|
+
const microseconds = requireIntegerString(value, path, "timestamp");
|
|
309
|
+
const timestamp = BigInt(microseconds);
|
|
310
|
+
if (timestamp < DAML_MIN_TIMESTAMP_MICROSECONDS || timestamp > DAML_MAX_TIMESTAMP_MICROSECONDS) {
|
|
311
|
+
throw materializationError(path, "timestamp is outside the DAML ledger range");
|
|
312
|
+
}
|
|
313
|
+
return new DamlTimestamp(microseconds);
|
|
314
|
+
}
|
|
315
|
+
function decodeNumeric(value, numericScale, path) {
|
|
316
|
+
if (!/^[+-]?\d+(?:\.\d*)?$/.test(value)) {
|
|
317
|
+
throw materializationError(path, "invalid numeric");
|
|
318
|
+
}
|
|
319
|
+
const decimalSeparator = value.indexOf(".");
|
|
320
|
+
const fractionLength = decimalSeparator === -1 ? 0 : value.length - decimalSeparator - 1;
|
|
321
|
+
const precision = value.replace(/[+-.]/g, "").length;
|
|
322
|
+
const maxScale = numericScale ?? 37;
|
|
323
|
+
if (!Number.isInteger(maxScale) || maxScale < 0 || maxScale > 37) {
|
|
324
|
+
throw materializationError(path, "numeric descriptor has an invalid scale");
|
|
325
|
+
}
|
|
326
|
+
else if (precision > 38) {
|
|
327
|
+
throw materializationError(path, "numeric exceeds DAML ledger precision");
|
|
328
|
+
}
|
|
329
|
+
else if (fractionLength > maxScale) {
|
|
330
|
+
throw materializationError(path, "numeric exceeds its DAML scale");
|
|
331
|
+
}
|
|
332
|
+
try {
|
|
333
|
+
return new DamlNumeric(canonicalizeLedgerNumeric(value));
|
|
334
|
+
}
|
|
335
|
+
catch {
|
|
336
|
+
throw materializationError(path, "invalid numeric");
|
|
337
|
+
}
|
|
338
|
+
}
|
|
339
|
+
function canonicalizeLedgerNumeric(value) {
|
|
340
|
+
const negative = value.startsWith("-");
|
|
341
|
+
const unsigned = value.startsWith("+") || negative ? value.slice(1) : value;
|
|
342
|
+
const decimalSeparator = unsigned.indexOf(".");
|
|
343
|
+
const integerPart = decimalSeparator === -1 ? unsigned : unsigned.slice(0, decimalSeparator);
|
|
344
|
+
const fractionPart = decimalSeparator === -1 ? "" : unsigned.slice(decimalSeparator + 1);
|
|
345
|
+
const canonicalIntegerPart = integerPart.replace(/^0+/, "") || "0";
|
|
346
|
+
const sign = negative ? "-" : "";
|
|
347
|
+
return fractionPart.length === 0
|
|
348
|
+
? `${sign}${canonicalIntegerPart}`
|
|
349
|
+
: `${sign}${canonicalIntegerPart}.${fractionPart}`;
|
|
350
|
+
}
|
|
351
|
+
function decodeParty(value, path) {
|
|
352
|
+
try {
|
|
353
|
+
return new DamlParty(value);
|
|
354
|
+
}
|
|
355
|
+
catch {
|
|
356
|
+
throw materializationError(path, "invalid party");
|
|
357
|
+
}
|
|
358
|
+
}
|
|
359
|
+
function objectEntries(record) {
|
|
360
|
+
return Object.keys(record).map((key) => [key, Reflect.get(record, key)]);
|
|
361
|
+
}
|
|
362
|
+
function fieldPath(path, propertyName) {
|
|
363
|
+
return `${path}.${propertyName}`;
|
|
364
|
+
}
|
|
365
|
+
function indexedPath(path, index) {
|
|
366
|
+
return `${path}[${index}]`;
|
|
367
|
+
}
|
|
368
|
+
function materializationError(path, detail) {
|
|
369
|
+
return new DamlMaterializationError(path, detail);
|
|
370
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { DamlEnum, DamlGenMap, DamlRecord, DamlTextMap, DamlVariant, } from "../../core/types/daml-values.js";
|
|
2
|
+
/** Converts decoded DAML containers into the shapes exposed by generated TypeScript declarations. */
|
|
3
|
+
export function materializeDamlValue(value) {
|
|
4
|
+
return materialize(value);
|
|
5
|
+
}
|
|
6
|
+
function materialize(value) {
|
|
7
|
+
if (value instanceof DamlRecord) {
|
|
8
|
+
return Object.fromEntries(Object.entries(value.fields).map(([name, field]) => [name, materialize(field)]));
|
|
9
|
+
}
|
|
10
|
+
else if (value instanceof DamlVariant) {
|
|
11
|
+
return Object.freeze({ tag: value.constructorName, value: materialize(value.value) });
|
|
12
|
+
}
|
|
13
|
+
else if (value instanceof DamlEnum) {
|
|
14
|
+
return value.constructorName;
|
|
15
|
+
}
|
|
16
|
+
else if (value instanceof DamlTextMap || value instanceof DamlGenMap) {
|
|
17
|
+
return new Map(value.entries.map(([key, entry]) => [materialize(key), materialize(entry)]));
|
|
18
|
+
}
|
|
19
|
+
else if (Array.isArray(value)) {
|
|
20
|
+
return value.map((element) => materialize(element));
|
|
21
|
+
}
|
|
22
|
+
return value;
|
|
23
|
+
}
|
|
@@ -33,6 +33,7 @@ export declare class DamlLfCompilation {
|
|
|
33
33
|
private buildIndexes;
|
|
34
34
|
private validateReferencesOrThrow;
|
|
35
35
|
private validateTypeOrThrow;
|
|
36
|
+
private validateDataTypeOrThrow;
|
|
36
37
|
private static createModuleKey;
|
|
37
38
|
private static createTypeKey;
|
|
38
39
|
private static createDefinitionKey;
|
|
@@ -105,9 +105,7 @@ export class DamlLfCompilation {
|
|
|
105
105
|
this.validateTypeOrThrow(definition.type);
|
|
106
106
|
}
|
|
107
107
|
if (definition instanceof DamlLfDataType) {
|
|
108
|
-
|
|
109
|
-
this.validateTypeOrThrow(field.type);
|
|
110
|
-
}
|
|
108
|
+
this.validateDataTypeOrThrow(definition);
|
|
111
109
|
}
|
|
112
110
|
if (definition instanceof DamlLfTemplate) {
|
|
113
111
|
this.getTypeSymbolOrThrow(definition.templateId.toTypeConReference());
|
|
@@ -124,12 +122,28 @@ export class DamlLfCompilation {
|
|
|
124
122
|
}
|
|
125
123
|
}
|
|
126
124
|
validateTypeOrThrow(type) {
|
|
125
|
+
for (const typeArgument of type.typeArguments) {
|
|
126
|
+
this.validateTypeOrThrow(typeArgument);
|
|
127
|
+
}
|
|
127
128
|
const reference = type.typeConReference;
|
|
128
129
|
if (reference === undefined) {
|
|
129
130
|
return;
|
|
130
131
|
}
|
|
131
132
|
this.getTypeSymbolOrThrow(reference);
|
|
132
133
|
}
|
|
134
|
+
validateDataTypeOrThrow(definition) {
|
|
135
|
+
if (definition.definition.kind === "record") {
|
|
136
|
+
for (const field of definition.definition.fields) {
|
|
137
|
+
this.validateTypeOrThrow(field.type);
|
|
138
|
+
}
|
|
139
|
+
return;
|
|
140
|
+
}
|
|
141
|
+
else if (definition.definition.kind === "variant") {
|
|
142
|
+
for (const constructor of definition.definition.constructors) {
|
|
143
|
+
this.validateTypeOrThrow(constructor.type);
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
}
|
|
133
147
|
static createModuleKey(packageId, moduleName) {
|
|
134
148
|
return `${packageId}::${moduleName}`;
|
|
135
149
|
}
|
|
@@ -1,7 +1,16 @@
|
|
|
1
1
|
export declare enum DamlLfBuiltinType {
|
|
2
|
+
unit = "unit",
|
|
3
|
+
bool = "bool",
|
|
2
4
|
int64 = "int64",
|
|
5
|
+
date = "date",
|
|
6
|
+
timestamp = "timestamp",
|
|
3
7
|
numeric = "numeric",
|
|
4
8
|
party = "party",
|
|
5
9
|
text = "text",
|
|
10
|
+
contractId = "contractId",
|
|
11
|
+
optional = "optional",
|
|
12
|
+
list = "list",
|
|
13
|
+
textMap = "textMap",
|
|
14
|
+
genMap = "genMap",
|
|
6
15
|
unknown = "unknown"
|
|
7
16
|
}
|
|
@@ -1,8 +1,17 @@
|
|
|
1
1
|
export var DamlLfBuiltinType;
|
|
2
2
|
(function (DamlLfBuiltinType) {
|
|
3
|
+
DamlLfBuiltinType["unit"] = "unit";
|
|
4
|
+
DamlLfBuiltinType["bool"] = "bool";
|
|
3
5
|
DamlLfBuiltinType["int64"] = "int64";
|
|
6
|
+
DamlLfBuiltinType["date"] = "date";
|
|
7
|
+
DamlLfBuiltinType["timestamp"] = "timestamp";
|
|
4
8
|
DamlLfBuiltinType["numeric"] = "numeric";
|
|
5
9
|
DamlLfBuiltinType["party"] = "party";
|
|
6
10
|
DamlLfBuiltinType["text"] = "text";
|
|
11
|
+
DamlLfBuiltinType["contractId"] = "contractId";
|
|
12
|
+
DamlLfBuiltinType["optional"] = "optional";
|
|
13
|
+
DamlLfBuiltinType["list"] = "list";
|
|
14
|
+
DamlLfBuiltinType["textMap"] = "textMap";
|
|
15
|
+
DamlLfBuiltinType["genMap"] = "genMap";
|
|
7
16
|
DamlLfBuiltinType["unknown"] = "unknown";
|
|
8
17
|
})(DamlLfBuiltinType || (DamlLfBuiltinType = {}));
|
|
@@ -1,11 +1,28 @@
|
|
|
1
1
|
import { DamlLfDefinition } from "./daml-lf-definition.js";
|
|
2
2
|
import { DamlLfField } from "./daml-lf-field.js";
|
|
3
3
|
import { DamlLfNodeKind } from "./daml-lf-node-kind.js";
|
|
4
|
+
import { DamlLfType } from "./daml-lf-type.js";
|
|
5
|
+
export type DamlLfDataTypeDefinition = {
|
|
6
|
+
readonly kind: "record";
|
|
7
|
+
readonly fields: readonly DamlLfField[];
|
|
8
|
+
} | {
|
|
9
|
+
readonly kind: "variant";
|
|
10
|
+
readonly constructors: readonly DamlLfVariantConstructor[];
|
|
11
|
+
} | {
|
|
12
|
+
readonly kind: "enum";
|
|
13
|
+
readonly constructors: readonly string[];
|
|
14
|
+
};
|
|
15
|
+
export interface DamlLfVariantConstructor {
|
|
16
|
+
readonly name: string;
|
|
17
|
+
readonly type: DamlLfType;
|
|
18
|
+
}
|
|
4
19
|
export declare class DamlLfDataType extends DamlLfDefinition {
|
|
5
20
|
readonly nodeKind = DamlLfNodeKind.dataType;
|
|
21
|
+
readonly definition: DamlLfDataTypeDefinition;
|
|
6
22
|
readonly fields: readonly DamlLfField[];
|
|
7
23
|
constructor(init: {
|
|
8
24
|
name: string;
|
|
9
|
-
|
|
25
|
+
definition?: DamlLfDataTypeDefinition;
|
|
26
|
+
fields?: readonly DamlLfField[];
|
|
10
27
|
});
|
|
11
28
|
}
|
|
@@ -2,11 +2,18 @@ import { DamlLfDefinition } from "./daml-lf-definition.js";
|
|
|
2
2
|
import { DamlLfNodeKind } from "./daml-lf-node-kind.js";
|
|
3
3
|
export class DamlLfDataType extends DamlLfDefinition {
|
|
4
4
|
nodeKind = DamlLfNodeKind.dataType;
|
|
5
|
+
definition;
|
|
5
6
|
fields;
|
|
6
7
|
constructor(init) {
|
|
7
8
|
super({
|
|
8
9
|
name: init.name,
|
|
9
10
|
});
|
|
10
|
-
this.
|
|
11
|
+
this.definition = init.definition ?? {
|
|
12
|
+
kind: "record",
|
|
13
|
+
fields: init.fields ?? [],
|
|
14
|
+
};
|
|
15
|
+
this.fields = this.definition.kind === "record"
|
|
16
|
+
? this.definition.fields
|
|
17
|
+
: [];
|
|
11
18
|
}
|
|
12
19
|
}
|
|
@@ -6,9 +6,11 @@ export declare class DamlLfType {
|
|
|
6
6
|
readonly builtinType: DamlLfBuiltinType;
|
|
7
7
|
readonly numericScale?: number;
|
|
8
8
|
readonly typeConReference?: TypeConReference;
|
|
9
|
+
readonly typeArguments: readonly DamlLfType[];
|
|
9
10
|
constructor(init: {
|
|
10
11
|
builtinType?: DamlLfBuiltinType;
|
|
11
12
|
numericScale?: number;
|
|
12
13
|
typeConReference?: TypeConReference;
|
|
14
|
+
typeArguments?: readonly DamlLfType[];
|
|
13
15
|
});
|
|
14
16
|
}
|
|
@@ -5,11 +5,13 @@ export class DamlLfType {
|
|
|
5
5
|
builtinType;
|
|
6
6
|
numericScale;
|
|
7
7
|
typeConReference;
|
|
8
|
+
typeArguments;
|
|
8
9
|
constructor(init) {
|
|
9
10
|
this.builtinType = init.builtinType ?? DamlLfBuiltinType.unknown;
|
|
10
11
|
if (init.numericScale !== undefined) {
|
|
11
12
|
this.numericScale = init.numericScale;
|
|
12
13
|
}
|
|
13
14
|
this.typeConReference = init.typeConReference;
|
|
15
|
+
this.typeArguments = Object.freeze([...(init.typeArguments ?? [])]);
|
|
14
16
|
}
|
|
15
17
|
}
|
|
@@ -4,6 +4,7 @@ import { DamlLfPackage } from "./daml-lf-package.js";
|
|
|
4
4
|
export declare class Lf2ModelMapper {
|
|
5
5
|
static mapPackage(packageId: string, rawPackage: LfArchivePackage, languageVersion: DamlLfLanguageVersion): DamlLfPackage;
|
|
6
6
|
private static mapType;
|
|
7
|
+
private static mapBuiltinType;
|
|
7
8
|
private static readNumericScale;
|
|
8
9
|
private static mapModule;
|
|
9
10
|
private static mapDataType;
|