@defuse-protocol/intents-sdk 0.27.0 → 0.29.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. package/dist/index.cjs +20 -11
  2. package/dist/index.d.cts +3 -1
  3. package/dist/index.d.ts +3 -1
  4. package/dist/index.js +3 -1
  5. package/dist/src/bridges/direct-bridge/direct-bridge-utils.cjs +16 -0
  6. package/dist/src/bridges/direct-bridge/direct-bridge-utils.js +16 -2
  7. package/dist/src/bridges/direct-bridge/direct-bridge.cjs +41 -8
  8. package/dist/src/bridges/direct-bridge/direct-bridge.js +41 -9
  9. package/dist/src/bridges/direct-bridge/error.cjs +17 -0
  10. package/dist/src/bridges/direct-bridge/error.d.cts +12 -0
  11. package/dist/src/bridges/direct-bridge/error.d.ts +12 -0
  12. package/dist/src/bridges/direct-bridge/error.js +15 -0
  13. package/dist/src/bridges/hot-bridge/hot-bridge.cjs +8 -1
  14. package/dist/src/bridges/hot-bridge/hot-bridge.js +8 -1
  15. package/dist/src/bridges/omni-bridge/omni-bridge.cjs +2 -2
  16. package/dist/src/bridges/omni-bridge/omni-bridge.js +1 -1
  17. package/dist/src/intents/expirable-nonce.cjs +83 -0
  18. package/dist/src/intents/expirable-nonce.d.cts +44 -0
  19. package/dist/src/intents/expirable-nonce.d.ts +44 -0
  20. package/dist/src/intents/expirable-nonce.js +75 -0
  21. package/dist/src/intents/intent-executer-impl/intent-executer.cjs +2 -2
  22. package/dist/src/intents/intent-executer-impl/intent-executer.js +2 -2
  23. package/dist/src/intents/intent-payload-factory.cjs +6 -6
  24. package/dist/src/intents/intent-payload-factory.js +6 -4
  25. package/dist/src/intents/interfaces/salt-manager.d.cts +9 -0
  26. package/dist/src/intents/interfaces/salt-manager.d.ts +9 -0
  27. package/dist/src/intents/salt-manager.cjs +76 -0
  28. package/dist/src/intents/salt-manager.js +72 -0
  29. package/dist/src/lib/hex.cjs +11 -0
  30. package/dist/src/lib/hex.js +10 -0
  31. package/dist/src/sdk.cjs +19 -3
  32. package/dist/src/sdk.d.cts +3 -0
  33. package/dist/src/sdk.d.ts +3 -0
  34. package/dist/src/sdk.js +20 -4
  35. package/package.json +3 -3
package/dist/index.cjs CHANGED
@@ -3,8 +3,10 @@ const require_route_enum = require('./src/constants/route-enum.cjs');
3
3
  const require_errors = require('./src/classes/errors.cjs');
4
4
  const require_caip2 = require('./src/lib/caip2.cjs');
5
5
  const require_bridge_name_enum = require('./src/constants/bridge-name-enum.cjs');
6
- const require_error = require('./src/bridges/hot-bridge/error.cjs');
7
- const require_error$1 = require('./src/bridges/omni-bridge/error.cjs');
6
+ const require_error = require('./src/bridges/direct-bridge/error.cjs');
7
+ const require_error$1 = require('./src/bridges/hot-bridge/error.cjs');
8
+ const require_error$2 = require('./src/bridges/omni-bridge/error.cjs');
9
+ const require_expirable_nonce = require('./src/intents/expirable-nonce.cjs');
8
10
  const require_route_config_factory = require('./src/lib/route-config-factory.cjs');
9
11
  const require_sdk = require('./src/sdk.cjs');
10
12
  const require_factories = require('./src/intents/intent-signer-impl/factories.cjs');
@@ -25,11 +27,12 @@ Object.defineProperty(exports, 'BaseError', {
25
27
  });
26
28
  exports.BridgeNameEnum = require_bridge_name_enum.BridgeNameEnum;
27
29
  exports.Chains = require_caip2.Chains;
28
- exports.FailedToFetchFeeError = require_error$1.FailedToFetchFeeError;
30
+ exports.DestinationExplicitNearAccountDoesntExistError = require_error.DestinationExplicitNearAccountDoesntExistError;
31
+ exports.FailedToFetchFeeError = require_error$2.FailedToFetchFeeError;
29
32
  exports.FeeExceedsAmountError = require_errors.FeeExceedsAmountError;
