@ton/sandbox 0.32.2 → 0.33.0-dev.20250610093937.e3733e4
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 +6 -0
- package/dist/blockchain/Blockchain.d.ts +14 -14
- package/dist/blockchain/Blockchain.js +28 -18
- package/dist/blockchain/BlockchainContractProvider.d.ts +4 -4
- package/dist/blockchain/BlockchainContractProvider.js +9 -8
- package/dist/blockchain/BlockchainSender.d.ts +1 -1
- package/dist/blockchain/BlockchainSender.js +5 -2
- package/dist/blockchain/BlockchainStorage.d.ts +6 -6
- package/dist/blockchain/BlockchainStorage.js +15 -7
- package/dist/blockchain/SmartContract.d.ts +4 -4
- package/dist/blockchain/SmartContract.js +24 -15
- package/dist/event/Event.d.ts +1 -1
- package/dist/event/Event.js +15 -13
- package/dist/executor/Executor.d.ts +2 -2
- package/dist/executor/Executor.js +52 -33
- package/dist/index.d.ts +10 -9
- package/dist/index.js +4 -1
- package/dist/jest/BenchmarkCommand.js +1 -1
- package/dist/jest/BenchmarkReporter.js +1 -1
- package/dist/meta/ContractsMeta.d.ts +1 -1
- package/dist/metric/collectMetric.js +6 -1
- package/dist/metric/deltaResult.js +2 -0
- package/dist/treasury/Treasury.d.ts +1 -1
- package/dist/treasury/Treasury.js +6 -11
- package/dist/utils/AsyncLock.js +5 -5
- package/dist/utils/base64.js +1 -1
- package/dist/utils/config.d.ts +3 -0
- package/dist/utils/config.js +78 -0
- package/dist/utils/crc16.js +19 -32
- package/dist/utils/ec.d.ts +1 -1
- package/dist/utils/message.d.ts +2 -2
- package/dist/utils/prettyLogTransaction.d.ts +1 -1
- package/dist/utils/prettyLogTransaction.js +1 -0
- package/dist/utils/printTransactionFees.d.ts +1 -1
- package/dist/utils/printTransactionFees.js +6 -4
- package/jest-environment.js +1 -1
- package/jest-reporter.js +1 -1
- package/package.json +9 -4
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,12 @@ All notable changes to this project will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## Unreleased
|
|
9
|
+
|
|
10
|
+
### Added
|
|
11
|
+
|
|
12
|
+
- Added `fetchConfig` and `setGlobalVersion` utility functions
|
|
13
|
+
|
|
8
14
|
## [0.32.2] - 2025-06-10
|
|
9
15
|
|
|
10
16
|
### Changed
|
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
import { Address, Cell, Message, Transaction, ContractProvider, Contract, Sender, ShardAccount, TupleItem, ExternalAddress, StateInit, OpenedContract } from
|
|
2
|
-
import { IExecutor, TickOrTock, PrevBlocksInfo } from
|
|
3
|
-
import { BlockchainStorage } from
|
|
4
|
-
import { Event } from
|
|
5
|
-
import { SandboxContractProvider } from
|
|
6
|
-
import { TreasuryContract } from
|
|
7
|
-
import { GetMethodParams, LogsVerbosity, MessageParams, SmartContract, SmartContractSnapshot, Verbosity } from
|
|
8
|
-
import { AsyncLock } from
|
|
9
|
-
import { ContractsMeta } from
|
|
1
|
+
import { Address, Cell, Message, Transaction, ContractProvider, Contract, Sender, ShardAccount, TupleItem, ExternalAddress, StateInit, OpenedContract } from '@ton/core';
|
|
2
|
+
import { IExecutor, TickOrTock, PrevBlocksInfo } from '../executor/Executor';
|
|
3
|
+
import { BlockchainStorage } from './BlockchainStorage';
|
|
4
|
+
import { Event } from '../event/Event';
|
|
5
|
+
import { SandboxContractProvider } from './BlockchainContractProvider';
|
|
6
|
+
import { TreasuryContract } from '../treasury/Treasury';
|
|
7
|
+
import { GetMethodParams, LogsVerbosity, MessageParams, SmartContract, SmartContractSnapshot, Verbosity } from './SmartContract';
|
|
8
|
+
import { AsyncLock } from '../utils/AsyncLock';
|
|
9
|
+
import { ContractsMeta } from '../meta/ContractsMeta';
|
|
10
10
|
export type ExternalOutInfo = {
|
|
11
11
|
type: 'external-out';
|
|
12
12
|
src: Address;
|
|
@@ -41,16 +41,16 @@ export type SendMessageResult = {
|
|
|
41
41
|
events: Event[];
|
|
42
42
|
externals: ExternalOut[];
|
|
43
43
|
};
|
|
44
|
-
type ExtendsContractProvider<T> = T extends ContractProvider ? true :
|
|
44
|
+
type ExtendsContractProvider<T> = T extends ContractProvider ? true : T extends SandboxContractProvider ? true : false;
|
|
45
45
|
export declare const SANDBOX_CONTRACT_SYMBOL: unique symbol;
|
|
46
46
|
/**
|
|
47
47
|
* @type SandboxContract Represents a sandbox contract.
|
|
48
48
|
* @template F Type parameter representing the original contract object.
|
|
49
49
|
*/
|
|
50
50
|
export type SandboxContract<F> = {
|
|
51
|
-
[P in keyof F]: P extends `${'get' | 'is'}${string}` ?
|
|
51
|
+
[P in keyof F]: P extends `${'get' | 'is'}${string}` ? F[P] extends (x: infer CP, ...args: infer P) => infer R ? ExtendsContractProvider<CP> extends true ? (...args: P) => R : never : never : P extends `send${string}` ? F[P] extends (x: infer CP, ...args: infer P) => infer R ? ExtendsContractProvider<CP> extends true ? (...args: P) => Promise<SendMessageResult & {
|
|
52
52
|
result: R extends Promise<infer PR> ? PR : R;
|
|
53
|
-
}> : never
|
|
53
|
+
}> : never : never : F[P];
|
|
54
54
|
};
|
|
55
55
|
/**
|
|
56
56
|
* Provide way to check if contract is in sandbox environment.
|
|
@@ -60,11 +60,11 @@ export type SandboxContract<F> = {
|
|
|
60
60
|
export declare function toSandboxContract<T>(contract: OpenedContract<T>): SandboxContract<T>;
|
|
61
61
|
export type PendingMessage = (({
|
|
62
62
|
type: 'message';
|
|
63
|
-
} & Message) |
|
|
63
|
+
} & Message) | {
|
|
64
64
|
type: 'ticktock';
|
|
65
65
|
which: TickOrTock;
|
|
66
66
|
on: Address;
|
|
67
|
-
})
|
|
67
|
+
}) & {
|
|
68
68
|
parentTransaction?: BlockchainTransaction;
|
|
69
69
|
};
|
|
70
70
|
/**
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.Blockchain = exports.toSandboxContract = exports.SANDBOX_CONTRACT_SYMBOL = void 0;
|
|
4
|
-
const defaultConfig_1 = require("../config/defaultConfig");
|
|
5
4
|
const core_1 = require("@ton/core");
|
|
5
|
+
const defaultConfig_1 = require("../config/defaultConfig");
|
|
6
6
|
const Executor_1 = require("../executor/Executor");
|
|
7
7
|
const BlockchainStorage_1 = require("./BlockchainStorage");
|
|
8
8
|
const Event_1 = require("../event/Event");
|
|
@@ -26,7 +26,9 @@ exports.SANDBOX_CONTRACT_SYMBOL = Symbol('SandboxContract');
|
|
|
26
26
|
* @throws Error if contract not a sandbox contract
|
|
27
27
|
*/
|
|
28
28
|
function toSandboxContract(contract) {
|
|
29
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
29
30
|
if (contract[exports.SANDBOX_CONTRACT_SYMBOL] === true) {
|
|
31
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
30
32
|
return contract;
|
|
31
33
|
}
|
|
32
34
|
throw new Error('Invalid contract: not a sandbox contract');
|
|
@@ -53,7 +55,7 @@ class Blockchain {
|
|
|
53
55
|
*/
|
|
54
56
|
snapshot() {
|
|
55
57
|
return {
|
|
56
|
-
contracts: this.storage.knownContracts().map(s => s.snapshot()),
|
|
58
|
+
contracts: this.storage.knownContracts().map((s) => s.snapshot()),
|
|
57
59
|
networkConfig: this.networkConfig,
|
|
58
60
|
lt: this.currentLt,
|
|
59
61
|
time: this.currentTime,
|
|
@@ -215,7 +217,7 @@ class Blockchain {
|
|
|
215
217
|
* let res = await blockchain.runTickTock(address, 'tock');
|
|
216
218
|
*/
|
|
217
219
|
async runTickTock(on, which, params) {
|
|
218
|
-
for (const addr of
|
|
220
|
+
for (const addr of Array.isArray(on) ? on : [on]) {
|
|
219
221
|
await this.pushTickTock(addr, which);
|
|
220
222
|
}
|
|
221
223
|
return await this.runQueue(params);
|
|
@@ -266,12 +268,17 @@ class Blockchain {
|
|
|
266
268
|
const txes = await this.processQueue(params);
|
|
267
269
|
return {
|
|
268
270
|
transactions: txes,
|
|
269
|
-
events: txes.map(tx => tx.events).flat(),
|
|
270
|
-
externals: txes.map(tx => tx.externals).flat(),
|
|
271
|
+
events: txes.map((tx) => tx.events).flat(),
|
|
272
|
+
externals: txes.map((tx) => tx.externals).flat(),
|
|
271
273
|
};
|
|
272
274
|
}
|
|
273
275
|
txIter(needsLocking, params) {
|
|
274
|
-
const it = {
|
|
276
|
+
const it = {
|
|
277
|
+
next: () => this.processTx(needsLocking, params),
|
|
278
|
+
[Symbol.asyncIterator]() {
|
|
279
|
+
return it;
|
|
280
|
+
},
|
|
281
|
+
};
|
|
275
282
|
return it;
|
|
276
283
|
}
|
|
277
284
|
async processInternal(params) {
|
|
@@ -331,7 +338,9 @@ class Blockchain {
|
|
|
331
338
|
}
|
|
332
339
|
async processTx(needsLocking, params) {
|
|
333
340
|
// Lock only if not locked already
|
|
334
|
-
return needsLocking
|
|
341
|
+
return needsLocking
|
|
342
|
+
? await this.lock.with(async () => this.processInternal(params))
|
|
343
|
+
: await this.processInternal(params);
|
|
335
344
|
}
|
|
336
345
|
async processQueue(params) {
|
|
337
346
|
params = {
|
|
@@ -403,7 +412,8 @@ class Blockchain {
|
|
|
403
412
|
const subwalletId = (0, testTreasurySubwalletId_1.testSubwalletId)(seed);
|
|
404
413
|
const wallet = this.openContract(Treasury_1.TreasuryContract.create(params?.workchain ?? 0, subwalletId));
|
|
405
414
|
const contract = await this.getContract(wallet.address);
|
|
406
|
-
if ((params?.predeploy ?? true) &&
|
|
415
|
+
if ((params?.predeploy ?? true) &&
|
|
416
|
+
(contract.accountState === undefined || contract.accountState.type === 'uninit')) {
|
|
407
417
|
await this.sendMessage((0, message_1.internal)({
|
|
408
418
|
from: new core_1.Address(0, Buffer.alloc(32)),
|
|
409
419
|
to: wallet.address,
|
|
@@ -461,9 +471,9 @@ class Blockchain {
|
|
|
461
471
|
}
|
|
462
472
|
this.meta?.upsert(address, { wrapperName: contract?.constructor?.name, abi: contract.abi });
|
|
463
473
|
const provider = this.provider(address, init);
|
|
464
|
-
|
|
474
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
465
475
|
return new Proxy(contract, {
|
|
466
|
-
get(target, prop) {
|
|
476
|
+
get: (target, prop) => {
|
|
467
477
|
if (prop === exports.SANDBOX_CONTRACT_SYMBOL) {
|
|
468
478
|
return true;
|
|
469
479
|
}
|
|
@@ -474,25 +484,27 @@ class Blockchain {
|
|
|
474
484
|
methodName: prop,
|
|
475
485
|
};
|
|
476
486
|
if (prop.startsWith('get')) {
|
|
487
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
477
488
|
return (...args) => value.apply(target, [provider, ...args]);
|
|
478
489
|
}
|
|
479
490
|
else if (prop.startsWith('send')) {
|
|
491
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
480
492
|
return async (...args) => {
|
|
481
493
|
let ret = value.apply(target, [provider, ...args]);
|
|
482
494
|
if (ret instanceof Promise) {
|
|
483
495
|
ret = await ret;
|
|
484
496
|
}
|
|
485
497
|
const out = {
|
|
486
|
-
...await
|
|
498
|
+
...(await this.runQueue()),
|
|
487
499
|
result: ret,
|
|
488
500
|
};
|
|
489
|
-
await (0, collectMetric_1.collectMetric)(
|
|
501
|
+
await (0, collectMetric_1.collectMetric)(this, ctx, out);
|
|
490
502
|
return out;
|
|
491
503
|
};
|
|
492
504
|
}
|
|
493
505
|
}
|
|
494
506
|
return value;
|
|
495
|
-
}
|
|
507
|
+
},
|
|
496
508
|
});
|
|
497
509
|
}
|
|
498
510
|
startFetchingContract(address) {
|
|
@@ -514,9 +526,6 @@ class Blockchain {
|
|
|
514
526
|
const contract = await this.startFetchingContract(address);
|
|
515
527
|
return contract;
|
|
516
528
|
}
|
|
517
|
-
catch (e) {
|
|
518
|
-
throw e;
|
|
519
|
-
}
|
|
520
529
|
finally {
|
|
521
530
|
this.contractFetches.delete(address.toRawString());
|
|
522
531
|
}
|
|
@@ -596,10 +605,11 @@ class Blockchain {
|
|
|
596
605
|
*/
|
|
597
606
|
static async create(opts) {
|
|
598
607
|
return new Blockchain({
|
|
599
|
-
executor: opts?.executor ?? await Executor_1.Executor.create(),
|
|
608
|
+
executor: opts?.executor ?? (await Executor_1.Executor.create()),
|
|
600
609
|
storage: opts?.storage ?? new BlockchainStorage_1.LocalBlockchainStorage(),
|
|
610
|
+
// eslint-disable-next-line @typescript-eslint/no-require-imports
|
|
601
611
|
meta: opts?.meta ?? require('@ton/test-utils')?.contractsMeta,
|
|
602
|
-
...opts
|
|
612
|
+
...opts,
|
|
603
613
|
});
|
|
604
614
|
}
|
|
605
615
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
|
-
import { Address, Cell, Contract, ContractGetMethodResult, ContractProvider, ContractState, ExtraCurrency, Message, OpenedContract, Sender, SendMode, StateInit, Transaction, TupleItem } from
|
|
3
|
-
import { TickOrTock } from
|
|
4
|
-
import { GetMethodResult, SmartContract } from
|
|
2
|
+
import { Address, Cell, Contract, ContractGetMethodResult, ContractProvider, ContractState, ExtraCurrency, Message, OpenedContract, Sender, SendMode, StateInit, Transaction, TupleItem } from '@ton/core';
|
|
3
|
+
import { TickOrTock } from '../executor/Executor';
|
|
4
|
+
import { GetMethodResult, SmartContract } from './SmartContract';
|
|
5
5
|
export interface SandboxContractProvider extends ContractProvider {
|
|
6
6
|
tickTock(which: TickOrTock): Promise<void>;
|
|
7
7
|
}
|
|
@@ -36,7 +36,7 @@ export declare class BlockchainContractProvider implements SandboxContractProvid
|
|
|
36
36
|
*
|
|
37
37
|
* @throws {Error}
|
|
38
38
|
*/
|
|
39
|
-
getTransactions(
|
|
39
|
+
getTransactions(_address: Address, _lt: bigint, _hash: Buffer, _limit?: number | undefined): Promise<Transaction[]>;
|
|
40
40
|
/**
|
|
41
41
|
* Pushes external-in message to message queue.
|
|
42
42
|
* @param message Message to push
|
|
@@ -12,12 +12,12 @@ function bigintToBuffer(x, n = 32) {
|
|
|
12
12
|
function convertState(state) {
|
|
13
13
|
if (state === undefined)
|
|
14
14
|
return {
|
|
15
|
-
type: 'uninit'
|
|
15
|
+
type: 'uninit',
|
|
16
16
|
};
|
|
17
17
|
switch (state.type) {
|
|
18
18
|
case 'uninit':
|
|
19
19
|
return {
|
|
20
|
-
type: 'uninit'
|
|
20
|
+
type: 'uninit',
|
|
21
21
|
};
|
|
22
22
|
case 'active':
|
|
23
23
|
return {
|
|
@@ -28,7 +28,7 @@ function convertState(state) {
|
|
|
28
28
|
case 'frozen':
|
|
29
29
|
return {
|
|
30
30
|
type: 'frozen',
|
|
31
|
-
stateHash: bigintToBuffer(state.stateHash)
|
|
31
|
+
stateHash: bigintToBuffer(state.stateHash),
|
|
32
32
|
};
|
|
33
33
|
}
|
|
34
34
|
}
|
|
@@ -72,6 +72,7 @@ class BlockchainContractProvider {
|
|
|
72
72
|
stackItems: result.stack,
|
|
73
73
|
logs: result.vmLogs,
|
|
74
74
|
};
|
|
75
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
75
76
|
delete ret.stackReader;
|
|
76
77
|
return ret;
|
|
77
78
|
}
|
|
@@ -81,15 +82,15 @@ class BlockchainContractProvider {
|
|
|
81
82
|
*
|
|
82
83
|
* @throws {Error}
|
|
83
84
|
*/
|
|
84
|
-
getTransactions(
|
|
85
|
-
throw new Error(
|
|
85
|
+
getTransactions(_address, _lt, _hash, _limit) {
|
|
86
|
+
throw new Error('`getTransactions` is not implemented in `BlockchainContractProvider`, do not use it in the tests');
|
|
86
87
|
}
|
|
87
88
|
/**
|
|
88
89
|
* Pushes external-in message to message queue.
|
|
89
90
|
* @param message Message to push
|
|
90
91
|
*/
|
|
91
92
|
async external(message) {
|
|
92
|
-
const init = (
|
|
93
|
+
const init = (await this.getState()).state.type !== 'active' && this.init ? this.init : undefined;
|
|
93
94
|
await this.blockchain.pushMessage({
|
|
94
95
|
info: {
|
|
95
96
|
type: 'external-in',
|
|
@@ -104,8 +105,8 @@ class BlockchainContractProvider {
|
|
|
104
105
|
* Pushes internal message to message queue.
|
|
105
106
|
*/
|
|
106
107
|
async internal(via, args) {
|
|
107
|
-
const init = (
|
|
108
|
-
const bounce =
|
|
108
|
+
const init = (await this.getState()).state.type !== 'active' && this.init ? this.init : undefined;
|
|
109
|
+
const bounce = args.bounce !== null && args.bounce !== undefined ? args.bounce : true;
|
|
109
110
|
const value = typeof args.value === 'string' ? (0, core_1.toNano)(args.value) : args.value;
|
|
110
111
|
const body = typeof args.body === 'string' ? (0, core_1.comment)(args.body) : args.body;
|
|
111
112
|
await via.send({
|
|
@@ -20,12 +20,15 @@ class BlockchainSender {
|
|
|
20
20
|
bounced: false,
|
|
21
21
|
src: this.address,
|
|
22
22
|
dest: args.to,
|
|
23
|
-
value: {
|
|
23
|
+
value: {
|
|
24
|
+
coins: args.value,
|
|
25
|
+
other: args.extracurrency ? (0, core_1.packExtraCurrencyDict)(args.extracurrency) : undefined,
|
|
26
|
+
},
|
|
24
27
|
forwardFee: 0n,
|
|
25
28
|
createdAt: 0,
|
|
26
29
|
createdLt: 0n,
|
|
27
30
|
},
|
|
28
|
-
body: args.body ?? new core_1.Cell()
|
|
31
|
+
body: args.body ?? new core_1.Cell(),
|
|
29
32
|
});
|
|
30
33
|
}
|
|
31
34
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
|
-
import { AccountState, Address } from
|
|
3
|
-
import { SmartContract } from
|
|
4
|
-
import { Blockchain } from
|
|
2
|
+
import { AccountState, Address } from '@ton/core';
|
|
3
|
+
import { SmartContract } from './SmartContract';
|
|
4
|
+
import { Blockchain } from './Blockchain';
|
|
5
5
|
/**
|
|
6
6
|
* @interface BlockchainStorage Provides information about contracts by blockchain
|
|
7
7
|
*/
|
|
@@ -66,13 +66,13 @@ export declare function wrapTonClient4ForRemote(client: {
|
|
|
66
66
|
getAccount(seqno: number, address: Address): Promise<{
|
|
67
67
|
account: {
|
|
68
68
|
state: {
|
|
69
|
-
type:
|
|
69
|
+
type: 'uninit';
|
|
70
70
|
} | {
|
|
71
|
-
type:
|
|
71
|
+
type: 'active';
|
|
72
72
|
code: string | null;
|
|
73
73
|
data: string | null;
|
|
74
74
|
} | {
|
|
75
|
-
type:
|
|
75
|
+
type: 'frozen';
|
|
76
76
|
stateHash: string;
|
|
77
77
|
};
|
|
78
78
|
balance: {
|
|
@@ -31,7 +31,13 @@ function convertTonClient4State(state) {
|
|
|
31
31
|
case 'uninit':
|
|
32
32
|
return { type: 'uninit' };
|
|
33
33
|
case 'active':
|
|
34
|
-
return {
|
|
34
|
+
return {
|
|
35
|
+
type: 'active',
|
|
36
|
+
state: {
|
|
37
|
+
code: state.code === null ? undefined : core_1.Cell.fromBase64(state.code),
|
|
38
|
+
data: state.data === null ? undefined : core_1.Cell.fromBase64(state.data),
|
|
39
|
+
},
|
|
40
|
+
};
|
|
35
41
|
case 'frozen':
|
|
36
42
|
return { type: 'frozen', stateHash: BigInt('0x' + Buffer.from(state.stateHash, 'base64').toString('hex')) };
|
|
37
43
|
default:
|
|
@@ -61,10 +67,12 @@ function wrapTonClient4ForRemote(client) {
|
|
|
61
67
|
return {
|
|
62
68
|
state: convertTonClient4State(account.state),
|
|
63
69
|
balance: BigInt(account.balance.coins),
|
|
64
|
-
lastTransaction: account.last === null
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
70
|
+
lastTransaction: account.last === null
|
|
71
|
+
? undefined
|
|
72
|
+
: {
|
|
73
|
+
lt: BigInt(account.last.lt),
|
|
74
|
+
hash: Buffer.from(account.last.hash, 'base64'),
|
|
75
|
+
},
|
|
68
76
|
};
|
|
69
77
|
},
|
|
70
78
|
};
|
|
@@ -89,7 +97,7 @@ class RemoteBlockchainStorage {
|
|
|
89
97
|
this.blockSeqno = blockSeqno;
|
|
90
98
|
}
|
|
91
99
|
async getLastBlockSeqno() {
|
|
92
|
-
return this.blockSeqno ?? await this.client.getLastBlockSeqno();
|
|
100
|
+
return this.blockSeqno ?? (await this.client.getLastBlockSeqno());
|
|
93
101
|
}
|
|
94
102
|
async getContract(blockchain, address) {
|
|
95
103
|
let existing = this.contracts.get(address.toString());
|
|
@@ -112,7 +120,7 @@ class RemoteBlockchainStorage {
|
|
|
112
120
|
storageExtra: null,
|
|
113
121
|
},
|
|
114
122
|
storage: {
|
|
115
|
-
lastTransLt: lt === 0n ? 0n :
|
|
123
|
+
lastTransLt: lt === 0n ? 0n : lt + 1n,
|
|
116
124
|
balance: { coins: account.balance },
|
|
117
125
|
state: account.state,
|
|
118
126
|
},
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import { ExtraCurrency } from
|
|
5
|
-
import { EmulationResult, RunCommonArgs, TickOrTock } from
|
|
2
|
+
import { Address, Cell, Message, ShardAccount, Transaction, TupleItem, TupleReader } from '@ton/core';
|
|
3
|
+
import { Blockchain } from './Blockchain';
|
|
4
|
+
import { ExtraCurrency } from '../utils/ec';
|
|
5
|
+
import { EmulationResult, RunCommonArgs, TickOrTock } from '../executor/Executor';
|
|
6
6
|
export declare function createShardAccount(args: {
|
|
7
7
|
address?: Address;
|
|
8
8
|
code: Cell;
|
|
@@ -30,9 +30,9 @@ function createShardAccount(args) {
|
|
|
30
30
|
type: 'active',
|
|
31
31
|
state: {
|
|
32
32
|
code: args.code,
|
|
33
|
-
data: args.data
|
|
34
|
-
}
|
|
35
|
-
}
|
|
33
|
+
data: args.data,
|
|
34
|
+
},
|
|
35
|
+
},
|
|
36
36
|
},
|
|
37
37
|
storageStats: {
|
|
38
38
|
used: {
|
|
@@ -42,10 +42,10 @@ function createShardAccount(args) {
|
|
|
42
42
|
lastPaid: 0,
|
|
43
43
|
duePayment: null,
|
|
44
44
|
storageExtra: null,
|
|
45
|
-
}
|
|
45
|
+
},
|
|
46
46
|
},
|
|
47
47
|
lastTransactionLt: 0n,
|
|
48
|
-
lastTransactionHash: 0n
|
|
48
|
+
lastTransactionHash: 0n,
|
|
49
49
|
};
|
|
50
50
|
}
|
|
51
51
|
exports.createShardAccount = createShardAccount;
|
|
@@ -55,30 +55,30 @@ function createEmptyAccount(address) {
|
|
|
55
55
|
storage: {
|
|
56
56
|
lastTransLt: 0n,
|
|
57
57
|
balance: { coins: 0n },
|
|
58
|
-
state: { type: 'uninit' }
|
|
58
|
+
state: { type: 'uninit' },
|
|
59
59
|
},
|
|
60
60
|
storageStats: {
|
|
61
61
|
used: { cells: 0n, bits: 0n },
|
|
62
62
|
lastPaid: 0,
|
|
63
63
|
storageExtra: null,
|
|
64
|
-
}
|
|
64
|
+
},
|
|
65
65
|
};
|
|
66
66
|
}
|
|
67
67
|
function createEmptyShardAccount(address) {
|
|
68
68
|
return {
|
|
69
69
|
account: createEmptyAccount(address),
|
|
70
70
|
lastTransactionLt: 0n,
|
|
71
|
-
lastTransactionHash: 0n
|
|
71
|
+
lastTransactionHash: 0n,
|
|
72
72
|
};
|
|
73
73
|
}
|
|
74
74
|
exports.createEmptyShardAccount = createEmptyShardAccount;
|
|
75
75
|
const verbosityToExecutorVerbosity = {
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
76
|
+
none: 'short',
|
|
77
|
+
vm_logs: 'full',
|
|
78
|
+
vm_logs_location: 'full_location',
|
|
79
|
+
vm_logs_gas: 'full_location_gas',
|
|
80
|
+
vm_logs_full: 'full_location_stack',
|
|
81
|
+
vm_logs_verbose: 'full_location_stack_verbose',
|
|
82
82
|
};
|
|
83
83
|
class GetMethodError extends Error {
|
|
84
84
|
constructor(exitCode, gasUsed, blockchainLogs, vmLogs, debugLogs) {
|
|
@@ -153,7 +153,8 @@ class SmartContract {
|
|
|
153
153
|
__classPrivateFieldSet(this, _SmartContract_verbosity, snapshot.verbosity === undefined ? undefined : { ...snapshot.verbosity }, "f");
|
|
154
154
|
}
|
|
155
155
|
get ec() {
|
|
156
|
-
return (0, ec_1.extractEc)(this.account.account?.storage.balance.other ??
|
|
156
|
+
return (0, ec_1.extractEc)(this.account.account?.storage.balance.other ??
|
|
157
|
+
core_1.Dictionary.empty(core_1.Dictionary.Keys.Uint(32), core_1.Dictionary.Values.BigVarUint(5)));
|
|
157
158
|
}
|
|
158
159
|
set ec(nv) {
|
|
159
160
|
const acc = this.account;
|
|
@@ -242,15 +243,18 @@ class SmartContract {
|
|
|
242
243
|
}
|
|
243
244
|
const res = await run();
|
|
244
245
|
if (this.verbosity.print && this.verbosity.blockchainLogs && res.logs.length > 0) {
|
|
246
|
+
// eslint-disable-next-line no-console
|
|
245
247
|
console.log(res.logs);
|
|
246
248
|
}
|
|
247
249
|
if (!res.result.success) {
|
|
248
250
|
throw new EmulationError(res.result.error, res.result.vmResults?.vmLog, res.result.vmResults?.vmExitCode, res.logs.length === 0 ? undefined : res.logs, res.debugLogs.length === 0 ? undefined : res.debugLogs);
|
|
249
251
|
}
|
|
250
252
|
if (this.verbosity.print && this.verbosity.vmLogs !== 'none' && res.result.vmLog.length > 0) {
|
|
253
|
+
// eslint-disable-next-line no-console
|
|
251
254
|
console.log(res.result.vmLog);
|
|
252
255
|
}
|
|
253
256
|
if (this.verbosity.print && this.verbosity.debugLogs && res.debugLogs.length > 0) {
|
|
257
|
+
// eslint-disable-next-line no-console
|
|
254
258
|
console.log(res.debugLogs);
|
|
255
259
|
}
|
|
256
260
|
const tx = (0, core_1.loadTransaction)(core_1.Cell.fromBase64(res.result.transaction).beginParse());
|
|
@@ -275,7 +279,9 @@ class SmartContract {
|
|
|
275
279
|
throw new Error('Trying to run get method on non-active contract');
|
|
276
280
|
}
|
|
277
281
|
const res = await this.blockchain.executor.runGetMethod({
|
|
282
|
+
// eslint-disable-next-line @typescript-eslint/no-non-null-asserted-optional-chain
|
|
278
283
|
code: this.account.account?.storage.state.state.code,
|
|
284
|
+
// eslint-disable-next-line @typescript-eslint/no-non-null-asserted-optional-chain
|
|
279
285
|
data: this.account.account?.storage.state.state.data,
|
|
280
286
|
methodId: typeof method === 'string' ? (0, selector_1.getSelectorForMethod)(method) : method,
|
|
281
287
|
stack,
|
|
@@ -292,15 +298,18 @@ class SmartContract {
|
|
|
292
298
|
prevBlocksInfo: this.blockchain.prevBlocks,
|
|
293
299
|
});
|
|
294
300
|
if (this.verbosity.print && this.verbosity.blockchainLogs && res.logs.length > 0) {
|
|
301
|
+
// eslint-disable-next-line no-console
|
|
295
302
|
console.log(res.logs);
|
|
296
303
|
}
|
|
297
304
|
if (!res.output.success) {
|
|
298
305
|
throw new Error('Error invoking get method: ' + res.output.error);
|
|
299
306
|
}
|
|
300
307
|
if (this.verbosity.print && this.verbosity.vmLogs !== 'none' && res.output.vm_log.length > 0) {
|
|
308
|
+
// eslint-disable-next-line no-console
|
|
301
309
|
console.log(res.output.vm_log);
|
|
302
310
|
}
|
|
303
311
|
if (this.verbosity.print && this.verbosity.debugLogs && res.debugLogs.length > 0) {
|
|
312
|
+
// eslint-disable-next-line no-console
|
|
304
313
|
console.log(res.debugLogs);
|
|
305
314
|
}
|
|
306
315
|
if (res.output.vm_exit_code !== 0 && res.output.vm_exit_code !== 1) {
|
package/dist/event/Event.d.ts
CHANGED
package/dist/event/Event.js
CHANGED
|
@@ -1,13 +1,9 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.extractEvents = void 0;
|
|
4
|
-
const extractors = [
|
|
5
|
-
extractAccountCreated,
|
|
6
|
-
extractMessageSent,
|
|
7
|
-
extractAccountDestroyed,
|
|
8
|
-
];
|
|
4
|
+
const extractors = [extractAccountCreated, extractMessageSent, extractAccountDestroyed];
|
|
9
5
|
function extractEvents(tx) {
|
|
10
|
-
return extractors.map(f => f(tx)).flat();
|
|
6
|
+
return extractors.map((f) => f(tx)).flat();
|
|
11
7
|
}
|
|
12
8
|
exports.extractEvents = extractEvents;
|
|
13
9
|
function doesAccountExist(state) {
|
|
@@ -15,32 +11,38 @@ function doesAccountExist(state) {
|
|
|
15
11
|
}
|
|
16
12
|
function extractAccountCreated(tx) {
|
|
17
13
|
if (!doesAccountExist(tx.oldStatus) && doesAccountExist(tx.endStatus))
|
|
18
|
-
return [
|
|
14
|
+
return [
|
|
15
|
+
{
|
|
19
16
|
type: 'account_created',
|
|
20
17
|
account: tx.inMessage.info.dest,
|
|
21
|
-
}
|
|
18
|
+
},
|
|
19
|
+
];
|
|
22
20
|
return [];
|
|
23
21
|
}
|
|
24
22
|
function extractAccountDestroyed(tx) {
|
|
25
23
|
if (doesAccountExist(tx.oldStatus) && !doesAccountExist(tx.endStatus))
|
|
26
|
-
return [
|
|
24
|
+
return [
|
|
25
|
+
{
|
|
27
26
|
type: 'account_destroyed',
|
|
28
27
|
account: tx.inMessage.info.dest,
|
|
29
|
-
}
|
|
28
|
+
},
|
|
29
|
+
];
|
|
30
30
|
return [];
|
|
31
31
|
}
|
|
32
32
|
function extractMessageSent(tx) {
|
|
33
|
-
return tx.outMessages.values().flatMap(m => {
|
|
33
|
+
return tx.outMessages.values().flatMap((m) => {
|
|
34
34
|
if (m.info.type !== 'internal') {
|
|
35
35
|
return [];
|
|
36
36
|
}
|
|
37
|
-
return [
|
|
37
|
+
return [
|
|
38
|
+
{
|
|
38
39
|
type: 'message_sent',
|
|
39
40
|
from: m.info.src,
|
|
40
41
|
to: m.info.dest,
|
|
41
42
|
value: m.info.value.coins,
|
|
42
43
|
body: m.body,
|
|
43
44
|
bounced: m.info.bounced,
|
|
44
|
-
}
|
|
45
|
+
},
|
|
46
|
+
];
|
|
45
47
|
});
|
|
46
48
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/// <reference types="node" />
|
|
2
|
-
import { Address, Cell, TupleItem } from
|
|
3
|
-
import { ExtraCurrency } from
|
|
2
|
+
import { Address, Cell, TupleItem } from '@ton/core';
|
|
3
|
+
import { ExtraCurrency } from '../utils/ec';
|
|
4
4
|
export type BlockId = {
|
|
5
5
|
workchain: number;
|
|
6
6
|
shard: bigint;
|