gen-typescript-from-tolk-dev 0.2.3 → 0.3.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.
@@ -43,6 +43,7 @@ const c = __importStar(require("@ton/core"));
43
43
  const unsupported_errors_1 = require("./unsupported-errors");
44
44
  const dynamic_validation_1 = require("./dynamic-validation");
45
45
  const types_kernel_1 = require("./types-kernel");
46
+ const emit_ts_types_1 = require("./emit-ts-types");
46
47
  /*
47
48
  Dynamic serialization works without generating TypeScript wrappers.
48
49
  Just given an ABI, serialize any JS input to a cell, and unpack back.
@@ -55,95 +56,97 @@ const types_kernel_1 = require("./types-kernel");
55
56
  function lookupPrefix(s, expected, prefixLen) {
56
57
  return s.remainingBits >= prefixLen && s.preloadUint(prefixLen) === expected;
57
58
  }
58
- function createTonCoreDictionaryKey(fieldPath, tyK) {
59
+ function createTonCoreDictionaryKey(ctx, fieldPath, tyKIdx) {
60
+ const tyK = ctx.symbols.tyByIdx(tyKIdx);
59
61
  if (tyK.kind === 'intN')
60
62
  return c.Dictionary.Keys.BigInt(tyK.n);
61
63
  if (tyK.kind === 'uintN')
62
64
  return c.Dictionary.Keys.BigUint(tyK.n);
63
65
  if (tyK.kind === 'address')
64
66
  return c.Dictionary.Keys.Address();
65
- throw new unsupported_errors_1.NonStandardDictKey(`'${fieldPath}' is 'map<${(0, types_kernel_1.renderTy)(tyK)}, ...>': such a non-standard map key can not be handled by @ton/core library`);
67
+ throw new unsupported_errors_1.NonStandardDictKey(`'${fieldPath}' is 'map<${(0, types_kernel_1.renderTy)(ctx.symbols, tyKIdx)}, ...>': such a non-standard map key can not be handled by @ton/core library`);
66
68
  }
67
- function createTonCoreDictionaryValue(ctx, fieldPath, tyV) {
69
+ function createTonCoreDictionaryValue(ctx, fieldPath, tyVIdx) {
68
70
  return {
69
71
  serialize(self, b) {
70
- dynamicPack(ctx, fieldPath, tyV, self, b);
72
+ dynamicPack(ctx, fieldPath, tyVIdx, self, b);
71
73
  },
72
74
  parse(s) {
73
- return dynamicUnpack(ctx, fieldPath, tyV, s);
75
+ return dynamicUnpack(ctx, fieldPath, tyVIdx, s);
74
76
  }
75
77
  };
76
78
  }
77
79
  // Parameter `fieldPath` is used for error messages only, e.g. when provided invalid input.
78
- function dynamicPack(ctx, fieldPath, ty, v, b) {
80
+ function dynamicPack(ctx, fieldPath, tyIdx, v, b, uLabelTyIdx) {
81
+ const ty = ctx.symbols.tyByIdx(tyIdx);
79
82
  switch (ty.kind) {
80
83
  case 'intN': {
81
- (0, dynamic_validation_1.checkIsNumber)(fieldPath, ty, v);
84
+ (0, dynamic_validation_1.checkIsNumber)(ctx, fieldPath, tyIdx, v);
82
85
  b.storeInt(v, ty.n);
83
86
  break;
84
87
  }
85
88
  case 'uintN': {
86
- (0, dynamic_validation_1.checkIsNumber)(fieldPath, ty, v);
89
+ (0, dynamic_validation_1.checkIsNumber)(ctx, fieldPath, tyIdx, v);
87
90
  b.storeUint(v, ty.n);
88
91
  break;
89
92
  }
90
93
  case 'varintN': {
91
- (0, dynamic_validation_1.checkIsNumber)(fieldPath, ty, v);
94
+ (0, dynamic_validation_1.checkIsNumber)(ctx, fieldPath, tyIdx, v);
92
95
  b.storeVarInt(v, Math.log2(ty.n));
93
96
  break;
94
97
  }
95
98
  case 'varuintN': {
96
- (0, dynamic_validation_1.checkIsNumber)(fieldPath, ty, v);
99
+ (0, dynamic_validation_1.checkIsNumber)(ctx, fieldPath, tyIdx, v);
97
100
  b.storeVarUint(v, Math.log2(ty.n));
98
101
  break;
99
102
  }
100
103
  case 'coins': {
101
- (0, dynamic_validation_1.checkIsNumber)(fieldPath, ty, v);
104
+ (0, dynamic_validation_1.checkIsNumber)(ctx, fieldPath, tyIdx, v);
102
105
  b.storeCoins(v);
103
106
  break;
104
107
  }
105
108
  case 'bool': {
106
- (0, dynamic_validation_1.checkIsBoolean)(fieldPath, ty, v);
109
+ (0, dynamic_validation_1.checkIsBoolean)(ctx, fieldPath, tyIdx, v);
107
110
  b.storeBit(v);
108
111
  break;
109
112
  }
110
113
  case 'cell': {
111
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
114
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
112
115
  b.storeRef(v);
113
116
  break;
114
117
  }
115
118
  case 'builder': {
116
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
119
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
117
120
  b.storeBuilder(v);
118
121
  break;
119
122
  }
120
123
  case 'slice': {
121
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
124
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
122
125
  b.storeSlice(v);
123
126
  break;
124
127
  }
125
128
  case 'string': {
126
- (0, dynamic_validation_1.checkIsString)(fieldPath, ty, v);
129
+ (0, dynamic_validation_1.checkIsString)(ctx, fieldPath, tyIdx, v);
127
130
  b.storeStringRefTail(v);
128
131
  break;
129
132
  }
130
133
  case 'remaining': {
131
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
134
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
132
135
  b.storeSlice(v);
133
136
  break;
134
137
  }
135
138
  case 'address': {
136
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
139
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
137
140
  b.storeAddress(v);
138
141
  break;
139
142
  }
140
143
  case 'addressOpt': {
141
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v, true);
144
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v, true);
142
145
  b.storeAddress(v);
143
146
  break;
144
147
  }
145
148
  case 'addressExt': {
146
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
149
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
147
150
  b.storeAddress(v);
148
151
  break;
149
152
  }
@@ -152,15 +155,15 @@ function dynamicPack(ctx, fieldPath, ty, v, b) {
152
155
  b.storeAddress(null);
153
156
  }
154
157
  else {
155
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
158
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
156
159
  b.storeAddress(v);
157
160
  }
158
161
  break;
159
162
  }
160
163
  case 'bitsN': {
161
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
164
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
162
165
  if (v.remainingBits !== ty.n || v.remainingRefs !== 0) {
163
- (0, dynamic_validation_1.throwInvalidInput)(fieldPath, ty, `expected ${ty.n} bits and 0 refs, got ${v.remainingBits} bits and ${v.remainingRefs} refs`);
166
+ (0, dynamic_validation_1.throwInvalidInput)(ctx, fieldPath, tyIdx, `expected ${ty.n} bits and 0 refs, got ${v.remainingBits} bits and ${v.remainingRefs} refs`);
164
167
  }
165
168
  b.storeSlice(v);
166
169
  break;
@@ -171,24 +174,24 @@ function dynamicPack(ctx, fieldPath, ty, v, b) {
171
174
  }
172
175
  else {
173
176
  b.storeUint(1, 1);
174
- dynamicPack(ctx, fieldPath, ty.inner, v, b);
177
+ dynamicPack(ctx, fieldPath, ty.inner_ty_idx, v, b);
175
178
  }
176
179
  break;
177
180
  }
178
181
  case 'cellOf': {
179
- (0, dynamic_validation_1.checkIsObjectWithProperty)(fieldPath, ty, v, 'ref');
182
+ (0, dynamic_validation_1.checkIsObjectWithProperty)(ctx, fieldPath, tyIdx, v, 'ref');
180
183
  let b_ref = c.beginCell();
181
- dynamicPack(ctx, fieldPath, ty.inner, v.ref, b_ref);
184
+ dynamicPack(ctx, fieldPath, ty.inner_ty_idx, v.ref, b_ref);
182
185
  b.storeRef(b_ref.endCell());
183
186
  break;
184
187
  }
185
188
  case 'arrayOf': {
186
- (0, dynamic_validation_1.checkIsArray)(fieldPath, ty, v);
189
+ (0, dynamic_validation_1.checkIsArray)(ctx, fieldPath, tyIdx, v);
187
190
  // the compiler stores array<T> in chunks; in TypeScript, for simplicity, store "1 elem = 1 ref"
188
191
  let tail = null;
189
192
  for (let i = 0; i < v.length; ++i) {
190
193
  let chunkB = c.beginCell().storeMaybeRef(tail);
191
- dynamicPack(ctx, fieldPath + '[ith]', ty.inner, v[v.length - 1 - i], chunkB);
194
+ dynamicPack(ctx, fieldPath + '[ith]', ty.inner_ty_idx, v[v.length - 1 - i], chunkB);
192
195
  tail = chunkB.endCell();
193
196
  }
194
197
  b.storeUint(v.length, 8);
@@ -196,11 +199,11 @@ function dynamicPack(ctx, fieldPath, ty, v, b) {
196
199
  break;
197
200
  }
198
201
  case 'lispListOf': {
199
- (0, dynamic_validation_1.checkIsArray)(fieldPath, ty, v);
202
+ (0, dynamic_validation_1.checkIsArray)(ctx, fieldPath, tyIdx, v);
200
203
  let tail = c.Cell.EMPTY;
201
204
  for (let i = 0; i < v.length; ++i) {
202
205
  let itemB = c.beginCell();
203
- dynamicPack(ctx, `${fieldPath}[${i}]`, ty.inner, v[i], itemB);
206
+ dynamicPack(ctx, `${fieldPath}[${i}]`, ty.inner_ty_idx, v[i], itemB);
204
207
  tail = itemB.storeRef(tail).endCell();
205
208
  }
206
209
  b.storeRef(tail);
@@ -208,50 +211,49 @@ function dynamicPack(ctx, fieldPath, ty, v, b) {
208
211
  }
209
212
  case 'tensor': // `(T1, T2)` and `[T1, T2]` are both TypeScript arrays
210
213
  case 'shapedTuple': { // (but in Tolk, they are different: a tensor and a TVM shaped tuple)
211
- (0, dynamic_validation_1.checkIsArray)(fieldPath, ty, v, ty.items.length);
214
+ (0, dynamic_validation_1.checkIsArray)(ctx, fieldPath, tyIdx, v, ty.items_ty_idx.length);
212
215
  for (let i = 0; i < v.length; ++i) {
213
- dynamicPack(ctx, `${fieldPath}[${i}]`, ty.items[i], v[i], b);
216
+ dynamicPack(ctx, `${fieldPath}[${i}]`, ty.items_ty_idx[i], v[i], b);
214
217
  }
215
218
  break;
216
219
  }
217
220
  case 'mapKV': {
218
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
219
- let dictKey = createTonCoreDictionaryKey(fieldPath, ty.k);
220
- let dictValue = createTonCoreDictionaryValue(ctx, fieldPath, ty.v);
221
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
222
+ let dictKey = createTonCoreDictionaryKey(ctx, fieldPath, ty.key_ty_idx);
223
+ let dictValue = createTonCoreDictionaryValue(ctx, fieldPath, ty.value_ty_idx);
221
224
  b.storeDict(v, dictKey, dictValue);
222
225
  break;
223
226
  }
224
227
  case 'EnumRef': {
225
- (0, dynamic_validation_1.checkIsNumber)(fieldPath, ty, v);
228
+ (0, dynamic_validation_1.checkIsNumber)(ctx, fieldPath, tyIdx, v);
226
229
  let enumRef = ctx.symbols.getEnum(ty.enum_name);
227
230
  if (enumRef.custom_pack_unpack?.pack_to_builder) {
228
231
  ctx.getCustomPackFnOrThrow(ty.enum_name, fieldPath)(v, b);
229
232
  break;
230
233
  }
231
- dynamicPack(ctx, fieldPath, enumRef.encoded_as, v, b);
234
+ dynamicPack(ctx, fieldPath, enumRef.encoded_as_ty_idx, v, b);
232
235
  break;
233
236
  }
234
237
  case 'StructRef': {
235
- (0, dynamic_validation_1.checkIsObject)(fieldPath, ty, v);
238
+ (0, dynamic_validation_1.checkIsObject)(ctx, fieldPath, tyIdx, v);
236
239
  let structRef = ctx.symbols.getStruct(ty.struct_name);
237
240
  if (structRef.custom_pack_unpack?.pack_to_builder) {
238
241
  ctx.getCustomPackFnOrThrow(ty.struct_name, fieldPath)(v, b);
239
242
  break;
240
243
  }
241
244
  if (structRef.prefix) {
242
- b.storeUint(+structRef.prefix.prefix_str, structRef.prefix.prefix_len);
245
+ b.storeUint(structRef.prefix.prefix_num, structRef.prefix.prefix_len);
243
246
  }
244
- for (let f of structRef.fields) {
245
- const fTy = ty.type_args ? (0, types_kernel_1.instantiateGenerics)(f.ty, structRef.type_params, ty.type_args) : f.ty;
247
+ for (let f of ctx.symbols.structFieldsOf(tyIdx)) {
246
248
  try {
247
- dynamicPack(ctx, `${fieldPath}.${f.name}`, fTy, v[f.name], b);
249
+ dynamicPack(ctx, `${fieldPath}.${f.name}`, f.ty_idx, v[f.name], b, f.uLabelTyIdx);
248
250
  }
249
251
  catch (ex) {
250
252
  if (ex instanceof unsupported_errors_1.InvalidDynamicInput) {
251
253
  throw ex;
252
254
  }
253
255
  // serialization errors from @ton/core, like "value is out of range"
254
- (0, dynamic_validation_1.throwInvalidInput)(`${fieldPath}.${f.name}`, fTy, ex.message ?? ex.toString());
256
+ (0, dynamic_validation_1.throwInvalidInput)(ctx, `${fieldPath}.${f.name}`, f.ty_idx, ex.message ?? ex.toString());
255
257
  }
256
258
  }
257
259
  break;
@@ -262,41 +264,42 @@ function dynamicPack(ctx, fieldPath, ty, v, b) {
262
264
  ctx.getCustomPackFnOrThrow(ty.alias_name, fieldPath)(v, b);
263
265
  break;
264
266
  }
265
- const targetTy = ty.type_args ? (0, types_kernel_1.instantiateGenerics)(aliasRef.target_ty, aliasRef.type_params, ty.type_args) : aliasRef.target_ty;
266
- dynamicPack(ctx, fieldPath, targetTy, v, b);
267
+ const target = ctx.symbols.aliasTargetOf(tyIdx);
268
+ dynamicPack(ctx, fieldPath, target.ty_idx, v, b, target.uLabelTyIdx);
267
269
  break;
268
270
  }
269
271
  case 'union': {
270
- const variants = (0, types_kernel_1.createLabelsForUnion)(ctx.symbols, ty.variants);
271
- const hasNull = variants.find(v => v.variant_ty.kind === 'nullLiteral');
272
+ const variants = (0, types_kernel_1.createLabelsForUnion)(ctx.symbols, ty.variants, uLabelTyIdx);
273
+ const hasNull = variants.find(v => ctx.symbols.tyByIdx(v.variant_ty_idx).kind === 'nullLiteral');
272
274
  if (hasNull && v === null) {
273
- b.storeUint(+hasNull.prefix_str, hasNull.prefix_len);
275
+ b.storeUint(hasNull.prefix_num, hasNull.prefix_len);
274
276
  }
275
277
  else {
276
- (0, dynamic_validation_1.checkIsObjectWithProperty)(fieldPath, ty, v, '$');
278
+ (0, dynamic_validation_1.checkIsObjectWithProperty)(ctx, fieldPath, tyIdx, v, '$');
277
279
  const activeVariant = variants.find(variant => v.$ === variant.labelStr);
278
280
  if (!activeVariant) {
279
- (0, dynamic_validation_1.throwInvalidInput)(fieldPath, ty, `non-existing union variant for $ = '${v.$}'`);
281
+ (0, dynamic_validation_1.throwInvalidInput)(ctx, fieldPath, tyIdx, `non-existing union variant for $ = '${v.$}'`);
280
282
  }
281
283
  if (activeVariant.hasValueField && !v.hasOwnProperty('value')) {
282
- (0, dynamic_validation_1.throwInvalidInput)(fieldPath, ty, `expected {$,value} but field 'value' not provided`);
284
+ (0, dynamic_validation_1.throwInvalidInput)(ctx, fieldPath, tyIdx, `expected {$,value} but field 'value' not provided`);
283
285
  }
284
286
  if (activeVariant.is_prefix_implicit) {
285
- b.storeUint(+activeVariant.prefix_str, activeVariant.prefix_len);
287
+ b.storeUint(activeVariant.prefix_num, activeVariant.prefix_len);
286
288
  }
287
289
  let actualValue = activeVariant.hasValueField ? v.value : v;
288
- dynamicPack(ctx, `${fieldPath}#${activeVariant.labelStr}`, activeVariant.variant_ty, actualValue, b);
290
+ dynamicPack(ctx, `${fieldPath}#${activeVariant.labelStr}`, activeVariant.variant_ty_idx, actualValue, b);
289
291
  }
290
292
  break;
291
293
  }
292
294
  case 'void':
293
295
  break;
294
296
  default:
295
- throw new unsupported_errors_1.CantPackDynamic(fieldPath, `type '${(0, types_kernel_1.renderTy)(ty)}' is not serializable`);
297
+ throw new unsupported_errors_1.CantPackDynamic(fieldPath, `type '${(0, types_kernel_1.renderTy)(ctx.symbols, tyIdx)}' is not serializable`);
296
298
  }
297
299
  }
298
300
  // Parameter `fieldPath` is used for error messages only, e.g. when can't deserialize exact field (bad slice).
299
- function dynamicUnpack(ctx, fieldPath, ty, s) {
301
+ function dynamicUnpack(ctx, fieldPath, tyIdx, s, uLabelTyIdx) {
302
+ const ty = ctx.symbols.tyByIdx(tyIdx);
300
303
  switch (ty.kind) {
301
304
  case 'intN': return s.loadIntBig(ty.n);
302
305
  case 'uintN': return s.loadUintBig(ty.n);
@@ -323,10 +326,10 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
323
326
  }
324
327
  case 'bitsN': return new c.Slice(new c.BitReader(s.loadBits(ty.n)), []);
325
328
  case 'nullLiteral': return null;
326
- case 'nullable': return s.loadBoolean() ? dynamicUnpack(ctx, fieldPath, ty.inner, s) : null;
329
+ case 'nullable': return s.loadBoolean() ? dynamicUnpack(ctx, fieldPath, ty.inner_ty_idx, s) : null;
327
330
  case 'cellOf': {
328
331
  let s_ref = s.loadRef().beginParse();
329
- return { ref: dynamicUnpack(ctx, fieldPath, ty.inner, s_ref) };
332
+ return { ref: dynamicUnpack(ctx, fieldPath, ty.inner_ty_idx, s_ref) };
330
333
  }
331
334
  case 'arrayOf': {
332
335
  let len = s.loadUint(8);
@@ -336,7 +339,7 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
336
339
  let s = head.beginParse();
337
340
  head = s.loadMaybeRef();
338
341
  while (s.remainingBits || s.remainingRefs) {
339
- outArr.push(dynamicUnpack(ctx, fieldPath + '[ith]', ty.inner, s));
342
+ outArr.push(dynamicUnpack(ctx, fieldPath + '[ith]', ty.inner_ty_idx, s));
340
343
  }
341
344
  }
342
345
  if (len !== outArr.length) {
@@ -349,7 +352,7 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
349
352
  let head = s.loadRef().beginParse();
350
353
  while (head.remainingRefs) {
351
354
  let tailSnaked = head.loadRef();
352
- let headValue = dynamicUnpack(ctx, fieldPath + '[ith]', ty.inner, head);
355
+ let headValue = dynamicUnpack(ctx, fieldPath + '[ith]', ty.inner_ty_idx, head);
353
356
  head.endParse(); // ensure no data is present besides T
354
357
  outArr.unshift(headValue);
355
358
  head = tailSnaked.beginParse();
@@ -358,11 +361,11 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
358
361
  }
359
362
  case 'tensor':
360
363
  case 'shapedTuple': {
361
- return ty.items.map((item, idx) => dynamicUnpack(ctx, `${fieldPath}[${idx}]`, item, s));
364
+ return ty.items_ty_idx.map((ty_idx, idx) => dynamicUnpack(ctx, `${fieldPath}[${idx}]`, ty_idx, s));
362
365
  }
363
366
  case 'mapKV': {
364
- let dictKey = createTonCoreDictionaryKey(fieldPath, ty.k);
365
- let dictValue = createTonCoreDictionaryValue(ctx, fieldPath, ty.v);
367
+ let dictKey = createTonCoreDictionaryKey(ctx, fieldPath, ty.key_ty_idx);
368
+ let dictValue = createTonCoreDictionaryValue(ctx, fieldPath, ty.value_ty_idx);
366
369
  return s.loadDict(dictKey, dictValue);
367
370
  }
368
371
  case 'EnumRef': {
@@ -370,7 +373,7 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
370
373
  if (enumRef.custom_pack_unpack?.unpack_from_slice) {
371
374
  return ctx.getCustomUnpackFnOrThrow(ty.enum_name, fieldPath)(s);
372
375
  }
373
- return dynamicUnpack(ctx, fieldPath, enumRef.encoded_as, s);
376
+ return dynamicUnpack(ctx, fieldPath, enumRef.encoded_as_ty_idx, s);
374
377
  }
375
378
  case 'StructRef': {
376
379
  let structRef = ctx.symbols.getStruct(ty.struct_name);
@@ -380,14 +383,13 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
380
383
  let result = { $: ty.struct_name };
381
384
  if (structRef.prefix) {
382
385
  let prefix = s.loadUint(structRef.prefix.prefix_len);
383
- if (prefix !== +structRef.prefix.prefix_str) {
384
- throw new unsupported_errors_1.CantUnpackDynamic(fieldPath, `incorrect prefix for '${ty.struct_name}', expected ${structRef.prefix.prefix_str}`);
386
+ if (prefix !== structRef.prefix.prefix_num) {
387
+ throw new unsupported_errors_1.CantUnpackDynamic(fieldPath, `incorrect prefix for '${ty.struct_name}', expected ${(0, emit_ts_types_1.emitPrefixHex)(structRef.prefix)}`);
385
388
  }
386
389
  }
387
- for (let f of structRef.fields) {
388
- const fTy = ty.type_args ? (0, types_kernel_1.instantiateGenerics)(f.ty, structRef.type_params, ty.type_args) : f.ty;
390
+ for (let f of ctx.symbols.structFieldsOf(tyIdx)) {
389
391
  try {
390
- result[f.name] = dynamicUnpack(ctx, `${fieldPath}.${f.name}`, fTy, s);
392
+ result[f.name] = dynamicUnpack(ctx, `${fieldPath}.${f.name}`, f.ty_idx, s, f.uLabelTyIdx);
391
393
  }
392
394
  catch (ex) {
393
395
  if (ex instanceof unsupported_errors_1.CantUnpackDynamic) {
@@ -404,19 +406,19 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
404
406
  if (aliasRef.custom_pack_unpack?.unpack_from_slice) {
405
407
  return ctx.getCustomUnpackFnOrThrow(ty.alias_name, fieldPath)(s);
406
408
  }
407
- const targetTy = ty.type_args ? (0, types_kernel_1.instantiateGenerics)(aliasRef.target_ty, aliasRef.type_params, ty.type_args) : aliasRef.target_ty;
408
- return dynamicUnpack(ctx, fieldPath, targetTy, s);
409
+ const target = ctx.symbols.aliasTargetOf(tyIdx);
410
+ return dynamicUnpack(ctx, fieldPath, target.ty_idx, s, target.uLabelTyIdx);
409
411
  }
410
- case 'genericT': throw new unsupported_errors_1.CantUnpackDynamic(fieldPath, 'unexpected genericT');
412
+ case 'genericT': throw new unsupported_errors_1.CantUnpackDynamic(fieldPath, `unexpected genericT at ${fieldPath}`);
411
413
  case 'union': {
412
- for (const variant of (0, types_kernel_1.createLabelsForUnion)(ctx.symbols, ty.variants)) {
413
- if (!lookupPrefix(s, +variant.prefix_str, variant.prefix_len)) {
414
+ for (const variant of (0, types_kernel_1.createLabelsForUnion)(ctx.symbols, ty.variants, uLabelTyIdx)) {
415
+ if (!lookupPrefix(s, variant.prefix_num, variant.prefix_len)) {
414
416
  continue;
415
417
  }
416
418
  if (variant.is_prefix_implicit) {
417
419
  s.skip(variant.prefix_len);
418
420
  }
419
- let actualValue = dynamicUnpack(ctx, `${fieldPath}#${variant.labelStr}`, variant.variant_ty, s);
421
+ let actualValue = dynamicUnpack(ctx, `${fieldPath}#${variant.labelStr}`, variant.variant_ty_idx, s);
420
422
  if (!variant.hasValueField) {
421
423
  return actualValue;
422
424
  }
@@ -427,27 +429,29 @@ function dynamicUnpack(ctx, fieldPath, ty, s) {
427
429
  case 'void':
428
430
  return void 0;
429
431
  default:
430
- throw new unsupported_errors_1.CantUnpackDynamic(fieldPath, `type '${(0, types_kernel_1.renderTy)(ty)}' is not serializable`);
432
+ throw new unsupported_errors_1.CantUnpackDynamic(fieldPath, `type '${(0, types_kernel_1.renderTy)(ctx.symbols, tyIdx)}' is not serializable`);
431
433
  }
432
434
  }
433
435
  /**
434
436
  * Pack any input to a builder according to an ABI schema.
435
437
  * Example: `struct Point { x: int8, y: int8 }`.
436
438
  * After being converted, it's stored as ABI.
437
- * Call: `packToBuilderDynamic(ctx, structTy, { x: 10, y: 20 }, b)` appends 0x0A14.
439
+ * Call: `packToBuilderDynamic(ctx, pointTyIdx, { x: 10, y: 20 }, b)` appends 0x0A14.
438
440
  * When input is incorrect (e.g. missing property in a JS object), throws InvalidDynamicInput.
439
441
  */