30
- exports.HotWithdrawalCancelledError = require_error.HotWithdrawalCancelledError;
31
- exports.HotWithdrawalNotFoundError = require_error.HotWithdrawalNotFoundError;
32
- exports.HotWithdrawalPendingError = require_error.HotWithdrawalPendingError;
33
+ exports.HotWithdrawalCancelledError = require_error$1.HotWithdrawalCancelledError;
34
+ exports.HotWithdrawalNotFoundError = require_error$1.HotWithdrawalNotFoundError;
35
+ exports.HotWithdrawalPendingError = require_error$1.HotWithdrawalPendingError;
33
36
  Object.defineProperty(exports, 'HttpRequestError', {
34
37
  enumerable: true,
35
38
  get: function () {
@@ -42,12 +45,12 @@ Object.defineProperty(exports, 'IntentSettlementError', {
42
45
  return __defuse_protocol_internal_utils.IntentSettlementError;
43
46
  }
44
47
  });
45
- exports.IntentsNearOmniAvailableBalanceTooLowError = require_error$1.IntentsNearOmniAvailableBalanceTooLowError;
48
+ exports.IntentsNearOmniAvailableBalanceTooLowError = require_error$2.IntentsNearOmniAvailableBalanceTooLowError;
46
49
  exports.IntentsSDK = require_sdk.IntentsSDK;
47
50
  exports.MinWithdrawalAmountError = require_errors.MinWithdrawalAmountError;
48
- exports.OmniTokenNormalisationCheckError = require_error$1.OmniTokenNormalisationCheckError;
49
- exports.OmniTransferDestinationChainHashNotFoundError = require_error$1.OmniTransferDestinationChainHashNotFoundError;
50
- exports.OmniTransferNotFoundError = require_error$1.OmniTransferNotFoundError;
51
+ exports.OmniTokenNormalisationCheckError = require_error$2.OmniTokenNormalisationCheckError;
52
+ exports.OmniTransferDestinationChainHashNotFoundError = require_error$2.OmniTransferDestinationChainHashNotFoundError;
53
+ exports.OmniTransferNotFoundError = require_error$2.OmniTransferNotFoundError;
51
54
  Object.defineProperty(exports, 'PoaWithdrawalInvariantError', {
52
55
  enumerable: true,
53
56
  get: function () {
@@ -91,10 +94,16 @@ Object.defineProperty(exports, 'TimeoutError', {
91
94
  return __defuse_protocol_internal_utils.TimeoutError;
92
95
  }
93
96
  });
94
- exports.TokenNotFoundInDestinationChainError = require_error$1.TokenNotFoundInDestinationChainError;
97
+ exports.TokenNotFoundInDestinationChainError = require_error$2.TokenNotFoundInDestinationChainError;
95
98
  exports.TrustlineNotFoundError = require_errors.TrustlineNotFoundError;
96
99
  exports.UnsupportedAssetIdError = require_errors.UnsupportedAssetIdError;
97
100
  exports.UnsupportedDestinationMemoError = require_errors.UnsupportedDestinationMemoError;
101
+ Object.defineProperty(exports, 'VersionedNonceBuilder', {
102
+ enumerable: true,
103
+ get: function () {
104
+ return require_expirable_nonce.VersionedNonceBuilder;
105
+ }
106
+ });
98
107
  exports.createDefaultRoute = require_route_config_factory.createDefaultRoute;
99
108
  exports.createHotBridgeRoute = require_route_config_factory.createHotBridgeRoute;
100
109
  exports.createIntentSignerNEP413 = require_factories.createIntentSignerNEP413;
package/dist/index.d.cts CHANGED
@@ -1,5 +1,6 @@
1
1
  import { BridgeNameEnum, BridgeNameEnumValues } from "./src/constants/bridge-name-enum.cjs";
2
2
  import { RouteEnum, RouteEnumValues } from "./src/constants/route-enum.cjs";
3
+ import { VersionedNonceBuilder } from "./src/intents/expirable-nonce.cjs";
3
4
  import { IntentPayload, IntentPayloadFactory, IntentPrimitive, IntentRelayParamsFactory, MultiPayload } from "./src/intents/shared-types.cjs";
4
5
  import { IIntentSigner } from "./src/intents/interfaces/intent-signer.cjs";
5
6
  import { OnBeforePublishIntentHook } from "./src/intents/intent-executer-impl/intent-executer.cjs";
@@ -9,7 +10,8 @@ import { IntentsSDK, IntentsSDKConfig } from "./src/sdk.cjs";
9
10
  import { createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem } from "./src/intents/intent-signer-impl/factories.cjs";
10
11
  import { createDefaultRoute, createHotBridgeRoute, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute } from "./src/lib/route-config-factory.cjs";
11
12
  import { FeeExceedsAmountError, FeeExceedsAmountErrorType, MinWithdrawalAmountError, MinWithdrawalAmountErrorType, TrustlineNotFoundError, TrustlineNotFoundErrorType, UnsupportedAssetIdError, UnsupportedAssetIdErrorType, UnsupportedDestinationMemoError, UnsupportedDestinationMemoErrorType } from "./src/classes/errors.cjs";
13
+ import { DestinationExplicitNearAccountDoesntExistError, DestinationExplicitNearAccountDoesntExistErrorType } from "./src/bridges/direct-bridge/error.cjs";
12
14
  import { HotWithdrawalCancelledError, HotWithdrawalCancelledErrorType, HotWithdrawalNotFoundError, HotWithdrawalNotFoundErrorType, HotWithdrawalPendingError, HotWithdrawalPendingErrorType } from "./src/bridges/hot-bridge/error.cjs";
13
15
  import { FailedToFetchFeeError, FailedToFetchFeeErrorType, IntentsNearOmniAvailableBalanceTooLowError, IntentsNearOmniAvailableBalanceTooLowErrorType, OmniTokenNormalisationCheckError, OmniTokenNormalisationCheckErrorType, OmniTransferDestinationChainHashNotFoundError, OmniTransferDestinationChainHashNotFoundErrorType, OmniTransferNotFoundError, OmniTransferNotFoundErrorType, TokenNotFoundInDestinationChainError, TokenNotFoundInDestinationChainErrorType } from "./src/bridges/omni-bridge/error.cjs";
14
16
  import { AssertionError, AssertionErrorType, BaseError, BaseErrorType, HttpRequestError, HttpRequestErrorType, ILogger, IntentSettlementError, IntentSettlementErrorType, NearIntentsEnv, PoaWithdrawalInvariantError, PoaWithdrawalInvariantErrorType, PoaWithdrawalNotFoundError, PoaWithdrawalNotFoundErrorType, PoaWithdrawalPendingError, PoaWithdrawalPendingErrorType, QuoteError, QuoteErrorType, RelayPublishError, RelayPublishErrorType, RetryOptions, RpcRequestError, RpcRequestErrorType, TimeoutError, TimeoutErrorType } from "@defuse-protocol/internal-utils";
15
- export { AssertionError, type AssertionErrorType, BaseError, type BaseErrorType, type BatchWithdrawalResult, BridgeNameEnum, type BridgeNameEnumValues, type Chain, Chains, FailedToFetchFeeError, type FailedToFetchFeeErrorType, type FeeEstimation, FeeExceedsAmountError, type FeeExceedsAmountErrorType, type HotBridgeRouteConfig, HotWithdrawalCancelledError, type HotWithdrawalCancelledErrorType, HotWithdrawalNotFoundError, type HotWithdrawalNotFoundErrorType, HotWithdrawalPendingError, type HotWithdrawalPendingErrorType, HttpRequestError, type HttpRequestErrorType, type IIntentSigner, type ILogger, type IntentPayload, type IntentPayloadFactory, type IntentPrimitive, type IntentPublishResult, type IntentRelayParamsFactory, IntentSettlementError, type IntentSettlementErrorType, type IntentSettlementStatus, IntentsNearOmniAvailableBalanceTooLowError, type IntentsNearOmniAvailableBalanceTooLowErrorType, IntentsSDK, type IntentsSDKConfig, type InternalTransferRouteConfig, MinWithdrawalAmountError, type MinWithdrawalAmountErrorType, type MultiPayload, type NearIntentsEnv, type NearTxInfo, type NearWithdrawalRouteConfig, type OmniBridgeRouteConfig, OmniTokenNormalisationCheckError, type OmniTokenNormalisationCheckErrorType, OmniTransferDestinationChainHashNotFoundError, type OmniTransferDestinationChainHashNotFoundErrorType, OmniTransferNotFoundError, type OmniTransferNotFoundErrorType, type OnBeforePublishIntentHook, type ParsedAssetInfo, type PoaBridgeRouteConfig, PoaWithdrawalInvariantError, type PoaWithdrawalInvariantErrorType, PoaWithdrawalNotFoundError, type PoaWithdrawalNotFoundErrorType, PoaWithdrawalPendingError, type PoaWithdrawalPendingErrorType, type ProcessWithdrawalArgs, QuoteError, type QuoteErrorType, RelayPublishError, type RelayPublishErrorType, type RetryOptions, type RouteConfig, RouteEnum, type RouteEnumValues, RpcRequestError, type RpcRequestErrorType, type SignAndSendArgs, type SignAndSendWithdrawalArgs, type SignedIntentsComposition, TimeoutError, type TimeoutErrorType, TokenNotFoundInDestinationChainError, type TokenNotFoundInDestinationChainErrorType, TrustlineNotFoundError, type TrustlineNotFoundErrorType, type TxInfo, type TxNoInfo, UnsupportedAssetIdError, type UnsupportedAssetIdErrorType, UnsupportedDestinationMemoError, type UnsupportedDestinationMemoErrorType, type VirtualChainRouteConfig, type WithdrawalIdentifier, type WithdrawalParams, type WithdrawalResult, createDefaultRoute, createHotBridgeRoute, createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute };
17
+ export { AssertionError, type AssertionErrorType, BaseError, type BaseErrorType, type BatchWithdrawalResult, BridgeNameEnum, type BridgeNameEnumValues, type Chain, Chains, DestinationExplicitNearAccountDoesntExistError, type DestinationExplicitNearAccountDoesntExistErrorType, FailedToFetchFeeError, type FailedToFetchFeeErrorType, type FeeEstimation, FeeExceedsAmountError, type FeeExceedsAmountErrorType, type HotBridgeRouteConfig, HotWithdrawalCancelledError, type HotWithdrawalCancelledErrorType, HotWithdrawalNotFoundError, type HotWithdrawalNotFoundErrorType, HotWithdrawalPendingError, type HotWithdrawalPendingErrorType, HttpRequestError, type HttpRequestErrorType, type IIntentSigner, type ILogger, type IntentPayload, type IntentPayloadFactory, type IntentPrimitive, type IntentPublishResult, type IntentRelayParamsFactory, IntentSettlementError, type IntentSettlementErrorType, type IntentSettlementStatus, IntentsNearOmniAvailableBalanceTooLowError, type IntentsNearOmniAvailableBalanceTooLowErrorType, IntentsSDK, type IntentsSDKConfig, type InternalTransferRouteConfig, MinWithdrawalAmountError, type MinWithdrawalAmountErrorType, type MultiPayload, type NearIntentsEnv, type NearTxInfo, type NearWithdrawalRouteConfig, type OmniBridgeRouteConfig, OmniTokenNormalisationCheckError, type OmniTokenNormalisationCheckErrorType, OmniTransferDestinationChainHashNotFoundError, type OmniTransferDestinationChainHashNotFoundErrorType, OmniTransferNotFoundError, type OmniTransferNotFoundErrorType, type OnBeforePublishIntentHook, type ParsedAssetInfo, type PoaBridgeRouteConfig, PoaWithdrawalInvariantError, type PoaWithdrawalInvariantErrorType, PoaWithdrawalNotFoundError, type PoaWithdrawalNotFoundErrorType, PoaWithdrawalPendingError, type PoaWithdrawalPendingErrorType, type ProcessWithdrawalArgs, QuoteError, type QuoteErrorType, RelayPublishError, type RelayPublishErrorType, type RetryOptions, type RouteConfig, RouteEnum, type RouteEnumValues, RpcRequestError, type RpcRequestErrorType, type SignAndSendArgs, type SignAndSendWithdrawalArgs, type SignedIntentsComposition, TimeoutError, type TimeoutErrorType, TokenNotFoundInDestinationChainError, type TokenNotFoundInDestinationChainErrorType, TrustlineNotFoundError, type TrustlineNotFoundErrorType, type TxInfo, type TxNoInfo, UnsupportedAssetIdError, type UnsupportedAssetIdErrorType, UnsupportedDestinationMemoError, type UnsupportedDestinationMemoErrorType, VersionedNonceBuilder, type VirtualChainRouteConfig, type WithdrawalIdentifier, type WithdrawalParams, type WithdrawalResult, createDefaultRoute, createHotBridgeRoute, createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute };
package/dist/index.d.ts CHANGED
@@ -1,5 +1,6 @@
1
1
  import { BridgeNameEnum, BridgeNameEnumValues } from "./src/constants/bridge-name-enum.js";
2
2
  import { RouteEnum, RouteEnumValues } from "./src/constants/route-enum.js";
3
+ import { VersionedNonceBuilder } from "./src/intents/expirable-nonce.js";
3
4
  import { IntentPayload, IntentPayloadFactory, IntentPrimitive, IntentRelayParamsFactory, MultiPayload } from "./src/intents/shared-types.js";
4
5
  import { IIntentSigner } from "./src/intents/interfaces/intent-signer.js";
5
6
  import { OnBeforePublishIntentHook } from "./src/intents/intent-executer-impl/intent-executer.js";
@@ -9,7 +10,8 @@ import { IntentsSDK, IntentsSDKConfig } from "./src/sdk.js";
9
10
  import { createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem } from "./src/intents/intent-signer-impl/factories.js";
10
11
  import { createDefaultRoute, createHotBridgeRoute, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute } from "./src/lib/route-config-factory.js";
11
12
  import { FeeExceedsAmountError, FeeExceedsAmountErrorType, MinWithdrawalAmountError, MinWithdrawalAmountErrorType, TrustlineNotFoundError, TrustlineNotFoundErrorType, UnsupportedAssetIdError, UnsupportedAssetIdErrorType, UnsupportedDestinationMemoError, UnsupportedDestinationMemoErrorType } from "./src/classes/errors.js";
13
+ import { DestinationExplicitNearAccountDoesntExistError, DestinationExplicitNearAccountDoesntExistErrorType } from "./src/bridges/direct-bridge/error.js";
12
14
  import { HotWithdrawalCancelledError, HotWithdrawalCancelledErrorType, HotWithdrawalNotFoundError, HotWithdrawalNotFoundErrorType, HotWithdrawalPendingError, HotWithdrawalPendingErrorType } from "./src/bridges/hot-bridge/error.js";
13
15
  import { FailedToFetchFeeError, FailedToFetchFeeErrorType, IntentsNearOmniAvailableBalanceTooLowError, IntentsNearOmniAvailableBalanceTooLowErrorType, OmniTokenNormalisationCheckError, OmniTokenNormalisationCheckErrorType, OmniTransferDestinationChainHashNotFoundError, OmniTransferDestinationChainHashNotFoundErrorType, OmniTransferNotFoundError, OmniTransferNotFoundErrorType, TokenNotFoundInDestinationChainError, TokenNotFoundInDestinationChainErrorType } from "./src/bridges/omni-bridge/error.js";
14
16
  import { AssertionError, AssertionErrorType, BaseError, BaseErrorType, HttpRequestError, HttpRequestErrorType, ILogger, IntentSettlementError, IntentSettlementErrorType, NearIntentsEnv, PoaWithdrawalInvariantError, PoaWithdrawalInvariantErrorType, PoaWithdrawalNotFoundError, PoaWithdrawalNotFoundErrorType, PoaWithdrawalPendingError, PoaWithdrawalPendingErrorType, QuoteError, QuoteErrorType, RelayPublishError, RelayPublishErrorType, RetryOptions, RpcRequestError, RpcRequestErrorType, TimeoutError, TimeoutErrorType } from "@defuse-protocol/internal-utils";
15
- export { AssertionError, type AssertionErrorType, BaseError, type BaseErrorType, type BatchWithdrawalResult, BridgeNameEnum, type BridgeNameEnumValues, type Chain, Chains, FailedToFetchFeeError, type FailedToFetchFeeErrorType, type FeeEstimation, FeeExceedsAmountError, type FeeExceedsAmountErrorType, type HotBridgeRouteConfig, HotWithdrawalCancelledError, type HotWithdrawalCancelledErrorType, HotWithdrawalNotFoundError, type HotWithdrawalNotFoundErrorType, HotWithdrawalPendingError, type HotWithdrawalPendingErrorType, HttpRequestError, type HttpRequestErrorType, type IIntentSigner, type ILogger, type IntentPayload, type IntentPayloadFactory, type IntentPrimitive, type IntentPublishResult, type IntentRelayParamsFactory, IntentSettlementError, type IntentSettlementErrorType, type IntentSettlementStatus, IntentsNearOmniAvailableBalanceTooLowError, type IntentsNearOmniAvailableBalanceTooLowErrorType, IntentsSDK, type IntentsSDKConfig, type InternalTransferRouteConfig, MinWithdrawalAmountError, type MinWithdrawalAmountErrorType, type MultiPayload, type NearIntentsEnv, type NearTxInfo, type NearWithdrawalRouteConfig, type OmniBridgeRouteConfig, OmniTokenNormalisationCheckError, type OmniTokenNormalisationCheckErrorType, OmniTransferDestinationChainHashNotFoundError, type OmniTransferDestinationChainHashNotFoundErrorType, OmniTransferNotFoundError, type OmniTransferNotFoundErrorType, type OnBeforePublishIntentHook, type ParsedAssetInfo, type PoaBridgeRouteConfig, PoaWithdrawalInvariantError, type PoaWithdrawalInvariantErrorType, PoaWithdrawalNotFoundError, type PoaWithdrawalNotFoundErrorType, PoaWithdrawalPendingError, type PoaWithdrawalPendingErrorType, type ProcessWithdrawalArgs, QuoteError, type QuoteErrorType, RelayPublishError, type RelayPublishErrorType, type RetryOptions, type RouteConfig, RouteEnum, type RouteEnumValues, RpcRequestError, type RpcRequestErrorType, type SignAndSendArgs, type SignAndSendWithdrawalArgs, type SignedIntentsComposition, TimeoutError, type TimeoutErrorType, TokenNotFoundInDestinationChainError, type TokenNotFoundInDestinationChainErrorType, TrustlineNotFoundError, type TrustlineNotFoundErrorType, type TxInfo, type TxNoInfo, UnsupportedAssetIdError, type UnsupportedAssetIdErrorType, UnsupportedDestinationMemoError, type UnsupportedDestinationMemoErrorType, type VirtualChainRouteConfig, type WithdrawalIdentifier, type WithdrawalParams, type WithdrawalResult, createDefaultRoute, createHotBridgeRoute, createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute };
17
+ export { AssertionError, type AssertionErrorType, BaseError, type BaseErrorType, type BatchWithdrawalResult, BridgeNameEnum, type BridgeNameEnumValues, type Chain, Chains, DestinationExplicitNearAccountDoesntExistError, type DestinationExplicitNearAccountDoesntExistErrorType, FailedToFetchFeeError, type FailedToFetchFeeErrorType, type FeeEstimation, FeeExceedsAmountError, type FeeExceedsAmountErrorType, type HotBridgeRouteConfig, HotWithdrawalCancelledError, type HotWithdrawalCancelledErrorType, HotWithdrawalNotFoundError, type HotWithdrawalNotFoundErrorType, HotWithdrawalPendingError, type HotWithdrawalPendingErrorType, HttpRequestError, type HttpRequestErrorType, type IIntentSigner, type ILogger, type IntentPayload, type IntentPayloadFactory, type IntentPrimitive, type IntentPublishResult, type IntentRelayParamsFactory, IntentSettlementError, type IntentSettlementErrorType, type IntentSettlementStatus, IntentsNearOmniAvailableBalanceTooLowError, type IntentsNearOmniAvailableBalanceTooLowErrorType, IntentsSDK, type IntentsSDKConfig, type InternalTransferRouteConfig, MinWithdrawalAmountError, type MinWithdrawalAmountErrorType, type MultiPayload, type NearIntentsEnv, type NearTxInfo, type NearWithdrawalRouteConfig, type OmniBridgeRouteConfig, OmniTokenNormalisationCheckError, type OmniTokenNormalisationCheckErrorType, OmniTransferDestinationChainHashNotFoundError, type OmniTransferDestinationChainHashNotFoundErrorType, OmniTransferNotFoundError, type OmniTransferNotFoundErrorType, type OnBeforePublishIntentHook, type ParsedAssetInfo, type PoaBridgeRouteConfig, PoaWithdrawalInvariantError, type PoaWithdrawalInvariantErrorType, PoaWithdrawalNotFoundError, type PoaWithdrawalNotFoundErrorType, PoaWithdrawalPendingError, type PoaWithdrawalPendingErrorType, type ProcessWithdrawalArgs, QuoteError, type QuoteErrorType, RelayPublishError, type RelayPublishErrorType, type RetryOptions, type RouteConfig, RouteEnum, type RouteEnumValues, RpcRequestError, type RpcRequestErrorType, type SignAndSendArgs, type SignAndSendWithdrawalArgs, type SignedIntentsComposition, TimeoutError, type TimeoutErrorType, TokenNotFoundInDestinationChainError, type TokenNotFoundInDestinationChainErrorType, TrustlineNotFoundError, type TrustlineNotFoundErrorType, type TxInfo, type TxNoInfo, UnsupportedAssetIdError, type UnsupportedAssetIdErrorType, UnsupportedDestinationMemoError, type UnsupportedDestinationMemoErrorType, VersionedNonceBuilder, type VirtualChainRouteConfig, type WithdrawalIdentifier, type WithdrawalParams, type WithdrawalResult, createDefaultRoute, createHotBridgeRoute, createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute };
package/dist/index.js CHANGED
@@ -2,11 +2,13 @@ import { RouteEnum } from "./src/constants/route-enum.js";
2
2
  import { FeeExceedsAmountError, MinWithdrawalAmountError, TrustlineNotFoundError, UnsupportedAssetIdError, UnsupportedDestinationMemoError } from "./src/classes/errors.js";
3
3
  import { Chains } from "./src/lib/caip2.js";
4
4
  import { BridgeNameEnum } from "./src/constants/bridge-name-enum.js";
5
+ import { DestinationExplicitNearAccountDoesntExistError } from "./src/bridges/direct-bridge/error.js";
5
6
  import { HotWithdrawalCancelledError, HotWithdrawalNotFoundError, HotWithdrawalPendingError } from "./src/bridges/hot-bridge/error.js";
6
7
  import { FailedToFetchFeeError, IntentsNearOmniAvailableBalanceTooLowError, OmniTokenNormalisationCheckError, OmniTransferDestinationChainHashNotFoundError, OmniTransferNotFoundError, TokenNotFoundInDestinationChainError } from "./src/bridges/omni-bridge/error.js";
8
+ import { VersionedNonceBuilder } from "./src/intents/expirable-nonce.js";
7
9
  import { createDefaultRoute, createHotBridgeRoute, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute } from "./src/lib/route-config-factory.js";
8
10
  import { IntentsSDK } from "./src/sdk.js";
9
11
  import { createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem } from "./src/intents/intent-signer-impl/factories.js";
10
12
  import { AssertionError, BaseError, HttpRequestError, IntentSettlementError, PoaWithdrawalInvariantError, PoaWithdrawalNotFoundError, PoaWithdrawalPendingError, QuoteError, RelayPublishError, RpcRequestError, TimeoutError } from "@defuse-protocol/internal-utils";
11
13
 
12
- export { AssertionError, BaseError, BridgeNameEnum, Chains, FailedToFetchFeeError, FeeExceedsAmountError, HotWithdrawalCancelledError, HotWithdrawalNotFoundError, HotWithdrawalPendingError, HttpRequestError, IntentSettlementError, IntentsNearOmniAvailableBalanceTooLowError, IntentsSDK, MinWithdrawalAmountError, OmniTokenNormalisationCheckError, OmniTransferDestinationChainHashNotFoundError, OmniTransferNotFoundError, PoaWithdrawalInvariantError, PoaWithdrawalNotFoundError, PoaWithdrawalPendingError, QuoteError, RelayPublishError, RouteEnum, RpcRequestError, TimeoutError, TokenNotFoundInDestinationChainError, TrustlineNotFoundError, UnsupportedAssetIdError, UnsupportedDestinationMemoError, createDefaultRoute, createHotBridgeRoute, createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute };
14
+ export { AssertionError, BaseError, BridgeNameEnum, Chains, DestinationExplicitNearAccountDoesntExistError, FailedToFetchFeeError, FeeExceedsAmountError, HotWithdrawalCancelledError, HotWithdrawalNotFoundError, HotWithdrawalPendingError, HttpRequestError, IntentSettlementError, IntentsNearOmniAvailableBalanceTooLowError, IntentsSDK, MinWithdrawalAmountError, OmniTokenNormalisationCheckError, OmniTransferDestinationChainHashNotFoundError, OmniTransferNotFoundError, PoaWithdrawalInvariantError, PoaWithdrawalNotFoundError, PoaWithdrawalPendingError, QuoteError, RelayPublishError, RouteEnum, RpcRequestError, TimeoutError, TokenNotFoundInDestinationChainError, TrustlineNotFoundError, UnsupportedAssetIdError, UnsupportedDestinationMemoError, VersionedNonceBuilder, createDefaultRoute, createHotBridgeRoute, createIntentSignerNEP413, createIntentSignerNearKeyPair, createIntentSignerViem, createInternalTransferRoute, createNearWithdrawalRoute, createOmniBridgeRoute, createPoaBridgeRoute, createVirtualChainRoute };
@@ -3,6 +3,8 @@ const require_route_enum = require('../../constants/route-enum.cjs');
3
3
  const require_direct_bridge_constants = require('./direct-bridge-constants.cjs');
4
4
  let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
5
5
  __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
6
+ let near_api_js_lib_providers = require("near-api-js/lib/providers");
7
+ near_api_js_lib_providers = require_rolldown_runtime.__toESM(near_api_js_lib_providers);
6
8
 
7
9
  //#region src/bridges/direct-bridge/direct-bridge-utils.ts
8
10
  function createWithdrawIntentPrimitive(params) {
@@ -25,7 +27,21 @@ function createWithdrawIntentPrimitive(params) {
25
27
  function withdrawalParamsInvariant(params) {
26
28
  (0, __defuse_protocol_internal_utils.assert)(!params.routeConfig ? true : params.routeConfig.route === require_route_enum.RouteEnum.NearWithdrawal, "Bridge is not direct");
27
29
  }
30
+ async function accountExistsInNEAR(provider, accountId) {
31
+ try {
32
+ await (0, __defuse_protocol_internal_utils.unwrapNearFailoverRpcProvider)(provider).query({
33
+ request_type: "view_account",
34
+ account_id: accountId,
35
+ finality: "final"
36
+ });
37
+ return true;
38
+ } catch (error) {
39
+ if (error instanceof near_api_js_lib_providers.TypedError && error.type === "AccountDoesNotExist") return false;
40
+ throw error;
41
+ }
42
+ }
28
43
 
29
44
  //#endregion
45
+ exports.accountExistsInNEAR = accountExistsInNEAR;
30
46
  exports.createWithdrawIntentPrimitive = createWithdrawIntentPrimitive;
31
47
  exports.withdrawalParamsInvariant = withdrawalParamsInvariant;
@@ -1,6 +1,7 @@
1
1
  import { RouteEnum } from "../../constants/route-enum.js";
2
2
  import { NEAR_NATIVE_ASSET_ID } from "./direct-bridge-constants.js";
3
- import { assert, utils } from "@defuse-protocol/internal-utils";
3
+ import { assert, unwrapNearFailoverRpcProvider, utils } from "@defuse-protocol/internal-utils";
4
+ import { TypedError } from "near-api-js/lib/providers";
4
5
 
5
6
  //#region src/bridges/direct-bridge/direct-bridge-utils.ts
6
7
  function createWithdrawIntentPrimitive(params) {
@@ -23,6 +24,19 @@ function createWithdrawIntentPrimitive(params) {
23
24
  function withdrawalParamsInvariant(params) {
24
25
  assert(!params.routeConfig ? true : params.routeConfig.route === RouteEnum.NearWithdrawal, "Bridge is not direct");
25
26
  }
27
+ async function accountExistsInNEAR(provider, accountId) {
28
+ try {
29
+ await unwrapNearFailoverRpcProvider(provider).query({
30
+ request_type: "view_account",
31
+ account_id: accountId,
32
+ finality: "final"
33
+ });
34
+ return true;
35
+ } catch (error) {
36
+ if (error instanceof TypedError && error.type === "AccountDoesNotExist") return false;
37
+ throw error;
38
+ }
39
+ }
26
40
 
27
41
  //#endregion
28
- export { createWithdrawIntentPrimitive, withdrawalParamsInvariant };
42
+ export { accountExistsInNEAR, createWithdrawIntentPrimitive, withdrawalParamsInvariant };
@@ -8,12 +8,23 @@ const require_validateAddress = require('../../lib/validateAddress.cjs');
8
8
  const require_bridge_name_enum = require('../../constants/bridge-name-enum.cjs');
9
9
  const require_direct_bridge_constants = require('./direct-bridge-constants.cjs');
10
10
  const require_direct_bridge_utils = require('./direct-bridge-utils.cjs');
11
+ const require_error = require('./error.cjs');
11
12
  let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
12
13
  __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
14
+ let lru_cache = require("lru-cache");
15
+ lru_cache = require_rolldown_runtime.__toESM(lru_cache);
13
16
 
14
17
  //#region src/bridges/direct-bridge/direct-bridge.ts
15
18
  var DirectBridge = class {
16
19
  constructor({ env, nearProvider, solverRelayApiKey }) {
20
+ this.storageDepositCache = new lru_cache.LRUCache({
21
+ max: 100,
22
+ ttl: 36e5
23
+ });
24
+ this.accountExistenceCache = new lru_cache.LRUCache({
25
+ max: 100,
26
+ ttl: 36e5
27
+ });
17
28
  this.env = env;
18
29
  this.nearProvider = nearProvider;
19
30
  this.solverRelayApiKey = solverRelayApiKey;
@@ -62,6 +73,7 @@ var DirectBridge = class {
62
73
  */
63
74
  async validateWithdrawal(args) {
64
75
  if (require_validateAddress.validateAddress(args.destinationAddress, require_caip2.Chains.Near) === false) throw new require_errors.InvalidDestinationAddressForWithdrawalError(args.destinationAddress, require_caip2.Chains.Near);
76
+ if (__defuse_protocol_internal_utils.utils.isImplicitAccount(args.destinationAddress) === false && await this.getCachedAccountExistenceCheck(args.destinationAddress) === false) throw new require_error.DestinationExplicitNearAccountDoesntExistError(args.destinationAddress);
65
77
  }
66
78
  async estimateWithdrawalFee(args) {
67
79
  require_direct_bridge_utils.withdrawalParamsInvariant(args.withdrawalParams);
@@ -71,14 +83,7 @@ var DirectBridge = class {
71
83
  amount: 0n,
72
84
  quote: null
73
85
  };
74
- const [minStorageBalance, userStorageBalance] = await Promise.all([(0, __defuse_protocol_internal_utils.getNearNep141MinStorageBalance)({
75
- contractId: tokenAccountId,
76
- nearProvider: this.nearProvider
77
- }), (0, __defuse_protocol_internal_utils.getNearNep141StorageBalance)({
78
- contractId: tokenAccountId,
79
- accountId: args.withdrawalParams.destinationAddress,
80
- nearProvider: this.nearProvider
81
- })]);
86
+ const [minStorageBalance, userStorageBalance] = await this.getCachedStorageDepositValue(tokenAccountId, args.withdrawalParams.destinationAddress);
82
87
  if (minStorageBalance <= userStorageBalance) return {
83
88
  amount: 0n,
84
89
  quote: null
@@ -99,6 +104,34 @@ var DirectBridge = class {
99
104
  quote: feeQuote
100
105
  };
101
106
  }
107
+ /**
108
+ * Gets storage deposit for a token to avoid frequent RPC calls.
109
+ */
110
+ async getCachedStorageDepositValue(contractId, accountId) {
111
+ const key = `${contractId}${accountId}`;
112
+ const cached = this.storageDepositCache.get(key);
113
+ if (cached !== void 0) return cached;
114
+ const result = await Promise.all([(0, __defuse_protocol_internal_utils.getNearNep141MinStorageBalance)({
115
+ contractId,
116
+ nearProvider: this.nearProvider
117
+ }), (0, __defuse_protocol_internal_utils.getNearNep141StorageBalance)({
118
+ contractId,
119
+ accountId,
120
+ nearProvider: this.nearProvider
121
+ })]);
122
+ if (result[1] >= result[0]) this.storageDepositCache.set(key, result);
123
+ return result;
124
+ }
125
+ /**
126
+ * Checks account existence to avoid frequent RPC calls.
127
+ */
128
+ async getCachedAccountExistenceCheck(accountId) {
129
+ const cached = this.accountExistenceCache.get(accountId);
130
+ if (cached !== void 0) return cached;
131
+ const exist = await require_direct_bridge_utils.accountExistsInNEAR(this.nearProvider, accountId);
132
+ if (exist) this.accountExistenceCache.set(accountId, exist);
133
+ return exist;
134
+ }
102
135
  async waitForWithdrawalCompletion(args) {
103
136
  return { hash: args.tx.hash };
104
137
  }
@@ -6,12 +6,22 @@ import { Chains } from "../../lib/caip2.js";
6
6
  import { validateAddress } from "../../lib/validateAddress.js";
7
7
  import { BridgeNameEnum } from "../../constants/bridge-name-enum.js";
8
8
  import { NEAR_NATIVE_ASSET_ID } from "./direct-bridge-constants.js";
9
- import { createWithdrawIntentPrimitive, withdrawalParamsInvariant } from "./direct-bridge-utils.js";
9
+ import { accountExistsInNEAR, createWithdrawIntentPrimitive, withdrawalParamsInvariant } from "./direct-bridge-utils.js";
10
+ import { DestinationExplicitNearAccountDoesntExistError } from "./error.js";
10
11
  import { assert, getNearNep141MinStorageBalance, getNearNep141StorageBalance, utils } from "@defuse-protocol/internal-utils";
12
+ import { LRUCache } from "lru-cache";
11
13
 
12
14
  //#region src/bridges/direct-bridge/direct-bridge.ts
13
15
  var DirectBridge = class {
14
16
  constructor({ env, nearProvider, solverRelayApiKey }) {
17
+ this.storageDepositCache = new LRUCache({
18
+ max: 100,
19
+ ttl: 36e5
20
+ });
21
+ this.accountExistenceCache = new LRUCache({
22
+ max: 100,
23
+ ttl: 36e5
24
+ });
15
25
  this.env = env;
16
26
  this.nearProvider = nearProvider;
17
27
  this.solverRelayApiKey = solverRelayApiKey;
@@ -60,6 +70,7 @@ var DirectBridge = class {
60
70
  */
61
71
  async validateWithdrawal(args) {
62
72
  if (validateAddress(args.destinationAddress, Chains.Near) === false) throw new InvalidDestinationAddressForWithdrawalError(args.destinationAddress, Chains.Near);
73
+ if (utils.isImplicitAccount(args.destinationAddress) === false && await this.getCachedAccountExistenceCheck(args.destinationAddress) === false) throw new DestinationExplicitNearAccountDoesntExistError(args.destinationAddress);
63
74
  }
64
75
  async estimateWithdrawalFee(args) {
65
76
  withdrawalParamsInvariant(args.withdrawalParams);
@@ -69,14 +80,7 @@ var DirectBridge = class {
69
80
  amount: 0n,
70
81
  quote: null
71
82
  };
72
- const [minStorageBalance, userStorageBalance] = await Promise.all([getNearNep141MinStorageBalance({
73
- contractId: tokenAccountId,
74
- nearProvider: this.nearProvider
75
- }), getNearNep141StorageBalance({
76
- contractId: tokenAccountId,
77
- accountId: args.withdrawalParams.destinationAddress,
78
- nearProvider: this.nearProvider
79
- })]);
83
+ const [minStorageBalance, userStorageBalance] = await this.getCachedStorageDepositValue(tokenAccountId, args.withdrawalParams.destinationAddress);
80
84
  if (minStorageBalance <= userStorageBalance) return {
81
85
  amount: 0n,
82
86
  quote: null
@@ -97,6 +101,34 @@ var DirectBridge = class {
97
101
  quote: feeQuote
98
102
  };
99
103
  }
104
+ /**
105
+ * Gets storage deposit for a token to avoid frequent RPC calls.
106
+ */
107
+ async getCachedStorageDepositValue(contractId, accountId) {
108
+ const key = `${contractId}${accountId}`;
109
+ const cached = this.storageDepositCache.get(key);
110
+ if (cached !== void 0) return cached;
111
+ const result = await Promise.all([getNearNep141MinStorageBalance({
112
+ contractId,
113
+ nearProvider: this.nearProvider
114
+ }), getNearNep141StorageBalance({
115
+ contractId,
116
+ accountId,
117
+ nearProvider: this.nearProvider
118
+ })]);
119
+ if (result[1] >= result[0]) this.storageDepositCache.set(key, result);
120
+ return result;
121
+ }
122
+ /**
123
+ * Checks account existence to avoid frequent RPC calls.
124
+ */
125
+ async getCachedAccountExistenceCheck(accountId) {
126
+ const cached = this.accountExistenceCache.get(accountId);
127
+ if (cached !== void 0) return cached;
128
+ const exist = await accountExistsInNEAR(this.nearProvider, accountId);
129
+ if (exist) this.accountExistenceCache.set(accountId, exist);
130
+ return exist;
131
+ }
100
132
  async waitForWithdrawalCompletion(args) {
101
133
  return { hash: args.tx.hash };
102
134
  }
@@ -0,0 +1,17 @@
1
+ const require_rolldown_runtime = require('../../../_virtual/rolldown_runtime.cjs');
2
+ let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
3
+ __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
4
+
5
+ //#region src/bridges/direct-bridge/error.ts
6
+ var DestinationExplicitNearAccountDoesntExistError = class extends __defuse_protocol_internal_utils.BaseError {
7
+ constructor(accountId) {
8
+ super("Destination explicit NEAR account doesn't exist.", {
9
+ metaMessages: [`Account Id: ${accountId}`],
10
+ name: "DestinationExplicitNearAccountDoesntExistError"
11
+ });
12
+ this.accountId = accountId;
13
+ }
14
+ };
15
+
16
+ //#endregion
17
+ exports.DestinationExplicitNearAccountDoesntExistError = DestinationExplicitNearAccountDoesntExistError;
@@ -0,0 +1,12 @@
1
+ import { BaseError } from "@defuse-protocol/internal-utils";
2
+
3
+ //#region src/bridges/direct-bridge/error.d.ts
4
+ type DestinationExplicitNearAccountDoesntExistErrorType = DestinationExplicitNearAccountDoesntExistError & {
5
+ name: "DestinationExplicitNearAccountDoesntExistError";
6
+ };
7
+ declare class DestinationExplicitNearAccountDoesntExistError extends BaseError {
8
+ accountId: string;
9
+ constructor(accountId: string);
10
+ }
11
+ //#endregion
12
+ export { DestinationExplicitNearAccountDoesntExistError, DestinationExplicitNearAccountDoesntExistErrorType };
@@ -0,0 +1,12 @@
1
+ import { BaseError } from "@defuse-protocol/internal-utils";
2
+
3
+ //#region src/bridges/direct-bridge/error.d.ts
4
+ type DestinationExplicitNearAccountDoesntExistErrorType = DestinationExplicitNearAccountDoesntExistError & {
5
+ name: "DestinationExplicitNearAccountDoesntExistError";
6
+ };
7
+ declare class DestinationExplicitNearAccountDoesntExistError extends BaseError {
8
+ accountId: string;
9
+ constructor(accountId: string);
10
+ }
11
+ //#endregion
12
+ export { DestinationExplicitNearAccountDoesntExistError, DestinationExplicitNearAccountDoesntExistErrorType };
@@ -0,0 +1,15 @@
1
+ import { BaseError } from "@defuse-protocol/internal-utils";
2
+
3
+ //#region src/bridges/direct-bridge/error.ts
4
+ var DestinationExplicitNearAccountDoesntExistError = class extends BaseError {
5
+ constructor(accountId) {
6
+ super("Destination explicit NEAR account doesn't exist.", {
7
+ metaMessages: [`Account Id: ${accountId}`],
8
+ name: "DestinationExplicitNearAccountDoesntExistError"
9
+ });
10
+ this.accountId = accountId;
11
+ }
12
+ };
13
+
14
+ //#endregion
15
+ export { DestinationExplicitNearAccountDoesntExistError };
@@ -9,6 +9,7 @@ const require_bridge_name_enum = require('../../constants/bridge-name-enum.cjs')
9
9
  const require_error = require('./error.cjs');
10
10
  const require_hot_bridge_constants = require('./hot-bridge-constants.cjs');
11
11
  const require_hot_bridge_utils = require('./hot-bridge-utils.cjs');
12
+ const require_hex = require('../../lib/hex.cjs');
12
13
  let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
13
14
  __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
14
15
  let __hot_labs_omni_sdk = require("@hot-labs/omni-sdk");
@@ -130,7 +131,13 @@ var HotBridge = class {
130
131
  const status = await this.hotSdk.getGaslessWithdrawStatus(nonce.toString());
131
132
  if (status === require_hot_bridge_constants.HotWithdrawStatus.Canceled) throw new require_error.HotWithdrawalCancelledError(args.tx.hash, args.index);
132
133
  if (status === require_hot_bridge_constants.HotWithdrawStatus.Completed) return { hash: null };
133
- if (typeof status === "string") return { hash: "chain" in args.routeConfig && args.routeConfig.chain !== void 0 ? require_hot_bridge_utils.formatTxHash(status, args.routeConfig.chain) : status };
134
+ if (typeof status === "string") {
135
+ if (!require_hex.default(status)) {
136
+ args.logger?.warn("HOT Bridge incorrect destination tx hash detected", { value: status });
137
+ return { hash: null };
138
+ }
139
+ return { hash: "chain" in args.routeConfig && args.routeConfig.chain !== void 0 ? require_hot_bridge_utils.formatTxHash(status, args.routeConfig.chain) : status };
140
+ }
134
141
  throw new require_error.HotWithdrawalPendingError(args.tx.hash, args.index);
135
142
  }, {
136
143
  ...args.retryOptions ?? __defuse_protocol_internal_utils.RETRY_CONFIGS.TWO_MINS_GRADUAL,
@@ -8,6 +8,7 @@ import { BridgeNameEnum } from "../../constants/bridge-name-enum.js";
8
8
  import { HotWithdrawalCancelledError, HotWithdrawalNotFoundError, HotWithdrawalPendingError } from "./error.js";
9
9
  import { HotWithdrawStatus } from "./hot-bridge-constants.js";
10
10
  import { formatTxHash, getFeeAssetIdForChain, hotBlockchainInvariant, hotNetworkIdToCAIP2, toHotNetworkId } from "./hot-bridge-utils.js";
11
+ import isHex from "../../lib/hex.js";
11
12
  import { RETRY_CONFIGS, assert } from "@defuse-protocol/internal-utils";
12
13
  import { OMNI_HOT_V2, utils as utils$1 } from "@hot-labs/omni-sdk";
13
14
  import { retry } from "@lifeomic/attempt";
@@ -126,7 +127,13 @@ var HotBridge$1 = class {
126
127
  const status = await this.hotSdk.getGaslessWithdrawStatus(nonce.toString());
127
128
  if (status === HotWithdrawStatus.Canceled) throw new HotWithdrawalCancelledError(args.tx.hash, args.index);
128
129
  if (status === HotWithdrawStatus.Completed) return { hash: null };
129
- if (typeof status === "string") return { hash: "chain" in args.routeConfig && args.routeConfig.chain !== void 0 ? formatTxHash(status, args.routeConfig.chain) : status };
130
+ if (typeof status === "string") {
131
+ if (!isHex(status)) {
132
+ args.logger?.warn("HOT Bridge incorrect destination tx hash detected", { value: status });
133
+ return { hash: null };
134
+ }
135
+ return { hash: "chain" in args.routeConfig && args.routeConfig.chain !== void 0 ? formatTxHash(status, args.routeConfig.chain) : status };
136
+ }
130
137
  throw new HotWithdrawalPendingError(args.tx.hash, args.index);
131
138
  }, {
132
139
  ...args.retryOptions ?? RETRY_CONFIGS.TWO_MINS_GRADUAL,
@@ -10,14 +10,14 @@ const require_omni_bridge_constants = require('./omni-bridge-constants.cjs');
10
10
  const require_omni_bridge_utils = require('./omni-bridge-utils.cjs');
11
11
  let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
12
12
  __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
13
+ let lru_cache = require("lru-cache");
14
+ lru_cache = require_rolldown_runtime.__toESM(lru_cache);
13
15
  let __lifeomic_attempt = require("@lifeomic/attempt");
14
16
  __lifeomic_attempt = require_rolldown_runtime.__toESM(__lifeomic_attempt);
15
17
  let __isaacs_ttlcache = require("@isaacs/ttlcache");
16
18
  __isaacs_ttlcache = require_rolldown_runtime.__toESM(__isaacs_ttlcache);
17
19
  let omni_bridge_sdk = require("omni-bridge-sdk");
18
20
  omni_bridge_sdk = require_rolldown_runtime.__toESM(omni_bridge_sdk);
19
- let lru_cache = require("lru-cache");
20
- lru_cache = require_rolldown_runtime.__toESM(lru_cache);
21
21
 
22
22
  //#region src/bridges/omni-bridge/omni-bridge.ts
23
23
  var OmniBridge = class {
@@ -8,10 +8,10 @@ import { FailedToFetchFeeError, IntentsNearOmniAvailableBalanceTooLowError, Omni
8
8
  import { MIN_ALLOWED_STORAGE_BALANCE_FOR_INTENTS_NEAR, NEAR_NATIVE_ASSET_ID, OMNI_BRIDGE_CONTRACT } from "./omni-bridge-constants.js";
9
9
  import { caip2ToChainKind, chainKindToCaip2, createWithdrawIntentsPrimitive, getAccountOmniStorageBalance, getBridgedToken, getTokenDecimals, validateOmniToken } from "./omni-bridge-utils.js";
10
10
  import { RETRY_CONFIGS, assert, configsByEnvironment, getNearNep141MinStorageBalance, getNearNep141StorageBalance } from "@defuse-protocol/internal-utils";
11
+ import { LRUCache } from "lru-cache";
11
12
  import { retry } from "@lifeomic/attempt";
12
13
  import TTLCache from "@isaacs/ttlcache";
13
14
  import { ChainKind, OmniBridgeAPI, getChain, getMinimumTransferableAmount, isEvmChain, omniAddress, parseOriginChain, verifyTransferAmount } from "omni-bridge-sdk";
14
- import { LRUCache } from "lru-cache";
15
15
 
16
16
  //#region src/bridges/omni-bridge/omni-bridge.ts
17
17
  var OmniBridge = class {
@@ -0,0 +1,83 @@
1
+ const require_rolldown_runtime = require('../../_virtual/rolldown_runtime.cjs');
2
+ let __scure_base = require("@scure/base");
3
+ __scure_base = require_rolldown_runtime.__toESM(__scure_base);
4
+ let near_api_js_lib_utils_serialize = require("near-api-js/lib/utils/serialize");
5
+ near_api_js_lib_utils_serialize = require_rolldown_runtime.__toESM(near_api_js_lib_utils_serialize);
6
+
7
+ //#region src/intents/expirable-nonce.ts
8
+ const VERSIONED_MAGIC_PREFIX = new Uint8Array([
9
+ 86,
10
+ 40,
11
+ 246,
12
+ 198
13
+ ]);
14
+ const LATEST_VERSION = 0;
15
+ var SaltedNonce = class {
16
+ constructor(salt, inner) {
17
+ this.salt = salt;
18
+ this.inner = inner;
19
+ }
20
+ };
21
+ /**
22
+ * VersionedNonce class representing a versioned expirable nonce
23
+ *
24
+ * @property version The version of the nonce
25
+ * @property value The current value of nonce, it is unknown to allow for future version types
26
+ */
27
+ var VersionedNonce = class VersionedNonce {
28
+ constructor(version, value) {
29
+ this.version = version;
30
+ this.value = value;
31
+ }
32
+ static latest(saltedNonce) {
33
+ return new VersionedNonce(LATEST_VERSION, saltedNonce);
34
+ }
35
+ };
36
+ const SALTED_NONCE_BORSH_SCHEMA = { struct: {
37
+ salt: { array: {
38
+ type: "u8",
39
+ len: 4
40
+ } },
41
+ inner: { struct: {
42
+ deadline: "u64",
43
+ nonce: { array: {
44
+ type: "u8",
45
+ len: 15
46
+ } }
47
+ } }
48
+ } };
49
+ let VersionedNonceBuilder;
50
+ (function(_VersionedNonceBuilder) {
51
+ function encodeNonce(salt, deadline) {
52
+ const expirableNonce = {
53
+ deadline: BigInt(deadline.getTime()) * 1000000n,
54
+ nonce: crypto.getRandomValues(new Uint8Array(15))
55
+ };
56
+ const versionedNonce = VersionedNonce.latest(new SaltedNonce(salt, expirableNonce));
57
+ const borshBytes = (0, near_api_js_lib_utils_serialize.serialize)(SALTED_NONCE_BORSH_SCHEMA, versionedNonce.value);
58
+ const result = new Uint8Array(5 + borshBytes.length);
59
+ result.set(VERSIONED_MAGIC_PREFIX, 0);
60
+ result.set([versionedNonce.version], 4);
61
+ result.set(borshBytes, 5);
62
+ return __scure_base.base64.encode(result);
63
+ }
64
+ _VersionedNonceBuilder.encodeNonce = encodeNonce;
65
+ function decodeNonce(encoded) {
66
+ const bytes = __scure_base.base64.decode(encoded);
67
+ if (bytes.length !== 32) throw new Error("Nonce too short");
68
+ const prefix = bytes.slice(0, 4);
69
+ const version = bytes[4];
70
+ const borshData = bytes.slice(5);
71
+ if (!prefix.every((byte, i) => byte === VERSIONED_MAGIC_PREFIX[i])) throw new Error("Invalid magic prefix");
72
+ return new VersionedNonce(version, (0, near_api_js_lib_utils_serialize.deserialize)(SALTED_NONCE_BORSH_SCHEMA, borshData));
73
+ }
74
+ _VersionedNonceBuilder.decodeNonce = decodeNonce;
75
+ })(VersionedNonceBuilder || (VersionedNonceBuilder = {}));
76
+
77
+ //#endregion
78
+ Object.defineProperty(exports, 'VersionedNonceBuilder', {
79
+ enumerable: true,
80
+ get: function () {
81
+ return VersionedNonceBuilder;
82
+ }
83
+ });
@@ -0,0 +1,44 @@
1
+ //#region src/intents/expirable-nonce.d.ts
2
+
3
+ type Salt = Uint8Array;
4
+ declare class ExpirableNonce {
5
+ deadline: bigint;
6
+ nonce: Uint8Array;
7
+ constructor(deadline: bigint, nonce: Uint8Array);
8
+ }
9
+ declare class SaltedNonce {
10
+ salt: Salt;
11
+ inner: ExpirableNonce;
12
+ constructor(salt: Salt, inner: ExpirableNonce);
13
+ }
14
+ /**
15
+ * VersionedNonce class representing a versioned expirable nonce
16
+ *
17
+ * @property version The version of the nonce
18
+ * @property value The current value of nonce, it is unknown to allow for future version types
19
+ */
20
+ declare class VersionedNonce {
21
+ version: number;
22
+ value: unknown;
23
+ constructor(version: number, value: unknown);
24
+ static latest(saltedNonce: SaltedNonce): VersionedNonce;
25
+ }
26
+ declare namespace VersionedNonceBuilder {
27
+ /**
28
+ * Encodes a versioned expirable nonce with the given salt and deadline
29
+ *
30
+ * @param salt The salt to use for the nonce
31
+ * @param deadline The expiration deadline for the nonce
32
+ * @returns The encoded nonce as a base64 string
33
+ */
34
+ function encodeNonce(salt: Salt, deadline: Date): string;
35
+ /**
36
+ * Decodes a versioned expirable nonce from a base64-encoded string
37
+ *
38
+ * @param encoded The encoded nonce string
39
+ * @returns The decoded VersionedNonce object
40
+ */
41
+ function decodeNonce(encoded: string): VersionedNonce;
42
+ }
43
+ //#endregion
44
+ export { Salt, VersionedNonceBuilder };
@@ -0,0 +1,44 @@
1
+ //#region src/intents/expirable-nonce.d.ts
2
+
3
+ type Salt = Uint8Array;
4
+ declare class ExpirableNonce {
5
+ deadline: bigint;
6
+ nonce: Uint8Array;
7
+ constructor(deadline: bigint, nonce: Uint8Array);
8
+ }
9
+ declare class SaltedNonce {
10
+ salt: Salt;
11
+ inner: ExpirableNonce;
12
+ constructor(salt: Salt, inner: ExpirableNonce);
13
+ }
14
+ /**
15
+ * VersionedNonce class representing a versioned expirable nonce
16
+ *
17
+ * @property version The version of the nonce
18
+ * @property value The current value of nonce, it is unknown to allow for future version types
19
+ */
20
+ declare class VersionedNonce {
21
+ version: number;
22
+ value: unknown;
23
+ constructor(version: number, value: unknown);
24
+ static latest(saltedNonce: SaltedNonce): VersionedNonce;
25
+ }
26
+ declare namespace VersionedNonceBuilder {
27
+ /**
28
+ * Encodes a versioned expirable nonce with the given salt and deadline
29
+ *
30
+ * @param salt The salt to use for the nonce
31
+ * @param deadline The expiration deadline for the nonce
32
+ * @returns The encoded nonce as a base64 string
33
+ */
34
+ function encodeNonce(salt: Salt, deadline: Date): string;
35
+ /**
36
+ * Decodes a versioned expirable nonce from a base64-encoded string
37
+ *
38
+ * @param encoded The encoded nonce string
39
+ * @returns The decoded VersionedNonce object
40
+ */
41
+ function decodeNonce(encoded: string): VersionedNonce;
42
+ }
43
+ //#endregion
44
+ export { Salt, VersionedNonceBuilder };
@@ -0,0 +1,75 @@
1
+ import { base64 } from "@scure/base";
2
+ import { deserialize, serialize } from "near-api-js/lib/utils/serialize";
3
+
4
+ //#region src/intents/expirable-nonce.ts
5
+ const VERSIONED_MAGIC_PREFIX = new Uint8Array([
6
+ 86,
7
+ 40,
8
+ 246,
9
+ 198
10
+ ]);
11
+ const LATEST_VERSION = 0;
12
+ var SaltedNonce = class {
13
+ constructor(salt, inner) {
14
+ this.salt = salt;
15
+ this.inner = inner;
16
+ }
17
+ };
18
+ /**
19
+ * VersionedNonce class representing a versioned expirable nonce
20
+ *
21
+ * @property version The version of the nonce
22
+ * @property value The current value of nonce, it is unknown to allow for future version types
23
+ */
24
+ var VersionedNonce = class VersionedNonce {
25
+ constructor(version, value) {
26
+ this.version = version;
27
+ this.value = value;
28
+ }
29
+ static latest(saltedNonce) {
30
+ return new VersionedNonce(LATEST_VERSION, saltedNonce);
31
+ }
32
+ };
33
+ const SALTED_NONCE_BORSH_SCHEMA = { struct: {
34
+ salt: { array: {
35
+ type: "u8",
36
+ len: 4
37
+ } },
38
+ inner: { struct: {
39
+ deadline: "u64",
40
+ nonce: { array: {
41
+ type: "u8",
42
+ len: 15
43
+ } }
44
+ } }
45
+ } };
46
+ let VersionedNonceBuilder;
47
+ (function(_VersionedNonceBuilder) {
48
+ function encodeNonce(salt, deadline) {
49
+ const expirableNonce = {
50
+ deadline: BigInt(deadline.getTime()) * 1000000n,
51
+ nonce: crypto.getRandomValues(new Uint8Array(15))
52
+ };
53
+ const versionedNonce = VersionedNonce.latest(new SaltedNonce(salt, expirableNonce));
54
+ const borshBytes = serialize(SALTED_NONCE_BORSH_SCHEMA, versionedNonce.value);
55
+ const result = new Uint8Array(5 + borshBytes.length);
56
+ result.set(VERSIONED_MAGIC_PREFIX, 0);
57
+ result.set([versionedNonce.version], 4);
58
+ result.set(borshBytes, 5);
59
+ return base64.encode(result);
60
+ }
61
+ _VersionedNonceBuilder.encodeNonce = encodeNonce;
62
+ function decodeNonce(encoded) {
63
+ const bytes = base64.decode(encoded);
64
+ if (bytes.length !== 32) throw new Error("Nonce too short");
65
+ const prefix = bytes.slice(0, 4);
66
+ const version = bytes[4];
67
+ const borshData = bytes.slice(5);
68
+ if (!prefix.every((byte, i) => byte === VERSIONED_MAGIC_PREFIX[i])) throw new Error("Invalid magic prefix");
69
+ return new VersionedNonce(version, deserialize(SALTED_NONCE_BORSH_SCHEMA, borshData));
70
+ }
71
+ _VersionedNonceBuilder.decodeNonce = decodeNonce;
72
+ })(VersionedNonceBuilder || (VersionedNonceBuilder = {}));
73
+
74
+ //#endregion
75
+ export { VersionedNonceBuilder };
@@ -14,9 +14,9 @@ var IntentExecuter = class {
14
14
  this.intentSigner = args.intentSigner;
15
15
  this.onBeforePublishIntent = args.onBeforePublishIntent;
16
16
  }
17
- async signAndSendIntent({ relayParams: relayParamsFactory, signedIntents,...intentParams }) {
17
+ async signAndSendIntent({ relayParams: relayParamsFactory, salt, signedIntents,...intentParams }) {
18
18
  const verifyingContract = __defuse_protocol_internal_utils.configsByEnvironment[this.env].contractID;
19
- let intentPayload = require_intent_payload_factory.defaultIntentPayloadFactory({
19
+ let intentPayload = require_intent_payload_factory.defaultIntentPayloadFactory(salt, {
20
20
  verifying_contract: verifyingContract,
21
21
  ...intentParams
22
22
  });
@@ -12,9 +12,9 @@ var IntentExecuter = class {
12
12
  this.intentSigner = args.intentSigner;
13
13
  this.onBeforePublishIntent = args.onBeforePublishIntent;
14
14
  }
15
- async signAndSendIntent({ relayParams: relayParamsFactory, signedIntents,...intentParams }) {
15
+ async signAndSendIntent({ relayParams: relayParamsFactory, salt, signedIntents,...intentParams }) {
16
16
  const verifyingContract = configsByEnvironment[this.env].contractID;
17
- let intentPayload = defaultIntentPayloadFactory({
17
+ let intentPayload = defaultIntentPayloadFactory(salt, {
18
18
  verifying_contract: verifyingContract,
19
19
  ...intentParams
20
20
  });
@@ -1,14 +1,14 @@
1
- const require_rolldown_runtime = require('../../_virtual/rolldown_runtime.cjs');
2
- let __scure_base = require("@scure/base");
3
- __scure_base = require_rolldown_runtime.__toESM(__scure_base);
1
+ const require_expirable_nonce = require('./expirable-nonce.cjs');
4
2
 
5
3
  //#region src/intents/intent-payload-factory.ts
6
- function defaultIntentPayloadFactory({ intents, verifying_contract,...params }) {
4
+ const DEFAULT_DEADLINE_MS = 60 * 1e3;
5
+ function defaultIntentPayloadFactory(salt, { intents, verifying_contract,...params }) {
7
6
  params = Object.fromEntries(Object.entries(params).filter(([, value]) => value !== void 0));
7
+ const deadline = new Date(Date.now() + DEFAULT_DEADLINE_MS);
8
8
  return {
9
9
  verifying_contract,
10
- deadline: new Date(Date.now() + 60 * 1e3).toISOString(),
11
- nonce: __scure_base.base64.encode(crypto.getRandomValues(new Uint8Array(32))),
10
+ deadline: deadline.toISOString(),
11
+ nonce: require_expirable_nonce.VersionedNonceBuilder.encodeNonce(salt, deadline),
12
12
  intents: intents == null ? [] : intents,
13
13
  signer_id: void 0,
14
14
  ...params
@@ -1,12 +1,14 @@
1
- import { base64 } from "@scure/base";
1
+ import { VersionedNonceBuilder } from "./expirable-nonce.js";
2
2
 
3
3
  //#region src/intents/intent-payload-factory.ts
4
- function defaultIntentPayloadFactory({ intents, verifying_contract,...params }) {
4
+ const DEFAULT_DEADLINE_MS = 60 * 1e3;
5
+ function defaultIntentPayloadFactory(salt, { intents, verifying_contract,...params }) {
5
6
  params = Object.fromEntries(Object.entries(params).filter(([, value]) => value !== void 0));
7
+ const deadline = new Date(Date.now() + DEFAULT_DEADLINE_MS);
6
8
  return {
7
9
  verifying_contract,
8
- deadline: new Date(Date.now() + 60 * 1e3).toISOString(),
9
- nonce: base64.encode(crypto.getRandomValues(new Uint8Array(32))),
10
+ deadline: deadline.toISOString(),
11
+ nonce: VersionedNonceBuilder.encodeNonce(salt, deadline),
10
12
  intents: intents == null ? [] : intents,
11
13
  signer_id: void 0,
12
14
  ...params
@@ -0,0 +1,9 @@
1
+ import { Salt } from "../expirable-nonce.cjs";
2
+
3
+ //#region src/intents/interfaces/salt-manager.d.ts
4
+ interface ISaltManager {
5
+ getCachedSalt(): Promise<Salt>;
6
+ refresh(): Promise<Salt>;
7
+ }
8
+ //#endregion
9
+ export { ISaltManager };
@@ -0,0 +1,9 @@
1
+ import { Salt } from "../expirable-nonce.js";
2
+
3
+ //#region src/intents/interfaces/salt-manager.d.ts
4
+ interface ISaltManager {
5
+ getCachedSalt(): Promise<Salt>;
6
+ refresh(): Promise<Salt>;
7
+ }
8
+ //#endregion
9
+ export { ISaltManager };
@@ -0,0 +1,76 @@
1
+ const require_rolldown_runtime = require('../../_virtual/rolldown_runtime.cjs');
2
+ let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
3
+ __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
4
+ let __scure_base = require("@scure/base");
5
+ __scure_base = require_rolldown_runtime.__toESM(__scure_base);
6
+ let valibot = require("valibot");
7
+ valibot = require_rolldown_runtime.__toESM(valibot);
8
+
9
+ //#region src/intents/salt-manager.ts
10
+ const SALT_TTL_MS = 30 * 1e3;
11
+ var SaltManager = class {
12
+ constructor({ env, nearProvider }) {
13
+ this.currentSalt = null;
14
+ this.fetchPromise = null;
15
+ this.lastFetchTime = 0;
16
+ this.intentsContract = __defuse_protocol_internal_utils.configsByEnvironment[env].contractID;
17
+ this.nearProvider = nearProvider;
18
+ }
19
+ /**
20
+ * Returns the cached salt if it's valid, otherwise fetches a new one
21
+ * Deduplicates concurrent requests so only one fetch runs at a time
22
+ */
23
+ async getCachedSalt() {
24
+ if (this.isCacheValid()) return this.currentSalt;
25
+ if (this.fetchPromise) return this.fetchPromise;
26
+ this.fetchPromise = this.fetchAndCache().finally(() => {
27
+ this.fetchPromise = null;
28
+ });
29
+ return this.fetchPromise;
30
+ }
31
+ /**
32
+ * Fetches a new salt from the contract and updates the cache
33
+ */
34
+ async refresh() {
35
+ this.invalidateCache();
36
+ return this.getCachedSalt();
37
+ }
38
+ async fetchAndCache() {
39
+ try {
40
+ this.currentSalt = await fetchSalt(this.nearProvider, this.intentsContract);
41
+ this.lastFetchTime = Date.now();
42
+ return this.currentSalt;
43
+ } catch (err) {
44
+ this.fetchPromise = null;
45
+ throw new Error(`Failed to fetch salt`, { cause: err });
46
+ }
47
+ }
48
+ isCacheValid() {
49
+ return this.currentSalt != null && Date.now() - this.lastFetchTime < SALT_TTL_MS;
50
+ }
51
+ invalidateCache() {
52
+ this.currentSalt = null;
53
+ this.lastFetchTime = 0;
54
+ }
55
+ };
56
+ /**
57
+ * Fetches the current salt from the NEAR contract
58
+ *
59
+ * @param nearProvider Near provider used for querying the contract
60
+ * @param contractId The NEAR contract ID to query
61
+ * @returns Promise resolving to the salt
62
+ */
63
+ async function fetchSalt(nearProvider, contractId) {
64
+ const value = await __defuse_protocol_internal_utils.utils.queryContract({
65
+ contractId,
66
+ methodName: "current_salt",
67
+ args: {},
68
+ finality: "optimistic",
69
+ nearClient: nearProvider,
70
+ schema: valibot.string()
71
+ });
72
+ return __scure_base.hex.decode(value);
73
+ }
74
+
75
+ //#endregion
76
+ exports.SaltManager = SaltManager;
@@ -0,0 +1,72 @@
1
+ import { configsByEnvironment, utils } from "@defuse-protocol/internal-utils";
2
+ import { hex } from "@scure/base";
3
+ import * as v from "valibot";
4
+
5
+ //#region src/intents/salt-manager.ts
6
+ const SALT_TTL_MS = 30 * 1e3;
7
+ var SaltManager = class {
8
+ constructor({ env, nearProvider }) {
9
+ this.currentSalt = null;
10
+ this.fetchPromise = null;
11
+ this.lastFetchTime = 0;
12
+ this.intentsContract = configsByEnvironment[env].contractID;
13
+ this.nearProvider = nearProvider;
14
+ }
15
+ /**
16
+ * Returns the cached salt if it's valid, otherwise fetches a new one
17
+ * Deduplicates concurrent requests so only one fetch runs at a time
18
+ */
19
+ async getCachedSalt() {
20
+ if (this.isCacheValid()) return this.currentSalt;
21
+ if (this.fetchPromise) return this.fetchPromise;
22
+ this.fetchPromise = this.fetchAndCache().finally(() => {
23
+ this.fetchPromise = null;
24
+ });
25
+ return this.fetchPromise;
26
+ }
27
+ /**
28
+ * Fetches a new salt from the contract and updates the cache
29
+ */
30
+ async refresh() {
31
+ this.invalidateCache();
32
+ return this.getCachedSalt();
33
+ }
34
+ async fetchAndCache() {
35
+ try {
36
+ this.currentSalt = await fetchSalt(this.nearProvider, this.intentsContract);
37
+ this.lastFetchTime = Date.now();
38
+ return this.currentSalt;
39
+ } catch (err) {
40
+ this.fetchPromise = null;
41
+ throw new Error(`Failed to fetch salt`, { cause: err });
42
+ }
43
+ }
44
+ isCacheValid() {
45
+ return this.currentSalt != null && Date.now() - this.lastFetchTime < SALT_TTL_MS;
46
+ }
47
+ invalidateCache() {
48
+ this.currentSalt = null;
49
+ this.lastFetchTime = 0;
50
+ }
51
+ };
52
+ /**
53
+ * Fetches the current salt from the NEAR contract
54
+ *
55
+ * @param nearProvider Near provider used for querying the contract
56
+ * @param contractId The NEAR contract ID to query
57
+ * @returns Promise resolving to the salt
58
+ */
59
+ async function fetchSalt(nearProvider, contractId) {
60
+ const value = await utils.queryContract({
61
+ contractId,
62
+ methodName: "current_salt",
63
+ args: {},
64
+ finality: "optimistic",
65
+ nearClient: nearProvider,
66
+ schema: v.string()
67
+ });
68
+ return hex.decode(value);
69
+ }
70
+
71
+ //#endregion
72
+ export { SaltManager };
@@ -0,0 +1,11 @@
1
+
2
+ //#region src/lib/hex.ts
3
+ /**
4
+ * @description verifies value is a non 0x-prefixed hex string
5
+ */
6
+ function isHex(value) {
7
+ return value.length % 2 === 0 && /^[0-9A-Fa-f]+$/.test(value);
8
+ }
9
+
10
+ //#endregion
11
+ exports.default = isHex;
@@ -0,0 +1,10 @@
1
+ //#region src/lib/hex.ts
2
+ /**
3
+ * @description verifies value is a non 0x-prefixed hex string
4
+ */
5
+ function isHex(value) {
6
+ return value.length % 2 === 0 && /^[0-9A-Fa-f]+$/.test(value);
7
+ }
8
+
9
+ //#endregion
10
+ export { isHex as default };
package/dist/src/sdk.cjs CHANGED
@@ -15,6 +15,7 @@ const require_intent_signer_noop = require('./intents/intent-signer-impl/intent-
15
15
  const require_array = require('./lib/array.cjs');
16
16
  const require_configure_rpc_config = require('./lib/configure-rpc-config.cjs');
17
17
  const require_route_config = require('./lib/route-config.cjs');
18
+ const require_salt_manager = require('./intents/salt-manager.cjs');
18
19
  let __defuse_protocol_internal_utils = require("@defuse-protocol/internal-utils");
19
20
  __defuse_protocol_internal_utils = require_rolldown_runtime.__toESM(__defuse_protocol_internal_utils);
20
21
  let __hot_labs_omni_sdk = require("@hot-labs/omni-sdk");
@@ -75,6 +76,10 @@ var IntentsSDK = class {
75
76
  solverRelayApiKey: this.solverRelayApiKey
76
77
  });
77
78
  this.intentSigner = args.intentSigner;
79
+ this.saltManager = new require_salt_manager.SaltManager({
80
+ env: this.env,
81
+ nearProvider
82
+ });
78
83
  }
79
84
  setIntentSigner(signer) {
80
85
  this.intentSigner = signer;
@@ -172,20 +177,31 @@ var IntentsSDK = class {
172
177
  async signAndSendIntent(args) {
173
178
  const intentSigner = args.signer ?? this.intentSigner;
174
179
  (0, __defuse_protocol_internal_utils.assert)(intentSigner != null, "Intent signer is not provided");
175
- const { ticket } = await new require_intent_executer.IntentExecuter({
180
+ const intentExecuter = new require_intent_executer.IntentExecuter({
176
181
  env: this.env,
177
182
  logger: args.logger,
178
183
  intentSigner,
179
184
  intentRelayer: this.intentRelayer,
180
185
  intentPayloadFactory: args.payload,
181
186
  onBeforePublishIntent: args.onBeforePublishIntent
182
- }).signAndSendIntent({
187
+ });
188
+ const { ticket } = await this.withSaltRetry(args, async (salt) => intentExecuter.signAndSendIntent({
183
189
  intents: args.intents,
190
+ salt,
184
191
  relayParams: args.relayParams,
185
192
  signedIntents: args.signedIntents
186
- });
193
+ }));
187
194
  return { intentHash: ticket };
188
195
  }
196
+ async withSaltRetry(args, fn) {
197
+ try {
198
+ return await fn(await this.saltManager.getCachedSalt());
199
+ } catch (err) {
200
+ if (!(err instanceof __defuse_protocol_internal_utils.RelayPublishError && err.code === "INVALID_SALT")) throw err;
201
+ args.logger?.warn?.("Salt error detected. Refreshing salt and retrying");
202
+ return fn(await this.saltManager.refresh());
203
+ }
204
+ }
189
205
  async signAndSendWithdrawalIntent(args) {
190
206
  let withdrawalParamsArray;
191
207
  let feeEstimations;
@@ -2,6 +2,7 @@ import { IntentHash, IntentPrimitive } from "./intents/shared-types.cjs";
2
2
  import { IIntentSigner } from "./intents/interfaces/intent-signer.cjs";
3
3
  import { BatchWithdrawalResult, Bridge, FeeEstimation, IIntentsSDK, IntentPublishResult, IntentSettlementStatus, NearTxInfo, ParsedAssetInfo, PartialRPCEndpointMap, ProcessWithdrawalArgs, QuoteOptions, SignAndSendArgs, SignAndSendWithdrawalArgs, TxInfo, TxNoInfo, WithdrawalIdentifier, WithdrawalParams, WithdrawalResult } from "./shared-types.cjs";
4
4
  import { IIntentRelayer } from "./intents/interfaces/intent-relayer.cjs";
5
+ import { ISaltManager } from "./intents/interfaces/salt-manager.cjs";
5
6
  import { ILogger, NearIntentsEnv, RetryOptions } from "@defuse-protocol/internal-utils";
6
7
 
7
8
  //#region src/sdk.d.ts
@@ -19,6 +20,7 @@ declare class IntentsSDK implements IIntentsSDK {
19
20
  protected intentSigner?: IIntentSigner;
20
21
  protected bridges: Bridge[];
21
22
  protected solverRelayApiKey: string | undefined;
23
+ protected saltManager: ISaltManager;
22
24
  constructor(args: IntentsSDKConfig);
23
25
  setIntentSigner(signer: IIntentSigner): void;
24
26
  createWithdrawalIntents(args: {
@@ -65,6 +67,7 @@ declare class IntentsSDK implements IIntentsSDK {
65
67
  }): Promise<Array<TxInfo | TxNoInfo>>;
66
68
  parseAssetId(assetId: string): ParsedAssetInfo;
67
69
  signAndSendIntent(args: SignAndSendArgs): Promise<IntentPublishResult>;
70
+ private withSaltRetry;
68
71
  signAndSendWithdrawalIntent(args: SignAndSendWithdrawalArgs<WithdrawalParams> | SignAndSendWithdrawalArgs<WithdrawalParams[]>): Promise<IntentPublishResult>;
69
72
  waitForIntentSettlement(args: {
70
73
  intentHash: IntentHash;
package/dist/src/sdk.d.ts CHANGED
@@ -2,6 +2,7 @@ import { IntentHash, IntentPrimitive } from "./intents/shared-types.js";
2
2
  import { IIntentSigner } from "./intents/interfaces/intent-signer.js";
3
3
  import { BatchWithdrawalResult, Bridge, FeeEstimation, IIntentsSDK, IntentPublishResult, IntentSettlementStatus, NearTxInfo, ParsedAssetInfo, PartialRPCEndpointMap, ProcessWithdrawalArgs, QuoteOptions, SignAndSendArgs, SignAndSendWithdrawalArgs, TxInfo, TxNoInfo, WithdrawalIdentifier, WithdrawalParams, WithdrawalResult } from "./shared-types.js";
4
4
  import { IIntentRelayer } from "./intents/interfaces/intent-relayer.js";
5
+ import { ISaltManager } from "./intents/interfaces/salt-manager.js";
5
6
  import { ILogger, NearIntentsEnv, RetryOptions } from "@defuse-protocol/internal-utils";
6
7
 
7
8
  //#region src/sdk.d.ts
@@ -19,6 +20,7 @@ declare class IntentsSDK implements IIntentsSDK {
19
20
  protected intentSigner?: IIntentSigner;
20
21
  protected bridges: Bridge[];
21
22
  protected solverRelayApiKey: string | undefined;
23
+ protected saltManager: ISaltManager;
22
24
  constructor(args: IntentsSDKConfig);
23
25
  setIntentSigner(signer: IIntentSigner): void;
24
26
  createWithdrawalIntents(args: {
@@ -65,6 +67,7 @@ declare class IntentsSDK implements IIntentsSDK {
65
67
  }): Promise<Array<TxInfo | TxNoInfo>>;
66
68
  parseAssetId(assetId: string): ParsedAssetInfo;
67
69
  signAndSendIntent(args: SignAndSendArgs): Promise<IntentPublishResult>;
70
+ private withSaltRetry;
68
71
  signAndSendWithdrawalIntent(args: SignAndSendWithdrawalArgs<WithdrawalParams> | SignAndSendWithdrawalArgs<WithdrawalParams[]>): Promise<IntentPublishResult>;
69
72
  waitForIntentSettlement(args: {
70
73
  intentHash: IntentHash;
package/dist/src/sdk.js CHANGED
@@ -14,7 +14,8 @@ import { noopIntentSigner } from "./intents/intent-signer-impl/intent-signer-noo
14
14
  import { zip } from "./lib/array.js";
15
15
  import { configureEvmRpcUrls, configureStellarRpcUrls } from "./lib/configure-rpc-config.js";
16
16
  import { determineRouteConfig } from "./lib/route-config.js";
17
- import { PUBLIC_NEAR_RPC_URLS, RETRY_CONFIGS, assert, configsByEnvironment, nearFailoverRpcProvider, solverRelay } from "@defuse-protocol/internal-utils";
17
+ import { SaltManager } from "./intents/salt-manager.js";
18
+ import { PUBLIC_NEAR_RPC_URLS, RETRY_CONFIGS, RelayPublishError, assert, configsByEnvironment, nearFailoverRpcProvider, solverRelay } from "@defuse-protocol/internal-utils";
18
19
  import { HotBridge } from "@hot-labs/omni-sdk";
19
20
  import { stringify } from "viem";
20
21
 
@@ -71,6 +72,10 @@ var IntentsSDK = class {
71
72
  solverRelayApiKey: this.solverRelayApiKey
72
73
  });
73
74
  this.intentSigner = args.intentSigner;
75
+ this.saltManager = new SaltManager({
76
+ env: this.env,
77
+ nearProvider
78
+ });
74
79
  }
75
80
  setIntentSigner(signer) {
76
81
  this.intentSigner = signer;
@@ -168,20 +173,31 @@ var IntentsSDK = class {
168
173
  async signAndSendIntent(args) {
169
174
  const intentSigner = args.signer ?? this.intentSigner;
170
175
  assert(intentSigner != null, "Intent signer is not provided");
171
- const { ticket } = await new IntentExecuter({
176
+ const intentExecuter = new IntentExecuter({
172
177
  env: this.env,
173
178
  logger: args.logger,
174
179
  intentSigner,
175
180
  intentRelayer: this.intentRelayer,
176
181
  intentPayloadFactory: args.payload,
177
182
  onBeforePublishIntent: args.onBeforePublishIntent
178
- }).signAndSendIntent({
183
+ });
184
+ const { ticket } = await this.withSaltRetry(args, async (salt) => intentExecuter.signAndSendIntent({
179
185
  intents: args.intents,
186
+ salt,
180
187
  relayParams: args.relayParams,
181
188
  signedIntents: args.signedIntents
182
- });
189
+ }));
183
190
  return { intentHash: ticket };
184
191
  }
192
+ async withSaltRetry(args, fn) {
193
+ try {
194
+ return await fn(await this.saltManager.getCachedSalt());
195
+ } catch (err) {
196
+ if (!(err instanceof RelayPublishError && err.code === "INVALID_SALT")) throw err;
197
+ args.logger?.warn?.("Salt error detected. Refreshing salt and retrying");
198
+ return fn(await this.saltManager.refresh());
199
+ }
200
+ }
185
201
  async signAndSendWithdrawalIntent(args) {
186
202
  let withdrawalParamsArray;
187
203
  let feeEstimations;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@defuse-protocol/intents-sdk",
3
- "version": "0.27.0",
3
+ "version": "0.29.0",
4
4
  "private": false,
5
5
  "type": "module",
6
6
  "sideEffects": false,
@@ -38,8 +38,8 @@
38
38
  "ripple-address-codec": "^5.0.0",
39
39
  "valibot": "^1.0.0",
40
40
  "viem": "^2.0.0",
41
- "@defuse-protocol/contract-types": "0.1.2",
42
- "@defuse-protocol/internal-utils": "0.16.0"
41
+ "@defuse-protocol/contract-types": "0.2.0",
42
+ "@defuse-protocol/internal-utils": "0.18.0"
43
43
  },
44
44
  "devDependencies": {
45
45
  "tsdown": "0.15.5",