@rozoai/intent-common 0.0.32-beta.1 → 0.0.32-beta.3

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 (52) hide show
  1. package/README.md +134 -0
  2. package/dist/api/base.d.ts +1 -1
  3. package/dist/api/base.js +2 -1
  4. package/dist/api/base.js.map +1 -1
  5. package/dist/api/fee.d.ts +2 -1
  6. package/dist/api/fee.js +5 -1
  7. package/dist/api/fee.js.map +1 -1
  8. package/dist/api/new-payment.d.ts +319 -0
  9. package/dist/api/new-payment.js +140 -0
  10. package/dist/api/new-payment.js.map +1 -0
  11. package/dist/api/payment.d.ts +106 -5
  12. package/dist/api/payment.js +117 -10
  13. package/dist/api/payment.js.map +1 -1
  14. package/dist/bridge.d.ts +84 -46
  15. package/dist/bridge.js +183 -169
  16. package/dist/bridge.js.map +1 -1
  17. package/dist/chain.d.ts +6 -0
  18. package/dist/chain.js +38 -14
  19. package/dist/chain.js.map +1 -1
  20. package/dist/daimoPay.d.ts +9 -9
  21. package/dist/daimoPay.js +5 -0
  22. package/dist/daimoPay.js.map +1 -1
  23. package/dist/index.d.ts +2 -0
  24. package/dist/index.js +2 -0
  25. package/dist/index.js.map +1 -1
  26. package/dist/token.d.ts +9 -0
  27. package/dist/token.js +111 -17
  28. package/dist/token.js.map +1 -1
  29. package/dist/validation.d.ts +9 -0
  30. package/dist/validation.js +47 -0
  31. package/dist/validation.js.map +1 -0
  32. package/package.json +4 -2
  33. package/src/api/base.ts +3 -1
  34. package/src/api/fee.ts +8 -2
  35. package/src/api/new-payment.ts +433 -0
  36. package/src/api/payment.ts +172 -13
  37. package/src/bridge.ts +225 -201
  38. package/src/chain.ts +40 -13
  39. package/src/daimoPay.ts +17 -9
  40. package/src/index.ts +2 -0
  41. package/src/token.ts +124 -18
  42. package/src/validation.ts +54 -0
  43. package/test/bridge.test.ts +393 -0
  44. package/dist/chainAddress.d.ts +0 -27
  45. package/dist/chainAddress.js +0 -87
  46. package/dist/chainAddress.js.map +0 -1
  47. package/dist/supportedChain.d.ts +0 -27
  48. package/dist/supportedChain.js +0 -87
  49. package/dist/supportedChain.js.map +0 -1
  50. package/dist/supportedChains.d.ts +0 -27
  51. package/dist/supportedChains.js +0 -87
  52. package/dist/supportedChains.js.map +0 -1
package/src/bridge.ts CHANGED
@@ -1,42 +1,36 @@
1
1
  import { parseUnits } from "viem";
2
2
  import {
3
- base,
4
3
  baseUSDC,
5
- bscUSDT,
6
- ethereum,
7
- ethereumUSDC,
4
+ getChainById,
8
5
  getKnownToken,
9
- polygon,
10
- polygonUSDC,
6
+ isChainSupported,
7
+ isTokenSupported,
8
+ PaymentResponse,
11
9
  RozoPayHydratedOrderWithOrg,
12
10
  RozoPayIntentStatus,
13
11
  RozoPayOrderMode,
14
12
  RozoPayOrderStatusDest,
15
13
  RozoPayOrderStatusSource,
16
14
  RozoPayUserMetadata,
17
- rozoSolana,
18
15
  rozoSolanaUSDC,
19
- rozoStellar,
20
16
  rozoStellarUSDC,
21
- worldchainUSDC,
17
+ validateAddressForChain,
22
18
  } from ".";
23
19
  import type { PaymentResponseData } from "./api/payment";
24
20
 
