diff --git a/contracts/contracts/ccip/ccipsend_executor/contract.tolk b/contracts/contracts/ccip/ccipsend_executor/contract.tolk index 8b6cdec0a..2ad7269f2 100644 --- a/contracts/contracts/ccip/ccipsend_executor/contract.tolk +++ b/contracts/contracts/ccip/ccipsend_executor/contract.tolk @@ -11,7 +11,19 @@ import "../router/messages" import "../fee_quoter/types" import "@stdlib/gas-payments" -const CONTRACT_VERSION = "1.6.0"; +tolk 1.4.1 + +const CONTRACT_VERSION = "1.6.1".literalSlice(); + +contract CCIPSendExecutor { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.1" + description: "link.chain.ton.ccip.CCIPSendExecutor" + + storage: CCIPSendExecutor_Data + storageAtDeployment: CCIPSendExecutor_InitialData + incomingMessages: CCIPSendExecutor_InMessage +} fun onInternalMessage(in: InMessage) { val msg = lazy CCIPSendExecutor_InMessage.fromSlice(in.body); @@ -153,7 +165,7 @@ fun CCIPSendExecutor.exitWithError(self, error: uint256) { } get fun typeAndVersion(): (slice, slice) { - return (CCIPSendExecutor_FACILITY_NAME, CONTRACT_VERSION); + return (CCIPSendExecutor_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -161,5 +173,5 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.CCIPSendExecutor"), local); + return getErrorCode("link.chain.ton.ccip.CCIPSendExecutor".crc32(), local); } diff --git a/contracts/contracts/ccip/ccipsend_executor/types.tolk b/contracts/contracts/ccip/ccipsend_executor/types.tolk index be18d795b..d1fdde01a 100644 --- a/contracts/contracts/ccip/ccipsend_executor/types.tolk +++ b/contracts/contracts/ccip/ccipsend_executor/types.tolk @@ -2,7 +2,8 @@ import "../onramp/messages.tolk"; const CCIPSendExecutor_FACILITY_NAME = "link.chain.ton.ccip.CCIPSendExecutor"; -const CCIPSendExecutor_FACILITY_ID = 178; // (crc32() % 640) + 10 +const CCIPSendExecutor_FACILITY_ID = CCIPSendExecutor_FACILITY_NAME.crc32() % 640 + 10; // 178 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions type CCIPSendExecutor_ID = uint224 diff --git a/contracts/contracts/ccip/common/cross_chain_address_validation.tolk b/contracts/contracts/ccip/common/cross_chain_address_validation.tolk index d47b7a612..6c31cbb0a 100644 --- a/contracts/contracts/ccip/common/cross_chain_address_validation.tolk +++ b/contracts/contracts/ccip/common/cross_chain_address_validation.tolk @@ -3,7 +3,7 @@ import "types" -tolk 1.2 +tolk 1.4.1 const EVM_PRECOMPILE_SPACE = 1024; const APTOS_PRECOMPILE_SPACE = 0x0b; diff --git a/contracts/contracts/ccip/common/types.tolk b/contracts/contracts/ccip/common/types.tolk index 0715c9a47..34d060b28 100644 --- a/contracts/contracts/ccip/common/types.tolk +++ b/contracts/contracts/ccip/common/types.tolk @@ -29,7 +29,7 @@ struct RampMessageHeader { // 512 nonce: uint64; } -const LEAF_DOMAIN_SEPARATOR: slice = stringHexToSlice("0000000000000000000000000000000000000000000000000000000000000000"); +const LEAF_DOMAIN_SEPARATOR: slice = "0000000000000000000000000000000000000000000000000000000000000000".hexToSlice(); // nolint:opcode : hex encoded bytes4(keccak256("CCIP EVMExtraArgsV2")) struct (0x181dcf10) GenericExtraArgsV2 { diff --git a/contracts/contracts/ccip/fee_quoter/contract.tolk b/contracts/contracts/ccip/fee_quoter/contract.tolk index cd8277c44..e6a1a8201 100644 --- a/contracts/contracts/ccip/fee_quoter/contract.tolk +++ b/contracts/contracts/ccip/fee_quoter/contract.tolk @@ -16,9 +16,24 @@ import "../../lib/math"; import "../router/messages" import "../ccipsend_executor/messages" -const CONTRACT_VERSION = "1.6.2"; +tolk 1.4.1 + +contract FeeQuoter { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.3" + description: "link.chain.ton.ccip.FeeQuoter" + + storage: Storage + incomingMessages: FeeQuoter_InMessage +} + +const CONTRACT_VERSION = "1.6.3".literalSlice(); const RESERVE = ton("1"); +fun requireSupportedVersion(version: slice) { + assert (version.bitsEqual("1.6.2".literalSlice())) throw Upgradeable_Error.VersionMismatch; +} + fun onInternalMessage(in: InMessage) { val msg = lazy FeeQuoter_InMessage.fromSlice(in.body); match (msg) { @@ -159,7 +174,7 @@ fun updateDestChainConfigs(mutate st: Storage, updates: SnakedCell -get fun tokenPrices(tokens: tuple): tuple { +get fun tokenPrices(tokens: array
): array?> { val st = lazy Storage.load(); - var list: tuple = createEmptyTuple(); - var iter = TupleIterator
.new(tokens); + var prices: array?> = []; + var tokenIterator = ArrayIterator
.new(tokens); - while(!iter.empty()) { - val token = iter.next(); + while(!tokenIterator.empty()) { + val token = tokenIterator.next(); val entry = st.usdPerToken.get(token); // NOTE: Need to skip missing items as nil entries rather than fail the query if (entry.isFound) { - list.push(entry.loadValue().toCell()); + prices.push(entry.loadValue().toCell()); } else { - list.push(null); + prices.push(null); } } - return list; + return prices; } get fun destinationChainGasPrice(destChainSelector: uint64): cell { @@ -580,7 +597,7 @@ get fun premiumMultiplierWeiPerEth(token: address): uint256 { } // vec
-get fun feeTokens(): tuple? { +get fun feeTokens(): lisp_list
{ val st = lazy Storage.load(); var feeTokens = st.premiumMultiplierWeiPerEth; return keysLispList(feeTokens); @@ -637,7 +654,7 @@ get fun pendingOwner(): address? { } get fun typeAndVersion(): (slice, slice) { - return (FeeQuoter_FACILITY_NAME, CONTRACT_VERSION); + return (FeeQuoter_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -645,10 +662,10 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.FeeQuoter"), local); + return getErrorCode("link.chain.ton.ccip.FeeQuoter".crc32(), local); } -get fun destChainSelectors(): tuple? { +get fun destChainSelectors(): lisp_list { val st = lazy Storage.load(); var d = st.destChainConfigs; return keysLispList(d)!; @@ -667,13 +684,5 @@ fun migrate(storage: cell, version: slice): cell { return st.toCell(); } -fun requireSupportedVersion(version: slice) { - assert ( - version.bitsEqual("1.6.0") - || version.bitsEqual("1.6.1") - ) - throw Upgradeable_Error.VersionMismatch; -} - @method_id(1001) fun version(): slice { return CONTRACT_VERSION; } diff --git a/contracts/contracts/ccip/fee_quoter/events.tolk b/contracts/contracts/ccip/fee_quoter/events.tolk index a1a6cd6a6..6c62d4a99 100644 --- a/contracts/contracts/ccip/fee_quoter/events.tolk +++ b/contracts/contracts/ccip/fee_quoter/events.tolk @@ -1,13 +1,13 @@ // SPDX-License-Identifier: BUSL-1.1 -const USD_PER_TOKEN_UPDATED_TOPIC: int = stringCrc32("UsdPerTokenUpdated"); +const USD_PER_TOKEN_UPDATED_TOPIC: int = "UsdPerTokenUpdated".crc32(); struct UsdPerTokenUpdated { sourceToken: address usdPerToken: uint224 timestamp: uint64 } -const USD_PER_UNIT_GAS_UPDATED: int = stringCrc32("UsdPerUnitGasUpdated"); +const USD_PER_UNIT_GAS_UPDATED: int = "UsdPerUnitGasUpdated".crc32(); struct UsdPerUnitGasUpdated { destChainSelector: uint64 executionGasPrice: uint112 diff --git a/contracts/contracts/ccip/fee_quoter/types.tolk b/contracts/contracts/ccip/fee_quoter/types.tolk index e8e0af5f9..193981a77 100644 --- a/contracts/contracts/ccip/fee_quoter/types.tolk +++ b/contracts/contracts/ccip/fee_quoter/types.tolk @@ -1,7 +1,8 @@ import "../../lib/utils" const FeeQuoter_FACILITY_NAME = "link.chain.ton.ccip.FeeQuoter"; -const FeeQuoter_FACILITY_ID = 344; // (crc32() % 640) + 10 +const FeeQuoter_FACILITY_ID = FeeQuoter_FACILITY_NAME.crc32() % 640 + 10; // 344 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions struct TimestampedPrice { value: uint224; diff --git a/contracts/contracts/ccip/merkle_root/contract.tolk b/contracts/contracts/ccip/merkle_root/contract.tolk index f9ad92c29..da334dfea 100644 --- a/contracts/contracts/ccip/merkle_root/contract.tolk +++ b/contracts/contracts/ccip/merkle_root/contract.tolk @@ -11,10 +11,21 @@ import "errors" import "storage" import "types" +tolk 1.4.1 + // MerkleRoot contract // Root is commited on Commit Reports and the existence of this contract is used to validate Execute Reports -const CONTRACT_VERSION = "1.6.0"; +const CONTRACT_VERSION = "1.6.1".literalSlice(); + +contract MerkleRoot { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.1" + description: "link.chain.ton.ccip.MerkleRoot" + + storage: MerkleRoot_Storage + incomingMessages: MerkleRoot_InMessage +} fun onInternalMessage(in: InMessage) { val msg = lazy MerkleRoot_InMessage.fromSlice(in.body); @@ -113,7 +124,7 @@ fun onInitExecute(mutate st: MerkleRoot_Storage, msg: MerkleRoot_Validate) { } get fun typeAndVersion(): (slice, slice) { - return (MerkleRoot_FACILITY_NAME, CONTRACT_VERSION); + return (MerkleRoot_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -121,5 +132,5 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.MerkleRoot"), local); + return getErrorCode("link.chain.ton.ccip.MerkleRoot".crc32(), local); } diff --git a/contracts/contracts/ccip/merkle_root/types.tolk b/contracts/contracts/ccip/merkle_root/types.tolk index 81ec9f4ec..01314ee46 100644 --- a/contracts/contracts/ccip/merkle_root/types.tolk +++ b/contracts/contracts/ccip/merkle_root/types.tolk @@ -1,3 +1,4 @@ // SPDX-License-Identifier: BUSL-1.1 const MerkleRoot_FACILITY_NAME = "link.chain.ton.ccip.MerkleRoot"; -const MerkleRoot_FACILITY_ID = 186; // (crc32() % 640) + 10 +const MerkleRoot_FACILITY_ID = MerkleRoot_FACILITY_NAME.crc32() % 640 + 10; // 186 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions diff --git a/contracts/contracts/ccip/offramp/contract.tolk b/contracts/contracts/ccip/offramp/contract.tolk index 8138f7a03..95fa49cfc 100644 --- a/contracts/contracts/ccip/offramp/contract.tolk +++ b/contracts/contracts/ccip/offramp/contract.tolk @@ -1,6 +1,7 @@ // SPDX-License-Identifier: BUSL-1.1 import "../../lib/versioning/upgradeable" import "../../lib/deployable/types" +import "../../lib/deployable/namespace" import "../../lib/access/ownable_2step.tolk" import "../../lib/funding/withdrawable.tolk" import "../../lib/crypto/merkle_multi_proof.tolk" @@ -8,7 +9,7 @@ import "../../lib/ocr/multi_ocr3_base" import "../../lib/ocr/types" import "../../lib/utils.tolk" import "../../lib/receiver/types" -import "../../lib/deployable/namespace" +import "../rmn_remote/lib.tolk" import "../common/types.tolk" @@ -25,7 +26,19 @@ import "types" import "storage" import "events" -const CONTRACT_VERSION = "1.6.2"; +tolk 1.4.1 + +contract OffRamp { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.3" + description: "link.chain.ton.ccip.OffRamp" + + storage: Storage + incomingMessages: OffRamp_InMessage +} + + +const CONTRACT_VERSION = "1.6.3".literalSlice(); const RESERVE = ton("5"); const MIN_GASLIMIT = ton("0.025"); @@ -242,11 +255,7 @@ fun migrate(storage: cell, version: slice): cell { } fun requireSupportedVersion(version: slice) { - assert ( - version.bitsEqual("1.6.0") - || version.bitsEqual("1.6.1") - ) - throw Upgradeable_Error.VersionMismatch; + assert (version.bitsEqual("1.6.2".literalSlice())) throw Upgradeable_Error.VersionMismatch; } @method_id(1001) @@ -691,10 +700,10 @@ fun onExecuteSingleReport(report: ExecutionReport, gasOverride: coins?, value: c // This acts as an extra check to ensure the message source chain selector matches the report's source chain. assert(message.header.sourceChainSelector == report.sourceChainSelector, Error.SourceChainSelectorMismatch); - var leafTuple: tuple = createEmptyTuple(); - leafTuple.push(message.generateMessageId(metadataHash)); + var leaves: array = []; + leaves.push(message.generateMessageId(metadataHash)); - val root = merkleRoot(TupleIterator.new(leafTuple), report.proofs.iter(), report.proofFlagBits); + val root = merkleRoot(ArrayIterator.new(leaves), report.proofs.iter(), report.proofFlagBits); // send message to MerkleRoot (execute) val executeMsg = createMessage({ @@ -936,7 +945,7 @@ get fun latestPriceSequenceNumber(): uint64 { return st.latestPriceSequenceNumber } -get fun sourceChainSelectors(): tuple? { +get fun sourceChainSelectors(): lisp_list { val st = lazy Storage.load(); var d = st.sourceChainConfigs; return keysLispList(d)!; @@ -971,7 +980,7 @@ get fun verifyNotCursed(subject: uint128): bool { return !st.cursedSubjects.isCursed(subject); } -get fun cursedSubjects(): tuple? { +get fun cursedSubjects(): lisp_list { val st = lazy Storage.load(); return keysLispList(st.cursedSubjects.data)!; } @@ -1005,7 +1014,7 @@ get fun pendingOwner(): address? { } get fun typeAndVersion(): (slice, slice) { - return (OffRamp_FACILITY_NAME, CONTRACT_VERSION); + return (OffRamp_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -1013,7 +1022,7 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.OffRamp"), local); + return getErrorCode("link.chain.ton.ccip.OffRamp".crc32(), local); } get fun reserve(): coins { diff --git a/contracts/contracts/ccip/offramp/events.tolk b/contracts/contracts/ccip/offramp/events.tolk index 8e27efa48..b3e21ddca 100644 --- a/contracts/contracts/ccip/offramp/events.tolk +++ b/contracts/contracts/ccip/offramp/events.tolk @@ -2,7 +2,7 @@ import "types" import "../fee_quoter/types" -const EXECUTION_STATE_CHANGED_TOPIC: int = stringCrc32("ExecutionStateChanged"); +const EXECUTION_STATE_CHANGED_TOPIC: int = "ExecutionStateChanged".crc32(); struct ExecutionStateChanged { sourceChainSelector: uint64, sequenceNumber: uint64, @@ -10,42 +10,42 @@ struct ExecutionStateChanged { state: ExecutionState, } -const TOPIC_COMMIT_REPORT_ACCEPTED: int = stringCrc32("CommitReportAccepted"); +const TOPIC_COMMIT_REPORT_ACCEPTED: int = "CommitReportAccepted".crc32(); struct CommitReportAccepted { merkleRoot: MerkleRoot? // vec priceUpdates: Cell?; } -const SOURCE_CHAIN_SELECTOR_ADDED_TOPIC: int = stringCrc32("SourceChainSelectorAdded"); +const SOURCE_CHAIN_SELECTOR_ADDED_TOPIC: int = "SourceChainSelectorAdded".crc32(); struct SourceChainSelectorAdded { sourceChainSelector: uint64; } -const SOURCE_CHAIN_CONFIG_UPDATED_TOPIC: int = stringCrc32("SourceChainConfigUpdated"); +const SOURCE_CHAIN_CONFIG_UPDATED_TOPIC: int = "SourceChainConfigUpdated".crc32(); struct SourceChainConfigUpdated { sourceChainSelector: uint64; sourceChainConfig: SourceChainConfig; } -const DYNAMIC_CONFIG_SET_TOPIC: int = stringCrc32("DynamicConfigSet"); +const DYNAMIC_CONFIG_SET_TOPIC: int = "DynamicConfigSet".crc32(); struct OffRamp_DynamicConfigSet { feeQuoter: address; permissionlessExecutionThresholdSeconds: uint32, } -const RECEIVE_EXECUTOR_INIT_EXECUTE_BOUNCED: int = stringCrc32("ReceiveExecutorInitExecuteBounced"); +const RECEIVE_EXECUTOR_INIT_EXECUTE_BOUNCED: int = "ReceiveExecutorInitExecuteBounced".crc32(); struct OffRamp_ReceiveExecutorInitExecuteBounced { receiveExecutor: address; root: address; sequenceNumber: uint64; } -const DEPLOYABLE_INITIALIZE_BOUNCED_TOPIC: int = stringCrc32("DeployableInitializeBounced"); +const DEPLOYABLE_INITIALIZE_BOUNCED_TOPIC: int = "DeployableInitializeBounced".crc32(); struct OffRamp_DeployableInitializeBounced { deployableAddress: address; } -const ROUTE_MESSAGE_BOUNCED_TOPIC: int = stringCrc32("RouteMessageBounced"); +const ROUTE_MESSAGE_BOUNCED_TOPIC: int = "RouteMessageBounced".crc32(); struct OffRamp_RouteMessageBounced { router: address; execId: uint192; diff --git a/contracts/contracts/ccip/offramp/types.tolk b/contracts/contracts/ccip/offramp/types.tolk index f8dcb6075..48b7edab4 100644 --- a/contracts/contracts/ccip/offramp/types.tolk +++ b/contracts/contracts/ccip/offramp/types.tolk @@ -5,7 +5,8 @@ import "../../lib/utils" import "../../lib/deployable/types" const OffRamp_FACILITY_NAME = "link.chain.ton.ccip.OffRamp"; -const OffRamp_FACILITY_ID = 221; // (crc32() % 640) + 10 +const OffRamp_FACILITY_ID = OffRamp_FACILITY_NAME.crc32() % 640 + 10; // 221 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions struct ExecutionReport { sourceChainSelector: uint64; @@ -22,7 +23,7 @@ struct CommitReport { } struct MessageMetadata { - _header: uint256 = stringSha256("Any2TVMMessageHashV1"); + _header: uint256 = "Any2TVMMessageHashV1".sha256(); sourceChainSelector: uint64; destChainSelector: uint64; onRamp: Cell; diff --git a/contracts/contracts/ccip/onramp/contract.tolk b/contracts/contracts/ccip/onramp/contract.tolk index 8f96aff7e..a1659ca50 100644 --- a/contracts/contracts/ccip/onramp/contract.tolk +++ b/contracts/contracts/ccip/onramp/contract.tolk @@ -1,6 +1,4 @@ // SPDX-License-Identifier: BUSL-1.1 -tolk 1.2 - import "../../lib/access/ownable_2step"; import "../../lib/utils"; import "../../lib/versioning/upgradeable" @@ -22,7 +20,22 @@ import "storage" import "errors" import "messages" -const CONTRACT_VERSION = "1.6.0"; +tolk 1.4.1 + +const CONTRACT_VERSION = "1.6.1".literalSlice(); + +contract OnRamp { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.1" + description: "link.chain.ton.ccip.OnRamp" + + storage: OnRamp_Storage + incomingMessages: OnRamp_InMessage +} + +fun requireSupportedVersion(version: slice) { + assert (version.bitsEqual("1.6.0".literalSlice())) throw Upgradeable_Error.VersionMismatch; +} fun onInternalMessage(in: InMessage) { val msg = lazy OnRamp_InMessage.fromSlice(in.body); @@ -312,7 +325,7 @@ fun onExecutorFinishedSuccessfully(st: OnRamp_Storage, msg: OnRamp_ExecutorFinis // Metadata hash preimage to ensure global uniqueness, ensuring 2 identical messages sent to 2 different lanes // will have a distinct hash. val metadataHash = beginCell() - .storeUint(stringSha256("TVM2AnyMessageHashV1"), 256) + .storeUint("TVM2AnyMessageHashV1".sha256(), 256) .storeUint(st.chainSelector, 64) .storeUint(ccipsend.destChainSelector, 64) .storeAddress(contract.getAddress()) @@ -406,7 +419,7 @@ fun onApplyDestChainConfigUpdates(mutate st: OnRamp_Storage, updates: SnakedCell router: update.router, sequenceNumber: 0, allowlistEnabled: update.allowlistEnabled, - allowedSenders: createEmptyMap(), + allowedSenders: [], }; st.destChainConfigs.set(update.destChainSelector, config); emit(DEST_CHAIN_SELECTOR_ADDED_TOPIC, DestChainSelectorAdded { @@ -512,7 +525,7 @@ get fun feeQuoter(destChainSelector: int): address { } // vec
-get fun allowedSendersList(destChainSelector: uint64): tuple? { +get fun allowedSendersList(destChainSelector: uint64): lisp_list
{ val st = lazy OnRamp_Storage.load(); val config = st.destChainConfigs.mustGet(destChainSelector,Error.UnknownDestChainSelector as int); var allowedSenders = config.allowedSenders; @@ -520,7 +533,7 @@ get fun allowedSendersList(destChainSelector: uint64): tuple? { return keysLispList(allowedSenders); } -get fun destChainSelectors(): tuple? { +get fun destChainSelectors(): lisp_list { val st = lazy OnRamp_Storage.load(); var d = st.destChainConfigs; return keysLispList(d)!; @@ -549,7 +562,7 @@ get fun sendExecutorCodeHash(): uint256 { } get fun typeAndVersion(): (slice, slice) { - return (OnRamp_FACILITY_NAME, CONTRACT_VERSION); + return (OnRamp_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -557,7 +570,7 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.OnRamp"), local); + return getErrorCode("link.chain.ton.ccip.OnRamp".crc32(), local); } get fun reserve(): coins { @@ -567,7 +580,10 @@ get fun reserve(): coins { } @method_id(1000) -fun migrate(storage: cell, version: slice): cell { throw Upgradeable_Error.VersionMismatch; } +fun migrate(storage: cell, version: slice): cell { + requireSupportedVersion(version); + return storage; +} @method_id(1001) fun version(): slice { return CONTRACT_VERSION; } diff --git a/contracts/contracts/ccip/onramp/events.tolk b/contracts/contracts/ccip/onramp/events.tolk index e8a367f22..3304acd52 100644 --- a/contracts/contracts/ccip/onramp/events.tolk +++ b/contracts/contracts/ccip/onramp/events.tolk @@ -1,24 +1,24 @@ // SPDX-License-Identifier: BUSL-1.1 import "types" -const CCIP_MESSAGE_SENT_TOPIC: int = stringCrc32("CCIPMessageSent"); +const CCIP_MESSAGE_SENT_TOPIC: int = "CCIPMessageSent".crc32(); struct CCIPMessageSent { message: TVM2AnyRampMessage; } -const DEST_CHAIN_SELECTOR_ADDED_TOPIC: int = stringCrc32("DestChainSelectorAdded"); +const DEST_CHAIN_SELECTOR_ADDED_TOPIC: int = "DestChainSelectorAdded".crc32(); struct DestChainSelectorAdded { destChainSelector: uint64; } -const DEST_CHAIN_CONFIG_UPDATED_TOPIC: int = stringCrc32("DestChainConfigUpdated"); +const DEST_CHAIN_CONFIG_UPDATED_TOPIC: int = "DestChainConfigUpdated".crc32(); struct DestChainConfigUpdated { destChainSelector: uint64; destChainConfig: OnRamp_DestChainConfig; } -const CONFIG_SET_TOPIC: int = stringCrc32("ConfigSet"); +const CONFIG_SET_TOPIC: int = "ConfigSet".crc32(); struct ConfigSet { chainSelector: uint64; dynamicConfig: OnRamp_DynamicConfig; diff --git a/contracts/contracts/ccip/onramp/types.tolk b/contracts/contracts/ccip/onramp/types.tolk index b11c9f012..8baac34d3 100644 --- a/contracts/contracts/ccip/onramp/types.tolk +++ b/contracts/contracts/ccip/onramp/types.tolk @@ -6,7 +6,8 @@ import "../../lib/deployable/types" import "../../lib/deployable/namespace" const OnRamp_FACILITY_NAME = "link.chain.ton.ccip.OnRamp"; -const OnRamp_FACILITY_ID = 134; // (crc32() % 640) + 10 +const OnRamp_FACILITY_ID = OnRamp_FACILITY_NAME.crc32() % 640 + 10; // 134 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions struct OnRamp_DestChainConfig { router: address; // Local router address that is allowed to send messages to the destination chain. diff --git a/contracts/contracts/ccip/receive_executor/contract.tolk b/contracts/contracts/ccip/receive_executor/contract.tolk index c1af32657..de2728e24 100644 --- a/contracts/contracts/ccip/receive_executor/contract.tolk +++ b/contracts/contracts/ccip/receive_executor/contract.tolk @@ -7,7 +7,18 @@ import "errors" import "../offramp/messages" import "../../lib/utils" -const CONTRACT_VERSION = "1.6.1"; +tolk 1.4.1 + +const CONTRACT_VERSION = "1.6.2".literalSlice(); + +contract ReceiveExecutor { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.2" + description: "link.chain.ton.ccip.ReceiveExecutor" + + storage: ReceiveExecutor_Storage + incomingMessages: ReceiveExecutor_InMessage +} fun onInternalMessage(in: InMessage) { val msg = lazy ReceiveExecutor_InMessage.fromSlice(in.body); @@ -109,7 +120,7 @@ fun onCCIPReceiveBounced(mutate st: ReceiveExecutor_Storage, msg: ReceiveExecuto } get fun typeAndVersion(): (slice, slice) { - return (ReceiveExecutor_FACILITY_NAME, CONTRACT_VERSION); + return (ReceiveExecutor_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -117,5 +128,5 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.ReceiveExecutor"), local); + return getErrorCode("link.chain.ton.ccip.ReceiveExecutor".crc32(), local); } diff --git a/contracts/contracts/ccip/receive_executor/types.tolk b/contracts/contracts/ccip/receive_executor/types.tolk index 7df64b4fd..f54a6135c 100644 --- a/contracts/contracts/ccip/receive_executor/types.tolk +++ b/contracts/contracts/ccip/receive_executor/types.tolk @@ -1,7 +1,8 @@ // SPDX-License-Identifier: BUSL-1.1 const ReceiveExecutor_FACILITY_NAME = "link.chain.ton.ccip.ReceiveExecutor"; -const ReceiveExecutor_FACILITY_ID = 376; // (crc32() % 640) + 10 +const ReceiveExecutor_FACILITY_ID = ReceiveExecutor_FACILITY_NAME.crc32() % 640 + 10; // 376 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions // State stores the general state machine indicating which phase we're in enum ReceiveExecutor_MessageState { diff --git a/contracts/contracts/ccip/router/contract.tolk b/contracts/contracts/ccip/router/contract.tolk index abd40bd99..f588ce550 100644 --- a/contracts/contracts/ccip/router/contract.tolk +++ b/contracts/contracts/ccip/router/contract.tolk @@ -8,6 +8,7 @@ import "../../lib/utils" import "../../lib/versioning/upgradeable" import "../../lib/receiver/types" import "../../lib/receiver/messages" +import "../rmn_remote/lib.tolk" import "../onramp/messages" import "../onramp/types" @@ -20,9 +21,24 @@ import "storage" import "errors" import "events" -const CONTRACT_VERSION = "1.6.0"; +tolk 1.4.1 + +const CONTRACT_VERSION = "1.6.1".literalSlice(); const RESERVE = ton("1"); +contract Router { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.1" + description: "link.chain.ton.ccip.Router" + + storage: Storage + incomingMessages: Router_InMsg +} + +fun requireSupportedVersion(version: slice) { + assert (version.bitsEqual("1.6.0".literalSlice())) throw Upgradeable_Error.VersionMismatch; +} + fun onInternalMessage(in: InMessage) { val msg = lazy Router_InMsg.fromSlice(in.body); match (msg) { @@ -620,7 +636,10 @@ fun assertSenderIsOnRamp(st: Storage, destChainSelector: uint64, sender: address } @method_id(1000) -fun migrate(storage: cell, version: slice): cell { throw Upgradeable_Error.VersionMismatch; } +fun migrate(storage: cell, version: slice): cell { + requireSupportedVersion(version); + return storage; +} @method_id(1001) fun version(): slice { return CONTRACT_VERSION; } @@ -631,7 +650,7 @@ get fun verifyNotCursed(subject: uint128): bool { return !rmn.cursedSubjects.isCursed(subject); } -get fun cursedSubjects(): tuple? { +get fun cursedSubjects(): lisp_list { val st = lazy Storage.load(); var rmn = st.rmnRemote.load(); return keysLispList(rmn.cursedSubjects.data)!; @@ -662,7 +681,7 @@ get fun rmn_pendingOwner(): address? { } get fun typeAndVersion(): (slice, slice) { - return (Router_FACILITY_NAME, CONTRACT_VERSION); + return (Router_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -670,7 +689,7 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.Router"), local); + return getErrorCode("link.chain.ton.ccip.Router".crc32(), local); } get fun onRamp(destChainSelector: uint64): address { @@ -688,38 +707,39 @@ struct Ramp { ramp: address } -get fun onRamps() { +/// TODO returns lisp_list +get fun onRamps(): lisp_list> { val st = lazy Storage.load(); - var list: tuple? = null; + var onRamps: lisp_list> = []; var r = st.onRamps.findFirst(); while (r.isFound) { val ramp = Ramp { chainSelector: r.getKey(), ramp: r.loadValue(), }; - list = listPrepend(ramp.toCell(), list); + onRamps.prependHead(ramp.toCell()); r = st.onRamps.iterateNext(r); } - return list; + return onRamps; } -//returns lispList -get fun offRamps() { +/// TODO returns lisp_list +get fun offRamps(): lisp_list> { val st = lazy Storage.load(); - var list: tuple? = null; + var offRamps: lisp_list> = []; var r = st.offRamps.findFirst(); while (r.isFound) { val ramp = Ramp { chainSelector: r.getKey(), ramp: r.loadValue(), }; - list = listPrepend(ramp.toCell(), list); + offRamps.prependHead(ramp.toCell()); r = st.offRamps.iterateNext(r); } - return list; + return offRamps; } -get fun destChainSelectors(): tuple { +get fun destChainSelectors(): lisp_list { val st = lazy Storage.load(); var d = st.onRamps; return keysLispList(d)!; diff --git a/contracts/contracts/ccip/router/events.tolk b/contracts/contracts/ccip/router/events.tolk index 0f02693e3..8ec2f5b02 100644 --- a/contracts/contracts/ccip/router/events.tolk +++ b/contracts/contracts/ccip/router/events.tolk @@ -1,35 +1,35 @@ // SPDX-License-Identifier: BUSL-1.1 import "../../lib/utils" -const ON_RAMP_SET_TOPIC: int = stringCrc32("OnRampSet"); +const ON_RAMP_SET_TOPIC: int = "OnRampSet".crc32(); struct OnRampSet { destChainSelectors: SnakedCell; onRamp: address?; } -const OFF_RAMP_ADDED_TOPIC: int = stringCrc32("OffRampAdded"); +const OFF_RAMP_ADDED_TOPIC: int = "OffRampAdded".crc32(); struct OffRampAdded { sourceChainSelectors: SnakedCell; offRampAdded: address; } -const OFF_RAMP_REMOVED_TOPIC: int = stringCrc32("OffRampRemoved"); +const OFF_RAMP_REMOVED_TOPIC: int = "OffRampRemoved".crc32(); struct OffRampRemoved { sourceChainSelectors: SnakedCell; offRampRemoved: address; } -const CURSED_TOPIC: int = stringCrc32("Cursed"); +const CURSED_TOPIC: int = "Cursed".crc32(); struct Cursed { subject: uint128; } -const UNCURSED_TOPIC: int = stringCrc32("Uncursed"); +const UNCURSED_TOPIC: int = "Uncursed".crc32(); struct Uncursed { subject: uint128; } -const MESSAGE_TO_OFF_RAMP_BOUNCED_TOPIC = stringCrc32("MessageToOffRampBounced"); +const MESSAGE_TO_OFF_RAMP_BOUNCED_TOPIC = "MessageToOffRampBounced".crc32(); struct MessageToOffRampBounced { offRamp: address, execId: uint192, diff --git a/contracts/contracts/ccip/router/types.tolk b/contracts/contracts/ccip/router/types.tolk index 78640105e..c632611ea 100644 --- a/contracts/contracts/ccip/router/types.tolk +++ b/contracts/contracts/ccip/router/types.tolk @@ -2,7 +2,8 @@ import "../../lib/utils" const Router_FACILITY_NAME = "link.chain.ton.ccip.Router"; -const Router_FACILITY_ID = 571; // (crc32() % 640) + 10 +const Router_FACILITY_ID = Router_FACILITY_NAME.crc32() % 640 + 10; // 571 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions struct OnRamps { destChainSelectors: SnakedCell; diff --git a/contracts/contracts/ccip/test/receiver/contract.tolk b/contracts/contracts/ccip/test/receiver/contract.tolk index 683586a85..3aec0682a 100644 --- a/contracts/contracts/ccip/test/receiver/contract.tolk +++ b/contracts/contracts/ccip/test/receiver/contract.tolk @@ -17,7 +17,18 @@ import "../../../lib/versioning/upgradeable" import "../../router/messages" -const CONTRACT_VERSION = "1.6.0"; +tolk 1.4.1 + +const CONTRACT_VERSION = "1.6.1".literalSlice(); + +contract TestReceiver { + author: "SmartContract Chainlink Limited SEZC" + version: "1.6.1" + description: "link.chain.ton.ccip.test.Receiver" + + storage: Storage + incomingMessages: TestReceiver_InMessage +} const RECEIVED_MESSAGE_TOPIC = 0xc5a40ab3; //crc32('Receiver_CCIPMessageReceived') @@ -126,7 +137,7 @@ fun onUpgrade(msg: Upgradeable_Upgrade) { @method_id(1000) fun migrate(storage: cell, version: slice): cell { - assert(version.bitsEqual(CONTRACT_VERSION), Upgradeable_Error.VersionMismatch); + assert(version.bitsEqual("1.6.0".literalSlice()), Upgradeable_Error.VersionMismatch); return storage; } @@ -149,7 +160,7 @@ get fun getBehavior(): int { } get fun typeAndVersion(): (slice, slice) { - return (TestReceiver_FACILITY_NAME, CONTRACT_VERSION); + return (TestReceiver_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { @@ -157,5 +168,5 @@ get fun facilityId(): uint16 { } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.ccip.test.Receiver"), local); + return getErrorCode("link.chain.ton.ccip.test.Receiver".crc32(), local); } diff --git a/contracts/contracts/ccip/test/receiver/types.tolk b/contracts/contracts/ccip/test/receiver/types.tolk index 63af37247..797319e0b 100644 --- a/contracts/contracts/ccip/test/receiver/types.tolk +++ b/contracts/contracts/ccip/test/receiver/types.tolk @@ -1,5 +1,7 @@ // SPDX-License-Identifier: BUSL-1.1 const TestReceiver_FACILITY_NAME = "link.chain.ton.ccip.test.Receiver"; -const TestReceiver_FACILITY_ID = 191; // (crc32() % 640) + 10 +const TestReceiver_FACILITY_ID = TestReceiver_FACILITY_NAME.crc32() % 640 + 10; // 191 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + const TestReceiver_ERROR_CODE = TestReceiver_FACILITY_ID * 100; diff --git a/contracts/contracts/examples/counter.tolk b/contracts/contracts/examples/counter.tolk index 3e28e478b..049650843 100644 --- a/contracts/contracts/examples/counter.tolk +++ b/contracts/contracts/examples/counter.tolk @@ -1,11 +1,11 @@ // SPDX-License-Identifier: MIT -tolk 1.2 +tolk 1.4.1 import "@stdlib/common.tolk" import "../lib/utils.tolk" import "../lib/access/ownable_2step.tolk" -const CONTRACT_VERSION = "1.1.2"; +const CONTRACT_VERSION = "1.1.3".literalSlice(); /// Counter contract + event emission (Tolk example) /// Message to set the counter value. @@ -71,7 +71,7 @@ fun onInternalMessage(in: InMessage) { val msg = lazy Msg.fromSlice(in.body); // 63 error code is thrown if the message opcode is unknown match (msg) { SetCount => { - /// Instructs the contract to set the counter. + // Instructs the contract to set the counter. var st = lazy Storage.load(); st.ownable.requireOwner(in.senderAddress); st.value = msg.newCount; @@ -94,7 +94,7 @@ fun onInternalMessage(in: InMessage) { reply.send(SEND_MODE_CARRY_ALL_REMAINING_MESSAGE_VALUE); } IncreaseCount => { - /// Instructs the contract to increase the counter. + // Instructs the contract to increase the counter. var st = lazy Storage.load(); st.ownable.requireOwner(in.senderAddress); st.value = st.value + 1; @@ -157,5 +157,5 @@ get fun value(): int { /// Gets the current type and version of the contract. get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.examples.Counter", CONTRACT_VERSION) + return ("link.chain.ton.examples.Counter".literalSlice(), CONTRACT_VERSION) } diff --git a/contracts/contracts/firedrill/firedrill_entrypoint.tolk b/contracts/contracts/firedrill/firedrill_entrypoint.tolk index faace60c7..06af9a7de 100644 --- a/contracts/contracts/firedrill/firedrill_entrypoint.tolk +++ b/contracts/contracts/firedrill/firedrill_entrypoint.tolk @@ -1,4 +1,15 @@ -tolk 1.2 +tolk 1.4.1 + +contract FiredrillEntrypoint { + author: "SmartContract Chainlink Limited SEZC" + + version: "1.6.0" + + description: "link.chain.ton.ccip.firedrill.firedrillEntrypoint.Router.FeeQuoter" + + storage: FiredrillEntrypoint_Storage + incomingMessages: FiredrillEntrypoint_InMessage +} import "../lib/utils.tolk" import "../lib/access/ownable_2step.tolk" @@ -265,7 +276,7 @@ get fun destChainConfig(destChainSelector: uint64): DestChainConfig { dataAvailabilityGasPrice: 1000000000, timestamp: blockchain.now() }.toCell(), - tokenTransferFeeConfigs: createEmptyMap(), + tokenTransferFeeConfigs: [], }; return destChainConfig; } @@ -309,5 +320,5 @@ get fun pendingOwner(): address? { } get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.ccip.firedrill.firedrillEntrypoint.Router.FeeQuoter", "1.6.0") + return ("link.chain.ton.ccip.firedrill.firedrillEntrypoint.Router.FeeQuoter".literalSlice(), "1.6.0".literalSlice()) } diff --git a/contracts/contracts/firedrill/firedrill_offramp.tolk b/contracts/contracts/firedrill/firedrill_offramp.tolk index 4aa5448f9..64be2a37b 100644 --- a/contracts/contracts/firedrill/firedrill_offramp.tolk +++ b/contracts/contracts/firedrill/firedrill_offramp.tolk @@ -1,4 +1,15 @@ -tolk 1.2 +tolk 1.4.1 + +contract FiredrillOffRamp { + author: "SmartContract Chainlink Limited SEZC" + + version: "1.6.0" + + description: "link.chain.ton.ccip.firedrill.firedrillOffRamp" + + storage: FiredrillOffRamp_Storage + incomingMessages: FiredrillOffRamp_InMessage +} import "../lib/utils.tolk" import "../ccip/offramp/events.tolk" @@ -119,17 +130,17 @@ get fun sourceChainConfig(sourceChainSelector: uint64): SourceChainConfig { }; } -get fun sourceChainSelectors(): tuple? { +get fun sourceChainSelectors(): array { val st = lazy FiredrillOffRamp_Storage.load(); - var res = createEmptyTuple(); + var res: array = []; res.push(st.chainSelector); - return res ; + return res; } -get fun cursedSubjects(): tuple? { - return null; +get fun cursedSubjects(): lisp_list { + return []; } get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.ccip.firedrill.firedrillOffRamp", "1.6.0") + return ("link.chain.ton.ccip.firedrill.firedrillOffRamp".literalSlice(), "1.6.0".literalSlice()); } diff --git a/contracts/contracts/firedrill/firedrill_onramp.tolk b/contracts/contracts/firedrill/firedrill_onramp.tolk index ec7778f31..3c51dcbae 100644 --- a/contracts/contracts/firedrill/firedrill_onramp.tolk +++ b/contracts/contracts/firedrill/firedrill_onramp.tolk @@ -1,4 +1,15 @@ -tolk 1.2 +tolk 1.4.1 + +contract FiredrillOnRamp { + author: "SmartContract Chainlink Limited SEZC" + + version: "1.6.0" + + description: "link.chain.ton.ccip.firedrill.firedrillOnRamp" + + storage: FiredrillOnRamp_Storage + incomingMessages: FiredrillOnRamp_InMessage +} import "../lib/utils.tolk" import "../ccip/onramp/events.tolk" @@ -99,10 +110,10 @@ get fun destChainConfig(destChainSelector: uint64): OnRamp_DestChainConfig { router: st.controlAddress, sequenceNumber: 0, allowlistEnabled: false, - allowedSenders: createEmptyMap() + allowedSenders: [] }; } get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.ccip.firedrill.firedrillOnRamp", "1.6.0") + return ("link.chain.ton.ccip.firedrill.firedrillOnRamp".literalSlice(), "1.6.0".literalSlice()); } diff --git a/contracts/contracts/lib/access/access_control.tolk b/contracts/contracts/lib/access/access_control.tolk index 5b2a8a2bc..29869de69 100644 --- a/contracts/contracts/lib/access/access_control.tolk +++ b/contracts/contracts/lib/access/access_control.tolk @@ -1,8 +1,14 @@ // SPDX-License-Identifier: MIT -tolk 1.2 +tolk 1.4.1 import "../utils.tolk"; +const AccessControl_FACILITY_NAME = "link.chain.ton.lib.access.AccessControl"; +const AccessControl_FACILITY_ID = AccessControl_FACILITY_NAME.crc32() % 640 + 10; // 474 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + +const AccessControl_ERROR_CODE = AccessControl_FACILITY_ID * 100; + /** * @dev Contract module that allows children to implement role-based access * control mechanisms. This version is a port of OpenZeppelin {access/AccessControl.sol} @@ -215,18 +221,18 @@ struct AccessControl_Hooks { const DEFAULT_ADMIN_ROLE = 0x00; -/// Error codes used by the Timelock contract. +/// Error codes used by the AccessControl contract. enum AccessControl_Error { - UnauthorizedAccount = 47400 // AccessControl.errorCode(0) + UnauthorizedAccount = AccessControl_ERROR_CODE // 47400 BadConfirmation } // --- Methods --- /// Returns the error code for this facility and the given local code. -/// errorCode(0) == 60900 +/// errorCode(0) == 47400 fun AccessControl.errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.lib.access.AccessControl"), local); + return getErrorCode(AccessControl_FACILITY_NAME.crc32(), local); } /// @dev Returns the sender of the message. @@ -395,7 +401,7 @@ fun AccessControl.getRoleMembers(self, role: uint256): map { // Check if the role is valid val data = self.data.roles.get(role); if (!data.isFound) { - return createEmptyMap(); // role does not exist + return []; // role does not exist } val d = lazy AccessControl_RoleData.fromCell(data.loadValue()); @@ -588,7 +594,7 @@ fun AccessControl_Data.getRoleDataOrSetDefault(mutate self, role: uint256): Acce var _data: AccessControl_RoleData = { adminRole: DEFAULT_ADMIN_ROLE, // Initialize hasRole as an empty map - hasRole: createEmptyMap(), + hasRole: [], membersLen: 0, }; self.roles.set(role, _data.toCell()); diff --git a/contracts/contracts/lib/access/ownable_2step.tolk b/contracts/contracts/lib/access/ownable_2step.tolk index 6db266e90..4fa07e79b 100644 --- a/contracts/contracts/lib/access/ownable_2step.tolk +++ b/contracts/contracts/lib/access/ownable_2step.tolk @@ -1,7 +1,10 @@ // SPDX-License-Identifier: MIT import "./../utils.tolk"; -const Ownable2Step_FACILITY_ID = 498; // (crc32() % 640) + 10 +const Ownable2Step_FACILITY_NAME = "link.chain.ton.lib.access.Ownable2Step"; +const Ownable2Step_FACILITY_ID = Ownable2Step_FACILITY_NAME.crc32() % 640 + 10; // 498 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + const Ownable2Step_ERROR_CODE = Ownable2Step_FACILITY_ID * 100; // Exit codes diff --git a/contracts/contracts/lib/crypto/merkle_multi_proof.tolk b/contracts/contracts/lib/crypto/merkle_multi_proof.tolk index af3d8fe4e..f85252534 100644 --- a/contracts/contracts/lib/crypto/merkle_multi_proof.tolk +++ b/contracts/contracts/lib/crypto/merkle_multi_proof.tolk @@ -1,8 +1,11 @@ // SPDX-License-Identifier: MIT import "../utils.tolk" -const MerkleMultiProof_FACILITY_ID= 120; // (crc32() % 640) + 10 -const MerkleMultiProof_ERROR_CODE= MerkleMultiProof_FACILITY_ID * 100; +const MerkleMultiProof_FACILITY_NAME = "link.chain.ton.lib.crypto.MerkleMultiProof"; +const MerkleMultiProof_FACILITY_ID = MerkleMultiProof_FACILITY_NAME.crc32() % 640 + 10; // 120 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + +const MerkleMultiProof_ERROR_CODE = MerkleMultiProof_FACILITY_ID * 100; // --- Errror Codes --- @@ -18,13 +21,13 @@ enum MerkleMultiProof_Error { const INTERNAL_DOMAIN_SEPARATOR: int = 0x0000000000000000000000000000000000000000000000000000000000000001; /// @notice Maximum number of hashes that can be computed in a single Merkle root calculation. -/// Capped to 255 because a TVM tuple can only hold at most 255 elements. +/// Capped to 255 because a TVM array can only hold at most 255 elements. const MAX_NUM_HASHES: int = 255; /// @notice Computes the Merkle root based on provided pre-hashed leaf nodes in `leaves`, internal nodes in `proofs`, /// and using `proofFlagBits` to determine whether to use a proof element or a previously computed node during each step. fun merkleRoot( - leaves: I, // Iterator or TupleIterator + leaves: I, // Iterator or ArrayIterator proofs: Iterator, proofFlagBits: uint256, ): uint256 { @@ -42,9 +45,9 @@ fun merkleRoot( return leaves.next(); } - var hashes = createEmptyTuple(); + var hashes: array = []; - // index over the hashes tuple + // index over the hashes array var hashPos: int = 0; var i: int = 0; while (i < totalHashes) { diff --git a/contracts/contracts/lib/crypto/merkle_proof.tolk b/contracts/contracts/lib/crypto/merkle_proof.tolk index 2fd890098..e153d1ee0 100644 --- a/contracts/contracts/lib/crypto/merkle_proof.tolk +++ b/contracts/contracts/lib/crypto/merkle_proof.tolk @@ -1,5 +1,5 @@ // SPDX-License-Identifier: MIT -tolk 1.2 +tolk 1.4.1 import "../utils.tolk" diff --git a/contracts/contracts/lib/deployable/types.tolk b/contracts/contracts/lib/deployable/types.tolk index 27b7bab8b..b6275c616 100644 --- a/contracts/contracts/lib/deployable/types.tolk +++ b/contracts/contracts/lib/deployable/types.tolk @@ -2,7 +2,8 @@ import "../utils" const Deployable_FACILITY_NAME = "link.chain.ton.lib.Deployable"; -const Deployable_FACILITY_ID = 92; // (crc32() % 640) + 10 +const Deployable_FACILITY_ID = Deployable_FACILITY_NAME.crc32() % 640 + 10; // 92 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions struct Deployable { owner: address; diff --git a/contracts/contracts/lib/funding/withdrawable.tolk b/contracts/contracts/lib/funding/withdrawable.tolk index 0a097eef0..ba9cdb037 100644 --- a/contracts/contracts/lib/funding/withdrawable.tolk +++ b/contracts/contracts/lib/funding/withdrawable.tolk @@ -1,5 +1,11 @@ // SPDX-License-Identifier: MIT -tolk 1.2 +tolk 1.4.1 + +const Withdrawable_FACILITY_NAME = "link.chain.ton.lib.funding.Withdrawable"; +const Withdrawable_FACILITY_ID = Withdrawable_FACILITY_NAME.crc32() % 640 + 10; // 571 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + +const Withdrawable_ERROR_CODE = Withdrawable_FACILITY_ID * 100; struct Withdrawable { reserve: coins; @@ -7,7 +13,7 @@ struct Withdrawable { enum Withdrawable_Error { // Trying to withdraw more TON than available in balance. - InsufficientBalance = 57100; // Facility ID * 100 + InsufficientBalance = Withdrawable_ERROR_CODE; // 57100, // Trying to withdraw more TON than available in balance above reserve. HitReserve; // Invalid withdrawal request: Amount is non-zero and drain is true or Amount is zero and drain is false. diff --git a/contracts/contracts/lib/ocr/errors.tolk b/contracts/contracts/lib/ocr/errors.tolk index 29d8c1d14..98f905475 100644 --- a/contracts/contracts/lib/ocr/errors.tolk +++ b/contracts/contracts/lib/ocr/errors.tolk @@ -1,5 +1,8 @@ // SPDX-License-Identifier: BUSL-1.1 -const MultiOCR3Base_FACILITY_ID = 545; // (crc32() % 640) + 10 +const MultiOCR3Base_FACILITY_NAME = "link.chain.ton.lib.ocr.MultiOCR3Base"; +const MultiOCR3Base_FACILITY_ID = MultiOCR3Base_FACILITY_NAME.crc32() % 640 + 10; // 545 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + const MultiOCR3Base_ERROR_CODE = MultiOCR3Base_FACILITY_ID * 100 enum MultiOCR3Base_Error { diff --git a/contracts/contracts/lib/ocr/multi_ocr3_base.tolk b/contracts/contracts/lib/ocr/multi_ocr3_base.tolk index ff55012dc..de01dbe1b 100644 --- a/contracts/contracts/lib/ocr/multi_ocr3_base.tolk +++ b/contracts/contracts/lib/ocr/multi_ocr3_base.tolk @@ -4,8 +4,8 @@ import "types.tolk"; import "errors"; -const OCR3BASE_CONFIG_SET_TOPIC: int = stringCrc32("OCR3Base_ConfigSet"); -const OCR3BASE_TRANSMITTED: int = stringCrc32("OCR3Base_Transmitted"); +const OCR3BASE_CONFIG_SET_TOPIC: int = "OCR3Base_ConfigSet".crc32(); +const OCR3BASE_TRANSMITTED: int = "OCR3Base_Transmitted".crc32(); /// @notice Event, triggers a new run of the offchain reporting protocol. /// @param ocrPluginType OCR plugin type for which the config was set. diff --git a/contracts/contracts/lib/ocr/types.tolk b/contracts/contracts/lib/ocr/types.tolk index fd1037be4..9170a47c3 100644 --- a/contracts/contracts/lib/ocr/types.tolk +++ b/contracts/contracts/lib/ocr/types.tolk @@ -18,8 +18,8 @@ struct OCRConfig { fun newOCRConfig(): OCRConfig { return OCRConfig { configInfo: ConfigInfo{}, - signers: createEmptyMap(), - transmitters: createEmptyMap() + signers: [], + transmitters: [] } } diff --git a/contracts/contracts/lib/receiver/errors.tolk b/contracts/contracts/lib/receiver/errors.tolk index f576d72d5..b84ac5cd1 100644 --- a/contracts/contracts/lib/receiver/errors.tolk +++ b/contracts/contracts/lib/receiver/errors.tolk @@ -1,9 +1,11 @@ // SPDX-License-Identifier: MIT const RECEIVER_FACILITY_NAME = "link.chain.ton.ccip.lib.Receiver"; -const RECEIVER_FACILITY_ID = 54; // (crc32() % 640) + 10 +const RECEIVER_FACILITY_ID = RECEIVER_FACILITY_NAME.crc32() % 640 + 10; // 54 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + const RECEIVER_ERROR_CODE = RECEIVER_FACILITY_ID * 100; enum Receiver_Error { - Unauthorized = 5400 //FACILITY_ID * 100, + Unauthorized = RECEIVER_ERROR_CODE, // 5400, LowValue, } diff --git a/contracts/contracts/lib/utils.tolk b/contracts/contracts/lib/utils.tolk index eacedc733..db6789b5a 100644 --- a/contracts/contracts/lib/utils.tolk +++ b/contracts/contracts/lib/utils.tolk @@ -3,14 +3,15 @@ import "@stdlib/lisp-lists" import "@stdlib/gas-payments"; const Utils_FACILITY_NAME = "link.chain.ton.lib.Utils"; -const Utils_FACILITY_ID = 135; // (crc32() % 640) + 10 +const Utils_FACILITY_ID = Utils_FACILITY_NAME.crc32() % 640 + 10; // 135 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions enum Utils_Error { InvalidData = Utils_FACILITY_ID * 100 BitmapOutOfBounds } -/// Returns the facility ID for the given CRC32 key (e.g. stringCrc32("link.chain.ton.mcms.Timelock")). +/// Returns the facility ID for the given CRC32 key (e.g. "link.chain.ton.mcms.Timelock".crc32()). /// Returns a value in range 10..649 (640 values). fun getFacilityId(crc32Key: int): uint16 { return (crc32Key % 640) + 10; @@ -167,31 +168,31 @@ fun Iterator.size(self, elemSize: int): int { // https://github.com/ton-org/ton-core/blob/213fed91d6f63d978c27588509e15ab53c8bafdb/src/dict/Dictionary.ts#L425 const ADDR_KEY_LEN = 267; -struct TupleIterator { +struct ArrayIterator { pos: int = 0; len: int; // TLEN is 26 gas, we cache the value for minimal savings - data: tuple; + data: array; } @inline -fun TupleIterator.new(data: tuple) { - return TupleIterator { data, len: data.size() }; +fun ArrayIterator.new(data: array) { + return ArrayIterator { data, len: data.size() }; } @inline -fun TupleIterator.empty(self): bool { +fun ArrayIterator.empty(self): bool { return self.pos >= self.len } @inline -fun TupleIterator.next(mutate self): T { +fun ArrayIterator.next(mutate self): T { var offset = self.pos; self.pos += 1; - return self.data.get(offset); + return self.data.get(offset); } @inline -fun TupleIterator.size(self, elemSize: int): int { +fun ArrayIterator.size(self, elemSize: int): int { // elemSize is ignored since we know exact size, // param is there for interface compatibility return self.len; @@ -228,15 +229,15 @@ fun countAddresses(data: cell): int { } // Returns a lisp-list with the keys of the map -fun keysLispList(dict: map): tuple? { - var list: tuple? = null; +fun keysLispList(dict: map): lisp_list { + var lisplist: lisp_list = []; var entry = dict.findFirst(); while (entry.isFound) { var key = entry.getKey(); - list = listPrepend(key, list); + lisplist.prependHead(key); entry = dict.iterateNext(entry); } ; - return list; + return lisplist; } // This type works as a wrapper for RemainingBitsAndRefs that implements @@ -245,25 +246,27 @@ fun keysLispList(dict: map): tuple? { // space. type RemainingBitsOrRef = T; -fun RemainingBitsOrRef.packToBuilder(self, mutate b: builder): void { - val serialized = (self as T).toCell(); - val nBits = serialized.remainingBitsCount(); - if (b.remainingSpace() < nBits + 1) { - // not enough space, create a new cell - b.storeBit(1); - b.storeRef(serialized); - } else { - b.storeBit(0); - b.storeSlice(serialized.beginParse()); - } -} - -fun RemainingBitsOrRef.unpackFromSlice(mutate s: slice): RemainingBitsOrRef { - val isRef = s.loadBit(); - if (isRef) { - val c = s.loadRef(); - return T.fromCell(c) as RemainingBitsOrRef; - } else { - return T.fromSlice(s) as RemainingBitsOrRef; - } -} +// TODO investigate why this was being ignored in 1.2 + +// fun RemainingBitsOrRef.packToBuilder(self, mutate b: builder): void { +// val serialized = (self as T).toCell(); +// val (nBits, _) = serialized.beginParse().remainingBitsAndRefsCount(); +// if (b.remainingSpace() < nBits + 1) { +// // not enough space, create a new cell +// b.storeBool(true); +// b.storeRef(serialized); +// } else { +// b.storeBool(false); +// b.storeSlice(serialized.beginParse()); +// } +// } + +// fun RemainingBitsOrRef.unpackFromSlice(mutate s: slice): RemainingBitsOrRef { +// val isRef = s.loadBool(); +// if (isRef) { +// val c = s.loadRef(); +// return T.fromCell(c) as RemainingBitsOrRef; +// } else { +// return T.fromSlice(s) as RemainingBitsOrRef; +// } +// } diff --git a/contracts/contracts/lib/versioning/upgradeable.tolk b/contracts/contracts/lib/versioning/upgradeable.tolk index 64ce58ddf..11f8d9acd 100644 --- a/contracts/contracts/lib/versioning/upgradeable.tolk +++ b/contracts/contracts/lib/versioning/upgradeable.tolk @@ -2,6 +2,12 @@ import "@stdlib/tvm-lowlevel"; import "../utils.tolk"; +const Upgradeable_FACILITY_NAME = "link.chain.ton.lib.versioning.Upgradeable"; +const Upgradeable_FACILITY_ID = Upgradeable_FACILITY_NAME.crc32() % 640 + 10; // 199 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + +const Upgradeable_ERROR_CODE = Upgradeable_FACILITY_ID * 100; + /// Upgradeable contract interface. /// This interface defines the structure and methods required for a contract to /// be upgradeable. @@ -100,7 +106,7 @@ struct Upgradeable { } enum Upgradeable_Error { - VersionMismatch = 19900; // Facility ID * 100 + VersionMismatch = Upgradeable_ERROR_CODE, // 19900 } /// Message for upgrading a contract. diff --git a/contracts/contracts/mcms/mcms.tolk b/contracts/contracts/mcms/mcms.tolk index 787cd17aa..3b8019cd1 100644 --- a/contracts/contracts/mcms/mcms.tolk +++ b/contracts/contracts/mcms/mcms.tolk @@ -1,12 +1,26 @@ // SPDX-License-Identifier: BUSL-1.1 -tolk 1.2 +tolk 1.4.1 import "../lib/utils"; import "../lib/secp256k1"; import "../lib/access/ownable_2step.tolk"; import "../lib/crypto/merkle_proof.tolk"; -const CONTRACT_VERSION = "0.0.4"; +const MCMS_FACILITY_NAME = "link.chain.ton.mcms.MCMS"; +const MCMS_FACILITY_ID = MCMS_FACILITY_NAME.crc32() % 640 + 10; // 104 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + +const MCMS_ERROR_CODE = MCMS_FACILITY_ID * 100; +const CONTRACT_VERSION = "0.0.5".literalSlice(); + +contract MCMS { + author: "SmartContract Chainlink Limited SEZC" + version: "0.0.5" + description: "link.chain.ton.mcms.MCMS" + + storage: MCMS_Data + incomingMessages: MCMS_InMessage +} /// This is a multi-sig contract that supports signing many transactions (called "ops" in /// the context of this contract to prevent confusion with transactions on the underlying chain) @@ -389,18 +403,18 @@ struct MCMS_Hooks { /// op. This value is for domain separation of the different values stored in the /// Merkle tree. const MANY_CHAIN_MULTI_SIG_DOMAIN_SEPARATOR_OP = - stringSha256("MANY_CHAIN_MULTI_SIG_DOMAIN_SEPARATOR_OP_TON"); + "MANY_CHAIN_MULTI_SIG_DOMAIN_SEPARATOR_OP_TON".sha256(); /// Should be used as the first 32 bytes of the pre-image of the leaf that holds the /// root metadata. This value is for domain separation of the different values stored in the /// Merkle tree. const MANY_CHAIN_MULTI_SIG_DOMAIN_SEPARATOR_METADATA = - stringSha256("MANY_CHAIN_MULTI_SIG_DOMAIN_SEPARATOR_METADATA_TON"); + "MANY_CHAIN_MULTI_SIG_DOMAIN_SEPARATOR_METADATA_TON".sha256(); const NUM_GROUPS = 32; const MAX_NUM_SIGNERS = 200; -const TOPIC_BOUNCE_HANDLED = stringCrc32("MCMS_BounceHandled"); +const TOPIC_BOUNCE_HANDLED = "MCMS_BounceHandled".crc32(); // --- Constants - storage --- @@ -410,7 +424,7 @@ const MIN_TON_TO_RESERVE: int = ton("0.05"); /// Error codes used by the Timelock contract. enum MCMS_Error { /// Thrown when number of signers is 0 or greater than MAX_NUM_SIGNERS. - OutOfBoundsNumSigners = 10400 // MCMS.errorCode(0) + OutOfBoundsNumSigners = MCMS_ERROR_CODE // 10400 /// Thrown when signerAddresses and signerGroups have different lengths. SignerGroupsLengthMismatch @@ -679,7 +693,7 @@ struct RootDescriptor { /// Returns the error code for this facility and the given local code. /// errorCode(0) == 10400 fun MCMS.errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.mcms.MCMS"), local); + return getErrorCode(MCMS_FACILITY_NAME.crc32(), local); } /// @dev Loads the MCMS contract data from persistent storage. @@ -765,7 +779,7 @@ fun MCMS.setRoot( var signer: Signer; var prevSigner: uint256 = 0; // start with zero address var ss = signatures.iter(); - var groupVoteCounts: map = createEmptyMap(); // number of votes per group, map (indexed) + var groupVoteCounts: map = []; // number of votes per group, map (indexed) while (!ss.empty()) { var s = ss.next(); val signerAddress = evm_ecrecoverFrom(signedHash, s.toCell().beginParse()); @@ -1098,7 +1112,7 @@ fun MCMS.setConfig( { // Validate group structure // counts the number of children of each group - var groupChildrenCounts: map = createEmptyMap(); + var groupChildrenCounts: map = []; // first, we count the signers as children while (!signerGroupIterator.empty()) { var g = signerGroupIterator.next(); @@ -1189,7 +1203,7 @@ fun MCMS.setConfig( self.data.signers.delete(s.address); oldSigner = config.signers.findFirst(); } - config.signers = createEmptyMap(); // reset signers + config.signers = []; // reset signers config.groupQuorums = groupQuorums; config.groupParents = groupParents; @@ -1423,7 +1437,7 @@ fun MCMS.cleanExpiredRoots( val rd = rootsIter.next(); assert(rd.validUntil < blockchain.now()) throw MCMS_Error.RootNotExpired; - /// Construct the ID (hash) of the root + // Construct the ID (hash) of the root val signedHash = self._hashRoot(rd.root, rd.validUntil); self.data.seenSignedHashes.delete(signedHash); } @@ -1463,7 +1477,7 @@ fun MCMS._hashRoot(self, root: uint256, validUntil: uint64): uint256 { // EIP191 Signed Message Hash wrapping // Format: "\x19Ethereum Signed Message:\n32" + messageHash - val eip191Prefix = stringHexToSlice("19457468657265756d205369676e6564204d6573736167653a0a3332"); + val eip191Prefix = "19457468657265756d205369676e6564204d6573736167653a0a3332". hexToSlice(); val eip191Data = beginCell() .storeSlice(eip191Prefix) .storeUint(_hash, 256); @@ -1696,7 +1710,7 @@ fun MCMS_Costs.submitErrorReport(): int { // --- Getters --- get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.mcms.MCMS", CONTRACT_VERSION); + return (MCMS_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } /// @see .getId> diff --git a/contracts/contracts/mcms/rbac_timelock.tolk b/contracts/contracts/mcms/rbac_timelock.tolk index f84bf3723..bffc58eb6 100644 --- a/contracts/contracts/mcms/rbac_timelock.tolk +++ b/contracts/contracts/mcms/rbac_timelock.tolk @@ -1,10 +1,24 @@ // SPDX-License-Identifier: BUSL-1.1 -tolk 1.2 +tolk 1.4.1 import "../lib/utils"; import "../lib/access/access_control"; -const CONTRACT_VERSION = "0.0.3"; +const Timelock_FACILITY_NAME = "link.chain.ton.mcms.Timelock"; +const Timelock_FACILITY_ID = Timelock_FACILITY_NAME.crc32() % 640 + 10; // 606 +// NOTE: inlined getFacilityId because compiler doesn't allow custom compile time functions + +const Timelock_ERROR_CODE = Timelock_FACILITY_ID * 100; +const CONTRACT_VERSION = "0.0.4".literalSlice(); + +contract Timelock { + author: "SmartContract Chainlink Limited SEZC" + version: "0.0.4" + description: "link.chain.ton.mcms.Timelock" + + storage: Timelock_Data + incomingMessages: Timelock_InMessage +} /** * Contract module which acts as a timelocked controller with role-based @@ -551,10 +565,10 @@ struct Timelock_Hooks { // --- Constants --- -const TOPIC_BYPASSER_CALL_EXECUTED = stringCrc32("Timelock_BypasserCallExecuted"); -const TOPIC_CALL_SCHEDULED = stringCrc32("Timelock_CallScheduled"); -const TOPIC_CALL_EXECUTED = stringCrc32("Timelock_CallExecuted"); -const TOPIC_BOUNCE_HANDLED = stringCrc32("Timelock_BounceHandled"); +const TOPIC_BYPASSER_CALL_EXECUTED = "Timelock_BypasserCallExecuted".crc32(); +const TOPIC_CALL_SCHEDULED = "Timelock_CallScheduled".crc32(); +const TOPIC_CALL_EXECUTED = "Timelock_CallExecuted".crc32(); +const TOPIC_BOUNCE_HANDLED = "Timelock_BounceHandled".crc32(); /// Notice: role constants are kept as original Ethereum implementation (keccak256) const ADMIN_ROLE = 0xa49807205ce4d355092ef5a8a18f56e8913cf4a201fbe287825b095693c21775; // keccak256('ADMIN_ROLE') @@ -575,7 +589,7 @@ const DEFAULT_FINALIZATION_TIMEOUT = 10; // in seconds /// Error codes used by the Timelock contract. enum Timelock_Error { /// Thrown when trying to schedule an operation which contains a blocked function selector. - SelectorIsBlocked = 60600 // Timelock.errorCode(0) + SelectorIsBlocked = Timelock_ERROR_CODE, // 60600 /// Thrown when trying to execute an operation which is not ready yet. OperationNotReady @@ -621,7 +635,7 @@ const MIN_TON_TO_RESERVE: int = ton("0.05"); /// Returns the error code for this facility and the given local code. /// errorCode(0) == 60600 fun Timelock.errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.mcms.Timelock"), local); + return getErrorCode(Timelock_FACILITY_NAME.crc32(), local); } /// Loads the Timelock contract data from persistent storage. @@ -774,7 +788,7 @@ fun Timelock.init( validAfter: blockchain.now(), opFinalizationTimeout, opPendingId: 0, - opPendingCalls: createEmptyMap() + opPendingCalls: [] }; // Reply back to sender @@ -979,7 +993,7 @@ fun Timelock.getCallFingerprint(self, target: address, truncatedBody: uint256 /// Resets the pending operation tracking info. fun Timelock.resetPendingOpTracking(mutate self): void { - self.data.opPendingInfo.opPendingCalls = createEmptyMap(); + self.data.opPendingInfo.opPendingCalls = []; self.data.opPendingInfo.opPendingId = 0; } @@ -1542,7 +1556,7 @@ fun Timelock_Costs.submitErrorReport(): int { // --- Getters --- get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.mcms.Timelock", CONTRACT_VERSION); + return (Timelock_FACILITY_NAME.literalSlice(), CONTRACT_VERSION); } /// @see .getId> diff --git a/contracts/contracts/test/examples/funding/withdrawable_wallet.tolk b/contracts/contracts/test/examples/funding/withdrawable_wallet.tolk index 771ef9d5d..2c912ea8c 100644 --- a/contracts/contracts/test/examples/funding/withdrawable_wallet.tolk +++ b/contracts/contracts/test/examples/funding/withdrawable_wallet.tolk @@ -4,7 +4,7 @@ import "../../../lib/access/ownable_2step"; import "../../../lib/funding/withdrawable"; const WithdrawableWallet_FACILITY_NAME = "link.chain.ton.examples.funding.WithdrawableWallet"; -const CONTRACT_VERSION = "1.0.1"; +const CONTRACT_VERSION = "1.0.1".literalSlice(); struct Storage { id: uint32; @@ -60,15 +60,15 @@ get fun pendingOwner(): address? { } get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.examples.funding.WithdrawableWallet", CONTRACT_VERSION); + return ("link.chain.ton.examples.funding.WithdrawableWallet".literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { - return getFacilityId(stringCrc32("link.chain.ton.examples.funding.WithdrawableWallet")); + return getFacilityId("link.chain.ton.examples.funding.WithdrawableWallet".crc32()); } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.examples.funding.WithdrawableWallet"), local); + return getErrorCode("link.chain.ton.examples.funding.WithdrawableWallet".crc32(), local); } get fun reserve(): coins { diff --git a/contracts/contracts/test/examples/ocr3_base.tolk b/contracts/contracts/test/examples/ocr3_base.tolk index a432fcbbf..ba90bdbbd 100644 --- a/contracts/contracts/test/examples/ocr3_base.tolk +++ b/contracts/contracts/test/examples/ocr3_base.tolk @@ -63,7 +63,7 @@ get fun ocr3ConfigInfo(ocrPluginType: uint16): ConfigInfo { return config!.configInfo; } -get fun ocr3Signers(ocrPluginType: uint16): tuple? { +get fun ocr3Signers(ocrPluginType: uint16): lisp_list { val s = lazy OCR3BaseExampleContract.load(); val config = s.ocr3Base.getConfig(ocrPluginType); assert(config != null, MultiOCR3Base_Error.NonExistentOcrPluginType); @@ -72,7 +72,7 @@ get fun ocr3Signers(ocrPluginType: uint16): tuple? { return keysLispList(d); } -get fun ocr3Transmitters(ocrPluginType: uint16): tuple? { +get fun ocr3Transmitters(ocrPluginType: uint16): lisp_list
{ val s = lazy OCR3BaseExampleContract.load(); val config = s.ocr3Base.getConfig(ocrPluginType); assert(config != null, MultiOCR3Base_Error.NonExistentOcrPluginType); diff --git a/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v1/contract.tolk b/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v1/contract.tolk index 82da7dc3f..b06e63245 100644 --- a/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v1/contract.tolk +++ b/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v1/contract.tolk @@ -15,7 +15,7 @@ fun saveData(data: StorageV1) { } const FACILITY_NAME= "link.chain.ton.examples.versioning.upgrades.UpgradeableCounter"; -const CONTRACT_VERSION = "1.0.0"; +const CONTRACT_VERSION = "1.0.0".literalSlice(); struct (0x00000001) Step { queryId: uint64; @@ -43,7 +43,7 @@ fun onInternalMessage(in: InMessage) { Upgradeable{ migrate, version }.upgrade(msg); } Step => { - /// Instructs the contract to step the counter. + // Instructs the contract to step the counter. storage.value += 1; saveData(storage); } @@ -74,13 +74,13 @@ fun migrate(storage: cell, version: slice): cell { throw Upgradeable_Error.Versi fun version(): slice { return CONTRACT_VERSION; } get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter", CONTRACT_VERSION); + return ("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter".literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { - return getFacilityId(stringCrc32("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter")); + return getFacilityId("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter".crc32()); } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter"), local); + return getErrorCode("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter".crc32(), local); } diff --git a/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v2/contract.tolk b/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v2/contract.tolk index 71d47a311..aaf08a492 100644 --- a/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v2/contract.tolk +++ b/contracts/contracts/test/examples/versioning/upgrades/upgradeable_counter/v2/contract.tolk @@ -16,7 +16,7 @@ fun saveData(data: StorageV2) { } const FACILITY_NAME= "link.chain.ton.examples.versioning.upgrades.UpgradeableCounter"; -const CONTRACT_VERSION = "2.0.0"; +const CONTRACT_VERSION = "2.0.0".literalSlice(); struct (0x00000001) Step { queryId: uint64; @@ -44,7 +44,7 @@ fun onInternalMessage(in: InMessage) { Upgradeable{ migrate, version }.upgrade(msg); } Step => { - /// Instructs the contract to step the counter. + // Instructs the contract to step the counter. storage.value -= 1; saveData(storage); } @@ -69,7 +69,7 @@ get fun pendingOwner(): address? { return storage.ownable2Step.get_pendingOwner(); } -const COUNTER_V1_CONTRACT_VERSION = "1.0.0"; +const COUNTER_V1_CONTRACT_VERSION = "1.0.0".literalSlice(); @method_id(1000) fun migrate(storage: cell, version: slice): cell { @@ -90,13 +90,13 @@ fun version(): slice { return CONTRACT_VERSION; } get fun typeAndVersion(): (slice, slice) { - return ("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter", CONTRACT_VERSION); + return ("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter".literalSlice(), CONTRACT_VERSION); } get fun facilityId(): uint16 { - return getFacilityId(stringCrc32("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter")); + return getFacilityId("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter".crc32()); } get fun errorCode(local: uint16): uint16 { - return getErrorCode(stringCrc32("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter"), local); + return getErrorCode("link.chain.ton.examples.versioning.upgrades.UpgradeableCounter".crc32(), local); } diff --git a/contracts/contracts/test/examples/versioning/upgrades/wrong_version.tolk b/contracts/contracts/test/examples/versioning/upgrades/wrong_version.tolk index 6bca847dd..a7cdd7e87 100644 --- a/contracts/contracts/test/examples/versioning/upgrades/wrong_version.tolk +++ b/contracts/contracts/test/examples/versioning/upgrades/wrong_version.tolk @@ -5,7 +5,7 @@ import "../../../../lib/versioning/upgradeable.tolk"; -const CONTRACT_VERSION = "invalid_version"; +const CONTRACT_VERSION = "invalid_version".literalSlice(); struct Storage { id: uint32; diff --git a/contracts/contracts/test/mock/relay.tolk b/contracts/contracts/test/mock/relay.tolk index c6c5cbd40..6928be795 100644 --- a/contracts/contracts/test/mock/relay.tolk +++ b/contracts/contracts/test/mock/relay.tolk @@ -1,5 +1,5 @@ // SPDX-License-Identifier: MIT -tolk 1.2 +tolk 1.4.1 struct (0x527146b1) Relay_Send { bounce: bool, diff --git a/contracts/default.nix b/contracts/default.nix index 634840bcc..5210e1afe 100644 --- a/contracts/default.nix +++ b/contracts/default.nix @@ -114,6 +114,32 @@ cp -r * $out/ ''; + meta = with pkgs.lib; { + description = "Chainlink TON smart contracts"; + + # TODO: update to MIT after March 12, 2029 as per LICENSE file + license = licenses.bsl11; + + # TODO: update to contracts project-specific tag + changelog = "https://github.com/smartcontractkit/chainlink-ton/releases/tag/v${finalAttrs.version}"; + }; + }); + contracts_1_6_2 = pkgs.stdenv.mkDerivation (finalAttrs: rec { + pname = "chainlink-contracts-ton"; + + src = builtins.fetchurl { + url = "https://github.com/smartcontractkit/chainlink-ton/releases/download/contracts/${finalAttrs.version}/contracts-${finalAttrs.version}.tar.gz"; + sha256 = "sha256:1gbvagivlzf0jwrshhq903ijrfxwqssbd255asjfi81924cyvayl"; + }; + version = "1.6.2"; + sourceRoot = "."; # pin source root to avoid issues with unpacker (produced multiple directories) + + skipBuild = true; + installPhase = '' + mkdir -p $out + cp -r * $out/ + ''; + meta = with pkgs.lib; { description = "Chainlink TON smart contracts"; @@ -132,6 +158,7 @@ in { inherit pkgs; contracts_1_6 = packages.contracts_1_6; contracts_1_6_1 = packages.contracts_1_6_1; + contracts_1_6_2 = packages.contracts_1_6_2; jetton-contracts = packages.contracts-jetton-func; inherit oplint; }; diff --git a/contracts/lock.nix b/contracts/lock.nix index 37a1e73fd..48a33541c 100644 --- a/contracts/lock.nix +++ b/contracts/lock.nix @@ -1,6 +1,6 @@ # Notice: `pkgs.lib.fakeHash` can be used as a placeholder, # but `lock-nix-tidy` will only replace actual hashes. {pkgs}: { - contracts = "sha256-c7Qty4uMeJASTle0yEgvTCle3KpMaZrYYyB9SO10kXo="; + contracts = "sha256-3F9NejeWPeLm6idkWDe8eKHssOSocZxvq33DywwMi/U="; contracts-jetton = "sha256-EZtvTf19MjSKTWNir6pcP9XHwUIpE4ILSlhS+cQD/7w="; } diff --git a/contracts/package.json b/contracts/package.json index b376ef821..739356756 100644 --- a/contracts/package.json +++ b/contracts/package.json @@ -29,6 +29,9 @@ "ccip-gas-report": "blueprint test --gas-report -- --config ccip-gas-report.config.ts", "get-key-pair": "ts-node scripts/getKeyPair.ts" }, + "resolutions": { + "axios": "v1.16.1" + }, "dependencies": { "@ethersproject/keccak256": "^5.8.0", "ethers": "^6.15.0" @@ -36,14 +39,14 @@ "devDependencies": { "@changesets/cli": "~2.29.6", "@tact-lang/compiler": "1.6.13", - "@ton-community/func-js": "^0.10.0", - "@ton/blueprint": "^0.44.0", - "@ton/core": "^0.62.0", - "@ton/crypto": "^3.3.0", - "@ton/sandbox": "^0.41.0", - "@ton/test-utils": "^0.12.0", - "@ton/tolk-js": "1.2.0", - "@ton/ton": "^16.0.0", + "@ton-community/func-js": "0.10.0", + "@ton/blueprint": "0.44.2", + "@ton/core": "0.63.1", + "@ton/crypto": "3.3.0", + "@ton/sandbox": "0.42.0", + "@ton/test-utils": "0.12.0", + "@ton/tolk-js": "1.4.1", + "@ton/ton": "16.2.4", "@types/jest": "^30.0.0", "@types/node": "^24.3.0", "crc-32": "^1.2.2", diff --git a/contracts/shell.nix b/contracts/shell.nix index e420116ab..0a3d9c880 100644 --- a/contracts/shell.nix +++ b/contracts/shell.nix @@ -4,6 +4,7 @@ lib, contracts_1_6, contracts_1_6_1, + contracts_1_6_2, jetton-contracts, oplint, }: @@ -29,11 +30,13 @@ pkgs.mkShell { PATH_CONTRACTS_JETTON = "${jetton-contracts}/lib/node_modules/jetton/build/"; PATH_CONTRACTS_1_6 = "${contracts_1_6}"; # Notice: loaded from GH release, artifacts in root of the package PATH_CONTRACTS_1_6_1 = "${contracts_1_6_1}"; # Notice: loaded from GH release, artifacts in root of the package + PATH_CONTRACTS_1_6_2 = "${contracts_1_6_2}"; # Notice: loaded from GH release, artifacts in root of the package shellHook = '' echo "Loaded TVM contracts at following paths:" echo " - CCIP 1.6.0: (env:PATH_CONTRACTS_1_6) $PATH_CONTRACTS_1_6" echo " - CCIP 1.6.1: (env:PATH_CONTRACTS_1_6_1) $PATH_CONTRACTS_1_6_1" + echo " - CCIP 1.6.2: (env:PATH_CONTRACTS_1_6_2) $PATH_CONTRACTS_1_6_2" echo " - Jetton: (env:PATH_CONTRACTS_JETTON) $PATH_CONTRACTS_JETTON" ''; } diff --git a/contracts/tests/Counter.spec.ts b/contracts/tests/Counter.spec.ts index c3ef9ad97..15f051152 100644 --- a/contracts/tests/Counter.spec.ts +++ b/contracts/tests/Counter.spec.ts @@ -45,7 +45,7 @@ describe('Counter', () => { it('should have type and version', async () => { const typeAndVersion = await bind.counter.getTypeAndVersion() expect(typeAndVersion.type).toBe('link.chain.ton.examples.Counter') - expect(typeAndVersion.version).toBe('1.1.2') + expect(typeAndVersion.version).toBe(counter.CONTRACT_VERSION) }) it('should have the right code and hash', async () => { diff --git a/contracts/tests/ccip/OffRamp.spec.ts b/contracts/tests/ccip/OffRamp.spec.ts index 0195010ca..3c634a973 100644 --- a/contracts/tests/ccip/OffRamp.spec.ts +++ b/contracts/tests/ccip/OffRamp.spec.ts @@ -173,18 +173,13 @@ describe('OffRamp - Withdrawable Tests', () => { describe('OffRamp - Upgrade Tests', () => { class OffRamp extends of.OffRamp {} - const codeLoaders = { - '1.6.0': () => contractCode.ccip.release_1_6_0('OffRamp'), - '1.6.1': () => contractCode.ccip.release_1_6_1('OffRamp'), - } as Record Promise> - const upgradeSpec = UpgradeableSpec.newUpgradeSpec({ contractType: of.OffRamp.type(), - prevVersionConfigs: of.OFFRAMP_SUPPORTED_PREV_VERSIONS.map((version) => ({ + prevVersionConfigs: Object.entries(of.SUPPORTED_PREV_VERSIONS).map(([version, getCode]) => ({ version, - getCode: codeLoaders[version], + getCode, deploy: async (blockchain: Blockchain, owner: SandboxContract) => - deployOffRampContract(blockchain, owner, await codeLoaders[version]()), + deployOffRampContract(blockchain, owner, await getCode()), })), currentVersion: OffRamp.version(), getCurrentCode: () => OffRamp.code(), diff --git a/contracts/tests/ccip/Receiver.spec.ts b/contracts/tests/ccip/Receiver.spec.ts index 643cfd908..da55d4db9 100644 --- a/contracts/tests/ccip/Receiver.spec.ts +++ b/contracts/tests/ccip/Receiver.spec.ts @@ -1,5 +1,5 @@ import { Blockchain, SandboxContract, TreasuryContract } from '@ton/sandbox' -import { Address, beginCell, toNano } from '@ton/core' +import { Address, beginCell, Cell, toNano } from '@ton/core' import { compile } from '@ton/blueprint' import '@ton/test-utils' @@ -18,8 +18,9 @@ import * as UpgradeableSpec from '../lib/versioning/UpgradeableSpec' async function deployReceiverContract( blockchain: Blockchain, owner: SandboxContract, + codeOverride?: Cell, ) { - const code = await tr.Receiver.code() + const code = codeOverride ?? (await tr.Receiver.code()) let data: tr.Storage = { id: generateRandomContractId(), ownable: { @@ -72,6 +73,25 @@ describe('Receiver - Current Version Tests', () => { currentVersionSpec.run() }) +describe('Receiver - Upgrade Tests', () => { + class Receiver extends tr.Receiver {} + + const upgradeSpec = UpgradeableSpec.newUpgradeSpec({ + contractType: tr.Receiver.type(), + prevVersionConfigs: Object.entries(tr.SUPPORTED_PREV_VERSIONS).map(([version, getCode]) => ({ + version, + getCode, + deploy: async (blockchain: Blockchain, owner: SandboxContract) => + deployReceiverContract(blockchain, owner, await getCode()), + })), + currentVersion: Receiver.version(), + getCurrentCode: () => Receiver.code(), + CurrentVersionConstructor: Receiver, + upgradeValue: toNano('0.05'), + }) + upgradeSpec.run() +}) + describe('Receiver', () => { let blockchain: Blockchain let deployer: SandboxContract diff --git a/contracts/tests/ccip/feequoter/FeeQuoter.spec.ts b/contracts/tests/ccip/feequoter/FeeQuoter.spec.ts index d6e65bddb..54d190660 100644 --- a/contracts/tests/ccip/feequoter/FeeQuoter.spec.ts +++ b/contracts/tests/ccip/feequoter/FeeQuoter.spec.ts @@ -51,18 +51,12 @@ describe('FeeQuoter - TypeAndVersion Tests', () => { describe('FeeQuoter - Upgrade Tests', () => { class FeeQuoter extends fq.FeeQuoter {} - const codeLoaders = { - '1.6.0': () => contractCode.ccip.release_1_6_0('FeeQuoter'), - '1.6.1': () => contractCode.ccip.release_1_6_1('FeeQuoter'), - } as Record Promise> - const upgradeSpec = UpgradeableSpec.newUpgradeSpec({ contractType: fq.FeeQuoter.type(), - prevVersionConfigs: FEE_QUOTER_SUPPORTED_PREV_VERSIONS.map((version) => ({ + prevVersionConfigs: Object.entries(fq.SUPPORTED_PREV_VERSIONS).map(([version, getCode]) => ({ version, - getCode: codeLoaders[version], - deploy: async (blockchain, owner) => - setupTestFeeQuoter(owner, blockchain, await codeLoaders[version]()), + getCode, + deploy: async (blockchain, owner) => setupTestFeeQuoter(owner, blockchain, await getCode()), })), currentVersion: FeeQuoter.version(), getCurrentCode: () => FeeQuoter.code(), diff --git a/contracts/tests/ccip/onramp/OnRamp.Setup.ts b/contracts/tests/ccip/onramp/OnRamp.Setup.ts index 3d9442539..f1e2574ee 100644 --- a/contracts/tests/ccip/onramp/OnRamp.Setup.ts +++ b/contracts/tests/ccip/onramp/OnRamp.Setup.ts @@ -1,4 +1,4 @@ -import { Address, Dictionary, beginCell, toNano } from '@ton/core' +import { Address, Cell, Dictionary, beginCell, toNano } from '@ton/core' import { Blockchain, SandboxContract, TreasuryContract } from '@ton/sandbox' import { generateRandomContractId } from '../../../src/utils' @@ -15,12 +15,25 @@ export const CHAINSEL_EVM_TEST = 909606746561742123n export const CHAINSEL_EVM_TEST_90000002 = 5548718428018410741n export const CHAINSEL_TON = 13879075125137744094n // TODO repeated constant +// Deprecated, use deployOnRampContractW instead for more flexibility in tests. Will be removed in a future version. +// TODO: refactor existing tests to use deployOnRampContractW and remove this function. export async function deployOnRampContract( blockchain: Blockchain, owner: SandboxContract, overrides: OnRampOverrides = {}, ) { - const code = await or.OnRamp.code() + return deployOnRampContractW(blockchain, owner, { overrides }) +} + +export async function deployOnRampContractW( + blockchain: Blockchain, + owner: SandboxContract, + opt: { + code?: Cell + overrides?: OnRampOverrides + } = {}, +) { + const code = opt.code ?? (await or.OnRamp.code()) const defaults: or.OnRampStorage = { id: generateRandomContractId(), ownable: { @@ -43,20 +56,20 @@ export async function deployOnRampContract( const config = { ...defaults.config, - ...(overrides.config ?? {}), + ...(opt.overrides?.config ?? {}), } const data: or.OnRampStorage = { ...defaults, - ...overrides, + ...(opt.overrides ?? {}), ownable: { ...defaults.ownable, - ...(overrides.ownable ?? {}), + ...(opt.overrides?.ownable ?? {}), }, config, executor: { ...defaults.executor, - ...(overrides.executor ?? {}), + ...(opt.overrides?.executor ?? {}), }, } const onramp = blockchain.openContract(or.OnRamp.createFromConfig(data, code)) diff --git a/contracts/tests/ccip/onramp/OnRamp.spec.ts b/contracts/tests/ccip/onramp/OnRamp.spec.ts index 9234398fa..139ef7eaf 100644 --- a/contracts/tests/ccip/onramp/OnRamp.spec.ts +++ b/contracts/tests/ccip/onramp/OnRamp.spec.ts @@ -10,7 +10,7 @@ import * as TypeAndVersionSpec from '../../lib/versioning/TypeAndVersionSpec' import * as Ownable2StepSpec from '../../../tests/lib/access/Ownable2StepSpec' import * as ownable2step from '../../../wrappers/libraries/access/Ownable2Step' import * as or from '../../../wrappers/ccip/OnRamp' -import { deployOnRampContract, CHAINSEL_TON, setup } from './OnRamp.Setup' +import { deployOnRampContract, CHAINSEL_TON, setup, deployOnRampContractW } from './OnRamp.Setup' describe('OnRamp - TypeAndVersion Tests', () => { const currentVersionSpec = TypeAndVersionSpec.newInstance({ @@ -27,33 +27,31 @@ describe('OnRamp - TypeAndVersion Tests', () => { ]) }) -// TODO when we have a new version -// describe('OnRamp - Upgrade Tests', () => { -// const upgradeSpec = UpgradeableSpec.newUpgradeSpec( -// { -// contractType: OnRampPrev.type(), -// prevVersion: OnRampPrev.version(), -// currentVersion: OnRamp.version(), -// getPrevCode: () => OnRampPrev.code(), -// getCurrentCode: () => OnRamp.code(), -// CurrentVersionConstructor: OnRamp, -// }, -// async (blockchain, owner) => { -// const codeV1 = await OnRampPrev.code() -// const data = {} as any // TODO fill with valid data -// const contract = blockchain.openContract( -// OnRampPrev.createFromConfig( -// data, -// codeV1, -// ), -// ) -// const deployer = await blockchain.treasury('deployer') -// await contract.sendDeploy(deployer.getSender(), toNano('0.05')) -// return contract -// }, -// ) -// upgradeSpec.run() -// }) +describe('OnRamp - Upgrade Tests', () => { + const upgradeSpec = UpgradeableSpec.newUpgradeSpec({ + contractType: or.OnRamp.type(), + prevVersionConfigs: Object.entries(or.SUPPORTED_PREV_VERSIONS).map(([version, getCode]) => ({ + version, + getCode, + deploy: async (blockchain: Blockchain, owner: SandboxContract) => { + const dep = await deployOnRampContractW(blockchain, owner, { + code: await getCode(), + }) + return dep.onramp + }, + })), + currentVersion: or.OnRamp.version(), + getCurrentCode: () => or.OnRamp.code(), + CurrentVersionConstructor: or.OnRamp, + upgradeValue: toNano('0.05'), + }) + upgradeSpec.run([ + { + code: 'OnRamp', + name: 'onramp', + }, + ]) +}) describe('OnRamp - Ownable Tests', () => { it('supports ownable messages', async () => { diff --git a/contracts/tests/ccip/receiveExecutor/ReceiveExecutor.spec.ts b/contracts/tests/ccip/receiveExecutor/ReceiveExecutor.spec.ts index 5de71c127..c81c17552 100644 --- a/contracts/tests/ccip/receiveExecutor/ReceiveExecutor.spec.ts +++ b/contracts/tests/ccip/receiveExecutor/ReceiveExecutor.spec.ts @@ -91,7 +91,7 @@ describe('ReceiveExecutor', () => { describe.each([ { version: rx.RECEIVE_EXECUTOR_CONTRACT_VERSION_PREV, - loadCode: contractCode.ccip.release_1_6_0, + loadCode: contractCode.ccip.release_1_6_1, }, { version: rx.RECEIVE_EXECUTOR_CONTRACT_VERSION, loadCode: contractCode.ccip.local }, ])('Unit Tests with ReceiveExecutor %s', ({ version, loadCode }) => { diff --git a/contracts/tests/ccip/router/Router.Setup.ts b/contracts/tests/ccip/router/Router.Setup.ts index a1cad6e3d..81a386033 100644 --- a/contracts/tests/ccip/router/Router.Setup.ts +++ b/contracts/tests/ccip/router/Router.Setup.ts @@ -436,8 +436,9 @@ async function configureRouterWithOnRamp( export async function deployRouterContract( blockchain: Blockchain, owner: SandboxContract, + codeOverride?: Cell, ) { - const code = await rt.Router.code() + const code = codeOverride ?? (await rt.Router.code()) let data: rt.Storage = { id: generateRandomContractId(), ownable: { diff --git a/contracts/tests/ccip/router/Router.spec.ts b/contracts/tests/ccip/router/Router.spec.ts index 373ede9bc..8673cce2e 100644 --- a/contracts/tests/ccip/router/Router.spec.ts +++ b/contracts/tests/ccip/router/Router.spec.ts @@ -13,6 +13,7 @@ import { ownable2StepSpec } from '../../lib/access/Ownable2StepSpec' import * as ownable2step from '../../../wrappers/libraries/access/Ownable2Step' import * as rt from '../../../wrappers/ccip/Router' import { contractsCoverageConfig, deployRouterContract, setup } from './Router.Setup' +import { toNano } from '@ton/core' describe('rt.Router - TypeAndVersion Tests', () => { const currentVersionSpec = TypeAndVersionSpec.newInstance({ @@ -44,33 +45,29 @@ describe('Router - Withdrawable Tests', () => { ]) }) -// TODO when we have a new version -// describe('Router - Upgrade Tests', () => { -// const upgradeSpec = UpgradeableSpec.newUpgradeSpec( -// { -// contractType: RouterPrev.type(), -// prevVersion: RouterPrev.version(), -// currentVersion: Router.version(), -// getPrevCode: () => RouterPrev.code(), -// getCurrentCode: () => Router.code(), -// CurrentVersionConstructor: Router, -// }, -// async (blockchain, owner) => { -// const codeV1 = await RouterPrev.code() -// const data = {} as any // TODO fill with valid data -// const contract = blockchain.openContract( -// RouterPrev.createFromConfig( -// data, -// codeV1, -// ), -// ) -// const deployer = await blockchain.treasury('deployer') -// await contract.sendDeploy(deployer.getSender(), toNano('0.05')) -// return contract -// }, -// ) -// upgradeSpec.run() -// }) +describe('Router - Upgrade Tests', () => { + class Router extends rt.Router {} + + const upgradeSpec = UpgradeableSpec.newUpgradeSpec({ + contractType: rt.Router.type(), + prevVersionConfigs: Object.entries(rt.SUPPORTED_PREV_VERSIONS).map(([version, getCode]) => ({ + version, + getCode, + deploy: async (blockchain: Blockchain, owner: SandboxContract) => + deployRouterContract(blockchain, owner, await getCode()), + })), + currentVersion: Router.version(), + getCurrentCode: () => Router.code(), + CurrentVersionConstructor: Router, + upgradeValue: toNano('0.05'), + }) + upgradeSpec.run([ + { + code: 'Router', + name: 'router', + }, + ]) +}) describe('Router - Current Version Tests', () => { const currentVersionSpec = UpgradeableSpec.newCurrentVersionSpec({ diff --git a/contracts/tests/lib/versioning/UpgradeableSpec.ts b/contracts/tests/lib/versioning/UpgradeableSpec.ts index e16d0c3de..32d374275 100644 --- a/contracts/tests/lib/versioning/UpgradeableSpec.ts +++ b/contracts/tests/lib/versioning/UpgradeableSpec.ts @@ -76,9 +76,7 @@ export type CurrentVersionTestConfig = { * Contract interface that must be implemented by upgradeable contracts for testing. */ export interface UpgradeableContract - extends upgradeable.Interface, - typeAndVersion.Interface, - Contract {} + extends upgradeable.Interface, typeAndVersion.Interface, Contract {} interface PrevVersionSetup { version: string diff --git a/contracts/tsconfig.base.json b/contracts/tsconfig.base.json index 4b93ca991..1c4508662 100644 --- a/contracts/tsconfig.base.json +++ b/contracts/tsconfig.base.json @@ -33,6 +33,7 @@ /* Experimental Options */ "experimentalDecorators": true /* Enables experimental support for ES7 decorators. */, "emitDecoratorMetadata": true /* Enables experimental support for emitting type metadata for decorators. */, - "resolveJsonModule": true /* Allows importing modules with a ‘.json’ extension */ + "resolveJsonModule": true /* Allows importing modules with a '.json' extension */, + "types": ["node", "jest"] } } diff --git a/contracts/wrappers/ccip/CCIPSendExecutor.ts b/contracts/wrappers/ccip/CCIPSendExecutor.ts index 88c062441..3d68675c1 100644 --- a/contracts/wrappers/ccip/CCIPSendExecutor.ts +++ b/contracts/wrappers/ccip/CCIPSendExecutor.ts @@ -19,7 +19,7 @@ import * as typeAndVersion from '../libraries/versioning/TypeAndVersion' import * as or from './OnRamp' import * as fq from './FeeQuoter' -export const CONTRACT_VERSION = '1.6.0' +export const CONTRACT_VERSION = '1.6.1' export const FACILITY_NAME = 'link.chain.ton.ccip.CCIPSendExecutor' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) diff --git a/contracts/wrappers/ccip/FeeQuoter.ts b/contracts/wrappers/ccip/FeeQuoter.ts index 6aabe3aeb..32fea722f 100644 --- a/contracts/wrappers/ccip/FeeQuoter.ts +++ b/contracts/wrappers/ccip/FeeQuoter.ts @@ -14,12 +14,13 @@ import { Slice, TupleItem, Tuple, + TupleItemSlice, } from '@ton/core' import { crc32 } from 'zlib' import { errorCode, facilityId, CellCodec, StackCodec } from '../utils' import { asSnakedCell } from '../../src/utils' -import { loadContractCode } from '../codeLoader' +import { contractCode, loadContractCode } from '../codeLoader' import { Maybe } from '@ton/core/dist/utils/maybe' @@ -29,8 +30,12 @@ import * as upgradeable from '../libraries/versioning/Upgradeable' import * as typeAndVersion from '../libraries/versioning/TypeAndVersion' import * as rt from './Router' -export const FEE_QUOTER_SUPPORTED_PREV_VERSIONS = ['1.6.0', '1.6.1'] as const -export const FEE_QUOTER_CONTRACT_VERSION = '1.6.2' +export const ARTIFACT_NAME = 'FeeQuoter' +export const FEE_QUOTER_SUPPORTED_PREV_VERSIONS = ['1.6.2'] as const +export const SUPPORTED_PREV_VERSIONS: Record Promise> = { + '1.6.2': () => contractCode.ccip.release_1_6_2(ARTIFACT_NAME), +} +export const FEE_QUOTER_CONTRACT_VERSION = '1.6.3' export const FACILITY_NAME = 'link.chain.ton.ccip.FeeQuoter' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) @@ -674,7 +679,7 @@ export class FeeQuoter } static code(): Promise { - return loadContractCode('FeeQuoter') + return loadContractCode(ARTIFACT_NAME) } async sendUpdateDestChainConfigs( @@ -921,12 +926,13 @@ export class FeeQuoter ): Promise<(TimestampedPrice | undefined)[]> { const tupleItems: TupleItem[] = [] for (const token of tokens) { - tupleItems.push({ + const item: TupleItemSlice = { type: 'slice', cell: beginCell().storeAddress(token).endCell(), - } as TupleItem) + } + tupleItems.push(item) } - const tuple = { type: 'tuple', items: tupleItems } as Tuple + const tuple: Tuple = { type: 'tuple', items: tupleItems } const result = await provider.get('tokenPrices', [tuple]) const resultTuple = result.stack.readTuple() const prices: (TimestampedPrice | undefined)[] = [] diff --git a/contracts/wrappers/ccip/MerkleRoot.ts b/contracts/wrappers/ccip/MerkleRoot.ts index 497617ea1..b6a6f52b8 100644 --- a/contracts/wrappers/ccip/MerkleRoot.ts +++ b/contracts/wrappers/ccip/MerkleRoot.ts @@ -17,7 +17,7 @@ import { loadContractCode } from '../codeLoader' import * as typeAndVersion from '../libraries/versioning/TypeAndVersion' -export const CONTRACT_VERSION = '1.6.0' +export const CONTRACT_VERSION = '1.6.1' export const FACILITY_NAME = 'link.chain.ton.ccip.MerkleRoot' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) diff --git a/contracts/wrappers/ccip/OffRamp.ts b/contracts/wrappers/ccip/OffRamp.ts index 8af709672..392797f3e 100644 --- a/contracts/wrappers/ccip/OffRamp.ts +++ b/contracts/wrappers/ccip/OffRamp.ts @@ -15,7 +15,7 @@ import { TupleItem, } from '@ton/core' import { Maybe } from '@ton/core/dist/utils/maybe' -import { loadContractCode } from '../codeLoader' +import { contractCode, loadContractCode } from '../codeLoader' import { crc32 } from 'zlib' import { errorCode, facilityId, CellCodec } from '../utils' @@ -41,8 +41,11 @@ export const opcodes = { }, } -export const OFFRAMP_SUPPORTED_PREV_VERSIONS = ['1.6.0', '1.6.1'] as const -export const OFFRAMP_CONTRACT_VERSION = '1.6.2' +export const ARTIFACT_NAME = 'OffRamp' +export const SUPPORTED_PREV_VERSIONS: Record Promise> = { + '1.6.2': () => contractCode.ccip.release_1_6_2(ARTIFACT_NAME), +} +export const OFFRAMP_CONTRACT_VERSION = '1.6.3' export const FACILITY_NAME = 'link.chain.ton.ccip.OffRamp' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) @@ -704,7 +707,7 @@ export class OffRamp } static code(): Promise { - return loadContractCode('OffRamp') + return loadContractCode(ARTIFACT_NAME) } async sendCommit( diff --git a/contracts/wrappers/ccip/OnRamp.ts b/contracts/wrappers/ccip/OnRamp.ts index 0495ce837..37b76064d 100644 --- a/contracts/wrappers/ccip/OnRamp.ts +++ b/contracts/wrappers/ccip/OnRamp.ts @@ -22,14 +22,18 @@ import { asSnakedCell, fromSnakeData } from '../../src/utils' import * as rt from './Router' import * as upgradeable from '../libraries/versioning/Upgradeable' import * as typeAndVersion from '../libraries/versioning/TypeAndVersion' -import { loadContractCode } from '../codeLoader' +import { contractCode, loadContractCode } from '../codeLoader' import * as fq from './FeeQuoter' +export const ARTIFACT_NAME = 'OnRamp' export const FACILITY_NAME = 'link.chain.ton.ccip.OnRamp' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) export const ERROR_CODE = errorCode(crc32(FACILITY_NAME)) -export const CONTRACT_VERSION = '1.6.0' +export const SUPPORTED_PREV_VERSIONS: Record Promise> = { + '1.6.0': () => contractCode.ccip.release_1_6_2(ARTIFACT_NAME), // Last bundle with version 1.6.0 +} +export const CONTRACT_VERSION = '1.6.1' export type OnRampStorage = { id: bigint @@ -791,7 +795,7 @@ export class OnRamp implements Contract, ownable2step.ContractClient { } static code(): Promise { - return loadContractCode('OnRamp') + return loadContractCode(ARTIFACT_NAME) } async sendSetDynamicConfig( diff --git a/contracts/wrappers/ccip/ReceiveExecutor.ts b/contracts/wrappers/ccip/ReceiveExecutor.ts index 3ed9b2a12..05133a708 100644 --- a/contracts/wrappers/ccip/ReceiveExecutor.ts +++ b/contracts/wrappers/ccip/ReceiveExecutor.ts @@ -19,8 +19,8 @@ import { OCR3Base } from '../libraries/ocr/MultiOCR3Base' import * as typeAndVersion from '../libraries/versioning/TypeAndVersion' import * as of from './OffRamp' -export const RECEIVE_EXECUTOR_CONTRACT_VERSION_PREV = '1.6.0' -export const RECEIVE_EXECUTOR_CONTRACT_VERSION = '1.6.1' +export const RECEIVE_EXECUTOR_CONTRACT_VERSION_PREV = '1.6.1' +export const RECEIVE_EXECUTOR_CONTRACT_VERSION = '1.6.2' export const FACILITY_NAME = 'link.chain.ton.ccip.ReceiveExecutor' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) diff --git a/contracts/wrappers/ccip/Router.ts b/contracts/wrappers/ccip/Router.ts index 836d4b88f..6bd3135ea 100644 --- a/contracts/wrappers/ccip/Router.ts +++ b/contracts/wrappers/ccip/Router.ts @@ -16,7 +16,7 @@ import { import { crc32 } from 'zlib' import { errorCode, facilityId, CellCodec } from '../utils' import { asSnakedCell, asSnakeDataUint, fromSnakeData } from '../../src/utils' -import { loadContractCode } from '../codeLoader' +import { contractCode, loadContractCode } from '../codeLoader' import * as ownable2step from '../libraries/access/Ownable2Step' import * as withdrawable from '../libraries/funding/Withdrawable' @@ -26,7 +26,12 @@ import * as or from '../ccip/OnRamp' import * as of from './OffRamp' import { Maybe } from '@ton/core/dist/utils/maybe' -export const ROUTER_CONTRACT_VERSION = '1.6.0' +export const ARTIFACT_NAME = 'Router' + +export const SUPPORTED_PREV_VERSIONS: Record Promise> = { + '1.6.0': () => contractCode.ccip.release_1_6_2(ARTIFACT_NAME), // Last bundle with version 1.6.0 +} +export const ROUTER_CONTRACT_VERSION = '1.6.1' export const FACILITY_NAME = 'link.chain.ton.ccip.Router' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) @@ -261,7 +266,7 @@ export class Router } static code(): Promise { - return loadContractCode('Router') + return loadContractCode(ARTIFACT_NAME) } async sendApplyRampUpdatesSetRamps( diff --git a/contracts/wrappers/codeLoader.ts b/contracts/wrappers/codeLoader.ts index 76819bab0..bc79d8878 100644 --- a/contracts/wrappers/codeLoader.ts +++ b/contracts/wrappers/codeLoader.ts @@ -98,6 +98,7 @@ export const contractCode = { local: createContractCodeLoader({ buildDirectory: BUILD_ROOT }), release_1_6_0: createContractCodeLoaderFromEnvDirectory('PATH_CONTRACTS_1_6'), release_1_6_1: createContractCodeLoaderFromEnvDirectory('PATH_CONTRACTS_1_6_1'), + release_1_6_2: createContractCodeLoaderFromEnvDirectory('PATH_CONTRACTS_1_6_2'), }, } diff --git a/contracts/wrappers/examples/Counter.ts b/contracts/wrappers/examples/Counter.ts index 50ac5b3d2..48993e55b 100644 --- a/contracts/wrappers/examples/Counter.ts +++ b/contracts/wrappers/examples/Counter.ts @@ -16,6 +16,8 @@ import { CellCodec } from '../utils' import * as ownable2step from '../libraries/access/Ownable2Step' import * as typeAndVersion from '../libraries/versioning/TypeAndVersion' +export const CONTRACT_VERSION = '1.1.3' + /// @dev Message to set the counter value. export type SetCount = { // Query ID of the change request. diff --git a/contracts/wrappers/examples/Receiver.ts b/contracts/wrappers/examples/Receiver.ts index c0e3a868a..04baa7922 100644 --- a/contracts/wrappers/examples/Receiver.ts +++ b/contracts/wrappers/examples/Receiver.ts @@ -13,7 +13,7 @@ import { import { crc32 } from 'zlib' import { errorCode, facilityId, CellCodec } from '../utils' -import { loadContractCode } from '../codeLoader' +import { contractCode, loadContractCode } from '../codeLoader' import * as ownable2step from '../libraries/access/Ownable2Step' import * as receiver from '../libraries/Receiver' @@ -23,7 +23,12 @@ import * as upgradeable from '../libraries/versioning/Upgradeable' export const FACILITY_NAME = 'link.chain.ton.ccip.test.Receiver' export const FACILITY_ID = facilityId(crc32(FACILITY_NAME)) export const ERROR_CODE = errorCode(crc32(FACILITY_NAME)) -export const CONTRACT_VERSION = '1.6.0' +export const CONTRACT_VERSION = '1.6.1' + +export const ARTIFACT_NAME = 'ccip.test.receiver' +export const SUPPORTED_PREV_VERSIONS: Record Promise> = { + '1.6.0': () => contractCode.ccip.release_1_6_2(ARTIFACT_NAME), // Last bundle with version 1.6.0 +} enum TestReceiverError { Rejected = 19100, // Facility ID * 100 @@ -161,7 +166,7 @@ export class Receiver implements Contract, receiver.Receiver, upgradeable.Interf } static code(): Promise { - return loadContractCode('ccip.test.receiver') + return loadContractCode(ARTIFACT_NAME) } async sendDeploy(provider: ContractProvider, via: Sender, value: bigint) { diff --git a/deployment/ccip/1_6_0/sequences/mcms_reader.go b/deployment/ccip/1_6_0/sequences/mcms_reader.go index 313017d2f..f1e501be3 100644 --- a/deployment/ccip/1_6_0/sequences/mcms_reader.go +++ b/deployment/ccip/1_6_0/sequences/mcms_reader.go @@ -2,7 +2,9 @@ package sequences import ( "fmt" + "strings" + "github.com/Masterminds/semver/v3" mcmston "github.com/smartcontractkit/mcms/sdk/ton" "github.com/smartcontractkit/mcms/types" @@ -11,10 +13,7 @@ import ( ccipdutils "github.com/smartcontractkit/chainlink-ccip/deployment/utils" ccipdcs "github.com/smartcontractkit/chainlink-ccip/deployment/utils/changesets" - ccipdds "github.com/smartcontractkit/chainlink-ccip/deployment/utils/datastore" ccipdmcms "github.com/smartcontractkit/chainlink-ccip/deployment/utils/mcms" - - "github.com/smartcontractkit/chainlink-ton/deployment/state" ) var _ ccipdcs.MCMSReader = &MCMSReaderAdapter{} @@ -49,10 +48,14 @@ func (r *MCMSReaderAdapter) GetChainMetadata(e cldf.Environment, cs uint64, inpu // GetTimelockRef returns the timelock contract address reference for a given MCMS input. func (r *MCMSReaderAdapter) GetTimelockRef(e cldf.Environment, cs uint64, input ccipdmcms.Input) (cldfds.AddressRef, error) { t := ccipdutils.RBACTimelock - version := state.TimelockVersion - ref := ccipdds.GetAddressRef(e.DataStore.Addresses().Filter(), cs, t, &version, input.Qualifier) + qualifier, version, err := parseQualifierVersion(input.Qualifier) + if err != nil { + return cldfds.AddressRef{}, fmt.Errorf("failed to parse timelock qualifier %q: %w", input.Qualifier, err) + } + + ref := getAddressRef(e.DataStore.Addresses(), cs, t, qualifier, version) if ref.Address == "" { - return cldfds.AddressRef{}, fmt.Errorf("timelock contract not found for chain selector %d", cs) + return cldfds.AddressRef{}, fmt.Errorf("timelock contract not found for chain selector %d and qualifier %q", cs, input.Qualifier) } return ref, nil @@ -74,11 +77,56 @@ func (r *MCMSReaderAdapter) GetMCMSRef(e cldf.Environment, cs uint64, input ccip return cldfds.AddressRef{}, fmt.Errorf("unsupported timelock action type: %s", input.TimelockAction) } - version := state.MCMSVersion - ref := ccipdds.GetAddressRef(e.DataStore.Addresses().Filter(), cs, t, &version, input.Qualifier) + qualifier, version, err := parseQualifierVersion(input.Qualifier) + if err != nil { + return cldfds.AddressRef{}, fmt.Errorf("failed to parse MCMS qualifier %q: %w", input.Qualifier, err) + } + + ref := getAddressRef(e.DataStore.Addresses(), cs, t, qualifier, version) if ref.Address == "" { - return cldfds.AddressRef{}, fmt.Errorf("MCMS contract not found for chain selector %d", cs) + return cldfds.AddressRef{}, fmt.Errorf("MCMS contract not found for chain selector %d and qualifier %q", cs, input.Qualifier) } return ref, nil } + +func getAddressRef(input cldfds.AddressRefStore, cs uint64, t cldf.ContractType, qualifier string, version *semver.Version) cldfds.AddressRef { + var filters = []cldfds.FilterFunc[cldfds.AddressRefKey, cldfds.AddressRef]{ + cldfds.AddressRefByChainSelector(cs), + cldfds.AddressRefByType(cldfds.ContractType(t)), + } + if qualifier != "" { + filters = append(filters, cldfds.AddressRefByQualifier(qualifier)) + } + if version != nil { + filters = append(filters, cldfds.AddressRefByVersion(version)) + } + filtered := input.Filter(filters...) + + var latestRef cldfds.AddressRef + for _, ref := range filtered { + if ref.Version == nil { + continue + } + + if latestRef.Version == nil || ref.Version.GreaterThan(latestRef.Version) { + latestRef = ref + } + } + + return latestRef +} + +func parseQualifierVersion(qualifier string) (string, *semver.Version, error) { + contractQualifier, contractVersion, hasVersion := strings.Cut(qualifier, "@") + if !hasVersion { + return qualifier, nil, nil + } + + version, err := semver.NewVersion(contractVersion) + if err != nil { + return "", nil, fmt.Errorf("invalid version in qualifier %q: %w", qualifier, err) + } + + return contractQualifier, version, nil +} diff --git a/deployment/ccip/1_6_0/sequences/mcms_reader_test.go b/deployment/ccip/1_6_0/sequences/mcms_reader_test.go new file mode 100644 index 000000000..36ee344b9 --- /dev/null +++ b/deployment/ccip/1_6_0/sequences/mcms_reader_test.go @@ -0,0 +1,166 @@ +package sequences + +import ( + "testing" + + "github.com/Masterminds/semver/v3" + "github.com/stretchr/testify/require" + + cldfds "github.com/smartcontractkit/chainlink-deployments-framework/datastore" + + ccipdutils "github.com/smartcontractkit/chainlink-ccip/deployment/utils" +) + +func TestGetAddressRefUsesVersionFromQualifier(t *testing.T) { + selector := uint64(123) + v003 := semver.MustParse("0.0.3") + v004 := semver.MustParse("0.0.4") + refs := []cldfds.AddressRef{ + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v003, + Qualifier: ccipdutils.CLLQualifier, + Address: "version-003", + }, + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v004, + Qualifier: ccipdutils.CLLQualifier, + Address: "version-004", + }, + } + + qualifier, version, err := parseQualifierVersion(ccipdutils.CLLQualifier + "@0.0.3") + require.NoError(t, err) + + ref := getAddressRef(addressRefStore(t, refs), selector, ccipdutils.RBACTimelock, qualifier, version) + + require.Equal(t, "version-003", ref.Address) +} + +func TestGetAddressRefUsesHighestVersionWhenQualifierDoesNotSpecifyVersion(t *testing.T) { + selector := uint64(123) + v003 := semver.MustParse("0.0.3") + v004 := semver.MustParse("0.0.4") + v005 := semver.MustParse("0.0.5") + refs := []cldfds.AddressRef{ + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v003, + Qualifier: ccipdutils.CLLQualifier, + Address: "version-003", + }, + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v004, + Qualifier: ccipdutils.CLLQualifier, + Address: "version-004", + }, + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v005, + Qualifier: "other", + Address: "other-qualifier-version-005", + }, + { + ChainSelector: selector + 1, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v005, + Qualifier: ccipdutils.CLLQualifier, + Address: "other-selector-version-005", + }, + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.ProposerManyChainMultisig), + Version: v005, + Qualifier: ccipdutils.CLLQualifier, + Address: "other-type-version-005", + }, + } + + ref := getAddressRef(addressRefStore(t, refs), selector, ccipdutils.RBACTimelock, ccipdutils.CLLQualifier, nil) + + require.Equal(t, "version-004", ref.Address) +} + +func TestGetAddressRefDoesNotFilterQualifierWhenEmpty(t *testing.T) { + selector := uint64(123) + v003 := semver.MustParse("0.0.3") + v004 := semver.MustParse("0.0.4") + refs := []cldfds.AddressRef{ + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v003, + Qualifier: "", + Address: "empty-qualifier-version-003", + }, + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v004, + Qualifier: ccipdutils.CLLQualifier, + Address: "cll-qualifier-version-004", + }, + } + + ref := getAddressRef(addressRefStore(t, refs), selector, ccipdutils.RBACTimelock, "", nil) + + require.Equal(t, "cll-qualifier-version-004", ref.Address) +} + +func TestGetAddressRefReturnsEmptyWhenSpecifiedVersionDoesNotMatch(t *testing.T) { + selector := uint64(123) + v003 := semver.MustParse("0.0.3") + refs := []cldfds.AddressRef{ + { + ChainSelector: selector, + Type: cldfds.ContractType(ccipdutils.RBACTimelock), + Version: v003, + Qualifier: ccipdutils.CLLQualifier, + Address: "version-003", + }, + } + + ref := getAddressRef(addressRefStore(t, refs), selector, ccipdutils.RBACTimelock, ccipdutils.CLLQualifier, semver.MustParse("0.0.4")) + + require.Empty(t, ref.Address) +} + +func TestParseQualifierVersionReturnsInvalidQualifierVersionError(t *testing.T) { + _, _, err := parseQualifierVersion(ccipdutils.CLLQualifier + "@not-a-version") + + require.ErrorContains(t, err, "invalid version in qualifier") +} + +func TestParseQualifierVersionSplitsQualifierAndVersion(t *testing.T) { + qualifier, version, err := parseQualifierVersion(ccipdutils.CLLQualifier + "@0.0.3") + + require.NoError(t, err) + require.Equal(t, ccipdutils.CLLQualifier, qualifier) + require.Equal(t, semver.MustParse("0.0.3"), version) +} + +func TestParseQualifierVersionLeavesEmptyQualifierEmpty(t *testing.T) { + qualifier, version, err := parseQualifierVersion("") + + require.NoError(t, err) + require.Empty(t, qualifier) + require.Nil(t, version) +} + +func addressRefStore(t *testing.T, refs []cldfds.AddressRef) cldfds.AddressRefStore { + t.Helper() + + ds := cldfds.NewMemoryDataStore() + for _, ref := range refs { + require.NoError(t, ds.Addresses().Add(ref)) + } + + return ds.Addresses() +} diff --git a/deployment/state/state.go b/deployment/state/state.go index 75019193a..d8fa23abd 100644 --- a/deployment/state/state.go +++ b/deployment/state/state.go @@ -24,9 +24,6 @@ import ( // Duplicates of chainlink/deployment/ccip/ to avoid import loops var ( Version1_6_0 = *semver.MustParse("1.6.0") - // MCMS contract versions - TimelockVersion = *semver.MustParse("0.0.3") - MCMSVersion = *semver.MustParse("0.0.4") // Core contracts LinkToken ds.ContractType = "LinkToken" TONNative ds.ContractType = "TONNative" diff --git a/integration-tests/deployment/ccip/cs_transfer_ownership_test.go b/integration-tests/deployment/ccip/cs_transfer_ownership_test.go index ed3d69745..87c484dc3 100644 --- a/integration-tests/deployment/ccip/cs_transfer_ownership_test.go +++ b/integration-tests/deployment/ccip/cs_transfer_ownership_test.go @@ -13,9 +13,10 @@ import ( "github.com/xssnick/tonutils-go/tvm/cell" chainsel "github.com/smartcontractkit/chain-selectors" - "github.com/smartcontractkit/chainlink-common/pkg/logger" mcmstypes "github.com/smartcontractkit/mcms/types" + "github.com/smartcontractkit/chainlink-common/pkg/logger" + "github.com/smartcontractkit/chainlink-deployments-framework/chain" cldfds "github.com/smartcontractkit/chainlink-deployments-framework/datastore" @@ -143,9 +144,9 @@ func TestTransferOwnershipWithDeployerAPI(t *testing.T) { {Address: stateCCIPChain.OffRamp.String(), Type: state.OffRamp, ChainSelector: selector}, {Address: stateCCIPChain.FeeQuoter.String(), Type: state.FeeQuoter, ChainSelector: selector}, // MCMS contracts - {Address: stateMCMSChainQ.Proposer.String(), Type: cldfds.ContractType(ccipdutils.ProposerManyChainMultisig), ChainSelector: selector, Version: &state.MCMSVersion}, - {Address: stateMCMSChainQ.Canceller.String(), Type: cldfds.ContractType(ccipdutils.CancellerManyChainMultisig), ChainSelector: selector, Version: &state.MCMSVersion}, - {Address: stateMCMSChainQ.Bypasser.String(), Type: cldfds.ContractType(ccipdutils.BypasserManyChainMultisig), ChainSelector: selector, Version: &state.MCMSVersion}, + {Address: stateMCMSChainQ.Proposer.String(), Type: cldfds.ContractType(ccipdutils.ProposerManyChainMultisig), ChainSelector: selector}, + {Address: stateMCMSChainQ.Canceller.String(), Type: cldfds.ContractType(ccipdutils.CancellerManyChainMultisig), ChainSelector: selector}, + {Address: stateMCMSChainQ.Bypasser.String(), Type: cldfds.ContractType(ccipdutils.BypasserManyChainMultisig), ChainSelector: selector}, } // Step 5: Transfer ownership from deployer to new wallet via the tooling API. diff --git a/package.json b/package.json index 3d8f1f0d2..91a4b16ef 100644 --- a/package.json +++ b/package.json @@ -11,6 +11,9 @@ "ci:changeset:publish": "yarn changeset publish", "ci:changeset:version": "yarn changeset version" }, + "resolutions": { + "axios": "v1.16.1" + }, "repository": { "type": "git", "url": "git+ssh://git@github.com/smartcontractkit/chainlink-ton.git" diff --git a/yarn.lock b/yarn.lock index 8d1827986..253c67ffa 100644 --- a/yarn.lock +++ b/yarn.lock @@ -312,6 +312,37 @@ resolve-from "^5.0.0" semver "^7.5.3" +"@changesets/apply-release-plan@^7.0.14": + version "7.1.1" + resolved "https://registry.npmjs.org/@changesets/apply-release-plan/-/apply-release-plan-7.1.1.tgz#198c3d4dd9eafd0b3fa402a5d212eabe89db134e" + integrity sha512-9qPCm/rLx/xoOFXIHGB229+4GOL76S4MC+7tyOuTsR6+1jYlfFDQORdvwR5hDA6y4FL2BPt3qpbcQIS+dW85LA== + dependencies: + "@changesets/config" "^3.1.4" + "@changesets/get-version-range-type" "^0.4.0" + "@changesets/git" "^3.0.4" + "@changesets/should-skip-package" "^0.1.2" + "@changesets/types" "^6.1.0" + "@manypkg/get-packages" "^1.1.3" + detect-indent "^6.0.0" + fs-extra "^7.0.1" + lodash.startcase "^4.4.0" + outdent "^0.5.0" + prettier "^2.7.1" + resolve-from "^5.0.0" + semver "^7.5.3" + +"@changesets/assemble-release-plan@^6.0.10": + version "6.0.10" + resolved "https://registry.npmjs.org/@changesets/assemble-release-plan/-/assemble-release-plan-6.0.10.tgz#cb82efed0dc17b741bc39b6ccd551e3c86a4eb3d" + integrity sha512-rSDcqdJ9KbVyjpBIuCidhvZNIiVt1XaIYp73ycVQRIA5n/j6wQaEk0ChRLMUQ1vkxZe51PTQ9OIhbg6HQMW45A== + dependencies: + "@changesets/errors" "^0.2.0" + "@changesets/get-dependents-graph" "^2.1.4" + "@changesets/should-skip-package" "^0.1.2" + "@changesets/types" "^6.1.0" + "@manypkg/get-packages" "^1.1.3" + semver "^7.5.3" + "@changesets/assemble-release-plan@^6.0.9": version "6.0.9" resolved "https://registry.yarnpkg.com/@changesets/assemble-release-plan/-/assemble-release-plan-6.0.9.tgz#8aa5baf0037a85812e320172e83b92ca31e85fd6" @@ -340,7 +371,7 @@ "@changesets/types" "^6.1.0" dotenv "^8.1.0" -"@changesets/cli@~2.29.2", "@changesets/cli@~2.29.6": +"@changesets/cli@~2.29.2": version "2.29.6" resolved "https://registry.yarnpkg.com/@changesets/cli/-/cli-2.29.6.tgz#8ad7943e211b929d793132632eed52033a2c7caa" integrity sha512-6qCcVsIG1KQLhpQ5zE8N0PckIx4+9QlHK3z6/lwKnw7Tir71Bjw8BeOZaxA/4Jt00pcgCnCSWZnyuZf5Il05QQ== @@ -374,6 +405,40 @@ spawndamnit "^3.0.1" term-size "^2.1.0" +"@changesets/cli@~2.29.6": + version "2.29.8" + resolved "https://registry.npmjs.org/@changesets/cli/-/cli-2.29.8.tgz#30f71f7ea4f68acab9fb3a0edf178ab43a337e0a" + integrity sha512-1weuGZpP63YWUYjay/E84qqwcnt5yJMM0tep10Up7Q5cS/DGe2IZ0Uj3HNMxGhCINZuR7aO9WBMdKnPit5ZDPA== + dependencies: + "@changesets/apply-release-plan" "^7.0.14" + "@changesets/assemble-release-plan" "^6.0.9" + "@changesets/changelog-git" "^0.2.1" + "@changesets/config" "^3.1.2" + "@changesets/errors" "^0.2.0" + "@changesets/get-dependents-graph" "^2.1.3" + "@changesets/get-release-plan" "^4.0.14" + "@changesets/git" "^3.0.4" + "@changesets/logger" "^0.1.1" + "@changesets/pre" "^2.0.2" + "@changesets/read" "^0.6.6" + "@changesets/should-skip-package" "^0.1.2" + "@changesets/types" "^6.1.0" + "@changesets/write" "^0.4.0" + "@inquirer/external-editor" "^1.0.2" + "@manypkg/get-packages" "^1.1.3" + ansi-colors "^4.1.3" + ci-info "^3.7.0" + enquirer "^2.4.1" + fs-extra "^7.0.1" + mri "^1.2.0" + p-limit "^2.2.0" + package-manager-detector "^0.2.0" + picocolors "^1.1.0" + resolve-from "^5.0.0" + semver "^7.5.3" + spawndamnit "^3.0.1" + term-size "^2.1.0" + "@changesets/config@^3.1.1": version "3.1.1" resolved "https://registry.yarnpkg.com/@changesets/config/-/config-3.1.1.tgz#3e5b1f74236a4552c5f4eddf2bd05a43a0b71160" @@ -387,6 +452,20 @@ fs-extra "^7.0.1" micromatch "^4.0.8" +"@changesets/config@^3.1.2", "@changesets/config@^3.1.4": + version "3.1.4" + resolved "https://registry.npmjs.org/@changesets/config/-/config-3.1.4.tgz#e503be9d86f122e52d64ccca868870e5ea943cfd" + integrity sha512-pf0bvD/v6WI2cRlZ6hzpjtZdSlXDXMAJ+Iz7xfFzV4ZxJ8OGGAON+1qYc99ZPrijnt4xp3VGG7eNvAOGS24V1Q== + dependencies: + "@changesets/errors" "^0.2.0" + "@changesets/get-dependents-graph" "^2.1.4" + "@changesets/logger" "^0.1.1" + "@changesets/should-skip-package" "^0.1.2" + "@changesets/types" "^6.1.0" + "@manypkg/get-packages" "^1.1.3" + fs-extra "^7.0.1" + micromatch "^4.0.8" + "@changesets/errors@^0.2.0": version "0.2.0" resolved "https://registry.yarnpkg.com/@changesets/errors/-/errors-0.2.0.tgz#3c545e802b0f053389cadcf0ed54e5636ff9026a" @@ -404,6 +483,16 @@ picocolors "^1.1.0" semver "^7.5.3" +"@changesets/get-dependents-graph@^2.1.4": + version "2.1.4" + resolved "https://registry.npmjs.org/@changesets/get-dependents-graph/-/get-dependents-graph-2.1.4.tgz#a18e56d94b41d45888f62021accc6e17a61b5d7c" + integrity sha512-ZsS00x6WvmHq3sQv8oCMwL0f/z3wbXCVuSVTJwCnnmbC/iBdNJGFx1EcbMG4PC6sXRyH69liM4A2WKXzn/kRPg== + dependencies: + "@changesets/types" "^6.1.0" + "@manypkg/get-packages" "^1.1.3" + picocolors "^1.1.0" + semver "^7.5.3" + "@changesets/get-github-info@^0.6.0": version "0.6.0" resolved "https://registry.yarnpkg.com/@changesets/get-github-info/-/get-github-info-0.6.0.tgz#faba66a20a3a5a0cbabea28efd43c9ede7429f11" @@ -424,6 +513,18 @@ "@changesets/types" "^6.1.0" "@manypkg/get-packages" "^1.1.3" +"@changesets/get-release-plan@^4.0.14": + version "4.0.16" + resolved "https://registry.npmjs.org/@changesets/get-release-plan/-/get-release-plan-4.0.16.tgz#18f01f037c4c9376acf32ab820f7bcb7e292eaa0" + integrity sha512-2K5Om6CrMPm45rtvckfzWo7e9jOVCKLCnXia5eUPaURH7/LWzri7pK1TycdzAuAtehLkW7VPbWLCSExTHmiI6g== + dependencies: + "@changesets/assemble-release-plan" "^6.0.10" + "@changesets/config" "^3.1.4" + "@changesets/pre" "^2.0.2" + "@changesets/read" "^0.6.7" + "@changesets/types" "^6.1.0" + "@manypkg/get-packages" "^1.1.3" + "@changesets/get-version-range-type@^0.4.0": version "0.4.0" resolved "https://registry.yarnpkg.com/@changesets/get-version-range-type/-/get-version-range-type-0.4.0.tgz#429a90410eefef4368502c41c63413e291740bf5" @@ -455,6 +556,14 @@ "@changesets/types" "^6.1.0" js-yaml "^3.13.1" +"@changesets/parse@^0.4.3": + version "0.4.3" + resolved "https://registry.npmjs.org/@changesets/parse/-/parse-0.4.3.tgz#912a7eac7f8cb387b05f749596a68f2f763660e0" + integrity sha512-ZDmNc53+dXdWEv7fqIUSgRQOLYoUom5Z40gmLgmATmYR9NbL6FJJHwakcCpzaeCy+1D0m0n7mT4jj2B/MQPl7A== + dependencies: + "@changesets/types" "^6.1.0" + js-yaml "^4.1.1" + "@changesets/pre@^2.0.2": version "2.0.2" resolved "https://registry.yarnpkg.com/@changesets/pre/-/pre-2.0.2.tgz#b35e84d25fca8b970340642ca04ce76c7fc34ced" @@ -478,6 +587,19 @@ p-filter "^2.1.0" picocolors "^1.1.0" +"@changesets/read@^0.6.6", "@changesets/read@^0.6.7": + version "0.6.7" + resolved "https://registry.npmjs.org/@changesets/read/-/read-0.6.7.tgz#65e144c960344b34ae8bd85144752a4b687e92d2" + integrity sha512-D1G4AUYGrBEk8vj8MGwf75k9GpN6XL3wg8i42P2jZZwFLXnlr2Pn7r9yuQNbaMCarP7ZQWNJbV6XLeysAIMhTA== + dependencies: + "@changesets/git" "^3.0.4" + "@changesets/logger" "^0.1.1" + "@changesets/parse" "^0.4.3" + "@changesets/types" "^6.1.0" + fs-extra "^7.0.1" + p-filter "^2.1.0" + picocolors "^1.1.0" + "@changesets/should-skip-package@^0.1.2": version "0.1.2" resolved "https://registry.yarnpkg.com/@changesets/should-skip-package/-/should-skip-package-0.1.2.tgz#c018e1e05eab3d97afa4c4590f2b0db7486ae488" @@ -563,6 +685,14 @@ chardet "^2.1.0" iconv-lite "^0.6.3" +"@inquirer/external-editor@^1.0.2": + version "1.0.3" + resolved "https://registry.npmjs.org/@inquirer/external-editor/-/external-editor-1.0.3.tgz#c23988291ee676290fdab3fd306e64010a6d13b8" + integrity sha512-RWbSrDiYmO4LbejWY7ttpxczuwQyZLBUyygsA9Nsv95hpzUWwnNTVQmAq3xuh7vNwCp07UTmE5i11XAEExx4RA== + dependencies: + chardet "^2.1.1" + iconv-lite "^0.7.0" + "@ipld/dag-pb@^2.0.2": version "2.1.18" resolved "https://registry.yarnpkg.com/@ipld/dag-pb/-/dag-pb-2.1.18.tgz#12d63e21580e87c75fd1a2c62e375a78e355c16f" @@ -598,50 +728,50 @@ resolved "https://registry.yarnpkg.com/@istanbuljs/schema/-/schema-0.1.3.tgz#e45e384e4b8ec16bce2fd903af78450f6bf7ec98" integrity sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA== -"@jest/console@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/console/-/console-30.0.5.tgz#d7d027c2db5c64c20a973b7f3e57b49956d6c335" - integrity sha512-xY6b0XiL0Nav3ReresUarwl2oIz1gTnxGbGpho9/rbUWsLH0f1OD/VT84xs8c7VmH7MChnLb0pag6PhZhAdDiA== +"@jest/console@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/console/-/console-30.4.1.tgz#e57725678c3fcc9f7e5597e691e454fee4ce0939" + integrity sha512-v3bhyxUh9Hgmo5p6hAOXe14/R3ZxZDOsvHleh4B07z3m/x4/ngPUXEm9XwK4sF4u+f+P2ORb0Ge+MgpaqRMVDA== dependencies: - "@jest/types" "30.0.5" + "@jest/types" "30.4.1" "@types/node" "*" chalk "^4.1.2" - jest-message-util "30.0.5" - jest-util "30.0.5" + jest-message-util "30.4.1" + jest-util "30.4.1" slash "^3.0.0" -"@jest/core@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/core/-/core-30.0.5.tgz#b5778922d2928f676636e3ec199829554e61e452" - integrity sha512-fKD0OulvRsXF1hmaFgHhVJzczWzA1RXMMo9LTPuFXo9q/alDbME3JIyWYqovWsUBWSoBcsHaGPSLF9rz4l9Qeg== - dependencies: - "@jest/console" "30.0.5" - "@jest/pattern" "30.0.1" - "@jest/reporters" "30.0.5" - "@jest/test-result" "30.0.5" - "@jest/transform" "30.0.5" - "@jest/types" "30.0.5" +"@jest/core@30.4.2": + version "30.4.2" + resolved "https://registry.npmjs.org/@jest/core/-/core-30.4.2.tgz#3d4081f894b7e2ff57d04a31842416bd07b76c32" + integrity sha512-TZJA6cPJUFxoWhxaLo8t0VX/MZX2wPWr0uIDvLSHIvN4gu9h02vSzqI2kBADG1ExqQlC+cY09xKMSreivvrChQ== + dependencies: + "@jest/console" "30.4.1" + "@jest/pattern" "30.4.0" + "@jest/reporters" "30.4.1" + "@jest/test-result" "30.4.1" + "@jest/transform" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" ansi-escapes "^4.3.2" chalk "^4.1.2" ci-info "^4.2.0" exit-x "^0.2.2" + fast-json-stable-stringify "^2.1.0" graceful-fs "^4.2.11" - jest-changed-files "30.0.5" - jest-config "30.0.5" - jest-haste-map "30.0.5" - jest-message-util "30.0.5" - jest-regex-util "30.0.1" - jest-resolve "30.0.5" - jest-resolve-dependencies "30.0.5" - jest-runner "30.0.5" - jest-runtime "30.0.5" - jest-snapshot "30.0.5" - jest-util "30.0.5" - jest-validate "30.0.5" - jest-watcher "30.0.5" - micromatch "^4.0.8" - pretty-format "30.0.5" + jest-changed-files "30.4.1" + jest-config "30.4.2" + jest-haste-map "30.4.1" + jest-message-util "30.4.1" + jest-regex-util "30.4.0" + jest-resolve "30.4.1" + jest-resolve-dependencies "30.4.2" + jest-runner "30.4.2" + jest-runtime "30.4.2" + jest-snapshot "30.4.1" + jest-util "30.4.1" + jest-validate "30.4.1" + jest-watcher "30.4.1" + pretty-format "30.4.1" slash "^3.0.0" "@jest/diff-sequences@30.0.1": @@ -649,15 +779,20 @@ resolved "https://registry.yarnpkg.com/@jest/diff-sequences/-/diff-sequences-30.0.1.tgz#0ededeae4d071f5c8ffe3678d15f3a1be09156be" integrity sha512-n5H8QLDJ47QqbCNn5SuFjCRDrOLEZ0h8vAHCK5RL9Ls7Xa8AQLa/YxAc9UjFqoEDM48muwtBGjtMY5cr0PLDCw== -"@jest/environment@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/environment/-/environment-30.0.5.tgz#eaaae0403c7d3f8414053c2224acc3011e1c3a1b" - integrity sha512-aRX7WoaWx1oaOkDQvCWImVQ8XNtdv5sEWgk4gxR6NXb7WBUnL5sRak4WRzIQRZ1VTWPvV4VI4mgGjNL9TeKMYA== +"@jest/diff-sequences@30.4.0": + version "30.4.0" + resolved "https://registry.npmjs.org/@jest/diff-sequences/-/diff-sequences-30.4.0.tgz#8be2d260e6241d6cddddd102c304fe13b4fc8e3e" + integrity sha512-zOpzlfUs45l6u7jm39qr87JCHUDsaeCtvL+kQe/Vn9jSnRB4/5IPXISm0h9I1vZW/o00Kn4UTJ2MOlhnUGwv3g== + +"@jest/environment@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/environment/-/environment-30.4.1.tgz#1ab5b736e3ce6336d59e00765fa24019649f1a30" + integrity sha512-AK9yNRqgKxiabqMoe4oW+3/TSSeV8vkdC7BGaxZdU0AFXfOpofTLqdru2GXKZghP3sdgwE9XXpnVwfZ8JnFV4w== dependencies: - "@jest/fake-timers" "30.0.5" - "@jest/types" "30.0.5" + "@jest/fake-timers" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" - jest-mock "30.0.5" + jest-mock "30.4.1" "@jest/expect-utils@30.0.5": version "30.0.5" @@ -666,40 +801,52 @@ dependencies: "@jest/get-type" "30.0.1" -"@jest/expect@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/expect/-/expect-30.0.5.tgz#2bbd101df4869f5d171c3cfee881f810f1525005" - integrity sha512-6udac8KKrtTtC+AXZ2iUN/R7dp7Ydry+Fo6FPFnDG54wjVMnb6vW/XNlf7Xj8UDjAE3aAVAsR4KFyKk3TCXmTA== +"@jest/expect-utils@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/expect-utils/-/expect-utils-30.4.1.tgz#e0c7436d52b08610de9027841912dc3734ae80b2" + integrity sha512-ZBn5CglH8fBsQsvs4VWNzD4aWfUYks+IdOOQU3MEK71ol/BcVm+P+rtb1KpiFBpSWSCE27uOahyyf1vfqOVbcQ== dependencies: - expect "30.0.5" - jest-snapshot "30.0.5" + "@jest/get-type" "30.1.0" -"@jest/fake-timers@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/fake-timers/-/fake-timers-30.0.5.tgz#c028a9465a44b7744cb2368196bed89ce13c7054" - integrity sha512-ZO5DHfNV+kgEAeP3gK3XlpJLL4U3Sz6ebl/n68Uwt64qFFs5bv4bfEEjyRGK5uM0C90ewooNgFuKMdkbEoMEXw== +"@jest/expect@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/expect/-/expect-30.4.1.tgz#7fefc67f86c2cb2af3c86d9d41fe4a1d74862b8c" + integrity sha512-ginrj6TMgh2GshLUGCjO94Ptx9HhdZA/I6A9iUfyeLKFtdAjnKzHDgzgP9HYQgbxM1lbXScQ2eUBz2lGeVDPWA== dependencies: - "@jest/types" "30.0.5" - "@sinonjs/fake-timers" "^13.0.0" + expect "30.4.1" + jest-snapshot "30.4.1" + +"@jest/fake-timers@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/fake-timers/-/fake-timers-30.4.1.tgz#ad2d3412d5d005a3e45740bd4c8ee1ccae2f89e1" + integrity sha512-iW5umdmfPeWzehrVhugFQZqCchSCud5S1l2YT0O9ZhjRR0ExclANDZkiSBwzqtnlOn0J1JXvO+HZ6rkuyOVOgQ== + dependencies: + "@jest/types" "30.4.1" + "@sinonjs/fake-timers" "^15.4.0" "@types/node" "*" - jest-message-util "30.0.5" - jest-mock "30.0.5" - jest-util "30.0.5" + jest-message-util "30.4.1" + jest-mock "30.4.1" + jest-util "30.4.1" "@jest/get-type@30.0.1": version "30.0.1" resolved "https://registry.yarnpkg.com/@jest/get-type/-/get-type-30.0.1.tgz#0d32f1bbfba511948ad247ab01b9007724fc9f52" integrity sha512-AyYdemXCptSRFirI5EPazNxyPwAL0jXt3zceFjaj8NFiKP9pOi0bfXonf6qkf82z2t3QWPeLCWWw4stPBzctLw== -"@jest/globals@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/globals/-/globals-30.0.5.tgz#ca70e0ac08ab40417cf8cd92bcb76116c2ccca63" - integrity sha512-7oEJT19WW4oe6HR7oLRvHxwlJk2gev0U9px3ufs8sX9PoD1Eza68KF0/tlN7X0dq/WVsBScXQGgCldA1V9Y/jA== +"@jest/get-type@30.1.0": + version "30.1.0" + resolved "https://registry.npmjs.org/@jest/get-type/-/get-type-30.1.0.tgz#4fcb4dc2ebcf0811be1c04fd1cb79c2dba431cbc" + integrity sha512-eMbZE2hUnx1WV0pmURZY9XoXPkUYjpc55mb0CrhtdWLtzMQPFvu/rZkTLZFTsdaVQa+Tr4eWAteqcUzoawq/uA== + +"@jest/globals@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/globals/-/globals-30.4.1.tgz#6376975e137ef87926349b5e75ccf230f491e843" + integrity sha512-ZbuY4cmXC8DkxYjfvT2DbcHWL2T6vmsMhXCDcmTB2T0y0gaezBI77ufq5ZAIdcRkYZ7NEQEDg1xFeKbxUJ5v5Q== dependencies: - "@jest/environment" "30.0.5" - "@jest/expect" "30.0.5" - "@jest/types" "30.0.5" - jest-mock "30.0.5" + "@jest/environment" "30.4.1" + "@jest/expect" "30.4.1" + "@jest/types" "30.4.1" + jest-mock "30.4.1" "@jest/pattern@30.0.1": version "30.0.1" @@ -709,31 +856,39 @@ "@types/node" "*" jest-regex-util "30.0.1" -"@jest/reporters@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/reporters/-/reporters-30.0.5.tgz#b83585e6448d390a8d92a641c567f1655976d5c6" - integrity sha512-mafft7VBX4jzED1FwGC1o/9QUM2xebzavImZMeqnsklgcyxBto8mV4HzNSzUrryJ+8R9MFOM3HgYuDradWR+4g== +"@jest/pattern@30.4.0": + version "30.4.0" + resolved "https://registry.npmjs.org/@jest/pattern/-/pattern-30.4.0.tgz#fcb519eeacc25caa3768f787595a27afa15302ae" + integrity sha512-RAWn3+f9u8BsHijKJ71uHcFp6vmyEt6VvoWXkl6hKF3qVIuWNmudVjg12DlBPGup/frIl5UcUlH5HfEuvHpEXg== + dependencies: + "@types/node" "*" + jest-regex-util "30.4.0" + +"@jest/reporters@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/reporters/-/reporters-30.4.1.tgz#41d42533f199e737ae352a0a0b32ff300826efe2" + integrity sha512-/SnkPCzEQpUaBH81kjdEdDdo2WZl5hxw+BmLDGWjRkm8o7XlhjwsU36cqwe5PGBE5WYpBvDzRSdXx9rbGuJtNA== dependencies: "@bcoe/v8-coverage" "^0.2.3" - "@jest/console" "30.0.5" - "@jest/test-result" "30.0.5" - "@jest/transform" "30.0.5" - "@jest/types" "30.0.5" + "@jest/console" "30.4.1" + "@jest/test-result" "30.4.1" + "@jest/transform" "30.4.1" + "@jest/types" "30.4.1" "@jridgewell/trace-mapping" "^0.3.25" "@types/node" "*" chalk "^4.1.2" collect-v8-coverage "^1.0.2" exit-x "^0.2.2" - glob "^10.3.10" + glob "^10.5.0" graceful-fs "^4.2.11" istanbul-lib-coverage "^3.0.0" istanbul-lib-instrument "^6.0.0" istanbul-lib-report "^3.0.0" istanbul-lib-source-maps "^5.0.0" istanbul-reports "^3.1.3" - jest-message-util "30.0.5" - jest-util "30.0.5" - jest-worker "30.0.5" + jest-message-util "30.4.1" + jest-util "30.4.1" + jest-worker "30.4.1" slash "^3.0.0" string-length "^4.0.2" v8-to-istanbul "^9.0.1" @@ -745,12 +900,19 @@ dependencies: "@sinclair/typebox" "^0.34.0" -"@jest/snapshot-utils@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/snapshot-utils/-/snapshot-utils-30.0.5.tgz#e23a0e786f174e8cff7f150c1cfbdc9cb7cc81a4" - integrity sha512-XcCQ5qWHLvi29UUrowgDFvV4t7ETxX91CbDczMnoqXPOIcZOxyNdSjm6kV5XMc8+HkxfRegU/MUmnTbJRzGrUQ== +"@jest/schemas@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/schemas/-/schemas-30.4.1.tgz#c3703fdd71357e2c83aa59bd38469e60a11529c6" + integrity sha512-i6b4qw5qnP8c5FEeBJg/uZQ4ddrkN6Ca8qISJh0pr7a5hfn3h3v5x60BEbOC7OYAGZNMs1LfFLwnW2CuK8F57Q== dependencies: - "@jest/types" "30.0.5" + "@sinclair/typebox" "^0.34.0" + +"@jest/snapshot-utils@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/snapshot-utils/-/snapshot-utils-30.4.1.tgz#0f829488b9d46b118854a16a56d509a3c6d9e064" + integrity sha512-ObY4ljvQ95mt6iwKtVLetR/4yXiAgl3H4nJxhztr0MTjrN97TwDYrnCp/kF60Ec9HdhkWTHSu+Hg05aXfngpOA== + dependencies: + "@jest/types" "30.4.1" chalk "^4.1.2" graceful-fs "^4.2.11" natural-compare "^1.4.0" @@ -764,43 +926,42 @@ callsites "^3.1.0" graceful-fs "^4.2.11" -"@jest/test-result@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/test-result/-/test-result-30.0.5.tgz#064c5210c24d5ea192fb02ceddad3be1cfa557c8" - integrity sha512-wPyztnK0gbDMQAJZ43tdMro+qblDHH1Ru/ylzUo21TBKqt88ZqnKKK2m30LKmLLoKtR2lxdpCC/P3g1vfKcawQ== +"@jest/test-result@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/test-result/-/test-result-30.4.1.tgz#e21146ebbb3e1f7f76c3c49805d9f39ae45f8de1" + integrity sha512-/ZG7pgEiOmmWkN9TplKbOu4id2N5lh7FHwRwlkgBVAzGdRH+OkkQ8wX/kIxg4zmd3ZQvAL1RwL2yWsvNYYECTw== dependencies: - "@jest/console" "30.0.5" - "@jest/types" "30.0.5" + "@jest/console" "30.4.1" + "@jest/types" "30.4.1" "@types/istanbul-lib-coverage" "^2.0.6" collect-v8-coverage "^1.0.2" -"@jest/test-sequencer@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/test-sequencer/-/test-sequencer-30.0.5.tgz#c6dba8fc3c386dd793c087626e8508ff1ead19f4" - integrity sha512-Aea/G1egWoIIozmDD7PBXUOxkekXl7ueGzrsGGi1SbeKgQqCYCIf+wfbflEbf2LiPxL8j2JZGLyrzZagjvW4YQ== +"@jest/test-sequencer@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/test-sequencer/-/test-sequencer-30.4.1.tgz#caf9a5e0924ed3b04957441edf9e8cef6a804391" + integrity sha512-PeYE+4td5rKjoRPxztObrXU+H8hsjZfxKMXOcmrr34JerSyB/ROOxbbicz8B7A5j9R9VayDnVPvBmedqCsFCdw== dependencies: - "@jest/test-result" "30.0.5" + "@jest/test-result" "30.4.1" graceful-fs "^4.2.11" - jest-haste-map "30.0.5" + jest-haste-map "30.4.1" slash "^3.0.0" -"@jest/transform@30.0.5": - version "30.0.5" - resolved "https://registry.yarnpkg.com/@jest/transform/-/transform-30.0.5.tgz#f8ca2e9f7466b77b406807d3bef1f6790dd384e4" - integrity sha512-Vk8amLQCmuZyy6GbBht1Jfo9RSdBtg7Lks+B0PecnjI8J+PCLQPGh7uI8Q/2wwpW2gLdiAfiHNsmekKlywULqg== +"@jest/transform@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/transform/-/transform-30.4.1.tgz#1646cddb800d38d9c4e30fecfd4a6eba0fa8acfa" + integrity sha512-Wz0LyktlTvRefoymh+n64hQ84KNXsRGcwdoZ8CSa0Ea+fgYcHZlnk+hDP7v2MS7il2bQ5uTEIxf4/NNfhMN4KQ== dependencies: "@babel/core" "^7.27.4" - "@jest/types" "30.0.5" + "@jest/types" "30.4.1" "@jridgewell/trace-mapping" "^0.3.25" - babel-plugin-istanbul "^7.0.0" + babel-plugin-istanbul "^7.0.1" chalk "^4.1.2" convert-source-map "^2.0.0" fast-json-stable-stringify "^2.1.0" graceful-fs "^4.2.11" - jest-haste-map "30.0.5" - jest-regex-util "30.0.1" - jest-util "30.0.5" - micromatch "^4.0.8" + jest-haste-map "30.4.1" + jest-regex-util "30.4.0" + jest-util "30.4.1" pirates "^4.0.7" slash "^3.0.0" write-file-atomic "^5.0.1" @@ -818,6 +979,19 @@ "@types/yargs" "^17.0.33" chalk "^4.1.2" +"@jest/types@30.4.1": + version "30.4.1" + resolved "https://registry.npmjs.org/@jest/types/-/types-30.4.1.tgz#f79b647a85cb2ff4a90cc55984b31dae820db1f7" + integrity sha512-f1x/vJXIfjOlEmejYpbkbgw1gOqpPECwMvMEtBqe47j7H2Hg8h8w3o3ikhSXq3MI15kg+oQ0exWO0uCtTNJLoQ== + dependencies: + "@jest/pattern" "30.4.0" + "@jest/schemas" "30.4.1" + "@types/istanbul-lib-coverage" "^2.0.6" + "@types/istanbul-reports" "^3.0.4" + "@types/node" "*" + "@types/yargs" "^17.0.33" + chalk "^4.1.2" + "@jridgewell/gen-mapping@^0.3.12", "@jridgewell/gen-mapping@^0.3.5": version "0.3.13" resolved "https://registry.yarnpkg.com/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz#6342a19f44347518c93e43b1ac69deb3c4656a1f" @@ -1009,10 +1183,10 @@ dependencies: type-detect "4.0.8" -"@sinonjs/fake-timers@^13.0.0": - version "13.0.5" - resolved "https://registry.yarnpkg.com/@sinonjs/fake-timers/-/fake-timers-13.0.5.tgz#36b9dbc21ad5546486ea9173d6bea063eb1717d5" - integrity sha512-36/hTbH2uaWuGVERyC6da9YwGWnzUZXuPro/F2LfsdOsLnCojz/iSH8MxUt/FD2S5XBSVPhmArFUXcpCQ2Hkiw== +"@sinonjs/fake-timers@^15.4.0": + version "15.4.0" + resolved "https://registry.npmjs.org/@sinonjs/fake-timers/-/fake-timers-15.4.0.tgz#5d40c151a9e66075fe4520bec40bccfe54931962" + integrity sha512-DsG+8/LscQIQg68J6Ef3dv10u6nVyetYn923s3/sus5eaGfTo1of5WMZSLf0UJc9KDuKPilPH0UDJCjvNbDNCA== dependencies: "@sinonjs/commons" "^3.0.1" @@ -1058,25 +1232,25 @@ resolved "https://registry.yarnpkg.com/@ton-community/func-js-bin/-/func-js-bin-0.4.6-wasmfix.debugger.0.tgz#26af588cf4c0a10ba4d2cdfdcdc50b330edea19e" integrity sha512-g23zEoaTn5Rja6TBTZxX3E4zh+PlWnt7iRJJT5mPuUvQXhWB9wkx9VNZN8KpTdICJIXTW5b5wEE/801W14xQvg== -"@ton-community/func-js@^0.10.0": +"@ton-community/func-js@0.10.0": version "0.10.0" - resolved "https://registry.yarnpkg.com/@ton-community/func-js/-/func-js-0.10.0.tgz#6f35f990255c5d1ea730d7ca9f5b4b2e2933f17a" + resolved "https://registry.npmjs.org/@ton-community/func-js/-/func-js-0.10.0.tgz#6f35f990255c5d1ea730d7ca9f5b4b2e2933f17a" integrity sha512-YvkRTwkwc7e54Ig7oRKGercE91Fi+EuEDLO1kp/RnwslcUcgKQ+w2P7OFMNh/FWCJnU3ADhOBtfTU+dta+XHpw== dependencies: "@ton-community/func-js-bin" "0.4.6-wasmfix.debugger.0" arg "^5.0.2" fflate "^0.8.2" -"@ton/blueprint@^0.44.0": - version "0.44.0" - resolved "https://registry.yarnpkg.com/@ton/blueprint/-/blueprint-0.44.0.tgz#832ed11db0fdc695836c6c8a631213b85bb5d62b" - integrity sha512-RkEJeAZUKvLmzBw/fpS7foKk6UhlMrMk/Rss58pOCiAGjB+O2iOxyMfQvk7irBtaE45OjlCFePNJPzPwyy1pqg== +"@ton/blueprint@0.44.2": + version "0.44.2" + resolved "https://registry.npmjs.org/@ton/blueprint/-/blueprint-0.44.2.tgz#83d30cc22509db6938b2a587fdfcf936052b752b" + integrity sha512-BqT6TlR4eJymYJxa3gXTTlSP/sBnKxJJ2bSa585EdnMaiwLXYDMWLXViYLXl3p3R0qqcdxxHvuwPnNqPE8btsQ== dependencies: "@ton-api/client" "^0.2.0" "@ton-api/ton-adapter" "^0.2.0" "@tonconnect/sdk" "^2.2.0" arg "^5.0.2" - axios "^1.7.7" + axios "1.15.0" chalk "^4.1.0" dotenv "^16.1.4" inquirer "^8.2.5" @@ -1091,6 +1265,11 @@ dependencies: symbol.inspect "1.0.1" +"@ton/core@0.63.1": + version "0.63.1" + resolved "https://registry.npmjs.org/@ton/core/-/core-0.63.1.tgz#eb7e9f96860e290cc9fea7b90df2cf0c3cc95629" + integrity sha512-hDWMjlKzc18W2E4OeV3hUP8ohRJNHPD4Wd1+AQJj8zshZyCRT0usrvnExgbNUTo/vntDqCGMzgYWbXxyaA+L4g== + "@ton/core@^0.61.0": version "0.61.0" resolved "https://registry.yarnpkg.com/@ton/core/-/core-0.61.0.tgz#09b37801cb2f5a942020fcc992be1e99f4b16689" @@ -1098,13 +1277,6 @@ dependencies: symbol.inspect "1.0.1" -"@ton/core@^0.62.0": - version "0.62.0" - resolved "https://registry.yarnpkg.com/@ton/core/-/core-0.62.0.tgz#0582b668c134ec565ed3dfeb9f898ad5a3ccdcee" - integrity sha512-GCYlzzx11rSESKkiHvNy9tL8zWth+ZtUbvV29WH478FvBp8xTw24AyoigwXWNV+OLCAcnwlGhZpTpxjD3wzCwA== - dependencies: - symbol.inspect "1.0.1" - "@ton/crypto-primitives@2.1.0": version "2.1.0" resolved "https://registry.yarnpkg.com/@ton/crypto-primitives/-/crypto-primitives-2.1.0.tgz#8c9277c250b59aae3c819e0d6bd61e44d998e9ca" @@ -1112,7 +1284,7 @@ dependencies: jssha "3.2.0" -"@ton/crypto@^3.2.0", "@ton/crypto@^3.3.0": +"@ton/crypto@3.3.0", "@ton/crypto@^3.2.0", "@ton/crypto@^3.3.0": version "3.3.0" resolved "https://registry.yarnpkg.com/@ton/crypto/-/crypto-3.3.0.tgz#019103df6540fbc1d8102979b4587bc85ff9779e" integrity sha512-/A6CYGgA/H36OZ9BbTaGerKtzWp50rg67ZCH2oIjV1NcrBaCK9Z343M+CxedvM7Haf3f/Ee9EhxyeTp0GKMUpA== @@ -1121,48 +1293,46 @@ jssha "3.2.0" tweetnacl "1.0.3" -"@ton/sandbox@^0.32.2": - version "0.32.2" - resolved "https://registry.yarnpkg.com/@ton/sandbox/-/sandbox-0.32.2.tgz#e949d1df2ae98c1552901597200209163dd8cc42" - integrity sha512-D+Yuyka3pMuoD1KPufRGzE3iFZ0QLyba/xC5mfrXoLtV111ubKxc7RscndOsggeru0bdDYm0i/iaWO5YQWqUfw== +"@ton/sandbox@0.42.0": + version "0.42.0" + resolved "https://registry.npmjs.org/@ton/sandbox/-/sandbox-0.42.0.tgz#5208c9bbabf8681bb59441cf02661adab8798669" + integrity sha512-OOqjNalZNkjnnilFC/KJTCz9sBoJxLskhi4O6t+ugoMemIlJMtBgzoSRD/WVv+zmrqAMxs0nvc7SJs2lOvsFkA== dependencies: + "@vscode/debugadapter" "^1.68.0" chalk "^4.1.2" + fflate "^0.8.2" table "^6.9.0" + ton-assembly "0.6.1" -"@ton/sandbox@^0.41.0": - version "0.41.0" - resolved "https://registry.yarnpkg.com/@ton/sandbox/-/sandbox-0.41.0.tgz#a0c81cca5dedb1891e1cf3f621f730f6bac63539" - integrity sha512-+WRWiHfm62xQebVt6BvLb2UhVphpBHCwSby8R5vP9llzdVck+XEs+p4csIkZBh6gRQsy1Xomzh1PpgZS5XVE3A== +"@ton/sandbox@^0.32.2": + version "0.32.2" + resolved "https://registry.yarnpkg.com/@ton/sandbox/-/sandbox-0.32.2.tgz#e949d1df2ae98c1552901597200209163dd8cc42" + integrity sha512-D+Yuyka3pMuoD1KPufRGzE3iFZ0QLyba/xC5mfrXoLtV111ubKxc7RscndOsggeru0bdDYm0i/iaWO5YQWqUfw== dependencies: - "@vscode/debugadapter" "^1.68.0" chalk "^4.1.2" - fflate "^0.8.2" table "^6.9.0" - ton-assembly "0.6.1" -"@ton/test-utils@^0.12.0": +"@ton/test-utils@0.12.0": version "0.12.0" - resolved "https://registry.yarnpkg.com/@ton/test-utils/-/test-utils-0.12.0.tgz#98b6c58842c29da7d1cde4af82504ba0467fa4d3" + resolved "https://registry.npmjs.org/@ton/test-utils/-/test-utils-0.12.0.tgz#98b6c58842c29da7d1cde4af82504ba0467fa4d3" integrity sha512-SJ6y+213M8C8vDc64JYIu07nEjaYMMlm3pU/64UFINackGkxFFpgmHdmRH/IzFJ2zclC0Wnv7LKNlBIAReT4sQ== dependencies: node-inspect-extracted "^2.0.0" -"@ton/tolk-js@1.2.0": - version "1.2.0" - resolved "https://registry.yarnpkg.com/@ton/tolk-js/-/tolk-js-1.2.0.tgz#5da304dc1193faddfa0be0ff6575a3b71f19958e" - integrity sha512-O7EoC3T4ESnfDT+hOvRBuqotujeDx9a0rGhBjzoAquqVpQFnmW69MMPQRtG8ewn1nvsz3NSeNIJapk64+romCw== +"@ton/tolk-js@1.4.1": + version "1.4.1" + resolved "https://registry.npmjs.org/@ton/tolk-js/-/tolk-js-1.4.1.tgz#a5a75667108a99626011080ce851ee6798d7ff5d" + integrity sha512-4RZD7Qh7iTTF1SSpR0UvQlJvrjFWSSkPXfopq0BRZqJ4c/DQDMjs7nLnHZ99w/Z90jzE+1Eq4A4lsEsWgGaBfA== dependencies: arg "^5.0.2" -"@ton/ton@^16.0.0": - version "16.0.0" - resolved "https://registry.yarnpkg.com/@ton/ton/-/ton-16.0.0.tgz#2af311dac82e2eb30a704068e6633c3c409cc4f6" - integrity sha512-Y5xtPtn0x6iNIEFqOaX8GjPFvDDyCG4YOnJ7WUnP9YQ4MYxANm7gOZZifMcxQcQ5KazxiIWqqyctp4PPVhOgPA== +"@ton/ton@16.2.4": + version "16.2.4" + resolved "https://registry.npmjs.org/@ton/ton/-/ton-16.2.4.tgz#aaace554af2ba876b3f41aa57141d414d63d3d1a" + integrity sha512-GWCNKizQm7MM99XNQGr+zWWdSfbFu/WLeQYm7tMIQDNKpAYEpLDKJUKuK/yrz763DBbnTDAFeq1NWAEy8rAOaQ== dependencies: - axios "^1.6.7" + axios "1.15.0" dataloader "^2.0.0" - symbol.inspect "1.0.1" - teslabot "^1.3.0" zod "^3.21.4" "@tonconnect/isomorphic-eventsource@^0.0.1": @@ -1289,7 +1459,7 @@ "@types/jest@^30.0.0": version "30.0.0" - resolved "https://registry.yarnpkg.com/@types/jest/-/jest-30.0.0.tgz#5e85ae568006712e4ad66f25433e9bdac8801f1d" + resolved "https://registry.npmjs.org/@types/jest/-/jest-30.0.0.tgz#5e85ae568006712e4ad66f25433e9bdac8801f1d" integrity sha512-XTYugzhuwqWjws0CVz8QpM36+T+Dz5mTEBKhNs/esGLnCIlGdRy+Dq78NRjd7ls7r8BC8ZRMOrKlkO1hU0JOwA== dependencies: expect "^30.0.0" @@ -1300,7 +1470,7 @@ resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.2.tgz#b74129719fc8d11c01868010082d483b7545591a" integrity sha512-MqTGEo5bj5t157U6fA/BiDynNkn0YknVdh48CMPkTSpFTVmvao5UQmm7uEF6xBEo7qIMAlY/JSleYaE6VOdpaA== -"@types/node@*", "@types/node@>=13.7.0", "@types/node@^24.3.0": +"@types/node@*", "@types/node@>=13.7.0": version "24.3.0" resolved "https://registry.yarnpkg.com/@types/node/-/node-24.3.0.tgz#89b09f45cb9a8ee69466f18ee5864e4c3eb84dec" integrity sha512-aPTXCrfwnDLj4VvXrm+UUCQjNEvJgNA8s5F1cvwQU+3KNltTOkBm1j30uNLyqqPNe7gE3KFzImYoZEfLhp4Yow== @@ -1319,6 +1489,13 @@ resolved "https://registry.yarnpkg.com/@types/node/-/node-12.20.55.tgz#c329cbd434c42164f846b909bd6f85b5537f6240" integrity sha512-J8xLz7q2OFulZ2cyGTLE1TbbZcjpno7FaN6zdJNrgAdrJ+DZzh/uFR6YrTb4C+nXakvud8Q4+rbhoIWlYQbUFQ== +"@types/node@^24.3.0": + version "24.12.4" + resolved "https://registry.npmjs.org/@types/node/-/node-24.12.4.tgz#2709745569811dcbdc57c097fafdd387c6330382" + integrity sha512-GUUEShf+PBCGW2KaXwcIt3Yk+e3pkKwWKb9GSyM9WQVE+ep2jzmHdGsHzu4wgcZy5fN9FBdVzjpBQsYlpfpgLA== + dependencies: + undici-types "~7.16.0" + "@types/pegjs@^0.10.3": version "0.10.6" resolved "https://registry.yarnpkg.com/@types/pegjs/-/pegjs-0.10.6.tgz#bc20fc4809fed4cddab8d0dbee0e568803741a82" @@ -1490,6 +1667,13 @@ aes-js@^3.1.2: resolved "https://registry.yarnpkg.com/aes-js/-/aes-js-3.1.2.tgz#db9aabde85d5caabbfc0d4f2a4446960f627146a" integrity sha512-e5pEa2kBnBOgR4Y/p20pskXI74UEz7de8ZGVo58asOtvSVG5YAbJeELPZxOmt+Bnz3rX753YKhfIn4X4l1PPRQ== +agent-base@6: + version "6.0.2" + resolved "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" + integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== + dependencies: + debug "4" + ajv@^8.0.1: version "8.17.1" resolved "https://registry.yarnpkg.com/ajv/-/ajv-8.17.1.tgz#37d9a5c776af6bc92d7f4f9510eba4c0a60d11a6" @@ -1564,6 +1748,11 @@ argparse@^1.0.7: dependencies: sprintf-js "~1.0.2" +argparse@^2.0.1: + version "2.0.1" + resolved "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" + integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== + array-union@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/array-union/-/array-union-2.1.0.tgz#b798420adbeb1de828d84acd8a2e23d3efe85e8d" @@ -1579,32 +1768,33 @@ asynckit@^0.4.0: resolved "https://registry.yarnpkg.com/asynckit/-/asynckit-0.4.0.tgz#c79ed97f7f34cb8f2ba1bc9790bcc366474b4b79" integrity sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q== -axios@^1.6.7, axios@^1.7.7: - version "1.11.0" - resolved "https://registry.yarnpkg.com/axios/-/axios-1.11.0.tgz#c2ec219e35e414c025b2095e8b8280278478fdb6" - integrity sha512-1Lx3WLFQWm3ooKDYZD1eXmoGO9fxYQjrycfHFC8P0sCfQVXyROp0p9PFWBehewBOdCwHc+f/b8I0fMto5eSfwA== +axios@1.15.0, axios@v1.16.1: + version "1.16.1" + resolved "https://registry.npmjs.org/axios/-/axios-1.16.1.tgz#517e29291d19d6e8cf919ff264f4fe157261ba12" + integrity sha512-caYkukvroVPO8KrzuJEb50Hm07KwfBZPEC3VeFHTsqWHvKTsy54hjJz9BS/cdaypROE2rH6xvm9mHX4fgWkr3A== dependencies: - follow-redirects "^1.15.6" - form-data "^4.0.4" - proxy-from-env "^1.1.0" + follow-redirects "^1.16.0" + form-data "^4.0.5" + https-proxy-agent "^5.0.1" + proxy-from-env "^2.1.0" -babel-jest@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/babel-jest/-/babel-jest-30.0.5.tgz#7cc7dd03d0d613125d458521f635b8c2361e89cc" - integrity sha512-mRijnKimhGDMsizTvBTWotwNpzrkHr+VvZUQBof2AufXKB8NXrL1W69TG20EvOz7aevx6FTJIaBuBkYxS8zolg== +babel-jest@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/babel-jest/-/babel-jest-30.4.1.tgz#63cba904438bbe64c4cf0acdea87b0a45cb809fc" + integrity sha512-fATAbM8piYxkiXQp3RBXmZHxZVNJZAVXXfyeyCN2Tida3+qJ8ea9UxhiJ2y4fLO90ZImKt6k9FlcH2+rLkJGhw== dependencies: - "@jest/transform" "30.0.5" + "@jest/transform" "30.4.1" "@types/babel__core" "^7.20.5" - babel-plugin-istanbul "^7.0.0" - babel-preset-jest "30.0.1" + babel-plugin-istanbul "^7.0.1" + babel-preset-jest "30.4.0" chalk "^4.1.2" graceful-fs "^4.2.11" slash "^3.0.0" -babel-plugin-istanbul@^7.0.0: - version "7.0.0" - resolved "https://registry.yarnpkg.com/babel-plugin-istanbul/-/babel-plugin-istanbul-7.0.0.tgz#629a178f63b83dc9ecee46fd20266283b1f11280" - integrity sha512-C5OzENSx/A+gt7t4VH1I2XsflxyPUmXRFPKBxt33xncdOmq7oROVM3bZv9Ysjjkv8OJYDMa+tKuKMvqU/H3xdw== +babel-plugin-istanbul@^7.0.1: + version "7.0.1" + resolved "https://registry.npmjs.org/babel-plugin-istanbul/-/babel-plugin-istanbul-7.0.1.tgz#d8b518c8ea199364cf84ccc82de89740236daf92" + integrity sha512-D8Z6Qm8jCvVXtIRkBnqNHX0zJ37rQcFJ9u8WOS6tkYOsRdHBzypCstaxWiu5ZIlqQtviRYbgnRLSoCEvjqcqbA== dependencies: "@babel/helper-plugin-utils" "^7.0.0" "@istanbuljs/load-nyc-config" "^1.0.0" @@ -1612,18 +1802,16 @@ babel-plugin-istanbul@^7.0.0: istanbul-lib-instrument "^6.0.2" test-exclude "^6.0.0" -babel-plugin-jest-hoist@30.0.1: - version "30.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-30.0.1.tgz#f271b2066d2c1fb26a863adb8e13f85b06247125" - integrity sha512-zTPME3pI50NsFW8ZBaVIOeAxzEY7XHlmWeXXu9srI+9kNfzCUTy8MFan46xOGZY8NZThMqq+e3qZUKsvXbasnQ== +babel-plugin-jest-hoist@30.4.0: + version "30.4.0" + resolved "https://registry.npmjs.org/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-30.4.0.tgz#f7d6a6d8f435808b56b45a81dc4b61a39e36794a" + integrity sha512-9EdtWM/sSfXLOGLwSn+GS6pIXyBnL07/8gyJlwFXjWy4DxMOyItqyUT29d4lQiS380EZwYlX7/At4PgBS+m2aA== dependencies: - "@babel/template" "^7.27.2" - "@babel/types" "^7.27.3" "@types/babel__core" "^7.20.5" -babel-preset-current-node-syntax@^1.1.0: +babel-preset-current-node-syntax@^1.2.0: version "1.2.0" - resolved "https://registry.yarnpkg.com/babel-preset-current-node-syntax/-/babel-preset-current-node-syntax-1.2.0.tgz#20730d6cdc7dda5d89401cab10ac6a32067acde6" + resolved "https://registry.npmjs.org/babel-preset-current-node-syntax/-/babel-preset-current-node-syntax-1.2.0.tgz#20730d6cdc7dda5d89401cab10ac6a32067acde6" integrity sha512-E/VlAEzRrsLEb2+dv8yp3bo4scof3l9nR4lrld+Iy5NyVqgVYUJnDAmunkhPMisRI32Qc4iRiz425d8vM++2fg== dependencies: "@babel/plugin-syntax-async-generators" "^7.8.4" @@ -1642,13 +1830,13 @@ babel-preset-current-node-syntax@^1.1.0: "@babel/plugin-syntax-private-property-in-object" "^7.14.5" "@babel/plugin-syntax-top-level-await" "^7.14.5" -babel-preset-jest@30.0.1: - version "30.0.1" - resolved "https://registry.yarnpkg.com/babel-preset-jest/-/babel-preset-jest-30.0.1.tgz#7d28db9531bce264e846c8483d54236244b8ae88" - integrity sha512-+YHejD5iTWI46cZmcc/YtX4gaKBtdqCHCVfuVinizVpbmyjO3zYmeuyFdfA8duRqQZfgCAMlsfmkVbJ+e2MAJw== +babel-preset-jest@30.4.0: + version "30.4.0" + resolved "https://registry.npmjs.org/babel-preset-jest/-/babel-preset-jest-30.4.0.tgz#295486c2ec1127b3dc7d0d2adaa72a1dcaaafccd" + integrity sha512-lBY4jxsNmCnSiu7kquw8ZC9F4+XLMOKypT3RnNHPvU2Kpd4W0xaPuLr5ZkRyOsvLYAY4yaW1ZwTW4xB7NIiZzg== dependencies: - babel-plugin-jest-hoist "30.0.1" - babel-preset-current-node-syntax "^1.1.0" + babel-plugin-jest-hoist "30.4.0" + babel-preset-current-node-syntax "^1.2.0" balanced-match@^1.0.0: version "1.0.2" @@ -1827,6 +2015,11 @@ chardet@^2.1.0: resolved "https://registry.yarnpkg.com/chardet/-/chardet-2.1.0.tgz#1007f441a1ae9f9199a4a67f6e978fb0aa9aa3fe" integrity sha512-bNFETTG/pM5ryzQ9Ad0lJOTa6HWD/YsScAR3EnCPZRPlQh77JocYktSHOUHelyhm8IARL+o4c4F1bP5KVOjiRA== +chardet@^2.1.1: + version "2.1.1" + resolved "https://registry.npmjs.org/chardet/-/chardet-2.1.1.tgz#5c75593704a642f71ee53717df234031e65373c8" + integrity sha512-PsezH1rqdV9VvyNhxxOW32/d75r01NY7TQCmOqomRo15ZSOKbpTFVsfjghxo6JloQUCGnH4k1LGu0R4yCLlWQQ== + ci-info@^3.7.0: version "3.9.0" resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-3.9.0.tgz#4279a62028a7b1f262f3473fc9605f5e218c59b4" @@ -1919,7 +2112,7 @@ core-js-pure@^3.38.0: crc-32@^1.2.2: version "1.2.2" - resolved "https://registry.yarnpkg.com/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff" + resolved "https://registry.npmjs.org/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff" integrity sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ== create-require@^1.1.0: @@ -1946,6 +2139,13 @@ dataloader@^2.0.0, dataloader@^2.1.0: resolved "https://registry.yarnpkg.com/dataloader/-/dataloader-2.2.3.tgz#42d10b4913515f5b37c6acedcb4960d6ae1b1517" integrity sha512-y2krtASINtPFS1rSDjacrFgn1dcUuoREVabwlOGOe4SdxenREqwjwjElAdwvbGM7kgZz9a3KVicWR7vcz8rnzA== +debug@4: + version "4.4.3" + resolved "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz#c6ae432d9bd9662582fce08709b038c58e9e3d6a" + integrity sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA== + dependencies: + ms "^2.1.3" + debug@^4.1.0, debug@^4.1.1, debug@^4.3.1: version "4.4.1" resolved "https://registry.yarnpkg.com/debug/-/debug-4.4.1.tgz#e5a8bc6cbc4c6cd3e64308b0693a3d4fa550189b" @@ -2151,7 +2351,19 @@ exit-x@^0.2.2: resolved "https://registry.yarnpkg.com/exit-x/-/exit-x-0.2.2.tgz#1f9052de3b8d99a696b10dad5bced9bdd5c3aa64" integrity sha512-+I6B/IkJc1o/2tiURyz/ivu/O0nKNEArIUB5O7zBrlDVJr22SCLH3xTeEry428LvFhRzIA1g8izguxJ/gbNcVQ== -expect@30.0.5, expect@^30.0.0: +expect@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/expect/-/expect-30.4.1.tgz#897e0390a0b6c333dbcf3a24dee3ad49553577e0" + integrity sha512-PMARsyh/JtqC20HoGqlFcIlQAyqUtW4PlI1rup1uhYJtKuwAjbvWi3GQMAn+STdHum/dk8xrKfUM1+5SAwpolA== + dependencies: + "@jest/expect-utils" "30.4.1" + "@jest/get-type" "30.1.0" + jest-matcher-utils "30.4.1" + jest-message-util "30.4.1" + jest-mock "30.4.1" + jest-util "30.4.1" + +expect@^30.0.0: version "30.0.5" resolved "https://registry.yarnpkg.com/expect/-/expect-30.0.5.tgz#c23bf193c5e422a742bfd2990ad990811de41a5a" integrity sha512-P0te2pt+hHI5qLJkIR+iMvS+lYUZml8rKKsohVHAGY+uClp9XVbdyYNJOIjSRpHVp8s8YqxJCiHUkSYZGr8rtQ== @@ -2235,10 +2447,10 @@ find-up@^4.0.0, find-up@^4.1.0: locate-path "^5.0.0" path-exists "^4.0.0" -follow-redirects@^1.15.6: - version "1.15.11" - resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.11.tgz#777d73d72a92f8ec4d2e410eb47352a56b8e8340" - integrity sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ== +follow-redirects@^1.16.0: + version "1.16.0" + resolved "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.16.0.tgz#28474a159d3b9d11ef62050a14ed60e4df6d61bc" + integrity sha512-y5rN/uOsadFT/JfYwhxRS5R7Qce+g3zG97+JrtFZlC9klX/W5hD7iiLzScI4nZqUS7DNUdhPgw4xI8W2LuXlUw== foreground-child@^3.1.0: version "3.3.1" @@ -2248,10 +2460,10 @@ foreground-child@^3.1.0: cross-spawn "^7.0.6" signal-exit "^4.0.1" -form-data@^4.0.4: - version "4.0.4" - resolved "https://registry.yarnpkg.com/form-data/-/form-data-4.0.4.tgz#784cdcce0669a9d68e94d11ac4eea98088edd2c4" - integrity sha512-KrGhL9Q4zjj0kiUt5OO4Mr/A/jlI2jDYs5eHBpYHPcBEVSiipAvn2Ko2HnPe20rmcuuvMHNdZFp+4IlGTMF0Ow== +form-data@^4.0.5: + version "4.0.5" + resolved "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz#b49e48858045ff4cbf6b03e1805cebcad3679053" + integrity sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w== dependencies: asynckit "^0.4.0" combined-stream "^1.0.8" @@ -2343,10 +2555,10 @@ glob-parent@^5.1.2: dependencies: is-glob "^4.0.1" -glob@^10.3.10: - version "10.4.5" - resolved "https://registry.yarnpkg.com/glob/-/glob-10.4.5.tgz#f4d9f0b90ffdbab09c9d77f5f29b4262517b0956" - integrity sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg== +glob@^10.5.0: + version "10.5.0" + resolved "https://registry.npmjs.org/glob/-/glob-10.5.0.tgz#8ec0355919cd3338c28428a23d4f24ecc5fe738c" + integrity sha512-DfXN8DfhJ7NH3Oe7cFmu3NCu1wKbkReJ8TorzSAFbSKrlNaQSKfIzqYqVY8zlbs2NLBbWpRiU52GX2PbaBVNkg== dependencies: foreground-child "^3.1.0" jackspeak "^3.1.2" @@ -2408,10 +2620,10 @@ hamt-sharding@^2.0.0: sparse-array "^1.3.1" uint8arrays "^3.0.0" -handlebars@^4.7.8: - version "4.7.8" - resolved "https://registry.yarnpkg.com/handlebars/-/handlebars-4.7.8.tgz#41c42c18b1be2365439188c77c6afae71c0cd9e9" - integrity sha512-vafaFqs8MZkRrSX7sFVUdo3ap/eNiLnb4IakshzvP56X5Nr1iGKAIqdX6tMlm6HcNRIkr6AxO5jFEoJzzpT8aQ== +handlebars@^4.7.9: + version "4.7.9" + resolved "https://registry.npmjs.org/handlebars/-/handlebars-4.7.9.tgz#6f139082ab58dc4e5a0e51efe7db5ae890d56a0f" + integrity sha512-4E71E0rpOaQuJR2A3xDZ+GM1HyWYv1clR58tC8emQNeQe3RH7MAzSbat+V0wG78LQBo6m6bzSG/L4pBuCsgnUQ== dependencies: minimist "^1.2.5" neo-async "^2.6.2" @@ -2449,6 +2661,14 @@ html-escaper@^2.0.0: resolved "https://registry.yarnpkg.com/html-escaper/-/html-escaper-2.0.2.tgz#dfd60027da36a36dfcbe236262c00a5822681453" integrity sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg== +https-proxy-agent@^5.0.1: + version "5.0.1" + resolved "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6" + integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA== + dependencies: + agent-base "6" + debug "4" + human-id@^4.1.1: version "4.1.1" resolved "https://registry.yarnpkg.com/human-id/-/human-id-4.1.1.tgz#2801fbd61b9a5c1c9170f332802db6408a39a4b0" @@ -2466,6 +2686,13 @@ iconv-lite@^0.6.3: dependencies: safer-buffer ">= 2.1.2 < 3.0.0" +iconv-lite@^0.7.0: + version "0.7.2" + resolved "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.7.2.tgz#d0bdeac3f12b4835b7359c2ad89c422a4d1cc72e" + integrity sha512-im9DjEDQ55s9fL4EYzOAv0yMqmMBSZp6G0VvFyTMPKWxiSBHUj9NW/qqLmXUwXrrM7AvqSlTCfvqRb0cM8yYqw== + dependencies: + safer-buffer ">= 2.1.2 < 3.0.0" + ieee754@^1.1.13, ieee754@^1.2.1: version "1.2.1" resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352" @@ -2727,84 +2954,83 @@ jackspeak@^3.1.2: optionalDependencies: "@pkgjs/parseargs" "^0.11.0" -jest-changed-files@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-changed-files/-/jest-changed-files-30.0.5.tgz#ec448f83bd9caa894dd7da8707f207c356a19924" - integrity sha512-bGl2Ntdx0eAwXuGpdLdVYVr5YQHnSZlQ0y9HVDu565lCUAe9sj6JOtBbMmBBikGIegne9piDDIOeiLVoqTkz4A== +jest-changed-files@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-changed-files/-/jest-changed-files-30.4.1.tgz#396fcf914165287f05960372a5d091f6f2275ec5" + integrity sha512-IuctmYrxi21iOSOaIXpJWalHyPAsVv0GeBHKDn8C1CA4W5htHn7INL+wdnL4Bo0+olEndvAFkmb++tIQJG+vvg== dependencies: execa "^5.1.1" - jest-util "30.0.5" + jest-util "30.4.1" p-limit "^3.1.0" -jest-circus@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-circus/-/jest-circus-30.0.5.tgz#9b4d44feb56c7ffe14411ad7fc08af188c5d4da7" - integrity sha512-h/sjXEs4GS+NFFfqBDYT7y5Msfxh04EwWLhQi0F8kuWpe+J/7tICSlswU8qvBqumR3kFgHbfu7vU6qruWWBPug== +jest-circus@30.4.2: + version "30.4.2" + resolved "https://registry.npmjs.org/jest-circus/-/jest-circus-30.4.2.tgz#9a5b9b9c57bf51871f112ccf7a673d486c28f8e7" + integrity sha512-rvHH7VlY6LgbJXJTQ87GW62g1FntOtbhh0zT+v04kC+pgL6aBKyYINXxWukCpj3dcIBMw5/XUbtDS9dU9JTXeQ== dependencies: - "@jest/environment" "30.0.5" - "@jest/expect" "30.0.5" - "@jest/test-result" "30.0.5" - "@jest/types" "30.0.5" + "@jest/environment" "30.4.1" + "@jest/expect" "30.4.1" + "@jest/test-result" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" chalk "^4.1.2" co "^4.6.0" dedent "^1.6.0" is-generator-fn "^2.1.0" - jest-each "30.0.5" - jest-matcher-utils "30.0.5" - jest-message-util "30.0.5" - jest-runtime "30.0.5" - jest-snapshot "30.0.5" - jest-util "30.0.5" + jest-each "30.4.1" + jest-matcher-utils "30.4.1" + jest-message-util "30.4.1" + jest-runtime "30.4.2" + jest-snapshot "30.4.1" + jest-util "30.4.1" p-limit "^3.1.0" - pretty-format "30.0.5" + pretty-format "30.4.1" pure-rand "^7.0.0" slash "^3.0.0" stack-utils "^2.0.6" -jest-cli@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-cli/-/jest-cli-30.0.5.tgz#c3fbfdabd1a5c428429476f915a1ba6d0774cc50" - integrity sha512-Sa45PGMkBZzF94HMrlX4kUyPOwUpdZasaliKN3mifvDmkhLYqLLg8HQTzn6gq7vJGahFYMQjXgyJWfYImKZzOw== +jest-cli@30.4.2: + version "30.4.2" + resolved "https://registry.npmjs.org/jest-cli/-/jest-cli-30.4.2.tgz#e353ef54035c5ac97f200807c97b3d857f52bddc" + integrity sha512-jfA2ocvVHMXS2QijrJ0d31ektP+d/W0T5RpcTX2Pq+3sVqHlsXVCM2+FmwpL+bdY8OfHpIg9xMxLF17Zg0U49Q== dependencies: - "@jest/core" "30.0.5" - "@jest/test-result" "30.0.5" - "@jest/types" "30.0.5" + "@jest/core" "30.4.2" + "@jest/test-result" "30.4.1" + "@jest/types" "30.4.1" chalk "^4.1.2" exit-x "^0.2.2" import-local "^3.2.0" - jest-config "30.0.5" - jest-util "30.0.5" - jest-validate "30.0.5" + jest-config "30.4.2" + jest-util "30.4.1" + jest-validate "30.4.1" yargs "^17.7.2" -jest-config@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-config/-/jest-config-30.0.5.tgz#567cf39b595229b786506a496c22e222d5e8d480" - integrity sha512-aIVh+JNOOpzUgzUnPn5FLtyVnqc3TQHVMupYtyeURSb//iLColiMIR8TxCIDKyx9ZgjKnXGucuW68hCxgbrwmA== +jest-config@30.4.2: + version "30.4.2" + resolved "https://registry.npmjs.org/jest-config/-/jest-config-30.4.2.tgz#78f589b5410d2805518b8bdce517217fb96b5e61" + integrity sha512-rNHAShJQqQwFNoL0hbf3BphSBOWnpOUAKvidLS/AjNVLPfoj5mSf4jQMfW3cYOs6hXeZC7nF7mDHaBnbxELOzg== dependencies: "@babel/core" "^7.27.4" - "@jest/get-type" "30.0.1" - "@jest/pattern" "30.0.1" - "@jest/test-sequencer" "30.0.5" - "@jest/types" "30.0.5" - babel-jest "30.0.5" + "@jest/get-type" "30.1.0" + "@jest/pattern" "30.4.0" + "@jest/test-sequencer" "30.4.1" + "@jest/types" "30.4.1" + babel-jest "30.4.1" chalk "^4.1.2" ci-info "^4.2.0" deepmerge "^4.3.1" - glob "^10.3.10" + glob "^10.5.0" graceful-fs "^4.2.11" - jest-circus "30.0.5" - jest-docblock "30.0.1" - jest-environment-node "30.0.5" - jest-regex-util "30.0.1" - jest-resolve "30.0.5" - jest-runner "30.0.5" - jest-util "30.0.5" - jest-validate "30.0.5" - micromatch "^4.0.8" + jest-circus "30.4.2" + jest-docblock "30.4.0" + jest-environment-node "30.4.1" + jest-regex-util "30.4.0" + jest-resolve "30.4.1" + jest-runner "30.4.2" + jest-util "30.4.1" + jest-validate "30.4.1" parse-json "^5.2.0" - pretty-format "30.0.5" + pretty-format "30.4.1" slash "^3.0.0" strip-json-comments "^3.1.1" @@ -2818,62 +3044,72 @@ jest-diff@30.0.5: chalk "^4.1.2" pretty-format "30.0.5" -jest-docblock@30.0.1: - version "30.0.1" - resolved "https://registry.yarnpkg.com/jest-docblock/-/jest-docblock-30.0.1.tgz#545ff59f2fa88996bd470dba7d3798a8421180b1" - integrity sha512-/vF78qn3DYphAaIc3jy4gA7XSAz167n9Bm/wn/1XhTLW7tTBIzXtCJpb/vcmc73NIIeeohCbdL94JasyXUZsGA== +jest-diff@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-diff/-/jest-diff-30.4.1.tgz#26691c73975768409af4a66b2754cea3182aa2dc" + integrity sha512-CRpFK0RtLriVDGcPPAnR6HMVI8bSR2jnUIgralhauzYQZIb4RH9AtEInTuQr65LmmGggGcRT6HIASxwqsVsmlA== + dependencies: + "@jest/diff-sequences" "30.4.0" + "@jest/get-type" "30.1.0" + chalk "^4.1.2" + pretty-format "30.4.1" + +jest-docblock@30.4.0: + version "30.4.0" + resolved "https://registry.npmjs.org/jest-docblock/-/jest-docblock-30.4.0.tgz#3ab779a027d1495ae21550accd4266bbe99af7a3" + integrity sha512-ZPMabUZCx5MpbZ2eBYSvZ0J8fvo3dR9oM+eeUpb3aKNQFuS2tu3Duw1TNlMoP8k3WQgKGJuhcMFvwcVuq6T7oA== dependencies: detect-newline "^3.1.0" -jest-each@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-each/-/jest-each-30.0.5.tgz#5962264ff246cd757ba44db096c1bc5b4835173e" - integrity sha512-dKjRsx1uZ96TVyejD3/aAWcNKy6ajMaN531CwWIsrazIqIoXI9TnnpPlkrEYku/8rkS3dh2rbH+kMOyiEIv0xQ== +jest-each@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-each/-/jest-each-30.4.1.tgz#b69e66da8e2b578c6140d357f6574044c2a40537" + integrity sha512-/8MJbH6fuj48TstjrMf+u/pd06Qezz5xOXvZA6442heNOWr8bdeoGZX2d9fCn028CoMgYmroH9//zky5GfyYmA== dependencies: - "@jest/get-type" "30.0.1" - "@jest/types" "30.0.5" + "@jest/get-type" "30.1.0" + "@jest/types" "30.4.1" chalk "^4.1.2" - jest-util "30.0.5" - pretty-format "30.0.5" + jest-util "30.4.1" + pretty-format "30.4.1" -jest-environment-node@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-environment-node/-/jest-environment-node-30.0.5.tgz#6a98dd80e0384ead67ed05643381395f6cda93c9" - integrity sha512-ppYizXdLMSvciGsRsMEnv/5EFpvOdXBaXRBzFUDPWrsfmog4kYrOGWXarLllz6AXan6ZAA/kYokgDWuos1IKDA== +jest-environment-node@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-30.4.1.tgz#43bbbee903e17d874eb1817195c50ff8b90e2fe0" + integrity sha512-4FZYVOk85hz2AyT6BbarKy9u37g6DbrDyCdFhsnDdXqyrueYQvB+0zO4f/kqLCRD0BsPRXPMNJeQwihKZV8naw== dependencies: - "@jest/environment" "30.0.5" - "@jest/fake-timers" "30.0.5" - "@jest/types" "30.0.5" + "@jest/environment" "30.4.1" + "@jest/fake-timers" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" - jest-mock "30.0.5" - jest-util "30.0.5" - jest-validate "30.0.5" + jest-mock "30.4.1" + jest-util "30.4.1" + jest-validate "30.4.1" -jest-haste-map@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-haste-map/-/jest-haste-map-30.0.5.tgz#fdd0daa322b02eb34267854cff2859fae21e92a6" - integrity sha512-dkmlWNlsTSR0nH3nRfW5BKbqHefLZv0/6LCccG0xFCTWcJu8TuEwG+5Cm75iBfjVoockmO6J35o5gxtFSn5xeg== +jest-haste-map@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-30.4.1.tgz#6d80d09d668c20bf3944977e50acac94fcd672fe" + integrity sha512-rFrcONd8jeFsyw+Z9CrScJgglRf2+NFmNam8dKu7n+SoHqNYT47mn0DdEcVUZJpvh7Iz6/si7f7yUH7GJHVgnw== dependencies: - "@jest/types" "30.0.5" + "@jest/types" "30.4.1" "@types/node" "*" anymatch "^3.1.3" fb-watchman "^2.0.2" graceful-fs "^4.2.11" - jest-regex-util "30.0.1" - jest-util "30.0.5" - jest-worker "30.0.5" - micromatch "^4.0.8" + jest-regex-util "30.4.0" + jest-util "30.4.1" + jest-worker "30.4.1" + picomatch "^4.0.3" walker "^1.0.8" optionalDependencies: fsevents "^2.3.3" -jest-leak-detector@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-leak-detector/-/jest-leak-detector-30.0.5.tgz#00cfd2b323f48d8f4416b0a3e05fcf4c51f18864" - integrity sha512-3Uxr5uP8jmHMcsOtYMRB/zf1gXN3yUIc+iPorhNETG54gErFIiUhLvyY/OggYpSMOEYqsmRxmuU4ZOoX5jpRFg== +jest-leak-detector@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-30.4.1.tgz#96077059a68e5871fc8f53aa90647a6a33f916cd" + integrity sha512-IpmyiioeHxiWDhesHnUFmOxcTzwCwKpgACgWajtAP+nYQXiY7DakTxB6Bx9JFiRMljr0AX1PvnQdaU1KFoz6NQ== dependencies: - "@jest/get-type" "30.0.1" - pretty-format "30.0.5" + "@jest/get-type" "30.1.0" + pretty-format "30.4.1" jest-matcher-utils@30.0.5: version "30.0.5" @@ -2885,6 +3121,16 @@ jest-matcher-utils@30.0.5: jest-diff "30.0.5" pretty-format "30.0.5" +jest-matcher-utils@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-30.4.1.tgz#3fee8c89dbd8fc6e60eb590def9897e18f110ec4" + integrity sha512-zvYfX5CaeEkFrrLS9suWe9rvJrm9J1Iv3ua8kIBv9GEPzcnsfBf0bob37la7s67fs0nlBC3EuvkOLnXQKxtx4A== + dependencies: + "@jest/get-type" "30.1.0" + chalk "^4.1.2" + jest-diff "30.4.1" + pretty-format "30.4.1" + jest-message-util@30.0.5: version "30.0.5" resolved "https://registry.yarnpkg.com/jest-message-util/-/jest-message-util-30.0.5.tgz#dd12ffec91dd3fa6a59cbd538a513d8e239e070c" @@ -2900,6 +3146,22 @@ jest-message-util@30.0.5: slash "^3.0.0" stack-utils "^2.0.6" +jest-message-util@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-message-util/-/jest-message-util-30.4.1.tgz#40f6bfa5f564363edcba7ce0ca64277fd2ad6af7" + integrity sha512-kwCKIvq0MCW1HzLoGola9Te6JUdzgV0loyKJ3Qghrkz9i5/RRIHsL95BMQc2HBBhlBKC4j22K9p11TGHH8RBpQ== + dependencies: + "@babel/code-frame" "^7.27.1" + "@jest/types" "30.4.1" + "@types/stack-utils" "^2.0.3" + chalk "^4.1.2" + graceful-fs "^4.2.11" + jest-util "30.4.1" + picomatch "^4.0.3" + pretty-format "30.4.1" + slash "^3.0.0" + stack-utils "^2.0.6" + jest-mock@30.0.5: version "30.0.5" resolved "https://registry.yarnpkg.com/jest-mock/-/jest-mock-30.0.5.tgz#ef437e89212560dd395198115550085038570bdd" @@ -2909,6 +3171,15 @@ jest-mock@30.0.5: "@types/node" "*" jest-util "30.0.5" +jest-mock@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-mock/-/jest-mock-30.4.1.tgz#5e11a05d7719a1e3c7bba6348b70ff4e1bc5ea68" + integrity sha512-/i8SVb8/NSB7RfNi8gfqu8gxLV23KaL5EpAttyb9iz8qWRIqXRLflycz/32wXsYkOnaUlx8NAKnJYtpsmXUmfw== + dependencies: + "@jest/types" "30.4.1" + "@types/node" "*" + jest-util "30.4.1" + jest-pnp-resolver@^1.2.3: version "1.2.3" resolved "https://registry.yarnpkg.com/jest-pnp-resolver/-/jest-pnp-resolver-1.2.3.tgz#930b1546164d4ad5937d5540e711d4d38d4cad2e" @@ -2919,108 +3190,113 @@ jest-regex-util@30.0.1: resolved "https://registry.yarnpkg.com/jest-regex-util/-/jest-regex-util-30.0.1.tgz#f17c1de3958b67dfe485354f5a10093298f2a49b" integrity sha512-jHEQgBXAgc+Gh4g0p3bCevgRCVRkB4VB70zhoAE48gxeSr1hfUOsM/C2WoJgVL7Eyg//hudYENbm3Ne+/dRVVA== -jest-resolve-dependencies@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-resolve-dependencies/-/jest-resolve-dependencies-30.0.5.tgz#53be4c51d296c84a0e75608e7b77b6fe92dbac29" - integrity sha512-/xMvBR4MpwkrHW4ikZIWRttBBRZgWK4d6xt3xW1iRDSKt4tXzYkMkyPfBnSCgv96cpkrctfXs6gexeqMYqdEpw== +jest-regex-util@30.4.0: + version "30.4.0" + resolved "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-30.4.0.tgz#f75ccc43857633df2563a03588b5cb45c7c2941b" + integrity sha512-mWlvLviKIgIQ8VCuM1xRdD0TWp3zlzionlmDBjuXVBs+VkmXq6FgW9T4Emr7oGz/Rk6feDCGyiugolcQEyp3mg== + +jest-resolve-dependencies@30.4.2: + version "30.4.2" + resolved "https://registry.npmjs.org/jest-resolve-dependencies/-/jest-resolve-dependencies-30.4.2.tgz#152f8a4cb2dd351cedeb5ada53c89f9683a3ad92" + integrity sha512-gDiVh1I+GxYzz9oXlyw+1wv6VOYX1WYxMOfjsA3iGKePV2oxmbHhwxfkALxNxYy1ciw6APWwkW2zZONwP97aEQ== dependencies: - jest-regex-util "30.0.1" - jest-snapshot "30.0.5" + jest-regex-util "30.4.0" + jest-snapshot "30.4.1" -jest-resolve@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-resolve/-/jest-resolve-30.0.5.tgz#f52f91600070b7073db465dc553eee5471ea8e06" - integrity sha512-d+DjBQ1tIhdz91B79mywH5yYu76bZuE96sSbxj8MkjWVx5WNdt1deEFRONVL4UkKLSrAbMkdhb24XN691yDRHg== +jest-resolve@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-resolve/-/jest-resolve-30.4.1.tgz#b9e432892dc0e2a470eb4826ef5f120a50b3205e" + integrity sha512-Zry8Yq/yJcNAZ7dJ5F2heic8AheXvbFZ7XI5V+h28nrYZ7Qoyy4dItq8OodjnYD270mvX+ZudmrNV9cysqhW5Q== dependencies: chalk "^4.1.2" graceful-fs "^4.2.11" - jest-haste-map "30.0.5" + jest-haste-map "30.4.1" jest-pnp-resolver "^1.2.3" - jest-util "30.0.5" - jest-validate "30.0.5" + jest-util "30.4.1" + jest-validate "30.4.1" slash "^3.0.0" unrs-resolver "^1.7.11" -jest-runner@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-runner/-/jest-runner-30.0.5.tgz#5cbaaf85964246da4f65d697f186846f23cd9b5a" - integrity sha512-JcCOucZmgp+YuGgLAXHNy7ualBx4wYSgJVWrYMRBnb79j9PD0Jxh0EHvR5Cx/r0Ce+ZBC4hCdz2AzFFLl9hCiw== +jest-runner@30.4.2: + version "30.4.2" + resolved "https://registry.npmjs.org/jest-runner/-/jest-runner-30.4.2.tgz#15debf3cb6d817538aa97427d5a79277cdff65fe" + integrity sha512-2dw0PslVYXxffXGpLo+Ejad+KcI1Qkjn7f4X4619gf21oCUmL+SPfjqIa/losUem3yEOvfNZe/F1HWUcNpODcg== dependencies: - "@jest/console" "30.0.5" - "@jest/environment" "30.0.5" - "@jest/test-result" "30.0.5" - "@jest/transform" "30.0.5" - "@jest/types" "30.0.5" + "@jest/console" "30.4.1" + "@jest/environment" "30.4.1" + "@jest/test-result" "30.4.1" + "@jest/transform" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" chalk "^4.1.2" emittery "^0.13.1" exit-x "^0.2.2" graceful-fs "^4.2.11" - jest-docblock "30.0.1" - jest-environment-node "30.0.5" - jest-haste-map "30.0.5" - jest-leak-detector "30.0.5" - jest-message-util "30.0.5" - jest-resolve "30.0.5" - jest-runtime "30.0.5" - jest-util "30.0.5" - jest-watcher "30.0.5" - jest-worker "30.0.5" + jest-docblock "30.4.0" + jest-environment-node "30.4.1" + jest-haste-map "30.4.1" + jest-leak-detector "30.4.1" + jest-message-util "30.4.1" + jest-resolve "30.4.1" + jest-runtime "30.4.2" + jest-util "30.4.1" + jest-watcher "30.4.1" + jest-worker "30.4.1" p-limit "^3.1.0" source-map-support "0.5.13" -jest-runtime@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-runtime/-/jest-runtime-30.0.5.tgz#d6a7e22687264240d1786d6f7682ac6a2872e552" - integrity sha512-7oySNDkqpe4xpX5PPiJTe5vEa+Ak/NnNz2bGYZrA1ftG3RL3EFlHaUkA1Cjx+R8IhK0Vg43RML5mJedGTPNz3A== +jest-runtime@30.4.2: + version "30.4.2" + resolved "https://registry.npmjs.org/jest-runtime/-/jest-runtime-30.4.2.tgz#03b5955003440975b12e76518ec85d091c25b84a" + integrity sha512-3/5e8iPz2k/VLqlr8DgTftYyLUv8Su3FkCAO2/Od81UsUTpSxOrS6O5x5KkoQwyUjmpYyDJKeyAvg2T2nvpNkQ== dependencies: - "@jest/environment" "30.0.5" - "@jest/fake-timers" "30.0.5" - "@jest/globals" "30.0.5" + "@jest/environment" "30.4.1" + "@jest/fake-timers" "30.4.1" + "@jest/globals" "30.4.1" "@jest/source-map" "30.0.1" - "@jest/test-result" "30.0.5" - "@jest/transform" "30.0.5" - "@jest/types" "30.0.5" + "@jest/test-result" "30.4.1" + "@jest/transform" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" chalk "^4.1.2" cjs-module-lexer "^2.1.0" collect-v8-coverage "^1.0.2" - glob "^10.3.10" + glob "^10.5.0" graceful-fs "^4.2.11" - jest-haste-map "30.0.5" - jest-message-util "30.0.5" - jest-mock "30.0.5" - jest-regex-util "30.0.1" - jest-resolve "30.0.5" - jest-snapshot "30.0.5" - jest-util "30.0.5" + jest-haste-map "30.4.1" + jest-message-util "30.4.1" + jest-mock "30.4.1" + jest-regex-util "30.4.0" + jest-resolve "30.4.1" + jest-snapshot "30.4.1" + jest-util "30.4.1" slash "^3.0.0" strip-bom "^4.0.0" -jest-snapshot@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-snapshot/-/jest-snapshot-30.0.5.tgz#6600716eef2e6d8ea1dd788ae4385f3a2791b11f" - integrity sha512-T00dWU/Ek3LqTp4+DcW6PraVxjk28WY5Ua/s+3zUKSERZSNyxTqhDXCWKG5p2HAJ+crVQ3WJ2P9YVHpj1tkW+g== +jest-snapshot@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-snapshot/-/jest-snapshot-30.4.1.tgz#0380cbbaa9d53d32cf7e61af98459ac10a339842" + integrity sha512-tEOkkfOMppUyeiHwjZswOQ3lcnoTnws/q5FnGIaeIh/jmoU0ZlgMYRR8sTlTj+nNGCoJ0RDq6SfxGxCsyMTPmw== dependencies: "@babel/core" "^7.27.4" "@babel/generator" "^7.27.5" "@babel/plugin-syntax-jsx" "^7.27.1" "@babel/plugin-syntax-typescript" "^7.27.1" "@babel/types" "^7.27.3" - "@jest/expect-utils" "30.0.5" - "@jest/get-type" "30.0.1" - "@jest/snapshot-utils" "30.0.5" - "@jest/transform" "30.0.5" - "@jest/types" "30.0.5" - babel-preset-current-node-syntax "^1.1.0" + "@jest/expect-utils" "30.4.1" + "@jest/get-type" "30.1.0" + "@jest/snapshot-utils" "30.4.1" + "@jest/transform" "30.4.1" + "@jest/types" "30.4.1" + babel-preset-current-node-syntax "^1.2.0" chalk "^4.1.2" - expect "30.0.5" + expect "30.4.1" graceful-fs "^4.2.11" - jest-diff "30.0.5" - jest-matcher-utils "30.0.5" - jest-message-util "30.0.5" - jest-util "30.0.5" - pretty-format "30.0.5" + jest-diff "30.4.1" + jest-matcher-utils "30.4.1" + jest-message-util "30.4.1" + jest-util "30.4.1" + pretty-format "30.4.1" semver "^7.7.2" synckit "^0.11.8" @@ -3036,52 +3312,64 @@ jest-util@30.0.5: graceful-fs "^4.2.11" picomatch "^4.0.2" -jest-validate@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-validate/-/jest-validate-30.0.5.tgz#d26fd218b8d566bff48fd98880b8ea94fd0d8456" - integrity sha512-ouTm6VFHaS2boyl+k4u+Qip4TSH7Uld5tyD8psQ8abGgt2uYYB8VwVfAHWHjHc0NWmGGbwO5h0sCPOGHHevefw== +jest-util@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-util/-/jest-util-30.4.1.tgz#979c9d014fdd12bb95d3dcde0192e1a9e0bc93d6" + integrity sha512-vjQb1sACEiv13DKJMDToJpzVW0joCsIQrmbg0fi7CyOOt+g9jTuQl2A216pWRBYhOVt53XbL/2LbMKg1BECWOw== dependencies: - "@jest/get-type" "30.0.1" - "@jest/types" "30.0.5" + "@jest/types" "30.4.1" + "@types/node" "*" + chalk "^4.1.2" + ci-info "^4.2.0" + graceful-fs "^4.2.11" + picomatch "^4.0.3" + +jest-validate@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-validate/-/jest-validate-30.4.1.tgz#dcc4784547bf644dca0226d3266fb1bde392c5a4" + integrity sha512-PDWi4SOwLnwqNDfHZjOcsEFyZ4fc/2W2gVL3DEoyqnB6jCQMLRtfBong8s6omIw3lI0HWOus12xfnFmQtjW3fw== + dependencies: + "@jest/get-type" "30.1.0" + "@jest/types" "30.4.1" camelcase "^6.3.0" chalk "^4.1.2" leven "^3.1.0" - pretty-format "30.0.5" + pretty-format "30.4.1" -jest-watcher@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-watcher/-/jest-watcher-30.0.5.tgz#90db6e3f582b88085bde58f7555cbdd3a1beb10d" - integrity sha512-z9slj/0vOwBDBjN3L4z4ZYaA+pG56d6p3kTUhFRYGvXbXMWhXmb/FIxREZCD06DYUwDKKnj2T80+Pb71CQ0KEg== +jest-watcher@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-watcher/-/jest-watcher-30.4.1.tgz#d2a78fd27553db9206947eeda6068d76bacfd276" + integrity sha512-/l9UonmvCwjHH7d2h3iAwIloLc1H0S8mJZ/LNK3i86hqwPAz8otUJjP9MfYtz9Tt77Su5FD2xGjZn8d31IZHlw== dependencies: - "@jest/test-result" "30.0.5" - "@jest/types" "30.0.5" + "@jest/test-result" "30.4.1" + "@jest/types" "30.4.1" "@types/node" "*" ansi-escapes "^4.3.2" chalk "^4.1.2" emittery "^0.13.1" - jest-util "30.0.5" + jest-util "30.4.1" string-length "^4.0.2" -jest-worker@30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest-worker/-/jest-worker-30.0.5.tgz#0b85cbab10610303e8d84e214f94d8f052c3cd04" - integrity sha512-ojRXsWzEP16NdUuBw/4H/zkZdHOa7MMYCk4E430l+8fELeLg/mqmMlRhjL7UNZvQrDmnovWZV4DxX03fZF48fQ== +jest-worker@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/jest-worker/-/jest-worker-30.4.1.tgz#ac010eb6c512425748a39e2d6bf05b2c4866ca4f" + integrity sha512-SHynN/q/QD++iNyvMdy+WMmbCGk8jIsNcRxycXbWubSOhvo6T+j2afcfUSl+3hYsiBebOTo0cT7c2H7CXugu1g== dependencies: "@types/node" "*" "@ungap/structured-clone" "^1.3.0" - jest-util "30.0.5" + jest-util "30.4.1" merge-stream "^2.0.0" supports-color "^8.1.1" jest@^30.0.5: - version "30.0.5" - resolved "https://registry.yarnpkg.com/jest/-/jest-30.0.5.tgz#ee62729fb77829790d67c660d852350fbde315ce" - integrity sha512-y2mfcJywuTUkvLm2Lp1/pFX8kTgMO5yyQGq/Sk/n2mN7XWYp4JsCZ/QXW34M8YScgk8bPZlREH04f6blPnoHnQ== + version "30.4.2" + resolved "https://registry.npmjs.org/jest/-/jest-30.4.2.tgz#e9bdb00f4bf1126d781b0d98e23130db096bbd9a" + integrity sha512-Yi1jqNC/Oq0N4hBgNH/YvBpP1P57QqundgytzYqy3yqAa7NZPNjSoi4SGbRAXDMdBzNE6xBCi5U7RgfrvMEUVQ== dependencies: - "@jest/core" "30.0.5" - "@jest/types" "30.0.5" + "@jest/core" "30.4.2" + "@jest/types" "30.4.1" import-local "^3.2.0" - jest-cli "30.0.5" + jest-cli "30.4.2" js-sha3@0.8.0: version "0.8.0" @@ -3101,6 +3389,13 @@ js-yaml@^3.13.1, js-yaml@^3.6.1: argparse "^1.0.7" esprima "^4.0.0" +js-yaml@^4.1.1: + version "4.1.1" + resolved "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.1.tgz#854c292467705b699476e1a2decc0c8a3458806b" + integrity sha512-qQKT4zQxXl8lLwBtHMWwaTcGfFOZviOJet3Oy/xmGk2gZH677CJM9EvtfdSkgWcATZhj/55JZ0rmy3myCT5lsA== + dependencies: + argparse "^2.0.1" + jsesc@^3.0.2: version "3.1.0" resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-3.1.0.tgz#74d335a234f67ed19907fdadfac7ccf9d409825d" @@ -3518,6 +3813,11 @@ picomatch@^4.0.2: resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-4.0.3.tgz#796c76136d1eead715db1e7bad785dedd695a042" integrity sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q== +picomatch@^4.0.3: + version "4.0.4" + resolved "https://registry.npmjs.org/picomatch/-/picomatch-4.0.4.tgz#fd6f5e00a143086e074dffe4c924b8fb293b0589" + integrity sha512-QP88BAKvMam/3NxH6vj2o21R6MjxZUAd6nlwAS/pnGvN9IVLocLHxGYIzFhg6fUQ+5th6P4dv4eW9jX3DSIj7A== + pify@^4.0.1: version "4.0.1" resolved "https://registry.yarnpkg.com/pify/-/pify-4.0.1.tgz#4b2cd25c50d598735c50292224fd8c6df41e3231" @@ -3541,9 +3841,9 @@ prettier@^2.7.1: integrity sha512-tdN8qQGvNjw4CHbY+XXk0JgCXn9QiF21a55rBe5LJAU+kDyC4WQn4+awm2Xfk2lQMk5fKup9XgzTZtGkjBdP9Q== prettier@^3.6.2: - version "3.6.2" - resolved "https://registry.yarnpkg.com/prettier/-/prettier-3.6.2.tgz#ccda02a1003ebbb2bfda6f83a074978f608b9393" - integrity sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ== + version "3.8.3" + resolved "https://registry.npmjs.org/prettier/-/prettier-3.8.3.tgz#560f2de55bf01b4c0503bc629d5df99b9a1d09b0" + integrity sha512-7igPTM53cGHMW8xWuVTydi2KO233VFiTNyF5hLJqpilHfmn8C8gPf+PS7dUT64YcXFbiMGZxS9pCSxL/Dxm/Jw== pretty-format@30.0.5, pretty-format@^30.0.0: version "30.0.5" @@ -3554,6 +3854,16 @@ pretty-format@30.0.5, pretty-format@^30.0.0: ansi-styles "^5.2.0" react-is "^18.3.1" +pretty-format@30.4.1: + version "30.4.1" + resolved "https://registry.npmjs.org/pretty-format/-/pretty-format-30.4.1.tgz#0911652e92e1e91f475e3e6a16e628e50649ea69" + integrity sha512-K6KiKMHTL4jjX4u3Kir2EW07nRfcqVTXIImx50wbjHQTcZPgg+gjVeNTIT3l3L1Rd4UefxfogquC9J37SoFyyw== + dependencies: + "@jest/schemas" "30.4.1" + ansi-styles "^5.2.0" + react-is-18 "npm:react-is@^18.3.1" + react-is-19 "npm:react-is@^19.2.5" + protobufjs@^6.10.2: version "6.11.4" resolved "https://registry.yarnpkg.com/protobufjs/-/protobufjs-6.11.4.tgz#29a412c38bf70d89e537b6d02d904a6f448173aa" @@ -3573,10 +3883,10 @@ protobufjs@^6.10.2: "@types/node" ">=13.7.0" long "^4.0.0" -proxy-from-env@^1.1.0: - version "1.1.0" - resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz#e102f16ca355424865755d2c9e8ea4f24d58c3e2" - integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== +proxy-from-env@^2.1.0: + version "2.1.0" + resolved "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-2.1.0.tgz#a7487568adad577cfaaa7e88c49cab3ab3081aba" + integrity sha512-cJ+oHTW1VAEa8cJslgmUZrc+sjRKgAKl3Zyse6+PV38hZe/V6Z14TbCuXcan9F9ghlz4QrFr2c92TNF82UkYHA== pure-rand@^7.0.0: version "7.0.1" @@ -3610,6 +3920,16 @@ rabin-wasm@^0.1.4: node-fetch "^2.6.1" readable-stream "^3.6.0" +"react-is-18@npm:react-is@^18.3.1": + version "18.3.1" + resolved "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz#e83557dc12eae63a99e003a46388b1dcbb44db7e" + integrity sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg== + +"react-is-19@npm:react-is@^19.2.5": + version "19.2.6" + resolved "https://registry.npmjs.org/react-is/-/react-is-19.2.6.tgz#aeee6159b159eb7f520d672cffcc69e7052d288f" + integrity sha512-XjBR15BhXuylgWGuslhDKqlSayuqvqBX91BP8pauG8kd1zY8kotkNWbXksTCNRarse4kuGbe2kIY05ARtwNIvw== + react-is@^18.3.1: version "18.3.1" resolved "https://registry.yarnpkg.com/react-is/-/react-is-18.3.1.tgz#e83557dc12eae63a99e003a46388b1dcbb44db7e" @@ -3708,6 +4028,11 @@ semver@^7.5.3, semver@^7.5.4, semver@^7.7.1, semver@^7.7.2: resolved "https://registry.yarnpkg.com/semver/-/semver-7.7.2.tgz#67d99fdcd35cec21e6f8b87a7fd515a33f982b58" integrity sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA== +semver@^7.8.0: + version "7.8.1" + resolved "https://registry.npmjs.org/semver/-/semver-7.8.1.tgz#bf4970b5e70fda0686363cc18bfe8805d5ed957e" + integrity sha512-rkVq3IXh+4FDGch+KwzX3aV9W3kO54GyEgpvBzSyctDA6Xtd7RJQV1xmXbeQp5v7+VzLOfVqiutSE6GICgPFvg== + shebang-command@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-2.0.0.tgz#ccd0af4f8835fbdc265b82461aaf0c36663f34ea" @@ -3907,7 +4232,7 @@ term-size@^2.1.0: resolved "https://registry.yarnpkg.com/term-size/-/term-size-2.2.1.tgz#2a6a54840432c2fb6320fea0f415531e90189f54" integrity sha512-wK0Ri4fOGjv/XPy8SBHZChl8CM7uMc5VML7SqiQ0zG7+J5Vr+RMQDoHa2CNT6KHUnTGIXH34UDMkPzAUyapBZg== -teslabot@^1.3.0, teslabot@^1.5.0: +teslabot@^1.5.0: version "1.5.0" resolved "https://registry.yarnpkg.com/teslabot/-/teslabot-1.5.0.tgz#70f544516699ca5f696d8ae94f3d12cd495d5cd6" integrity sha512-e2MmELhCgrgZEGo7PQu/6bmYG36IDH+YrBI1iGm6jovXkeDIGa3pZ2WSqRjzkuw2vt1EqfkZoV5GpXgqL8QJVg== @@ -3982,23 +4307,23 @@ tr46@~0.0.3: integrity sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw== ts-jest@^29.4.1: - version "29.4.1" - resolved "https://registry.yarnpkg.com/ts-jest/-/ts-jest-29.4.1.tgz#42d33beb74657751d315efb9a871fe99e3b9b519" - integrity sha512-SaeUtjfpg9Uqu8IbeDKtdaS0g8lS6FT6OzM3ezrDfErPJPHNDo/Ey+VFGP1bQIDfagYDLyRpd7O15XpG1Es2Uw== + version "29.4.11" + resolved "https://registry.npmjs.org/ts-jest/-/ts-jest-29.4.11.tgz#42f5de21c37ccc01a580253afae6955abbf4d0b3" + integrity sha512-IrFl7l9AuB/qrNw5quqvAv/hmKMb8dhWOH4jQOGo0Oq8tCeo1O86/iTFG1FaRimgUkF13l4PcepO8ATFT6Ns4g== dependencies: bs-logger "^0.2.6" fast-json-stable-stringify "^2.1.0" - handlebars "^4.7.8" + handlebars "^4.7.9" json5 "^2.2.3" lodash.memoize "^4.1.2" make-error "^1.3.6" - semver "^7.7.2" + semver "^7.8.0" type-fest "^4.41.0" yargs-parser "^21.1.1" ts-node@^10.9.1, ts-node@^10.9.2: version "10.9.2" - resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.9.2.tgz#70f021c9e185bccdca820e26dc413805c101c71f" + resolved "https://registry.npmjs.org/ts-node/-/ts-node-10.9.2.tgz#70f021c9e185bccdca820e26dc413805c101c71f" integrity sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ== dependencies: "@cspotcode/source-map-support" "^0.8.0" @@ -4051,9 +4376,9 @@ type-fest@^4.41.0: integrity sha512-TeTSQ6H5YHvpqVwBRcnLDCBnDOHWYu7IvGbHT6N8AOymcr9PJGjc1GTtiWZTYg0NCgYwvnYWEkVChQAr9bjfwA== typescript@^5.9.2: - version "5.9.2" - resolved "https://registry.yarnpkg.com/typescript/-/typescript-5.9.2.tgz#d93450cddec5154a2d5cabe3b8102b83316fb2a6" - integrity sha512-CWBzXQrc/qOkhidw1OzBTQuYRbfyxDXJMVJ1XNwUHGROVmuaeiEm3OslpZ1RV96d7SKKjZKrSJu3+t/xlw3R9A== + version "5.9.3" + resolved "https://registry.npmjs.org/typescript/-/typescript-5.9.3.tgz#5b4f59e15310ab17a216f5d6cf53ee476ede670f" + integrity sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw== uglify-js@^3.1.4: version "3.19.3" @@ -4077,6 +4402,11 @@ undici-types@~7.10.0: resolved "https://registry.yarnpkg.com/undici-types/-/undici-types-7.10.0.tgz#4ac2e058ce56b462b056e629cc6a02393d3ff350" integrity sha512-t5Fy/nfn+14LuOc2KNYg75vZqClpAiqscVvMygNnlsHBFpSXdJaYtXMcdNLpl/Qvc3P2cB3s6lOV51nqsFq4ag== +undici-types@~7.16.0: + version "7.16.0" + resolved "https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz#ffccdff36aea4884cbfce9a750a0580224f58a46" + integrity sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw== + universalify@^0.1.0: version "0.1.2" resolved "https://registry.yarnpkg.com/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66"