@chainlink/ccip-sdk 0.94.0 → 0.96.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 (170) hide show
  1. package/README.md +2 -2
  2. package/dist/all-chains.d.ts +23 -0
  3. package/dist/all-chains.d.ts.map +1 -0
  4. package/dist/all-chains.js +24 -0
  5. package/dist/all-chains.js.map +1 -0
  6. package/dist/api/index.d.ts +86 -7
  7. package/dist/api/index.d.ts.map +1 -1
  8. package/dist/api/index.js +270 -10
  9. package/dist/api/index.js.map +1 -1
  10. package/dist/api/types.d.ts +134 -13
  11. package/dist/api/types.d.ts.map +1 -1
  12. package/dist/aptos/index.d.ts +38 -17
  13. package/dist/aptos/index.d.ts.map +1 -1
  14. package/dist/aptos/index.js +91 -61
  15. package/dist/aptos/index.js.map +1 -1
  16. package/dist/aptos/logs.js +3 -3
  17. package/dist/aptos/logs.js.map +1 -1
  18. package/dist/chain.d.ts +300 -42
  19. package/dist/chain.d.ts.map +1 -1
  20. package/dist/chain.js +160 -9
  21. package/dist/chain.js.map +1 -1
  22. package/dist/errors/codes.d.ts +9 -3
  23. package/dist/errors/codes.d.ts.map +1 -1
  24. package/dist/errors/codes.js +10 -3
  25. package/dist/errors/codes.js.map +1 -1
  26. package/dist/errors/index.d.ts +8 -8
  27. package/dist/errors/index.d.ts.map +1 -1
  28. package/dist/errors/index.js +8 -8
  29. package/dist/errors/index.js.map +1 -1
  30. package/dist/errors/recovery.d.ts.map +1 -1
  31. package/dist/errors/recovery.js +10 -4
  32. package/dist/errors/recovery.js.map +1 -1
  33. package/dist/errors/specialized.d.ts +62 -21
  34. package/dist/errors/specialized.d.ts.map +1 -1
  35. package/dist/errors/specialized.js +128 -41
  36. package/dist/errors/specialized.js.map +1 -1
  37. package/dist/evm/extra-args.d.ts +25 -0
  38. package/dist/evm/extra-args.d.ts.map +1 -0
  39. package/dist/evm/extra-args.js +328 -0
  40. package/dist/evm/extra-args.js.map +1 -0
  41. package/dist/evm/gas.d.ts +14 -0
  42. package/dist/evm/gas.d.ts.map +1 -0
  43. package/dist/evm/gas.js +92 -0
  44. package/dist/evm/gas.js.map +1 -0
  45. package/dist/evm/index.d.ts +76 -32
  46. package/dist/evm/index.d.ts.map +1 -1
  47. package/dist/evm/index.js +94 -104
  48. package/dist/evm/index.js.map +1 -1
  49. package/dist/evm/offchain.d.ts.map +1 -1
  50. package/dist/evm/offchain.js +8 -8
  51. package/dist/evm/offchain.js.map +1 -1
  52. package/dist/execution.d.ts.map +1 -1
  53. package/dist/execution.js +24 -3
  54. package/dist/execution.js.map +1 -1
  55. package/dist/extra-args.d.ts +103 -4
  56. package/dist/extra-args.d.ts.map +1 -1
  57. package/dist/extra-args.js +28 -3
  58. package/dist/extra-args.js.map +1 -1
  59. package/dist/gas.d.ts +46 -19
  60. package/dist/gas.d.ts.map +1 -1
  61. package/dist/gas.js +56 -68
  62. package/dist/gas.js.map +1 -1
  63. package/dist/index.d.ts +18 -15
  64. package/dist/index.d.ts.map +1 -1
  65. package/dist/index.js +14 -13
  66. package/dist/index.js.map +1 -1
  67. package/dist/offchain.d.ts +5 -4
  68. package/dist/offchain.d.ts.map +1 -1
  69. package/dist/offchain.js +7 -6
  70. package/dist/offchain.js.map +1 -1
  71. package/dist/requests.d.ts +30 -20
  72. package/dist/requests.d.ts.map +1 -1
  73. package/dist/requests.js +86 -56
  74. package/dist/requests.js.map +1 -1
  75. package/dist/selectors.d.ts +2 -1
  76. package/dist/selectors.d.ts.map +1 -1
  77. package/dist/selectors.js +625 -278
  78. package/dist/selectors.js.map +1 -1
  79. package/dist/solana/exec.d.ts.map +1 -1
  80. package/dist/solana/exec.js +2 -1
  81. package/dist/solana/exec.js.map +1 -1
  82. package/dist/solana/index.d.ts +73 -22
  83. package/dist/solana/index.d.ts.map +1 -1
  84. package/dist/solana/index.js +91 -28
  85. package/dist/solana/index.js.map +1 -1
  86. package/dist/solana/offchain.js +2 -2
  87. package/dist/solana/offchain.js.map +1 -1
  88. package/dist/solana/send.d.ts.map +1 -1
  89. package/dist/solana/send.js +6 -9
  90. package/dist/solana/send.js.map +1 -1
  91. package/dist/solana/utils.d.ts +29 -1
  92. package/dist/solana/utils.d.ts.map +1 -1
  93. package/dist/solana/utils.js +39 -1
  94. package/dist/solana/utils.js.map +1 -1
  95. package/dist/sui/discovery.d.ts +7 -4
  96. package/dist/sui/discovery.d.ts.map +1 -1
  97. package/dist/sui/discovery.js +66 -19
  98. package/dist/sui/discovery.js.map +1 -1
  99. package/dist/sui/events.d.ts +23 -12
  100. package/dist/sui/events.d.ts.map +1 -1
  101. package/dist/sui/events.js +267 -128
  102. package/dist/sui/events.js.map +1 -1
  103. package/dist/sui/index.d.ts +57 -41
  104. package/dist/sui/index.d.ts.map +1 -1
  105. package/dist/sui/index.js +286 -159
  106. package/dist/sui/index.js.map +1 -1
  107. package/dist/sui/objects.d.ts +14 -4
  108. package/dist/sui/objects.d.ts.map +1 -1
  109. package/dist/sui/objects.js +61 -68
  110. package/dist/sui/objects.js.map +1 -1
  111. package/dist/sui/types.d.ts +33 -0
  112. package/dist/sui/types.d.ts.map +1 -1
  113. package/dist/sui/types.js.map +1 -1
  114. package/dist/ton/index.d.ts +67 -21
  115. package/dist/ton/index.d.ts.map +1 -1
  116. package/dist/ton/index.js +159 -30
  117. package/dist/ton/index.js.map +1 -1
  118. package/dist/ton/send.d.ts +52 -0
  119. package/dist/ton/send.d.ts.map +1 -0
  120. package/dist/ton/send.js +166 -0
  121. package/dist/ton/send.js.map +1 -0
  122. package/dist/ton/utils.d.ts +3 -3
  123. package/dist/ton/utils.d.ts.map +1 -1
  124. package/dist/ton/utils.js +6 -5
  125. package/dist/ton/utils.js.map +1 -1
  126. package/dist/types.d.ts +126 -9
  127. package/dist/types.d.ts.map +1 -1
  128. package/dist/types.js +19 -5
  129. package/dist/types.js.map +1 -1
  130. package/dist/utils.d.ts +67 -4
  131. package/dist/utils.d.ts.map +1 -1
  132. package/dist/utils.js +126 -17
  133. package/dist/utils.js.map +1 -1
  134. package/package.json +14 -9
  135. package/src/all-chains.ts +26 -0
  136. package/src/api/index.ts +348 -13
  137. package/src/api/types.ts +160 -13
  138. package/src/aptos/index.ts +98 -76
  139. package/src/aptos/logs.ts +3 -3
  140. package/src/chain.ts +408 -51
  141. package/src/errors/codes.ts +10 -3
  142. package/src/errors/index.ts +8 -5
  143. package/src/errors/recovery.ts +18 -5
  144. package/src/errors/specialized.ts +168 -49
  145. package/src/evm/extra-args.ts +377 -0
  146. package/src/evm/gas.ts +150 -0
  147. package/src/evm/index.ts +123 -155
  148. package/src/evm/offchain.ts +15 -9
  149. package/src/execution.ts +26 -3
  150. package/src/extra-args.ts +108 -4
  151. package/src/gas.ts +101 -115
  152. package/src/index.ts +27 -14
  153. package/src/offchain.ts +12 -6
  154. package/src/requests.ts +117 -67
  155. package/src/selectors.ts +632 -280
  156. package/src/solana/exec.ts +3 -1
  157. package/src/solana/index.ts +97 -37
  158. package/src/solana/offchain.ts +2 -2
  159. package/src/solana/send.ts +5 -23
  160. package/src/solana/utils.ts +66 -0
  161. package/src/sui/discovery.ts +92 -31
  162. package/src/sui/events.ts +346 -239
  163. package/src/sui/index.ts +365 -212
  164. package/src/sui/objects.ts +74 -98
  165. package/src/sui/types.ts +35 -0
  166. package/src/ton/index.ts +199 -35
  167. package/src/ton/send.ts +222 -0
  168. package/src/ton/utils.ts +7 -6
  169. package/src/types.ts +128 -9
  170. package/src/utils.ts +169 -21