25
21
  export interface PaymentBridgeConfig {
26
- toChain?: number;
27
- toToken?: string;
22
+ toChain: number;
23
+ toToken: string;
28
24
  toAddress: string;
29
- toStellarAddress?: string;
30
- toSolanaAddress?: string;
31
25
  toUnits: string;
32
- payInTokenAddress: string;
33
- log?: (msg: string) => void;
26
+ preferredChain: number;
27
+ preferredTokenAddress: string;
34
28
  }
35
29
 
36
30
  export interface PreferredPaymentConfig {
37
31
  preferredChain: string;
38
- preferredToken: "USDC" | "USDT" | "XLM";
39
- preferredTokenAddress?: string;
32
+ preferredToken: string;
33
+ preferredTokenAddress: string;
40
34
  }
41
35
 
42
36
  export interface DestinationConfig {
@@ -47,11 +41,17 @@ export interface DestinationConfig {
47
41
  tokenAddress: string;
48
42
  }
49
43
 
44
+ interface PaymentBridge {
45
+ preferred: PreferredPaymentConfig;
46
+ destination: DestinationConfig;
47
+ isIntentPayment: boolean;
48
+ }
49
+
50
50
  /**
51
51
  * Creates payment bridge configuration for cross-chain payment routing
52
52
  *
53
53
  * Determines the optimal payment routing based on the destination chain/token
54
- * and the wallet payment option selected by the user. This function handles
54
+ * and the preferred payment method selected by the user. This function handles
55
55
  * the complexity of multi-chain payments by:
56
56
  *
57
57
  * 1. **Preferred Payment Method**: Identifies which chain/token the user will pay from
@@ -60,198 +60,178 @@ export interface DestinationConfig {
60
60
  *
61
61
  * 2. **Destination Configuration**: Determines where funds will be received
62
62
  * - Supports Base, Solana, Stellar, and Worldchain as destination chains
63
- * - Handles special address formats for Solana and Stellar addresses
64
- * - Defaults to Base USDC when no special destination is specified
63
+ * - Automatically handles special address formats for Solana and Stellar addresses
64
+ * - Configures destination token based on chain type (e.g., Stellar/Solana USDC)
65
65
  *
66
- * 3. **Cross-Chain Bridging**: Configures the payment bridge parameters
67
- * - Maps user's selected wallet/token to the appropriate payment method
68
- * - Sets up destination chain and token configuration
69
- * - Handles token address formatting (e.g., Stellar's `USDC:issuerPK` format)
66
+ * 3. **Intent Payment Detection**: Determines if this is a cross-chain intent payment
67
+ * - Returns `isIntentPayment: true` when preferred chain/token differs from destination
68
+ * - Returns `isIntentPayment: false` for same-chain, same-token payments
70
69
  *
71
70
  * @param config - Payment bridge configuration parameters
72
- * @param config.toChain - Destination chain ID (defaults to Base: 8453)
73
- * @param config.toToken - Destination token address (defaults to Base USDC)
74
- * @param config.toAddress - Standard EVM destination address
75
- * @param config.toStellarAddress - Stellar-specific destination address (if paying to Stellar)
76
- * @param config.toSolanaAddress - Solana-specific destination address (if paying to Solana)
77
- * @param config.toUnits - Amount in token units (smallest denomination)
78
- * @param config.payInTokenAddress - Token address user selected to pay with
79
- * @param config.log - Optional logging function for debugging
71
+ * @param config.toChain - Destination chain ID (e.g., 8453 for Base, 900 for Solana, 10001 for Stellar)
72
+ * @param config.toToken - Destination token address (must be a supported token on the destination chain)
73
+ * @param config.toAddress - Destination address (format validated based on chain type: EVM 0x..., Solana Base58, Stellar G...)
74
+ * @param config.toUnits - Amount in human-readable units (e.g., "1" for 1 USDC, "0.5" for half a USDC)
75
+ * @param config.preferredChain - Chain ID where the user will pay from (e.g., 137 for Polygon, 8453 for Base)
76
+ * @param config.preferredTokenAddress - Token address the user selected to pay with (must be a supported token on preferredChain)
80
77
  *
81
- * @returns Payment routing configuration
78
+ * @returns Payment routing configuration object
82
79
  * @returns preferred - Source payment configuration (chain, token user will pay from)
80
+ * @returns preferred.preferredChain - Chain ID as string where payment originates
81
+ * @returns preferred.preferredToken - Token symbol (e.g., "USDC", "USDT")
82
+ * @returns preferred.preferredTokenAddress - Token contract address
83
83
  * @returns destination - Destination payment configuration (chain, token user will receive)
84
+ * @returns destination.destinationAddress - Address where funds will be received
85
+ * @returns destination.chainId - Destination chain ID as string
86
+ * @returns destination.amountUnits - Payment amount in token units
87
+ * @returns destination.tokenSymbol - Destination token symbol
88
+ * @returns destination.tokenAddress - Destination token contract address
89
+ * @returns isIntentPayment - Boolean indicating if this is a cross-chain intent payment
90
+ *
91
+ * @throws {Error} If the destination token is not supported for the destination chain
92
+ * @throws {Error} If the destination address format is invalid for the destination chain
93
+ * @throws {Error} If the preferred token is not supported for the preferred chain
94
+ * @throws {Error} If the destination chain or token is not supported
84
95
  *
85
96
  * @example
86
97
  * ```typescript
87
98
  * // User wants to pay with Polygon USDC to receive on Base
88
- * const { preferred, destination } = createPaymentBridgeConfig({
89
- * toChain: 8453, // Base
99
+ * import { baseUSDC, polygonUSDCe } from '@rozoai/intent-common';
100
+ * import { base, polygon } from '@rozoai/intent-common';
101
+ *
102
+ * const { preferred, destination, isIntentPayment } = createPaymentBridgeConfig({
103
+ * toChain: base.chainId, // 8453
90
104
  * toToken: baseUSDC.token,
91
- * toAddress: '0x123...',
92
- * toUnits: '1000000', // 1 USDC
93
- * payInTokenAddress: polygonUSDC.token,
94
- * log: console.log
105
+ * toAddress: '0x742d35Cc6634C0532925a3b844Bc9e7595f0bEb',
106
+ * toUnits: '1000000', // 1 USDC (6 decimals)
107
+ * preferredChain: polygon.chainId, // 137
108
+ * preferredToken: polygonUSDCe.token,
95
109
  * });
96
110
  *
97
- * // preferred = { preferredChain: '137', preferredToken: 'USDC', preferredTokenAddress: '0x2791...' }
98
- * // destination = { destinationAddress: '0x123...', chainId: '8453', amountUnits: '1000000', ... }
111
+ * // preferred = { preferredChain: '137', preferredToken: 'USDCe', preferredTokenAddress: '0x2791...' }
112
+ * // destination = { destinationAddress: '0x742d...', chainId: '8453', amountUnits: '1000000', tokenSymbol: 'USDC', tokenAddress: '0x8335...' }
113
+ * // isIntentPayment = true (different chains)
99
114
  * ```
100
115
  *
101
116
  * @example
102
117
  * ```typescript
103
- * // User wants to pay to a Stellar address
104
- * const { preferred, destination } = createPaymentBridgeConfig({
105
- * toStellarAddress: 'GDZS...',
106
- * toUnits: '1000000',
107
- * payInTokenAddress: baseUSDC.token,
118
+ * // User wants to pay to a Stellar address using Base USDC
119
+ * import { baseUSDC, rozoStellarUSDC } from '@rozoai/intent-common';
120
+ * import { base, rozoStellar } from '@rozoai/intent-common';
121
+ *
122
+ * const { preferred, destination, isIntentPayment } = createPaymentBridgeConfig({
123
+ * toChain: rozoStellar.chainId, // 10001
124
+ * toToken: rozoStellarUSDC.token,
125
+ * toAddress: 'GA5ZSEJYB37JRC5AVCIA5MOP4RHTM335X2KGX3IHOJAPP5RE34K4KZVN',
126
+ * toUnits: '10000000', // 1 USDC (7 decimals for Stellar)
127
+ * preferredChain: base.chainId, // 8453
128
+ * preferredToken: baseUSDC.token,
108
129
  * });
109
130
  *
110
- * // destination will be configured for Stellar chain with USDC:issuerPK format
131
+ * // preferred = { preferredChain: '8453', preferredToken: 'USDC', preferredTokenAddress: '0x8335...' }
132
+ * // destination = { destinationAddress: 'GA5Z...', chainId: '10001', amountUnits: '10000000', tokenSymbol: 'USDC', tokenAddress: 'USDC:GA5Z...' }
133
+ * // isIntentPayment = true (Base to Stellar)
111
134
  * ```
112
135
  *
113
- * @note Currently only supports Base USDC and Stellar USDC as destination chains.
114
- * Support for additional destination chains is planned.
136
+ * @example
137
+ * ```typescript
138
+ * // Same-chain payment (not an intent payment)
139
+ * const { preferred, destination, isIntentPayment } = createPaymentBridgeConfig({
140
+ * toChain: base.chainId, // 8453
141
+ * toToken: baseUSDC.token,
142
+ * toAddress: '0x742d35Cc6634C0532925a3b844Bc9e7595f0bEb',
143
+ * toUnits: '1000000',
144
+ * preferredChain: base.chainId, // 8453
145
+ * preferredToken: baseUSDC.token,
146
+ * });
147
+ *
148
+ * // isIntentPayment = false (same chain and token)
149
+ * ```
115
150
  *
116
151
  * @see PreferredPaymentConfig
117
152
  * @see DestinationConfig
153
+ * @see PaymentBridgeConfig
118
154
  */
119
155
  export function createPaymentBridgeConfig({
120
- toChain = baseUSDC.chainId,
121
- toToken = baseUSDC.token,
156
+ toChain,
157
+ toToken,
122
158
  toAddress,
123
- toStellarAddress,
124
- toSolanaAddress,
125
159
  toUnits,
126
- payInTokenAddress,
127
- log,
128
- }: PaymentBridgeConfig): {
129
- preferred: PreferredPaymentConfig;
130
- destination: DestinationConfig;
131
- } {
132
- // Default configuration for Base USDC payments
160
+ preferredChain,
161
+ preferredTokenAddress,
162
+ }: PaymentBridgeConfig): PaymentBridge {
163
+ const chain = getChainById(toChain);
164
+ const token = getKnownToken(toChain, toToken);
165
+
166
+ if (!token) {
167
+ throw new Error(
168
+ `Unsupported token ${toToken} for chain ${chain.name} (${toChain})`
169
+ );
170
+ }
171
+
172
+ const addressValid = validateAddressForChain(toChain, toAddress);
173
+ if (!addressValid) {
174
+ throw new Error(
175
+ `Invalid address ${toAddress} for chain ${chain.name} (${toChain})`
176
+ );
177
+ }
178
+
179
+ const tokenConfig = getKnownToken(preferredChain, preferredTokenAddress);
180
+ if (!tokenConfig) {
181
+ throw new Error(
182
+ `Unknown token ${preferredTokenAddress} for chain ${chain.name} (${preferredChain})`
183
+ );
184
+ }
185
+
133
186
  let preferred: PreferredPaymentConfig = {
134
- preferredChain: String(toChain),
135
- preferredToken: "USDC",
187
+ preferredChain: String(preferredChain),
188
+ preferredToken: tokenConfig.symbol,
189
+ preferredTokenAddress: preferredTokenAddress,
136
190
  };
137
191
 
138
192
  let destination: DestinationConfig = {
139
193
  destinationAddress: toAddress,
140
194
  chainId: String(toChain),
141
195
  amountUnits: toUnits,
142
- tokenSymbol: "USDC",
196
+ tokenSymbol: token.symbol,
143
197
  tokenAddress: toToken,
144
198
  };
145
199
 
146
- /**
147
- * IMPORTANT: Because we only support PAY OUT USDC EVM & NON-EVM
148
- * So, We force toChain and toToken to Base USDC as default PayParams
149
- *
150
- * @TODO: Adjust this when we support another PAY OUT chain
151
- */
152
- const supportedChains = [
153
- base.chainId,
154
- polygon.chainId,
155
- ethereum.chainId,
156
- rozoSolana.chainId,
157
- rozoStellar.chainId,
158
- ];
159
- const supportedTokens = [
160
- baseUSDC.token,
161
- polygonUSDC.token,
162
- ethereumUSDC.token,
163
- rozoSolanaUSDC.token,
164
- rozoStellarUSDC.token,
165
- ];
166
-
167
- if (supportedChains.includes(toChain) && supportedTokens.includes(toToken)) {
168
- // Determine preferred payment method based on wallet selection
169
- if (payInTokenAddress) {
170
- // Pay In USDC Polygon
171
- if (payInTokenAddress === polygonUSDC.token) {
172
- log?.(`[Payment Bridge] Pay In USDC Polygon`);
173
- preferred = {
174
- preferredChain: String(polygonUSDC.chainId),
175
- preferredToken: "USDC",
176
- preferredTokenAddress: polygonUSDC.token,
177
- };
178
- }
179
- // Pay In USDC Ethereum
180
- else if (payInTokenAddress === ethereumUSDC.token) {
181
- log?.(`[Payment Bridge] Pay In USDC Ethereum`);
182
- preferred = {
183
- preferredChain: String(ethereumUSDC.chainId),
184
- preferredToken: "USDC",
185
- preferredTokenAddress: ethereumUSDC.token,
186
- };
187
- }
188
- // Pay In USDC Solana
189
- else if (payInTokenAddress === rozoSolanaUSDC.token) {
190
- log?.(`[Payment Bridge] Pay In USDC Solana`);
191
- preferred = {
192
- preferredChain: String(rozoSolanaUSDC.chainId),
193
- preferredToken: "USDC",
194
- preferredTokenAddress: rozoSolanaUSDC.token,
195
- };
196
- }
197
- // Pay In USDC Stellar
198
- else if (
199
- payInTokenAddress === rozoStellarUSDC.token ||
200
- payInTokenAddress === `USDC:${rozoStellarUSDC.token}`
201
- ) {
202
- log?.(`[Payment Bridge] Pay In USDC Stellar`);
203
- preferred = {
204
- preferredChain: String(rozoStellarUSDC.chainId),
205
- preferredToken: "USDC",
206
- preferredTokenAddress: `USDC:${rozoStellarUSDC.token}`,
207
- };
208
- }
209
- // Pay In USDC Worldchain
210
- else if (payInTokenAddress === worldchainUSDC.token) {
211
- log?.(`[Payment Bridge] Pay In USDC Worldchain`);
212
- preferred = {
213
- preferredChain: String(worldchainUSDC.chainId),
214
- preferredToken: "USDC",
215
- preferredTokenAddress: worldchainUSDC.token,
216
- };
217
- }
218
- // Pay In USDT BSC
219
- else if (payInTokenAddress === bscUSDT.token) {
220
- log?.(`[Payment Bridge] Pay In USDT BSC`);
221
- preferred = {
222
- preferredChain: String(bscUSDT.chainId),
223
- preferredToken: "USDT",
224
- preferredTokenAddress: bscUSDT.token,
225
- };
226
- }
227
- }
200
+ if (isChainSupported(toChain) && isTokenSupported(toChain, toToken)) {
201
+ preferred = {
202
+ preferredChain: String(tokenConfig.chainId),
203
+ preferredToken: tokenConfig.symbol,
204
+ preferredTokenAddress: tokenConfig.token,
205
+ };
228
206
 
229
207
  // Determine destination based on special address types
230
- if (toStellarAddress) {
231
- log?.(`[Payment Bridge] Pay Out USDC Stellar`);
208
+ if (isChainSupported(toChain, "stellar")) {
232
209
  destination = {
233
- destinationAddress: toStellarAddress,
234
- chainId: String(rozoStellar.chainId),
235
- amountUnits: toUnits,
236
- tokenSymbol: "USDC",
237
- tokenAddress: `USDC:${rozoStellarUSDC.token}`,
210
+ ...destination,
211
+ tokenSymbol: rozoStellarUSDC.symbol,
212
+ chainId: String(rozoStellarUSDC.chainId),
213
+ tokenAddress: rozoStellarUSDC.token,
238
214
  };
239
- } else if (toSolanaAddress) {
240
- log?.(`[Payment Bridge] Pay Out USDC Solana`);
215
+ } else if (isChainSupported(toChain, "solana")) {
241
216
  destination = {
242
- destinationAddress: toSolanaAddress,
217
+ ...destination,
218
+ tokenSymbol: rozoSolanaUSDC.symbol,
243
219
  chainId: String(rozoSolanaUSDC.chainId),
244
- amountUnits: toUnits,
245
- tokenSymbol: "USDC",
246
220
  tokenAddress: rozoSolanaUSDC.token,
247
221
  };
248
- } else {
249
- log?.(`[Payment Bridge] Pay Out USDC EVM`);
250
- // Keep default Base configuration
251
222
  }
223
+ } else {
224
+ throw new Error(
225
+ `Unsupported chain ${chain.name} (${toChain}) or token ${token.symbol} (${toToken})`
226
+ );
252
227
  }
253
228
 
254
- return { preferred, destination };
229
+ // If the preferred chain and token are not the same as the toChain and toToken, then it is an intent payment
230
+ const isIntentPayment =
231
+ preferred.preferredChain !== String(toChain) &&
232
+ preferred.preferredTokenAddress !== toToken;
233
+
234
+ return { preferred, destination, isIntentPayment };
255
235
  }
256
236
 
257
237
  /**
@@ -327,9 +307,9 @@ export function formatResponseToHydratedOrder(
327
307
 
328
308
  const requiredChain = order.metadata.preferredChain || baseUSDC.chainId;
329
309
 
330
- const chain = getKnownToken(
310
+ const token = getKnownToken(
331
311
  Number(requiredChain),
332
- Number(requiredChain) === rozoStellar.chainId
312
+ Number(requiredChain) === rozoStellarUSDC.chainId
333
313
  ? rozoStellarUSDC.token
334
314
  : order.metadata.preferredTokenAddress
335
315
  );
@@ -338,51 +318,48 @@ export function formatResponseToHydratedOrder(
338
318
  id: BigInt(Math.floor(Math.random() * Number.MAX_SAFE_INTEGER)),
339
319
  mode: RozoPayOrderMode.HYDRATED,
340
320
  intentAddr: destAddress,
341
- handoffAddr: destAddress,
342
- escrowContractAddress: destAddress,
343
- bridgerContractAddress: destAddress,
344
321
  // @TODO: use correct destination token
345
- bridgeTokenOutOptions: [
346
- {
347
- token: {
348
- chainId: baseUSDC.chainId,
349
- token: baseUSDC.token,
350
- symbol: baseUSDC.symbol,
351
- usd: 1,
352
- priceFromUsd: 1,
353
- decimals: baseUSDC.decimals,
354
- displayDecimals: 2,
355
- logoSourceURI: baseUSDC.logoSourceURI,
356
- logoURI: baseUSDC.logoURI,
357
- maxAcceptUsd: 100000,
358
- maxSendUsd: 0,
359
- },
360
- amount: parseUnits(
361
- order.destination.amountUnits,
362
- baseUSDC.decimals
363
- ).toString() as `${bigint}`,
364
- usd: Number(order.destination.amountUnits),
365
- },
366
- ],
367
- selectedBridgeTokenOutAddr: null,
368
- selectedBridgeTokenOutAmount: null,
322
+ // bridgeTokenOutOptions: [
323
+ // {
324
+ // token: {
325
+ // chainId: baseUSDC.chainId,
326
+ // token: baseUSDC.token,
327
+ // symbol: baseUSDC.symbol,
328
+ // usd: 1,
329
+ // priceFromUsd: 1,
330
+ // decimals: baseUSDC.decimals,
331
+ // displayDecimals: 2,
332
+ // logoSourceURI: baseUSDC.logoSourceURI,
333
+ // logoURI: baseUSDC.logoURI,
334
+ // maxAcceptUsd: 100000,
335
+ // maxSendUsd: 0,
336
+ // },
337
+ // amount: parseUnits(
338
+ // order.destination.amountUnits,
339
+ // baseUSDC.decimals
340
+ // ).toString() as `${bigint}`,
341
+ // usd: Number(order.destination.amountUnits),
342
+ // },
343
+ // ],
344
+ // selectedBridgeTokenOutAddr: null,
345
+ // selectedBridgeTokenOutAmount: null,
369
346
  destFinalCallTokenAmount: {
370
347
  token: {
371
- chainId: chain ? chain.chainId : baseUSDC.chainId,
372
- token: chain ? chain.token : baseUSDC.token,
373
- symbol: chain ? chain.symbol : baseUSDC.symbol,
348
+ chainId: token ? token.chainId : baseUSDC.chainId,
349
+ token: token ? token.token : baseUSDC.token,
350
+ symbol: token ? token.symbol : baseUSDC.symbol,
374
351
  usd: 1,
375
352
  priceFromUsd: 1,
376
- decimals: chain ? chain.decimals : baseUSDC.decimals,
353
+ decimals: token ? token.decimals : baseUSDC.decimals,
377
354
  displayDecimals: 2,
378
- logoSourceURI: chain ? chain.logoSourceURI : baseUSDC.logoSourceURI,
379
- logoURI: chain ? chain.logoURI : baseUSDC.logoURI,
355
+ logoSourceURI: token ? token.logoSourceURI : baseUSDC.logoSourceURI,
356
+ logoURI: token ? token.logoURI : baseUSDC.logoURI,
380
357
  maxAcceptUsd: 100000,
381
358
  maxSendUsd: 0,
382
359
  },
383
360
  amount: parseUnits(
384
361
  order.destination.amountUnits,
385
- chain ? chain.decimals : baseUSDC.decimals
362
+ token ? token.decimals : baseUSDC.decimals
386
363
  ).toString() as `${bigint}`,
387
364
  usd: Number(order.destination.amountUnits),
388
365
  },
@@ -394,10 +371,10 @@ export function formatResponseToHydratedOrder(
394
371
  },
395
372
  refundAddr: (order.source?.sourceAddress as `0x${string}`) || null,
396
373
  nonce: order.nonce as unknown as bigint,
397
- sourceTokenAmount: null,
398
374
  sourceFulfillerAddr: null,
375
+ sourceTokenAmount: null,
399
376
  sourceInitiateTxHash: null,
400
- sourceStartTxHash: null,
377
+ // sourceStartTxHash: null,
401
378
  sourceStatus: RozoPayOrderStatusSource.WAITING_PAYMENT,
402
379
  destStatus: RozoPayOrderStatusDest.PENDING,
403
380
  intentStatus: RozoPayIntentStatus.UNPAID,
@@ -414,10 +391,57 @@ export function formatResponseToHydratedOrder(
414
391
  } as any,
415
392
  externalId: order.externalId as string | null,
416
393
  userMetadata: order.userMetadata as RozoPayUserMetadata | null,
417
- expirationTs: BigInt(Math.floor(Date.now() / 1000 + 5 * 60).toString()),
394
+ expirationTs: order.expiresAt
395
+ ? BigInt(
396
+ Math.floor(
397
+ new Date(String(order.expiresAt)).getTime() / 1000
398
+ ).toString()
399
+ )
400
+ : BigInt(Math.floor(Date.now() / 1000 + 5 * 60).toString()),
418
401
  org: {
419
402
  orgId: order.orgId as string,
420
- name: "Pay Rozo",
403
+ name: "",
421
404
  },
422
405
  };
423
406
  }
407
+
408
+ export function formatPaymentResponseToHydratedOrder(
409
+ order: PaymentResponse
410
+ ): RozoPayHydratedOrderWithOrg {
411
+ // Source amount is in the same units as the destination amount without fee
412
+ const sourceAmountUnits = order.source?.amount ?? "0";
413
+
414
+ return formatResponseToHydratedOrder({
415
+ id: order.id,
416
+ expiresAt: new Date(order.expiresAt).toISOString(),
417
+ updatedAt: new Date(order.updatedAt).toISOString(),
418
+ createdAt: new Date(order.createdAt).toISOString(),
419
+ status: RozoPayOrderMode.HYDRATED,
420
+ display: order.display,
421
+ metadata: {
422
+ ...order.metadata,
423
+ receivingAddress: order.source?.receiverAddress,
424
+ memo: order.source?.receiverMemo ?? null,
425
+ } as any,
426
+ destination: {
427
+ destinationAddress: order.destination?.receiverAddress ?? "",
428
+ chainId: String(order.destination?.chainId ?? ""),
429
+ amountUnits: sourceAmountUnits,
430
+ tokenSymbol: order.destination?.tokenSymbol ?? "",
431
+ tokenAddress: order.destination?.tokenAddress ?? "",
432
+ txHash: order.destination?.txHash ?? null,
433
+ },
434
+ source: {
435
+ sourceAddress: order.source?.senderAddress ?? undefined,
436
+ chainId: String(order.source?.chainId ?? ""),
437
+ amountUnits: sourceAmountUnits,
438
+ tokenSymbol: order.source?.tokenSymbol ?? "",
439
+ tokenAddress: order.source?.tokenAddress ?? "",
440
+ },
441
+ url: order.url,
442
+ externalId: order.externalId,
443
+ userMetadata: order.userMetadata,
444
+ nonce: order.nonce,
445
+ orgId: order.orgId,
446
+ });
447
+ }
package/src/chain.ts CHANGED
@@ -107,21 +107,44 @@ export const rozoStellar: Chain = {
107
107
  cctpDomain: null,
108
108
  };
109
109
 
110
+ export const gnosis: Chain = {
111
+ type: "evm",
112
+ chainId: 100,
113
+ name: "Gnosis",
114
+ cctpDomain: null,
115
+ };
116
+
117
+ export const avalanche: Chain = {
118
+ type: "evm",
119
+ chainId: 43114,
120
+ name: "Avalanche",
121
+ cctpDomain: null,
122
+ };
123
+
124
+ /**
125
+ * Supported chains for Near Intents cross-chain swaps
126
+ * Based on USDC/USDT support documentation
127
+ */
110
128
  export const supportedChains: Chain[] = [
111
- arbitrum,
112
- base,
113
- bsc,
114
- celo,
115
- ethereum,
116
- linea,
117
- mantle,
118
- optimism,
119
- polygon,
120
- solana,
121
- stellar,
129
+ // Supported for Near Intents (USDC/USDT)
130
+ arbitrum, // USDC & USDT
131
+ avalanche, // USDC & USDT
132
+ base, // USDC only (no USDT)
133
+ bsc, // USDC & USDT
134
+ ethereum, // USDC & USDT
135
+ gnosis, // USDC & USDT
136
+ optimism, // USDC & USDT
137
+ polygon, // USDC & USDT
122
138
  worldchain,
123
- rozoSolana,
124
- rozoStellar,
139
+ rozoSolana, // USDC & USDT (chainId: 900)
140
+ rozoStellar, // USDC only (chainId: 1500, no USDT)
141
+
142
+ // Not supported for Near Intents - kept for other features
143
+ // celo, // Not in Near Intents docs
144
+ // linea, // Not in Near Intents docs
145
+ // mantle, // Not in Near Intents docs
146
+ // solana, // Use rozoSolana (900) instead of solana (501)
147
+ // stellar, // Use rozoStellar (1500) instead of stellar (10001)
125
148
  ];
126
149
 
127
150
  // https://developers.circle.com/stablecoins/supported-domains
@@ -186,6 +209,10 @@ export function getChainExplorerByChainId(chainId: number): string | undefined {
186
209
  return "https://optimistic.etherscan.io";
187
210
  case polygon.chainId:
188
211
  return "https://polygonscan.com";
212
+ case gnosis.chainId:
213
+ return "https://gnosisscan.io";
214
+ case avalanche.chainId:
215
+ return "https://snowtrace.io";
189
216
  case solana.chainId:
190
217
  case rozoSolana.chainId:
191
218
  return "https://solscan.io";