440
- function packToBuilderDynamic(ctx, ty, value, b) {
442
+ function packToBuilderDynamic(ctx, tyIdx, value, b) {
443
+ let ty = ctx.symbols.tyByIdx(tyIdx);
441
444
  let fieldPath = ty.kind === 'StructRef' ? ty.struct_name : 'self';
442
- dynamicPack(ctx, fieldPath, ty, value, b);
445
+ dynamicPack(ctx, fieldPath, tyIdx, value, b);
443
446
  }
444
447
  /**
445
448
  * Unpack any slice to a JS variable according to an ABI schema.
446
449
  * Example: `struct Point { x: int8, y: int8 }`.
447
- * Call: `unpackFromSliceDynamic(ctx, structTy, hex"0A14")` returns `{ x: 10, y: 20 }`.
450
+ * Call: `unpackFromSliceDynamic(ctx, pointTyIdx, hex"0A14")` returns `{ x: 10, y: 20 }`.
448
451
  * When ty can't be deserialized, throws CantUnpackDynamic.
449
452
  */
450
- function unpackFromSliceDynamic(ctx, ty, s) {
453
+ function unpackFromSliceDynamic(ctx, tyIdx, s) {
454
+ let ty = ctx.symbols.tyByIdx(tyIdx);
451
455
  let fieldPath = ty.kind === 'StructRef' ? ty.struct_name : 'self';
452
- return dynamicUnpack(ctx, fieldPath, ty, s);
456
+ return dynamicUnpack(ctx, fieldPath, tyIdx, s);
453
457
  }
@@ -1,8 +1,8 @@
1
- import type { Ty } from './abi-types';
2
- export declare function throwInvalidInput(fieldPath: string, expectedTy: Ty, msgWhyInvalid: string): never;
3
- export declare function checkIsNumber(fieldPath: string, expectedTy: Ty, passedV: any): void;
4
- export declare function checkIsBoolean(fieldPath: string, expectedTy: Ty, passedV: any): void;
5
- export declare function checkIsString(fieldPath: string, expectedTy: Ty, passedV: any): void;
6
- export declare function checkIsArray(fieldPath: string, expectedTy: Ty, passedV: any, expectedLen?: number): void;
7
- export declare function checkIsObject(fieldPath: string, expectedTy: Ty, passedV: any, allowNull?: boolean): void;
8
- export declare function checkIsObjectWithProperty(fieldPath: string, expectedTy: Ty, passedV: any, propertyName: string): void;
1
+ import { DynamicCtx } from './dynamic-ctx';
2
+ export declare function throwInvalidInput(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, msgWhyInvalid: string): never;
3
+ export declare function checkIsNumber(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, passedV: any): void;
4
+ export declare function checkIsBoolean(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, passedV: any): void;
5
+ export declare function checkIsString(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, passedV: any): void;
6
+ export declare function checkIsArray(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, passedV: any, expectedLen?: number): void;
7
+ export declare function checkIsObject(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, passedV: any, allowNull?: boolean): void;
8
+ export declare function checkIsObjectWithProperty(ctx: DynamicCtx, fieldPath: string, expectedTyIdx: number, passedV: any, propertyName: string): void;
@@ -9,48 +9,48 @@ exports.checkIsObject = checkIsObject;
9
9
  exports.checkIsObjectWithProperty = checkIsObjectWithProperty;
10
10
  const unsupported_errors_1 = require("./unsupported-errors");
11
11
  const types_kernel_1 = require("./types-kernel");
12
- function throwInvalidInput(fieldPath, expectedTy, msgWhyInvalid) {
13
- throw new unsupported_errors_1.InvalidDynamicInput(`invalid value passed for '${fieldPath}' of type '${(0, types_kernel_1.renderTy)(expectedTy)}': ${msgWhyInvalid}`);
12
+ function throwInvalidInput(ctx, fieldPath, expectedTyIdx, msgWhyInvalid) {
13
+ throw new unsupported_errors_1.InvalidDynamicInput(`invalid value passed for '${fieldPath}' of type '${(0, types_kernel_1.renderTy)(ctx.symbols, expectedTyIdx)}': ${msgWhyInvalid}`);
14
14
  }
15
- function checkIsNumber(fieldPath, expectedTy, passedV) {
15
+ function checkIsNumber(ctx, fieldPath, expectedTyIdx, passedV) {
16
16
  let isNumber = typeof passedV === 'bigint' || typeof passedV === 'number';
17
17
  if (!isNumber) {
18
- throwInvalidInput(fieldPath, expectedTy, 'not a number');
18
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, 'not a number');
19
19
  }
20
20
  }
21
- function checkIsBoolean(fieldPath, expectedTy, passedV) {
21
+ function checkIsBoolean(ctx, fieldPath, expectedTyIdx, passedV) {
22
22
  let isBoolean = typeof passedV === 'boolean';
23
23
  if (!isBoolean) {
24
- throwInvalidInput(fieldPath, expectedTy, 'not a boolean');
24
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, 'not a boolean');
25
25
  }
26
26
  }
27
- function checkIsString(fieldPath, expectedTy, passedV) {
27
+ function checkIsString(ctx, fieldPath, expectedTyIdx, passedV) {
28
28
  let isString = typeof passedV === 'string';
29
29
  if (!isString) {
30
- throwInvalidInput(fieldPath, expectedTy, 'not a string');
30
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, 'not a string');
31
31
  }
32
32
  }
33
- function checkIsArray(fieldPath, expectedTy, passedV, expectedLen) {
33
+ function checkIsArray(ctx, fieldPath, expectedTyIdx, passedV, expectedLen) {
34
34
  let isArray = Array.isArray(passedV);
35
35
  if (!isArray) {
36
- throwInvalidInput(fieldPath, expectedTy, 'not an array');
36
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, 'not an array');
37
37
  }
38
38
  if (expectedLen !== undefined && passedV.length !== expectedLen) {
39
- throwInvalidInput(fieldPath, expectedTy, `expected ${expectedLen} elements, got ${passedV.length}`);
39
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, `expected ${expectedLen} elements, got ${passedV.length}`);
40
40
  }
41
41
  }
42
- function checkIsObject(fieldPath, expectedTy, passedV, allowNull = false) {
42
+ function checkIsObject(ctx, fieldPath, expectedTyIdx, passedV, allowNull = false) {
43
43
  let isObject = typeof passedV === 'object' && !Array.isArray(passedV);
44
44
  if (passedV === null && !allowNull) {
45
45
  isObject = false;
46
46
  }
47
47
  if (!isObject) {
48
- throwInvalidInput(fieldPath, expectedTy, 'not an object');
48
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, 'not an object');
49
49
  }
50
50
  }
51
- function checkIsObjectWithProperty(fieldPath, expectedTy, passedV, propertyName) {
51
+ function checkIsObjectWithProperty(ctx, fieldPath, expectedTyIdx, passedV, propertyName) {
52
52
  let isObject = typeof passedV === 'object' && !Array.isArray(passedV) && passedV !== null;
53
53
  if (!isObject || !passedV.hasOwnProperty(propertyName)) {
54
- throwInvalidInput(fieldPath, expectedTy, `not an object with property ${propertyName}`);
54
+ throwInvalidInput(ctx, fieldPath, expectedTyIdx, `not an object with property ${propertyName}`);
55
55
  }
56
56
  }
@@ -1,5 +1,5 @@
1
- import { ABIConstExpression, Ty } from './abi-types';
1
+ import { ABIConstExpression } from './abi-types';
2
2
  import { CodegenCtx } from './codegen-ctx';
3
- export declare function isDefaultValueSupported(fieldTy: Ty): boolean;
3
+ export declare function isDefaultValueSupported(ctx: CodegenCtx, fieldTyIdx: number): boolean;
4
4
  export declare function emitFieldDefault(ctx: CodegenCtx, expr: ABIConstExpression): string;
5
- export declare function emitFieldDefaultInComment(expr: ABIConstExpression): string;
5
+ export declare function emitFieldDefaultInComment(ctx: CodegenCtx, expr: ABIConstExpression): string;
@@ -10,15 +10,16 @@ const types_kernel_1 = require("./types-kernel");
10
10
  // But in theory, a field can be a union, for example. It will require a large amount of work to support
11
11
  // cases like `f: int8 | slice = 5` or `f: int32 | int64 = 5 as int64` (to generate correct `$` labels).
12
12
  // So, if such a field exists, then we just assume it has no default.
13
- function isDefaultValueSupported(fieldTy) {
13
+ function isDefaultValueSupported(ctx, fieldTyIdx) {
14
+ const fieldTy = ctx.symbols.tyByIdx(fieldTyIdx);
14
15
  if (fieldTy.kind === 'arrayOf')
15
- return isDefaultValueSupported(fieldTy.inner);
16
+ return isDefaultValueSupported(ctx, fieldTy.inner_ty_idx);
16
17
  if (fieldTy.kind === 'lispListOf')
17
- return isDefaultValueSupported(fieldTy.inner);
18
+ return isDefaultValueSupported(ctx, fieldTy.inner_ty_idx);
18
19
  if (fieldTy.kind === 'tensor')
19
- return fieldTy.items.every(isDefaultValueSupported);
20
+ return fieldTy.items_ty_idx.every(ty_idx => isDefaultValueSupported(ctx, ty_idx));
20
21
  if (fieldTy.kind === 'shapedTuple')
21
- return fieldTy.items.every(isDefaultValueSupported);
22
+ return fieldTy.items_ty_idx.every(ty_idx => isDefaultValueSupported(ctx, ty_idx));
22
23
  return fieldTy.kind !== 'union' && fieldTy.kind !== 'mapKV';
23
24
  }
24
25
  // Default values of fields (particularly, in storage) are precalculated by the compiler
@@ -45,17 +46,17 @@ function emitFieldDefault(ctx, expr) {
45
46
  // Output a default value not as a TypeScript expression, but as a human-readable one.
46
47
  // For instance, "123" instead of bigint "123n".
47
48
  // It's inserted inside comments next to fields having defaults.
48
- function emitFieldDefaultInComment(expr) {
49
+ function emitFieldDefaultInComment(ctx, expr) {
49
50
  switch (expr.kind) {
50
51
  case 'int': return expr.v;
51
52
  case 'bool': return expr.v ? 'true' : 'false';
52
53
  case 'slice': return `hex('${expr.hex}')`;
53
54
  case 'string': return JSON.stringify(expr.str);
54
55
  case 'address': return `address('${expr.addr}')`;
55
- case 'tensor': return `[${expr.items.map(emitFieldDefaultInComment).join(', ')}]`;
56
- case 'shapedTuple': return `[${expr.items.map(emitFieldDefaultInComment).join(', ')}]`;
57
- case 'object': return `${expr.struct_name} { ${expr.fields.map(emitFieldDefaultInComment).join(', ')} }`;
58
- case 'castTo': return `${emitFieldDefaultInComment(expr.inner)} as ${(0, types_kernel_1.renderTy)(expr.cast_to)}`;
56
+ case 'tensor': return `[${expr.items.map(i => emitFieldDefaultInComment(ctx, i)).join(', ')}]`;
57
+ case 'shapedTuple': return `[${expr.items.map(i => emitFieldDefaultInComment(ctx, i)).join(', ')}]`;
58
+ case 'object': return `${expr.struct_name} { ${expr.fields.map(i => emitFieldDefaultInComment(ctx, i)).join(', ')} }`;
59
+ case 'castTo': return `${emitFieldDefaultInComment(ctx, expr.inner)} as ${(0, types_kernel_1.renderTy)(ctx.symbols, expr.cast_to_ty_idx)}`;
59
60
  case 'null': return `null`;
60
61
  }
61
62
  }
@@ -1,9 +1,15 @@
1
- import type { Ty } from './abi-types';
2
1
  import { CodegenCtx } from './codegen-ctx';
3
- export declare function emitLoadExpr(ctx: CodegenCtx, fieldPath: string, ty: Ty): string;
4
- export declare function emitLoadCallback(ctx: CodegenCtx, fieldPath: string, ty: Ty): string;
5
- export declare function emitStoreStatement(ctx: CodegenCtx, tsExpr: string, ty: Ty): string;
6
- export declare function emitStoreCallback(ctx: CodegenCtx, ty: Ty): string;
7
- export declare function emitMakeCellFromExpr(ctx: CodegenCtx, tsExpr: string, ty: Ty, disableShortHand?: boolean): string;
8
- export declare function emitCallToCreateMethodExpr(ctx: CodegenCtx, bodyArg: string, ty: Ty): string;
9
- export declare function emitDictKVSerializers(ctx: CodegenCtx, fieldPath: string, tyK: Ty, tyV: Ty): string;
2
+ import { ABIAlias, ABIEnum, ABIStruct } from './abi-types';
3
+ export declare function emitLoadOfStruct(ctx: CodegenCtx, structRef: ABIStruct, instantiationTyIdx: number): string;
4
+ export declare function emitLoadOfAlias(ctx: CodegenCtx, aliasRef: ABIAlias, instantiationTyIdx: number): string;
5
+ export declare function emitLoadOfEnum(ctx: CodegenCtx, enumRef: ABIEnum): string;
6
+ export declare function emitLoadExpr(ctx: CodegenCtx, fieldPath: string, tyIdx: number, uLabelTyIdx?: number): string;
7
+ export declare function emitLoadCallback(ctx: CodegenCtx, fieldPath: string, tyIdx: number): string;
8
+ export declare function emitStoreOfStruct(ctx: CodegenCtx, tsExpr: string, structRef: ABIStruct, instantiationTyIdx: number): string;
9
+ export declare function emitStoreOfAlias(ctx: CodegenCtx, tsExpr: string, aliasRef: ABIAlias, instantiationTyIdx: number): string;
10
+ export declare function emitStoreOfEnum(ctx: CodegenCtx, tsExpr: string, enumRef: ABIEnum): string;
11
+ export declare function emitStoreStatement(ctx: CodegenCtx, tsExpr: string, tyIdx: number, uLabelTyIdx?: number): string;
12
+ export declare function emitStoreCallback(ctx: CodegenCtx, tyIdx: number): string;
13
+ export declare function emitMakeCellFromExpr(ctx: CodegenCtx, tsExpr: string, tyIdx: number, disableShortHand?: boolean): string;
14
+ export declare function emitCallToCreateMethodExpr(ctx: CodegenCtx, bodyArg: string, tyIdx: number): string;
15
+ export declare function emitDictKVSerializers(ctx: CodegenCtx, fieldPath: string, tyKIdx: number, tyVIdx: number): string;