@hyperbridge/sdk
Version:
The hyperclient SDK provides utilities for querying proofs and statuses for cross-chain requests from HyperBridge.
1,648 lines (1,640 loc) • 63.2 kB
TypeScript
import { ConsolaInstance } from 'consola';
import { GraphQLClient } from 'graphql-request';
import { Hex, Log, PublicClient } from 'viem';
import { ApiPromise } from '@polkadot/api';
import { SignerOptions } from '@polkadot/api/types';
type HexString = `0x${string}`;
interface IConfig {
source: IEvmConfig | ISubstrateConfig;
dest: IEvmConfig | ISubstrateConfig;
hyperbridge: IHyperbridgeConfig;
tracing?: boolean;
}
interface IEvmConfig {
rpcUrl: string;
stateMachineId: string;
host: string;
consensusStateId: string;
}
interface ISubstrateConfig {
wsUrl: string;
consensusStateId: string;
hasher: "Keccak" | "Blake2";
stateMachineId: string;
}
interface IHyperbridgeConfig {
wsUrl: string;
stateMachineId: string;
consensusStateId: string;
}
interface IPostRequest {
source: string;
dest: string;
from: HexString;
to: HexString;
nonce: bigint;
body: HexString;
timeoutTimestamp: bigint;
}
interface IGetRequest {
source: string;
dest: string;
from: HexString;
nonce: bigint;
height: bigint;
keys: HexString[];
timeoutTimestamp: bigint;
context: HexString;
}
interface GetResponseStorageValues {
key: HexString;
value: HexString;
}
interface IPostResponse {
post: IPostRequest;
response: string;
timeoutTimestamp: bigint;
}
type IMessage = {
Requests: HexString[];
} | {
Responses: HexString[];
};
type IndexerQueryClient = GraphQLClient;
interface ClientConfig {
pollInterval: number;
queryClient: IndexerQueryClient;
tracing?: boolean;
source: IEvmConfig | ISubstrateConfig;
dest: IEvmConfig | ISubstrateConfig;
hyperbridge: IHyperbridgeConfig;
}
interface RetryConfig {
maxRetries: number;
backoffMs: number;
logMessage?: string;
logger?: ConsolaInstance;
}
interface IsmpRequest {
source: string;
dest: string;
from: string;
to: string;
nonce: bigint;
body: string;
timeoutTimestamp: bigint;
storage_key?: string;
}
declare const RequestStatus: Readonly<{
SOURCE: "SOURCE";
SOURCE_FINALIZED: "SOURCE_FINALIZED";
HYPERBRIDGE_DELIVERED: "HYPERBRIDGE_DELIVERED";
HYPERBRIDGE_FINALIZED: "HYPERBRIDGE_FINALIZED";
DESTINATION: "DESTINATION";
TIMED_OUT: "TIMED_OUT";
HYPERBRIDGE_TIMED_OUT: "HYPERBRIDGE_TIMED_OUT";
}>;
type RequestStatus = typeof RequestStatus;
type RequestStatusKey = keyof typeof RequestStatus;
declare const TimeoutStatus: Readonly<{
PENDING_TIMEOUT: "PENDING_TIMEOUT";
DESTINATION_FINALIZED_TIMEOUT: "DESTINATION_FINALIZED_TIMEOUT";
HYPERBRIDGE_TIMED_OUT: "HYPERBRIDGE_TIMED_OUT";
HYPERBRIDGE_FINALIZED_TIMEOUT: "HYPERBRIDGE_FINALIZED_TIMEOUT";
TIMED_OUT: "TIMED_OUT";
}>;
type TimeoutStatus = typeof TimeoutStatus;
type TimeoutStatusKey = keyof typeof TimeoutStatus;
type AllStatusKey = RequestStatusKey | TimeoutStatusKey;
declare enum HyperClientStatus {
PENDING = "PENDING",
SOURCE_FINALIZED = "SOURCE_FINALIZED",
HYPERBRIDGE_FINALIZED = "HYPERBRIDGE_FINALIZED",
HYPERBRIDGE_VERIFIED = "HYPERBRIDGE_VERIFIED",
DESTINATION = "DESTINATION",
TIMED_OUT = "TIMED_OUT",
HYPERBRIDGE_TIMED_OUT = "HYPERBRIDGE_TIMED_OUT",
ERROR = "ERROR"
}
declare enum OrderStatus {
PLACED = "PLACED",
FILLED = "FILLED",
REDEEMED = "REDEEMED",
REFUNDED = "REFUNDED"
}
declare enum TeleportStatus {
TELEPORTED = "TELEPORTED",
RECEIVED = "RECEIVED",
REFUNDED = "REFUNDED"
}
interface TokenGatewayAssetTeleportedResponse {
tokenGatewayAssetTeleporteds: {
nodes: Array<{
id: string;
from: string;
to: string;
sourceChain: string;
destChain: string;
commitment: string;
amount: string;
usdValue: string;
assetId: string;
redeem: boolean;
status: TeleportStatus;
createdAt: string;
blockNumber: string;
blockTimestamp: string;
transactionHash: string;
statusMetadata: {
nodes: Array<{
status: TeleportStatus;
chain: string;
timestamp: string;
blockNumber: string;
blockHash: string;
transactionHash: string;
}>;
};
}>;
};
}
interface TokenGatewayAssetTeleportedWithStatus {
id: string;
from: string;
to: string;
sourceChain: string;
destChain: string;
commitment: string;
amount: bigint;
usdValue: string;
assetId: string;
redeem: boolean;
status: TeleportStatus;
createdAt: Date;
blockNumber: bigint;
blockTimestamp: bigint;
transactionHash: string;
statuses: Array<{
status: TeleportStatus;
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp: bigint;
};
}>;
}
interface BlockMetadata {
blockHash: string;
blockNumber: number;
transactionHash: string;
calldata?: string;
timestamp?: number;
}
interface PostRequestStatus {
status: RequestStatusKey;
metadata: Partial<BlockMetadata>;
}
interface PostRequestTimeoutStatus {
status: TimeoutStatusKey;
metadata?: Partial<BlockMetadata>;
}
interface StateMachineUpdate {
height: number;
chain: string;
blockHash: string;
blockNumber: number;
transactionHash: string;
transactionIndex: number;
stateMachineId: string;
timestamp: number;
}
interface RequestResponse {
requests: {
nodes: Array<{
source: string;
dest: string;
to: HexString;
from: HexString;
nonce: bigint;
body: HexString;
timeoutTimestamp: bigint;
statusMetadata: {
nodes: Array<{
blockHash: string;
blockNumber: string;
timestamp: string;
chain: string;
status: string;
transactionHash: string;
}>;
};
}>;
};
}
interface GetRequestResponse {
getRequests: {
nodes: Array<{
source: string;
dest: string;
to: HexString;
from: HexString;
nonce: bigint;
height: bigint;
keys: HexString[];
context: HexString;
timeoutTimestamp: bigint;
statusMetadata: {
nodes: Array<{
blockHash: string;
blockNumber: string;
timestamp: string;
chain: string;
status: string;
transactionHash: string;
}>;
};
}>;
};
}
type RequestStatusWithMetadata = {
status: RequestStatus["SOURCE"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: RequestStatus["SOURCE_FINALIZED"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: RequestStatus["HYPERBRIDGE_DELIVERED"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: RequestStatus["HYPERBRIDGE_FINALIZED"];
metadata: {
calldata: Hex;
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: RequestStatus["DESTINATION"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: TimeoutStatus["PENDING_TIMEOUT"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
};
} | {
status: TimeoutStatus["DESTINATION_FINALIZED_TIMEOUT"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: TimeoutStatus["HYPERBRIDGE_TIMED_OUT"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: TimeoutStatus["HYPERBRIDGE_FINALIZED_TIMEOUT"];
metadata: {
calldata: Hex;
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
} | {
status: TimeoutStatus["TIMED_OUT"];
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp?: number;
};
};
interface GenericRequestWithStatuses {
source: string;
dest: string;
from: HexString;
nonce: bigint;
timeoutTimestamp: bigint;
statuses: Array<RequestStatusWithMetadata>;
}
interface PostRequestWithStatus extends GenericRequestWithStatuses {
to: HexString;
body: HexString;
}
interface GetRequestWithStatus extends GenericRequestWithStatuses {
height: bigint;
keys: HexString[];
context: HexString;
}
interface GetResponseByRequestIdResponse {
getResponses: {
nodes: Array<{
id: string;
commitment: string;
responseMessage: string[];
}>;
};
}
interface ResponseCommitmentWithValues {
commitment: string;
values: string[];
}
interface RequestCommitment {
requests: {
nodes: Array<{
id: string;
commitment: string;
}>;
};
}
interface StateMachineResponse {
stateMachineUpdateEvents: {
nodes: {
height: number;
chain: string;
blockHash: string;
blockNumber: number;
transactionHash: string;
transactionIndex: number;
stateMachineId: string;
createdAt: string;
}[];
};
}
interface AssetTeleported {
id: string;
from: string;
to: string;
amount: bigint;
dest: string;
commitment: string;
createdAt: Date;
blockNumber: number;
}
interface AssetTeleportedResponse {
assetTeleporteds: {
nodes: AssetTeleported[];
};
}
interface StateMachineIdParams {
stateId: {
Evm?: number;
Substrate?: HexString;
Polkadot?: number;
Kusama?: number;
};
consensusStateId: HexString;
}
/**
* Configuration for a blockchain chain
*/
interface ChainConfig {
/**
* The unique identifier for the chain
*/
chainId: number;
/**
* The RPC URL to connect to the chain
*/
rpcUrl: string;
/**
* The address of the IntentGateway contract on this chain
*/
intentGatewayAddress: string;
}
/**
* Represents token information for an order
*/
interface TokenInfo {
/**
* The address of the ERC20 token
* address(0) is used as a sentinel for the native token
*/
token: HexString;
/**
* The amount of the token
*/
amount: bigint;
}
/**
* Represents payment information for an order
*/
interface PaymentInfo extends TokenInfo {
/**
* The address to receive the output tokens
*/
beneficiary: HexString;
}
/**
* Represents an order in the IntentGateway
*/
interface Order {
/**
* The unique identifier for the order
*/
id?: string;
/**
* The address of the user who is initiating the transfer
*/
user: HexString;
/**
* The state machine identifier of the origin chain
*/
sourceChain: string;
/**
* The state machine identifier of the destination chain
*/
destChain: string;
/**
* The block number by which the order must be filled on the destination chain
*/
deadline: bigint;
/**
* The nonce of the order
*/
nonce: bigint;
/**
* Represents the dispatch fees associated with the IntentGateway
*/
fees: bigint;
/**
* The tokens that the filler will provide
*/
outputs: PaymentInfo[];
/**
* The tokens that are escrowed for the filler
*/
inputs: TokenInfo[];
/**
* A bytes array to store the calls if any
*/
callData: HexString;
/**
* The transaction hash of the order
*/
transactionHash?: HexString;
}
interface DecodedOrderPlacedLog extends Log {
eventName: string;
args: {
user: HexString;
sourceChain: Hex;
destChain: Hex;
deadline: bigint;
nonce: bigint;
fees: bigint;
outputs: Array<{
token: HexString;
amount: bigint;
beneficiary: HexString;
}>;
inputs: Array<{
token: HexString;
amount: bigint;
}>;
callData: HexString;
};
transactionHash: HexString;
}
/**
* Options for filling an order
*/
interface FillOptions {
/**
* The fee paid to the relayer for processing transactions
*/
relayerFee: bigint;
}
/**
* Options for canceling an order
*/
interface CancelOptions {
/**
* The fee paid to the relayer for processing transactions
*/
relayerFee: string;
/**
* Stores the height value
*/
height: string;
}
/**
* Represents a new deployment of IntentGateway
*/
interface NewDeployment {
/**
* Identifier for the state machine
*/
stateMachineId: HexString;
/**
* The gateway identifier
*/
gateway: HexString;
}
/**
* Represents the body of a request
*/
interface RequestBody {
/**
* Represents the commitment of an order
*/
commitment: HexString;
/**
* Stores the identifier for the beneficiary
*/
beneficiary: HexString;
/**
* An array of token identifiers
*/
tokens: TokenInfo[];
}
/**
* Represents the parameters for the IntentGateway module
*/
interface IntentGatewayParams {
/**
* The address of the host contract
*/
host: string;
/**
* Address of the dispatcher contract responsible for handling intents
*/
dispatcher: string;
}
/**
* Enum representing the different kinds of incoming requests
*/
declare enum RequestKind {
/**
* Identifies a request for redeeming an escrow
*/
RedeemEscrow = 0,
/**
* Identifies a request for recording new contract deployments
*/
NewDeployment = 1,
/**
* Identifies a request for updating parameters
*/
UpdateParams = 2
}
/**
* Configuration for the IntentFiller
*/
interface FillerConfig {
/**
* Policy for determining confirmation requirements
*/
confirmationPolicy: {
getConfirmationBlocks: (chainId: number, amount: bigint) => number;
};
/**
* Maximum number of orders to process concurrently
*/
maxConcurrentOrders?: number;
/**
* Minimum profitability threshold to consider filling an order
* Expressed as a percentage (e.g., 0.5 = 0.5%)
*/
minProfitabilityThreshold?: number;
/**
* Gas price strategy for each chain
* Maps chainId to a gas price strategy function
*/
gasPriceStrategy?: Record<string, () => Promise<string>>;
/**
* Maximum gas price willing to pay for each chain
* Maps chainId to maximum gas price in wei
*/
maxGasPrice?: Record<string, string>;
/**
* Retry configuration for failed transactions
*/
retryConfig?: {
/**
* Maximum number of retry attempts
*/
maxAttempts: number;
/**
* Initial delay between retries in ms
*/
initialDelayMs: number;
};
/**
* Configuration for the pending queue
*/
pendingQueueConfig?: {
/**
* Delay in milliseconds before rechecking an order for confirmations
* Default: 30000 (30 seconds)
*/
recheckDelayMs?: number;
/**
* Maximum number of times to recheck an order before giving up
* Default: 10
*/
maxRechecks?: number;
};
}
/**
* Result of an order execution attempt
*/
interface ExecutionResult {
/**
* Whether the execution was successful
*/
success: boolean;
/**
* The transaction hash if successful
*/
txHash?: string;
/**
* Error message if unsuccessful
*/
error?: string;
/**
* Gas used by the transaction
*/
gasUsed?: string;
/**
* Gas price used for the transaction
*/
gasPrice?: string;
/**
* Total transaction cost in wei
*/
txCost?: string;
/**
* Block number when the transaction was confirmed
*/
confirmedAtBlock?: number;
/**
* Timestamp when the transaction was confirmed
*/
confirmedAt?: Date;
/**
* Actual profitability achieved
*/
actualProfitability?: number;
/**
* Strategy used to fill the order
*/
strategyUsed?: string;
/**
* Any tokens exchanged during the fill process
*/
exchanges?: Array<{
fromToken: HexString;
toToken: HexString;
fromAmount: string;
toAmount: string;
exchangeRate: string;
}>;
/**
* The time it took to fill the order
*/
processingTimeMs?: number;
}
/**
* Represents a dispatch post for cross-chain communication
*/
interface DispatchPost {
/**
* Bytes representation of the destination state machine
*/
dest: HexString;
/**
* The destination module
*/
to: HexString;
/**
* The request body
*/
body: HexString;
/**
* Timeout for this request in seconds
*/
timeout: bigint;
/**
* The amount put up to be paid to the relayer,
* this is charged in `IIsmpHost.feeToken` to `msg.sender`
*/
fee: bigint;
/**
* Who pays for this request?
*/
payer: HexString;
}
interface DispatchGet {
/**
* Bytes representation of the destination state machine
*/
dest: HexString;
/**
* Height at which to read the state machine
*/
height: bigint;
/**
* Raw storage keys to fetch values from the counterparty
*/
keys: HexString[];
/**
* Timeout for this request in seconds
*/
timeout: bigint;
/**
* The amount put up to be paid to the relayer
*/
fee: bigint;
/**
* Context for the request
*/
context: HexString;
}
interface StateMachineHeight {
id: {
stateId: {
Evm?: number;
Substrate?: HexString;
Polkadot?: number;
Kusama?: number;
};
consensusStateId: HexString;
};
height: bigint;
}
/**
* The EvmHost protocol parameters
*/
interface HostParams {
/**
* The default timeout in seconds for messages. If messages are dispatched
* with a timeout value lower than this this value will be used instead
*/
defaultTimeout: bigint;
/**
* The default per byte fee
*/
perByteFee: bigint;
/**
* The cost for applications to access the hyperbridge state commitment.
* They might do so because the hyperbridge state contains the verified state commitments
* for all chains and they want to directly read the state of these chains state bypassing
* the ISMP protocol entirely.
*/
stateCommitmentFee: bigint;
/**
* The fee token contract address. This will typically be DAI.
* but we allow it to be configurable to prevent future regrets.
*/
feeToken: HexString;
/**
* The admin account, this only has the rights to freeze, or unfreeze the bridge
*/
admin: HexString;
/**
* Ismp message handler contract. This performs all verification logic
* needed to validate cross-chain messages before they are dispatched to local modules
*/
handler: HexString;
/**
* The authorized host manager contract, is itself an `IIsmpModule`
* which receives governance requests from the Hyperbridge chain to either
* withdraw revenue from the host or update its protocol parameters
*/
hostManager: HexString;
/**
* The local UniswapV2Router02 contract, used for swapping the native token to the feeToken.
*/
uniswapV2: HexString;
/**
* The unstaking period of Polkadot's validators. In order to prevent long-range attacks
*/
unStakingPeriod: bigint;
/**
* Minimum challenge period for state commitments in seconds
*/
challengePeriod: bigint;
/**
* The consensus client contract which handles consensus proof verification
*/
consensusClient: HexString;
/**
* State machines whose state commitments are accepted
*/
readonly stateMachines: readonly bigint[];
/**
* The state machine identifier for hyperbridge
*/
hyperbridge: HexString;
}
declare enum EvmLanguage {
Solidity = 0,
Vyper = 1
}
interface OrderStatusMetadata {
status: OrderStatus;
chain: string;
timestamp: bigint;
blockNumber: string;
transactionHash: string;
filler?: string;
}
interface OrderWithStatus {
id: string;
user: string;
sourceChain: string;
destChain: string;
commitment: string;
deadline: bigint;
nonce: bigint;
fees: bigint;
inputTokens: string[];
inputAmounts: bigint[];
inputValuesUSD: string[];
inputUSD: string;
outputTokens: string[];
outputAmounts: bigint[];
outputBeneficiaries: string[];
calldata: string;
status: OrderStatus;
createdAt: Date;
blockNumber: bigint;
blockTimestamp: bigint;
transactionHash: string;
statuses: Array<{
status: OrderStatus;
metadata: {
blockHash: string;
blockNumber: number;
transactionHash: string;
timestamp: bigint;
filler?: string;
};
}>;
}
interface OrderResponse {
orderPlaceds: {
nodes: Array<{
id: string;
user: string;
sourceChain: string;
destChain: string;
commitment: string;
deadline: string;
nonce: string;
fees: string;
inputTokens: string[];
inputAmounts: string[];
inputValuesUSD: string[];
inputUSD: string;
outputTokens: string[];
outputAmounts: string[];
outputBeneficiaries: string[];
calldata: string;
status: OrderStatus;
createdAt: string;
blockNumber: string;
blockTimestamp: string;
transactionHash: string;
statusMetadata: {
nodes: Array<{
status: OrderStatus;
chain: string;
timestamp: string;
blockNumber: string;
blockHash: string;
transactionHash: string;
filler?: string;
}>;
};
}>;
};
}
declare class AbortSignalInternal extends Error {
constructor(message: string);
static isError(error: unknown): error is AbortSignalInternal;
}
/**
* The default address used as fallback when no address is provided.
* This represents the zero address in EVM chains.
*/
declare const DEFAULT_ADDRESS = "0x0000000000000000000000000000000000000000";
/**
* Parameters for an EVM chain.
*/
interface EvmChainParams {
/**
* The chain ID of the EVM chain.
*/
chainId: number;
/**
* The host address of the EVM chain.
*/
host: HexString;
/**
* The URL of the EVM chain.
*/
url: string;
}
/**
* Encapsulates an EVM chain.
*/
declare class EvmChain implements IChain {
private readonly params;
private publicClient;
constructor(params: EvmChainParams);
/**
* Derives the key for the request receipt.
* @param {HexString} commitment - The commitment to derive the key from.
* @returns {HexString} The derived key.
*/
requestReceiptKey(commitment: HexString): HexString;
/**
* Queries the request receipt.
* @param {HexString} commitment - The commitment to query.
* @returns {Promise<HexString | undefined>} The relayer address responsible for delivering the request.
*/
queryRequestReceipt(commitment: HexString): Promise<HexString | undefined>;
/**
* Queries the proof of the commitments.
* @param {IMessage} message - The message to query.
* @param {string} counterparty - The counterparty address.
* @param {bigint} [at] - The block number to query at.
* @returns {Promise<HexString>} The proof.
*/
queryProof(message: IMessage, counterparty: string, at?: bigint): Promise<HexString>;
/**
* Query and return the encoded storage proof for the provided keys at the given height.
* @param {bigint} at - The block height at which to query the storage proof.
* @param {HexString[]} keys - The keys for which to query the storage proof.
* @returns {Promise<HexString>} The encoded storage proof.
*/
queryStateProof(at: bigint, keys: HexString[]): Promise<HexString>;
/**
* Returns the current timestamp of the chain.
* @returns {Promise<bigint>} The current timestamp.
*/
timestamp(): Promise<bigint>;
/**
* Get the latest state machine height for a given state machine ID.
* @param {StateMachineIdParams} stateMachineId - The state machine ID.
* @returns {Promise<bigint>} The latest state machine height.
*/
latestStateMachineHeight(stateMachineId: StateMachineIdParams): Promise<bigint>;
/**
* Get the state machine update time for a given state machine height.
* @param {StateMachineHeight} stateMachineheight - The state machine height.
* @returns {Promise<bigint>} The statemachine update time in seconds.
*/
stateMachineUpdateTime(stateMachineHeight: StateMachineHeight): Promise<bigint>;
/**
* Get the challenge period for a given state machine id.
* @param {StateMachineIdParams} stateMachineId - The state machine ID.
* @returns {Promise<bigint>} The challenge period in seconds.
*/
challengePeriod(stateMachineId: StateMachineIdParams): Promise<bigint>;
/**
* Encodes an ISMP message for the EVM chain.
* @param {IIsmpMessage} message The ISMP message to encode.
* @returns {HexString} The encoded calldata.
*/
encode(message: IIsmpMessage): HexString;
}
/**
* Slot for storing request commitments.
*/
declare const REQUEST_COMMITMENTS_SLOT = 0n;
/**
* Slot index for response commitments map
*/
declare const RESPONSE_COMMITMENTS_SLOT = 1n;
/**
* Slot index for requests receipts map
*/
declare const REQUEST_RECEIPTS_SLOT = 2n;
/**
* Slot index for response receipts map
*/
declare const RESPONSE_RECEIPTS_SLOT = 3n;
/**
* Slot index for state commitment map
*/
declare const STATE_COMMITMENTS_SLOT = 5n;
/**
* Derives the storage slot for a specific field in the StateCommitment struct
*
* struct StateCommitment {
* uint256 timestamp; // slot + 0
* bytes32 overlayRoot; // slot + 1
* bytes32 stateRoot; // slot + 2
* }
*
* @param stateMachineId - The state machine ID
* @param height - The block height
* @param field - The field index in the struct (0 for timestamp, 1 for overlayRoot, 2 for stateRoot)
* @returns The storage slot for the specific field
*/
declare function getStateCommitmentFieldSlot(stateMachineId: bigint, height: bigint, field: 0 | 1 | 2): HexString;
declare function getStateCommitmentSlot(stateMachineId: bigint, height: bigint): HexString;
/**
* Generates a Merkle Mountain Range (MMR) root hash and proof for a post request.
*
* This function takes a post request and tree size, encodes it according to the PostRequest format,
* and generates both the MMR root hash and a proof. The function builds an MMR with `treeSize` leaves,
* where most leaves are variations of the encoded request (XORed with their index), except for the
* last leaf, which is the unmodified request. The proof is generated for this unmodified leaf.
*
* @param postRequest - The post request to generate the MMR root and proof for
* @param treeSize - Controls how many leaves will be added to the MMR (exactly `treeSize` leaves)
* @returns An object containing:
* - root: The MMR root hash as a hex string
* - proof: An array of hex strings representing the MMR proof for the unmodified request
* - index: The index of the unmodified request in the MMR
* - kIndex: The k-index of the unmodified request in the MMR
* - treeSize: The number of leaves in the MMR
* - mmrSize: The size of the MMR in nodes
*/
declare function generateRootWithProof(postRequest: IPostRequest, treeSize: bigint): Promise<{
root: HexString;
proof: HexString[];
index: bigint;
kIndex: bigint;
treeSize: bigint;
mmrSize: bigint;
}>;
declare function __test(): Promise<string>;
type IStateMachine = {
tag: "Evm";
value: number;
} | {
tag: "Polkadot";
value: number;
} | {
tag: "Kusama";
value: number;
} | {
tag: "Substrate";
value: number[];
} | {
tag: "Tendermint";
value: number[];
};
declare const ADDRESS_ZERO: HexString;
declare const DUMMY_PRIVATE_KEY: HexString;
/**
* Calculates the commitment hash for a post request.
* @param post The post request to calculate the commitment hash for.
* @returns The commitment hash and the encode packed data.
*/
declare function postRequestCommitment(post: IPostRequest): {
commitment: HexString;
encodePacked: HexString;
};
declare function orderCommitment(order: Order): HexString;
/**
* Converts a bytes32 token address to bytes20 format
* This removes the extra padded zeros from the address
*/
declare function bytes32ToBytes20(bytes32Address: string): HexString;
declare function bytes20ToBytes32(bytes20Address: string): HexString;
declare function hexToString(hex: string): string;
/**
* Calculates the commitment hash for a get request.
* @param get The get request to calculate the commitment hash for.
* @returns The commitment hash.
*/
declare function getRequestCommitment(get: IGetRequest): HexString;
/**
* Estimates the gas required for a post request transaction on the source chain.
* This function constructs a post request, generates mock proofs, and estimates
* the gas cost for executing the transaction on the source chain.
*/
declare function estimateGasForPost(params: {
postRequest: IPostRequest;
sourceClient: PublicClient;
hostLatestStateMachineHeight: bigint;
hostAddress: HexString;
}): Promise<bigint>;
/**
* Constructs the request body for a redeem escrow operation.
* This function encodes the order commitment, beneficiary address, and token inputs
* to match the format expected by the IntentGateway contract.
*/
declare function constructRedeemEscrowRequestBody(order: Order, beneficiary: HexString): HexString;
/**
* Calculates the balance mapping location for a given slot and holder address.
* This function handles the different encoding formats used by Solidity and Vyper.
*
* @param slot - The slot number to calculate the mapping location for.
* @param holder - The address of the holder to calculate the mapping location for.
* @param language - The language of the contract.
* @returns The balance mapping location as a HexString.
*/
declare function calculateBalanceMappingLocation(slot: bigint, holder: string, language: EvmLanguage): HexString;
interface SubstrateChainParams {
ws: string;
hasher: "Keccak" | "Blake2";
}
declare class SubstrateChain implements IChain {
private readonly params;
api?: ApiPromise;
constructor(params: SubstrateChainParams);
connect(): Promise<void>;
/**
* Disconnects the Substrate chain connection.
*/
disconnect(): Promise<void>;
/**
* Returns the storage key for a request receipt in the child trie
* The request commitment is the key
* @param key - The H256 hash key (as a 0x-prefixed hex string)
* @returns The storage key as a hex string
*/
requestReceiptKey(key: HexString): HexString;
/**
* Returns the storage key for a request commitment in the child trie
* The request commitment is the key
* @param key - The H256 hash key (as a 0x-prefixed hex string)
* @returns The storage key as a hex string
*/
requestCommitmentKey(key: HexString): HexString;
/**
* Queries a request commitment from the ISMP child trie storage.
* @param {HexString} commitment - The commitment hash to look up.
* @returns {Promise<HexString | undefined>} The commitment data if found, undefined otherwise.
*/
queryRequestCommitment(commitment: HexString): Promise<HexString | undefined>;
/**
* Queries the request receipt.
* @param {HexString} commitment - The commitment to query.
* @returns {Promise<HexString | undefined>} The relayer address responsible for delivering the request.
*/
queryRequestReceipt(commitment: HexString): Promise<HexString | undefined>;
/**
* Returns the current timestamp of the chain.
* @returns {Promise<bigint>} The current timestamp.
*/
timestamp(): Promise<bigint>;
/**
* Queries the proof of the commitments.
* @param {IMessage} message - The message to query.
* @param {string} counterparty - The counterparty address.
* @param {bigint} [at] - The block number to query at.
* @returns {Promise<HexString>} The proof.
*/
queryProof(message: IMessage, counterparty: string, at?: bigint): Promise<HexString>;
/**
* Submit an unsigned ISMP transaction to the chain. Resolves when the transaction is finalized.
* @param message - The message to be submitted.
* @returns A promise that resolves to an object containing the transaction hash, block hash, and block number.
*/
submitUnsigned(message: IIsmpMessage): Promise<{
transactionHash: string;
blockHash: string;
blockNumber: number;
timestamp: number;
}>;
/**
* Query the state proof for a given set of keys at a specific block height.
* @param at The block height to query the state proof at.
* @param keys The keys to query the state proof for.
* @returns The state proof as a hexadecimal string.
*/
queryStateProof(at: bigint, keys: HexString[]): Promise<HexString>;
/**
* Get the latest state machine height for a given state machine ID.
* @param {StateMachineIdParams} stateMachineId - The state machine ID.
* @returns {Promise<bigint>} The latest state machine height.
*/
latestStateMachineHeight(stateMachineId: StateMachineIdParams): Promise<bigint>;
/**
* Get the state machine update time for a given state machine height.
* @param {StateMachineHeight} stateMachineheight - The state machine height.
* @returns {Promise<bigint>} The statemachine update time in seconds.
*/
stateMachineUpdateTime(stateMachineHeight: StateMachineHeight): Promise<bigint>;
/**
* Get the challenge period for a given state machine id.
* @param {StateMachineIdParams} stateMachineId - The state machine ID.
* @returns {Promise<bigint>} The challenge period in seconds.
*/
challengePeriod(stateMachineId: StateMachineIdParams): Promise<bigint>;
/**
* Encode an ISMP calldata for a substrate chain.
* @param message The ISMP message to encode.
* @returns The encoded message as a hexadecimal string.
*/
encode(message: IIsmpMessage): HexString;
/**
* Returns the index of a pallet by its name, by looking up the pallets in the runtime metadata.
* @param {string} name - The name of the pallet.
* @returns {number} The index of the pallet.
*/
private getPalletIndex;
}
/**
* Converts a state machine ID string to an enum value.
* @param {string} id - The state machine ID string.
* @returns {IStateMachine} The corresponding enum value.
*/
declare function convertStateMachineIdToEnum(id: string): IStateMachine;
declare function encodeISMPMessage(message: IIsmpMessage): Uint8Array;
/**
* Type representing an ISMP message.
*/
type IIsmpMessage = IRequestMessage | ITimeoutPostRequestMessage | IGetResponseMessage;
interface IRequestMessage {
/**
* The kind of message.
*/
kind: "PostRequest";
/**
* The requests to be posted.
*/
requests: IPostRequest[];
/**
* The proof of the requests.
*/
proof: IProof;
/**
* The signer of the message.
*/
signer: HexString;
}
interface IGetRequestMessage {
/**
* The kind of message.
*/
kind: "GetRequest";
/**
* The requests to be posted.
*/
requests: IGetRequest[];
/**
* The proof of the requests.
*/
proof: IProof;
/**
* The signer of the message.
*/
signer: HexString;
}
interface IGetResponse {
/**
* The request that triggered this response.
*/
get: IGetRequest;
/**
* The response message.
*/
values: GetResponseStorageValues[];
}
interface IGetResponseMessage {
/**
* The kind of message.
*/
kind: "GetResponse";
/**
* The responses to be posted.
*/
responses: IGetResponse[];
/**
* The proof of the responses.
*/
proof: IProof;
/**
* The signer of the message.
*/
signer: HexString;
}
interface ITimeoutPostRequestMessage {
/**
* The kind of message.
*/
kind: "TimeoutPostRequest";
/**
* The requests to be posted.
*/
requests: IPostRequest[];
/**
* The proof of the requests.
*/
proof: IProof;
}
interface IProof {
/**
* The height of the proof.
*/
height: bigint;
/**
* The state machine identifier of the proof.
*/
stateMachine: string;
/**
* The associated consensus state identifier of the proof.
*/
consensusStateId: string;
/**
* The encoded storage proof
*/
proof: HexString;
}
/**
* Interface representing a chain.
*/
interface IChain {
timestamp(): Promise<bigint>;
/**
* Returns the state trie key for the request-receipt storage item for the given request commitment.
*/
requestReceiptKey(commitment: HexString): HexString;
/**
* Query and return the request-receipt for the given request commitment.
*/
queryRequestReceipt(commitment: HexString): Promise<HexString | undefined>;
/**
* Query and return the encoded storage proof for the provided keys at the given height.
*/
queryStateProof(at: bigint, keys: HexString[]): Promise<HexString>;
queryProof(message: IMessage, counterparty: string, at?: bigint): Promise<HexString>;
encode(message: IIsmpMessage): HexString;
/**
* Get the latest state machine height for a given state machine ID.
*/
latestStateMachineHeight(stateMachineId: StateMachineIdParams): Promise<bigint>;
/**
* Get the challenge period for a given state machine ID.
*/
challengePeriod(stateMachineId: StateMachineIdParams): Promise<bigint>;
/**
* Get the update time for a statemachine height.
*/
stateMachineUpdateTime(stateMachineHeight: StateMachineHeight): Promise<bigint>;
}
/**
* Returns the chain interface for a given state machine identifier
* @param chainConfig - Chain configuration
* @returns Chain interface
*/
declare function getChain(chainConfig: IEvmConfig | ISubstrateConfig): Promise<IChain>;
/**
* IndexerClient provides methods for interacting with the Hyperbridge indexer.
*
* This client facilitates querying and tracking cross-chain requests and their status
* through the Hyperbridge protocol. It supports:
*
* - Querying state machine updates by block height or timestamp
* - Retrieving request status information by transaction hash
* - Monitoring request status changes through streaming interfaces
* - Handling request timeout flows and related proof generation
* - Tracking request finalization across source and destination chains
*
* The client implements automatic retries with exponential backoff for network
* resilience and provides both simple query methods and advanced streaming
* interfaces for real-time status tracking.
*
* The URLs provided in the configuration must point to archive nodes to allow the client to query for storage proofs
* of potentially much older blocks. Regular nodes only store the state for recent blocks and will not be able
* to provide the necessary proofs for cross-chain verification, especially in timeout scenarios.
*
* @example
* ```typescript
* const client = new IndexerClient({
* url: "https://indexer.hyperbridge.xyz/graphql",
* pollInterval: 2000,
* source: {
* stateMachineId: "EVM-1",
* consensusStateId: "ETH0"
* rpcUrl: "",
* host: "0x87ea45..",
* },
* dest: {
* stateMachineId: "EVM-42161",
* consensusStateId: "ETH0"
* rpcUrl: "",
* host: "0x87ea42345..",
* },
* hyperbridge: {
* stateMachineId: "POLKADOT-3367",
* consensusStateId: "DOT0"
* wsUrl: "ws://localhost:9944"
* }
* });
*
* // Query a request status
* const status = await client.queryRequestWithStatus("0x1234...");
*
* // Stream status updates
* for await (const update of client.postRequestStatusStream("0x1234...")) {
* console.log(`Request status: ${update.status}`);
* }
* ```
*/
declare class IndexerClient {
/**
* GraphQL client used for making requests to the indexer
*/
private client;
/**
* Configuration for the IndexerClient including URLs, poll intervals, and chain-specific settings
*/
private config;
private logger;
/**
* Default configuration for retry behavior when network requests fail
* - maxRetries: Maximum number of retry attempts before failing
* - backoffMs: Initial backoff time in milliseconds (doubles with each retry)
*/
private defaultRetryConfig;
/**
* Creates a new IndexerClient instance
*/
constructor(config: PartialClientConfig);
/**
* Query for a single state machine update event greater than or equal to the given height.
* @params statemachineId - ID of the state machine
* @params height - Starting block height
* @params chain - The identifier for the chain where the state machine update should be queried (corresponds to a stateMachineId)
* @returns Closest state machine update
*/
queryStateMachineUpdateByHeight({ statemachineId, height, chain, }: {
statemachineId: string;
chain: string;
height: number;
}): Promise<StateMachineUpdate | undefined>;
/**
* Query for a single state machine update event greater than or equal to the given timestamp.
* @params statemachineId - ID of the state machine
* @params timestamp - Starting block timestamp
* @params chain - The identifier for the chain where the state machine update should be queried (corresponds to a stateMachineId)
* @returns Closest state machine update
*/
queryStateMachineUpdateByTimestamp({ statemachineId, commitmentTimestamp, chain, }: {
statemachineId: string;
commitmentTimestamp: bigint;
chain: string;
}): Promise<StateMachineUpdate | undefined>;
/**
* Queries a request by CommitmentHash
*
* @param commitment_hash - Can be commitment
* @returns Latest status and block metadata of the request
*/
queryPostRequest(commitment_hash: string): Promise<PostRequestWithStatus | undefined>;
/**
* Queries a request by any of its associated hashes and returns it alongside its statuses
* Statuses will be one of SOURCE, HYPERBRIDGE_DELIVERED and DESTINATION
* @param hash - Can be commitment, hyperbridge tx hash, source tx hash, destination tx hash, or timeout tx hash
* @returns Latest status and block metadata of the request
*/
queryGetRequest(hash: string): Promise<GetRequestWithStatus | undefined>;
/**
* Queries the response associated with a specific request ID and returns its commitment
* @param requestId - The ID of the request to find the associated response for
* @returns The response associated with the given request ID, or undefined if not found
*/
queryResponseByRequestId(requestId: string): Promise<ResponseCommitmentWithValues | undefined>;
/**
* Enhances a request with finality events by querying state machine updates.
*
* This method augments a request object with additional inferred status events
* that represent chain finality confirmations. It adds:
* - SOURCE_FINALIZED: When the source chain has finalized the request
* - HYPERBRIDGE_FINALIZED: When Hyperbridge has finalized the delivery confirmation
*
* The method also generates appropriate calldata for submitting cross-chain proofs
* when applicable.
*
* @param request - The request to enhance with finality events
* @returns The request with finality events added
* @private
*/
private addRequestFinalityEvents;
/**
* Adds timeout finality events to a request by querying for relevant timeout proofs and
* chain state necessary for timeout processing.
*
* This method enhances a request object with additional status events related to the
* timeout flow, including:
* - PENDING_TIMEOUT: When a request has passed its timeout timestamp
* - DESTINATION_FINALIZED: When the destination chain has finalized the timeout timestamp
* - HYPERBRIDGE_FINALIZED_TIMEOUT: When hyperbridge has finalized the timeout state
*
* The method also generates appropriate calldata for submitting timeout proofs.
*
* @param request - Request to fill timeout events for
* @returns Request with timeout events filled in, including any proof calldata for timeout submissions
* @private
*/
private addTimeoutFinalityEvents;
/**
* Queries a request returns it alongside its statuses,
* including any finalization events.
* @param hash - Commitment hash
* @returns Full request data with all inferred status events, including SOURCE_FINALIZED and HYPERBRIDGE_FINALIZED
* @remarks Unlike queryRequest(), this method adds derived finalization status events by querying state machine updates
*/
queryRequestWithStatus(hash: string): Promise<PostRequestWithStatus | undefined>;
/**
* Create a Stream of status updates for a post request.
* Stream ends when either the request reaches the destination or times out.
* If the stream yields TimeoutStatus.PENDING_TIMEOUT, use postRequestTimeoutStream() to begin timeout processing.
* @param hash - Can be commitment, hyperbridge tx hash, source tx hash, destination tx hash, or timeout tx hash
* @returns AsyncGenerator that emits status updates until a terminal state is reached
* @example
*
* let client = new IndexerClient(config)
* let stream = client.postRequestStatusStream(hash)
*
* // you can use a for-await-of loop
* for await (const status of stream) {
* console.log(status)
* }
*
* // you can also use a while loop
* while (true) {
* const status = await stream.next()
* if (status.done) {
* break
* }
* console.log(status.value)
* }
*
*/
postRequestStatusStream(hash: HexString): AsyncGenerator<RequestStatusWithMetadata, void>;
timeoutStream(timeoutTimestamp: bigint, chain: IChain): AsyncGenerator<RequestStatusWithMetadata, void>;
/**
* Create a Stream of status updates
* @param hash - Can be commitment, hyperbridge tx hash, source tx hash, destination tx hash, or timeout tx hash
* @returns AsyncGenerator that emits status updates until a terminal state is reached
*/
private postRequestStatusStreamInternal;
private sleep_for;
private sleep_for_interval;
/**
* Create a Stream of status updates for a get request.
* Stream ends when either the request reaches the destination or times out.
* If the stream yields TimeoutStatus.PENDING_TIMEOUT, use postRequestTimeoutStream() to begin timeout processing.
* @param hash - Can be commitment, hyperbridge tx hash, source tx hash, destination tx hash, or timeout tx hash
* @returns AsyncGenerator that emits status updates until a terminal state is reached
* @example
*
* let client = new IndexerClient(config)
* let stream = client.getRequestStatusStream(hash)
*
* // you can use a for-await-of loop
* for await (const status of stream) {
* console.log(status)
* }
*
* // you can also use a while loop
* while (true) {
* const status = await stream.next()
* if (status.done) {
* break
* }
* console.log(status.value)
* }
*
*/
getRequestStatusStream(hash: HexString): AsyncGenerator<RequestStatusWithMetadata, void>;
/**
* Create a Stream of status updates
* @param hash - Can be commitment, hyperbridge tx hash, source tx hash, destination tx hash, or timeout tx hash
* @returns AsyncGenerator that emits status updates until a terminal state is reached
*/
private getRequestStatusStreamInternal;
/**
* Create a Stream of status updates for a timed out post request.
* @param ha