@@ -0,0 +1,222 @@
1
+ import { type Cell, beginCell, toNano } from '@ton/core'
2
+ import { type TonClient, Address } from '@ton/ton'
3
+ import { zeroPadValue } from 'ethers'
4
+
5
+ import type { UnsignedTONTx } from './types.ts'
6
+ import { CCIPError, CCIPErrorCode } from '../errors/index.ts'
7
+ import { EVMExtraArgsV2Tag } from '../extra-args.ts'
8
+ import type { AnyMessage, WithLogger } from '../types.ts'
9
+ import { bytesToBuffer, getDataBytes } from '../utils.ts'
10
+
11
+ /** Opcode for Router ccipSend operation */
12
+ export const CCIP_SEND_OPCODE = 0x31768d95
13
+
14
+ /** Default gas buffer to add to fee for transaction execution */
15
+ export const DEFAULT_GAS_BUFFER = toNano('0.5')
16
+
17
+ /** Default gas limit for destination chain execution */
18
+ export const DEFAULT_GAS_LIMIT = 200_000n
19
+
20
+ /**
21
+ * WRAPPED_NATIVE address for TON - sentinel address representing native TON.
22
+ * Used as feeToken for native TON payments in FeeQuoter calls.
23
+ */
24
+ export const WRAPPED_NATIVE = Address.parse(
25
+ '0:0000000000000000000000000000000000000000000000000000000000000001',
26
+ )
27
+
28
+ /**
29
+ * Encodes token amounts as a snaked cell.
30
+ * Empty cell for no tokens.
31
+ */
32
+ function encodeTokenAmounts(
33
+ tokenAmounts: readonly { token: string; amount: bigint }[] | undefined,
34
+ ): Cell {
35
+ if (!tokenAmounts || tokenAmounts.length === 0) {
36
+ return beginCell().endCell()
37
+ }
38
+
39
+ const builder = beginCell()
40
+ for (const ta of tokenAmounts) {
41
+ builder.storeRef(
42
+ beginCell().storeAddress(Address.parse(ta.token)).storeUint(ta.amount, 256).endCell(),
43
+ )
44
+ }
45
+ return builder.endCell()
46
+ }
47
+
48
+ /**
49
+ * Encodes extraArgs as a Cell using the GenericExtraArgsV2 (EVMExtraArgsV2) format.
50
+ *
51
+ * Format per chainlink-ton TL-B:
52
+ * - tag: 32-bit opcode (0x181dcf10)
53
+ * - gasLimit: Maybe<uint256> (1 bit flag + 256 bits if present)
54
+ * - allowOutOfOrderExecution: 1 bit (must be true)
55
+ */
56
+ function encodeExtraArgsCell(extraArgs: AnyMessage['extraArgs']): Cell {
57
+ const allowOutOfOrderExecution = true
58
+
59
+ let gasLimit = 0n
60
+ let hasGasLimit = false
61
+
62
+ if ('gasLimit' in extraArgs && extraArgs.gasLimit > 0n) {
63
+ hasGasLimit = true
64
+ gasLimit = extraArgs.gasLimit
65
+ }
66
+
67
+ const builder = beginCell()
68
+ .storeUint(Number(EVMExtraArgsV2Tag), 32) // 0x181dcf10
69
+ .storeBit(hasGasLimit)
70
+
71
+ if (hasGasLimit) {
72
+ builder.storeUint(gasLimit, 256)
73
+ }
74
+
75
+ return builder.storeBit(allowOutOfOrderExecution).endCell()
76
+ }
77
+
78
+ /**
79
+ * Builds the Router ccipSend message cell.
80
+ *
81
+ * Relies on TL-B structure (Router_CCIPSend) from chainlink-ton repo.
82
+ */
83
+ export function buildCcipSendCell(
84
+ destChainSelector: bigint,
85
+ message: AnyMessage,
86
+ feeTokenAddress: Address | null = null,
87
+ queryId = 0n,
88
+ ): Cell {
89
+ // Get receiver bytes and pad to 32 bytes for cross-chain encoding
90
+ const paddedReceiver = bytesToBuffer(zeroPadValue(getDataBytes(message.receiver), 32))
91
+
92
+ // Data cell (ref 0)
93
+ const dataCell = beginCell()
94
+ .storeBuffer(bytesToBuffer(message.data || '0x'))
95
+ .endCell()
96
+
97
+ // Token amounts snaked cell (ref 1)
98
+ const tokenAmountsCell = encodeTokenAmounts(message.tokenAmounts)
99
+
100
+ // ExtraArgs cell (ref 2)
101
+ const extraArgsCell = encodeExtraArgsCell(message.extraArgs)
102
+
103
+ return beginCell()
104
+ .storeUint(CCIP_SEND_OPCODE, 32) // opcode
105
+ .storeUint(Number(queryId), 64) // queryID
106
+ .storeUint(destChainSelector, 64) // destChainSelector
107
+ .storeUint(paddedReceiver.length, 8) // receiver length in bytes
108
+ .storeBuffer(paddedReceiver) // receiver bytes (32 bytes, left-padded)
109
+ .storeRef(dataCell) // ref 0: data
110
+ .storeRef(tokenAmountsCell) // ref 1: tokenAmounts
111
+ .storeAddress(feeTokenAddress) // null = addr_none for native TON
112
+ .storeRef(extraArgsCell) // ref 2: extraArgs
113
+ .endCell()
114
+ }
115
+
116
+ /**
117
+ * Gets the fee for sending a CCIP message by calling FeeQuoter.validatedFee.
118
+ *
119
+ * @param ctx - Context with TonClient provider and logger
120
+ * @param router - Router contract address
121
+ * @param destChainSelector - Destination chain selector
122
+ * @param message - CCIP message to quote
123
+ * @returns Fee amount in nanotons
124
+ */
125
+ export async function getFee(
126
+ ctx: { provider: TonClient } & WithLogger,
127
+ router: string,
128
+ destChainSelector: bigint,
129
+ message: AnyMessage,
130
+ ): Promise<bigint> {
131
+ const { provider, logger = console } = ctx
132
+ const routerAddress = Address.parse(router)
133
+
134
+ // FeeQuoter requires WRAPPED_NATIVE for native TON
135
+ const feeTokenAddress = message.feeToken ? Address.parse(message.feeToken) : WRAPPED_NATIVE
136
+
137
+ // Get FeeQuoter address via OnRamp
138
+ let feeQuoterAddress: Address
139
+ try {
140
+ const { stack: onRampStack } = await provider.runMethod(routerAddress, 'onRamp', [
141
+ { type: 'int', value: destChainSelector },
142
+ ])
143
+ const onRampAddress = onRampStack.readAddress()
144
+ logger.debug('OnRamp:', onRampAddress.toString())
145
+
146
+ const { stack: feeQuoterStack } = await provider.runMethod(onRampAddress, 'feeQuoter', [
147
+ { type: 'int', value: destChainSelector },
148
+ ])
149
+ feeQuoterAddress = feeQuoterStack.readAddress()
150
+ logger.debug('FeeQuoter:', feeQuoterAddress.toString())
151
+ } catch (e) {
152
+ throw new CCIPError(
153
+ CCIPErrorCode.CONTRACT_TYPE_INVALID,
154
+ `Could not get FeeQuoter address: ${e instanceof Error ? e.message : String(e)}`,
155
+ )
156
+ }
157
+
158
+ // Build stack parameters for validatedFee call
159
+ const paddedReceiver = bytesToBuffer(zeroPadValue(getDataBytes(message.receiver), 32))
160
+ const receiverSlice = beginCell().storeBuffer(paddedReceiver).endCell()
161
+ const dataCell = beginCell()
162
+ .storeBuffer(bytesToBuffer(message.data || '0x'))
163
+ .endCell()
164
+ const tokenAmountsCell = encodeTokenAmounts(message.tokenAmounts)
165
+ const extraArgsCell = encodeExtraArgsCell(message.extraArgs)
166
+ const feeTokenSlice = beginCell().storeAddress(feeTokenAddress).endCell()
167
+
168
+ const { stack: feeStack } = await provider.runMethod(feeQuoterAddress, 'validatedFee', [
169
+ { type: 'int', value: 0n },
170
+ { type: 'int', value: destChainSelector },
171
+ { type: 'slice', cell: receiverSlice },
172
+ { type: 'cell', cell: dataCell },
173
+ { type: 'cell', cell: tokenAmountsCell },
174
+ { type: 'slice', cell: feeTokenSlice },
175
+ { type: 'cell', cell: extraArgsCell },
176
+ ])
177
+
178
+ const fee = feeStack.readBigNumber()
179
+ if (fee < 0n) {
180
+ throw new CCIPError(CCIPErrorCode.MESSAGE_INVALID, `Invalid fee: ${fee}`)
181
+ }
182
+ logger.debug('CCIP fee:', fee.toString(), 'nanotons')
183
+ return fee
184
+ }
185
+
186
+ /**
187
+ * Generates an unsigned CCIP send transaction for the Router.
188
+ *
189
+ * @param ctx - Context with TonClient provider and logger
190
+ * @param _sender - Sender address (unused, for interface compatibility)
191
+ * @param router - Router contract address
192
+ * @param destChainSelector - Destination chain selector
193
+ * @param message - CCIP message with fee included
194
+ * @param opts - Optional gas buffer override
195
+ * @returns Unsigned transaction ready for signing
196
+ */
197
+ export function generateUnsignedCcipSend(
198
+ ctx: { provider: TonClient } & WithLogger,
199
+ _sender: string,
200
+ router: string,
201
+ destChainSelector: bigint,
202
+ message: AnyMessage & { fee: bigint },
203
+ opts?: { gasBuffer?: bigint },
204
+ ): Omit<UnsignedTONTx, 'family'> {
205
+ const { logger = console } = ctx
206
+ const gasBuffer = opts?.gasBuffer ?? DEFAULT_GAS_BUFFER
207
+
208
+ // Router accepts addr_none for native TON (unlike FeeQuoter which needs WRAPPED_NATIVE)
209
+ const feeTokenAddress = message.feeToken ? Address.parse(message.feeToken) : null
210
+
211
+ const ccipSendCell = buildCcipSendCell(destChainSelector, message, feeTokenAddress)
212
+ const totalValue = message.fee + gasBuffer
213
+
214
+ logger.debug('Generating ccipSend tx to router:', router)
215
+ logger.debug('Total value:', totalValue.toString(), 'nanotons')
216
+
217
+ return {
218
+ to: router,
219
+ body: ccipSendCell,
220
+ value: totalValue,
221
+ }
222
+ }
package/src/ton/utils.ts CHANGED
@@ -2,7 +2,7 @@ import { Cell, Dictionary, beginCell } from '@ton/core'
2
2
  import { hexlify, toBeHex } from 'ethers'
3
3
 
4
4
  import { CCIPTransactionNotFoundError } from '../errors/specialized.ts'
5
- import type { WithLogger } from '../types.ts'
5
+ import { type WithLogger, NetworkType } from '../types.ts'
6
6
  import { bytesToBuffer } from '../utils.ts'
7
7
 
8
8
  /**
@@ -340,14 +340,14 @@ export async function parseJettonContent(
340
340
  * TonCenter V3 provides an index that allows hash-only lookups.
341
341
  *
342
342
  * @param hash - Raw 64-char hex transaction hash
343
- * @param isTestnet - Whether to use testnet API
343
+ * @param networkType - Network type (mainnet or testnet)
344
344
  * @param fetch - Rate-limited fetch function
345
345
  * @param logger - Logger instance
346
346
  * @returns Transaction identifier components needed for V4 API lookup
347
347
  */
348
348
  export async function lookupTxByRawHash(
349
349
  hash: string,
350
- isTestnet: boolean,
350
+ networkType: NetworkType,
351
351
  fetch = globalThis.fetch,
352
352
  { logger = console }: WithLogger = {},
353
353
  ): Promise<{
@@ -355,9 +355,10 @@ export async function lookupTxByRawHash(
355
355
  lt: string
356
356
  hash: string
357
357
  }> {
358
- const baseUrl = isTestnet
359
- ? 'https://testnet.toncenter.com/api/v3/transactions'
360
- : 'https://toncenter.com/api/v3/transactions'
358
+ const baseUrl =
359
+ networkType === NetworkType.Mainnet
360
+ ? 'https://toncenter.com/api/v3/transactions'
361
+ : 'https://testnet.toncenter.com/api/v3/transactions'
361
362
 
362
363
  // TonCenter V3 accepts hex directly
363
364
  const cleanHash = bytesToBuffer(hash).toString('hex')
package/src/types.ts CHANGED
@@ -1,6 +1,7 @@
1
1
  import type { AbiParametersToPrimitiveTypes, ExtractAbiEvent } from 'abitype'
2
2
  import type { BytesLike, Log } from 'ethers'
3
3
 
4
+ import type { APICCIPRequestMetadata } from './api/types.ts'
4
5
  import type OffRamp_1_6_ABI from './evm/abi/OffRamp_1_6.ts'
5
6
  import type { CCIPMessage_EVM, CCIPMessage_V1_6_EVM } from './evm/messages.ts'
6
7
  import type { ExtraArgs } from './extra-args.ts'
@@ -60,15 +61,26 @@ export type MergeArrayElements<T, U> = {
60
61
  * Enumeration of supported blockchain families.
61
62
  */
62
63
  export const ChainFamily = {
63
- EVM: 'evm',
64
- Solana: 'solana',
65
- Aptos: 'aptos',
66
- Sui: 'sui',
67
- TON: 'ton',
64
+ EVM: 'EVM',
65
+ Solana: 'SVM',
66
+ Aptos: 'APTOS',
67
+ Sui: 'SUI',
68
+ TON: 'TON',
69
+ Unknown: 'UNKNOWN',
68
70
  } as const
69
71
  /** Type representing one of the supported chain families. */
70
72
  export type ChainFamily = (typeof ChainFamily)[keyof typeof ChainFamily]
71
73
 
74
+ /**
75
+ * Enumeration of network types (mainnet vs testnet).
76
+ */
77
+ export const NetworkType = {
78
+ Mainnet: 'MAINNET',
79
+ Testnet: 'TESTNET',
80
+ } as const
81
+ /** Type representing the network environment type. */
82
+ export type NetworkType = (typeof NetworkType)[keyof typeof NetworkType]
83
+
72
84
  /**
73
85
  * Enumeration of supported CCIP protocol versions.
74
86
  */
@@ -88,23 +100,44 @@ type ChainFamilyWithId<F extends ChainFamily> = F extends
88
100
  : F extends typeof ChainFamily.Solana
89
101
  ? { readonly family: F; readonly chainId: string }
90
102
  : F extends typeof ChainFamily.Aptos | typeof ChainFamily.Sui
91
- ? { readonly family: F; readonly chainId: `${F}:${number}` }
103
+ ? { readonly family: F; readonly chainId: `${Lowercase<F>}:${number}` }
92
104
  : never
93
105
 
94
106
  /**
95
107
  * Network information including chain selector and metadata.
108
+ *
109
+ * @example
110
+ * ```typescript
111
+ * const info: NetworkInfo = {
112
+ * chainSelector: 16015286601757825753n,
113
+ * name: 'ethereum-testnet-sepolia',
114
+ * networkType: 'TESTNET',
115
+ * family: 'EVM',
116
+ * chainId: 11155111,
117
+ * }
118
+ * ```
96
119
  */
97
120
  export type NetworkInfo<F extends ChainFamily = ChainFamily> = {
98
121
  /** Unique chain selector used by CCIP. */
99
122
  readonly chainSelector: bigint
100
123
  /** Human-readable network name. */
101
124
  readonly name: string
102
- /** Whether this is a testnet. */
103
- readonly isTestnet: boolean
125
+ /** Network environment type. */
126
+ readonly networkType: NetworkType
104
127
  } & ChainFamilyWithId<F>
105
128
 
106
129
  /**
107
130
  * CCIP lane configuration connecting source and destination chains.
131
+ *
132
+ * @example
133
+ * ```typescript
134
+ * const lane: Lane = {
135
+ * sourceChainSelector: 16015286601757825753n, // Ethereum Sepolia
136
+ * destChainSelector: 12532609583862916517n, // Polygon Mumbai
137
+ * onRamp: '0x1234...abcd',
138
+ * version: '1.6.0',
139
+ * }
140
+ * ```
108
141
  */
109
142
  export interface Lane<V extends CCIPVersion = CCIPVersion> {
110
143
  /** Source chain selector. */
@@ -138,6 +171,17 @@ export type Log_ = Pick<Log, 'topics' | 'index' | 'address' | 'blockNumber' | 't
138
171
 
139
172
  /**
140
173
  * Generic transaction structure compatible across chain families.
174
+ *
175
+ * @example
176
+ * ```typescript
177
+ * const tx: ChainTransaction = {
178
+ * hash: '0xabc123...',
179
+ * logs: [],
180
+ * blockNumber: 12345678,
181
+ * timestamp: 1704067200,
182
+ * from: '0x1234...abcd',
183
+ * }
184
+ * ```
141
185
  */
142
186
  export type ChainTransaction = {
143
187
  /** Transaction hash. */
@@ -166,6 +210,29 @@ export interface CCIPRequest<V extends CCIPVersion = CCIPVersion> {
166
210
  log: Log_
167
211
  /** Transaction that emitted the request. */
168
212
  tx: Pick<ChainTransaction, 'hash' | 'logs' | 'blockNumber' | 'timestamp' | 'from' | 'error'>
213
+
214
+ /**
215
+ * API-enriched metadata. Present only when fetched via CCIP API.
216
+ *
217
+ * @remarks
218
+ * When a request is fetched using {@link Chain.getMessageById} or as a fallback
219
+ * in {@link Chain.getMessagesInTx}, this field contains additional information
220
+ * including message status, execution details, and network info.
221
+ *
222
+ * When constructed from on-chain data only, this field is `undefined`.
223
+ *
224
+ * @example
225
+ * ```typescript
226
+ * const request = await chain.getMessageById(messageId)
227
+ * if (request.metadata) {
228
+ * console.log('Status:', request.metadata.status)
229
+ * console.log('Delivery time:', request.metadata.deliveryTime)
230
+ * }
231
+ * ```
232
+ *
233
+ * @see {@link APICCIPRequestMetadata}
234
+ */
235
+ metadata?: APICCIPRequestMetadata
169
236
  }
170
237
 
171
238
  /**
@@ -216,6 +283,12 @@ export const MessageStatus = {
216
283
  Success: 'SUCCESS',
217
284
  /** Message execution failed on destination. */
218
285
  Failed: 'FAILED',
286
+ /** Message is being verified by the CCIP network */
287
+ Verifying: 'VERIFYING',
288
+ /** Message has been verified by the CCIP network */
289
+ Verified: 'VERIFIED',
290
+ /** Unknown status returned by API */
291
+ Unknown: 'UNKNOWN',
219
292
  } as const
220
293
  /** Type representing a CCIP message lifecycle status. */
221
294
  export type MessageStatus = (typeof MessageStatus)[keyof typeof MessageStatus]
@@ -237,6 +310,16 @@ export type IntentStatus = (typeof IntentStatus)[keyof typeof IntentStatus]
237
310
 
238
311
  /**
239
312
  * Receipt of a CCIP message execution on the destination chain.
313
+ *
314
+ * @example
315
+ * ```typescript
316
+ * const receipt: ExecutionReceipt = {
317
+ * messageId: '0xabc123...',
318
+ * sequenceNumber: 42n,
319
+ * state: ExecutionState.Success,
320
+ * sourceChainSelector: 16015286601757825753n,
321
+ * }
322
+ * ```
240
323
  */
241
324
  export type ExecutionReceipt = {
242
325
  /** Unique message identifier. */
@@ -274,6 +357,17 @@ export type OffchainTokenData = { _tag: string; [k: string]: BytesLike } | undef
274
357
 
275
358
  /**
276
359
  * Execution report containing message, proofs, and offchain token data.
360
+ *
361
+ * @example
362
+ * ```typescript
363
+ * const report: ExecutionReport = {
364
+ * message: { messageId: '0x...', ... },
365
+ * proofs: ['0xproof1...', '0xproof2...'],
366
+ * proofFlagBits: 0n,
367
+ * merkleRoot: '0xroot...',
368
+ * offchainTokenData: [],
369
+ * }
370
+ * ```
277
371
  */
278
372
  export type ExecutionReport<M extends CCIPMessage = CCIPMessage> = {
279
373
  /** The CCIP message to execute. */
@@ -290,6 +384,16 @@ export type ExecutionReport<M extends CCIPMessage = CCIPMessage> = {
290
384
 
291
385
  /**
292
386
  * A message to be sent to another network.
387
+ *
388
+ * @example
389
+ * ```typescript
390
+ * const message: AnyMessage = {
391
+ * receiver: '0x1234...abcd',
392
+ * extraArgs: { gasLimit: 200_000n, allowOutOfOrderExecution: true },
393
+ * data: '0xdeadbeef',
394
+ * tokenAmounts: [{ token: '0xtoken...', amount: 1000000n }],
395
+ * }
396
+ * ```
293
397
  */
294
398
  export type AnyMessage = {
295
399
  /** Receiver address on the destination chain. */
@@ -305,7 +409,22 @@ export type AnyMessage = {
305
409
  }
306
410
 
307
411
  /**
308
- * Partial [[AnyMessage]], which populates default fields like `extraArgs` if needed
412
+ * Partial {@link AnyMessage}, which populates default fields like `extraArgs` if needed.
413
+ *
414
+ * @example
415
+ * ```typescript
416
+ * // Minimal input - only receiver required, defaults applied for extraArgs
417
+ * const input: MessageInput = {
418
+ * receiver: '0x1234...abcd',
419
+ * }
420
+ *
421
+ * // With custom gas limit
422
+ * const inputWithGas: MessageInput = {
423
+ * receiver: '0x1234...abcd',
424
+ * extraArgs: { gasLimit: 500_000n },
425
+ * data: '0xdeadbeef',
426
+ * }
427
+ * ```
309
428
  */
310
429
  export type MessageInput = Partial<AnyMessage> & {
311
430
  receiver: AnyMessage['receiver']