@owney/sdk 0.2.7 → 0.2.9

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.
package/README.md CHANGED
@@ -32,9 +32,10 @@ const balances = await sdk.getBalances();
32
32
 
33
33
  Create a new SDK instance.
34
34
 
35
- | Param | Type | Description |
36
- |-------|------|-------------|
37
- | `config.apiKey` | `string` | Your Owney API key, used to authenticate with the routing API and fetch agent-specific keys |
35
+ | Param | Type | Description |
36
+ | --------------------- | ---------------------------------------------- | ------------------------------------------------------------------------------------------- |
37
+ | `config.apiKey` | `string` | Your Owney API key, used to authenticate with the routing API and fetch agent-specific keys |
38
+ | `config.zyfaiRpcUrls` | `{ 8453?: string; 42161?: string }` (optional) | Per-chain RPC URL overrides used by Zyfai SDK network calls |
38
39
 
39
40
  ```typescript
40
41
  import { OwneySDK } from "@owney/sdk";
@@ -42,12 +43,32 @@ import { OwneySDK } from "@owney/sdk";
42
43
  const sdk = new OwneySDK({ apiKey: "your-owney-api-key" });
43
44
  ```
44
45
 
46
+ #### Custom Zyfai RPC URLs
47
+
48
+ Use `zyfaiRpcUrls` to override Zyfai SDK RPC endpoints (for example, to avoid public endpoint rate limits).
49
+
50
+ ```typescript
51
+ const sdk = new OwneySDK({
52
+ apiKey: "your-owney-api-key",
53
+ zyfaiRpcUrls: {
54
+ 8453: "https://base-mainnet.g.alchemy.com/v2/<key>",
55
+ 42161: "https://arb-mainnet.g.alchemy.com/v2/<key>",
56
+ },
57
+ });
58
+ ```
59
+
60
+ Notes:
61
+
62
+ - These overrides are used by Zyfai SDK flows only.
63
+ - If omitted, Zyfai SDK uses its default RPC endpoints.
64
+ - Other app-level RPC clients (for example, direct viem calls outside Zyfai) are configured separately.
65
+
45
66
  ### `connect(provider)`
46
67
 
47
68
  Establish connection state. Must be called before any wallet-dependent operation.
48
69
 
49
- | Param | Type | Description |
50
- |-------|------|-------------|
70
+ | Param | Type | Description |
71
+ | ---------- | ----------------- | ---------------------------------------------- |
51
72
  | `provider` | EIP-1193 provider | Wallet provider (e.g. MetaMask, WalletConnect) |
52
73
 
53
74
  ```typescript
@@ -89,9 +110,9 @@ if (chainId) {
89
110
 
90
111
  Activate the user's smart wallet for the specified agents, or all chain-compatible agents if omitted. Deploys the Safe contract and creates a session key if not already set up. Saves the chainId for use by all subsequent SDK calls.
91
112
 
92
- | Param | Type | Description |
93
- |-------|------|-------------|
94
- | `chainId` | `number` | Target chain ID (e.g. `8453` for Base, `42161` for Arbitrum) |
113
+ | Param | Type | Description |
114
+ | --------- | ---------------------- | ----------------------------------------------------------------------------- |
115
+ | `chainId` | `number` | Target chain ID (e.g. `8453` for Base, `42161` for Arbitrum) |
95
116
  | `agentId` | `AgentId[]` (optional) | Agents to activate. Omit to activate all agents that support the given chain. |
96
117
 
97
118
  ```typescript
@@ -104,14 +125,14 @@ await sdk.activateAgent(42161);
104
125
 
105
126
  ### `deposit(options)`
106
127
 
107
- Deposit funds into a specific agent, or split equally across all agents if `agentId` is omitted. Validates that the asset is supported by the target agent(s) on the active chain. When splitting across agents, `depositCallback` is invoked once per agent with that agent's split amount and smart wallet address — expect multiple wallet prompts.
128
+ Deposit funds into a specific agent, or split equally across all agents if `agentId` is omitted. Validates that the asset is supported by the target agent(s) on the active chain, and agent minimum deposit amounts are taken into account. When splitting across agents, `depositCallback` is invoked once per final valid agent with that agent's split amount and smart wallet address — expect multiple wallet prompts.
108
129
 
109
- | Param | Type | Description |
110
- |-------|------|-------------|
111
- | `options.amount` | `string` | Amount in smallest unit (e.g. `"100000000"` for 100 USDC) |
112
- | `options.asset` | `string` | Asset symbol (e.g. `"USDC"`) |
113
- | `options.depositCallback` | `DepositCallback` | Callback that performs the token transfer and returns a tx hash |
114
- | `options.agentId` | `AgentId` (optional) | Target agent. Omit to split equally across all agents. |
130
+ | Param | Type | Description |
131
+ | ------------------------- | -------------------- | --------------------------------------------------------------- |
132
+ | `options.amount` | `string` | Amount in smallest unit (e.g. `"100000000"` for 100 USDC) |
133
+ | `options.asset` | `string` | Asset symbol (e.g. `"USDC"`) |
134
+ | `options.depositCallback` | `DepositCallback` | Callback that performs the token transfer and returns a tx hash |
135
+ | `options.agentId` | `AgentId` (optional) | Target agent. Omit to split equally across all agents. |
115
136
 
116
137
  Returns: `OwneyDepositResult` (single agent) or `OwneyMultiDepositResult` (all agents)
117
138
 
@@ -126,9 +147,9 @@ const result = await sdk.deposit({
126
147
  return txHash;
127
148
  },
128
149
  });
129
- console.log(result.txHash); // "0x..."
130
- console.log(result.smartWallet); // "0x..."
131
- console.log(result.amount); // "100000000"
150
+ console.log(result.txHash); // "0x..."
151
+ console.log(result.smartWallet); // "0x..."
152
+ console.log(result.amount); // "100000000"
132
153
 
133
154
  // Split equally across all agents
134
155
  const results = await sdk.deposit({
@@ -138,19 +159,19 @@ const results = await sdk.deposit({
138
159
  return await transferTokens(smartWallet, amount);
139
160
  },
140
161
  });
141
- console.log(results.agentResults.zyfai.amount); // "50000000"
142
- console.log(results.agentResults.sail.amount); // "50000000"
162
+ console.log(results.agentResults.zyfai.amount); // "50000000"
163
+ console.log(results.agentResults.sail.amount); // "50000000"
143
164
  ```
144
165
 
145
166
  ### `withdraw(options)`
146
167
 
147
168
  Withdraw funds from a specific agent, or all agents that support the active chain+asset if `agentId` is omitted. Validates that the asset is supported.
148
169
 
149
- | Param | Type | Description |
150
- |-------|------|-------------|
151
- | `options.asset` | `string` | Asset symbol (e.g. `"USDC"`) |
152
- | `options.amount` | `string` (optional) | Amount to withdraw. Omit for full withdrawal. |
153
- | `options.agentId` | `AgentId` (optional) | Target agent. Omit to withdraw from all. |
170
+ | Param | Type | Description |
171
+ | ----------------- | -------------------- | --------------------------------------------- |
172
+ | `options.asset` | `string` | Asset symbol (e.g. `"USDC"`) |
173
+ | `options.amount` | `string` (optional) | Amount to withdraw. Omit for full withdrawal. |
174
+ | `options.agentId` | `AgentId` (optional) | Target agent. Omit to withdraw from all. |
154
175
 
155
176
  Returns: `AgentWithdrawResult` (single agent) or `OwneyWithdrawResult` (all agents)
156
177
 
@@ -161,21 +182,21 @@ const result = await sdk.withdraw({
161
182
  agentId: "zyfai",
162
183
  amount: "50000000",
163
184
  });
164
- console.log(result.type); // "partial"
165
- console.log(result.amount); // "50000000"
185
+ console.log(result.type); // "partial"
186
+ console.log(result.amount); // "50000000"
166
187
 
167
188
  // Full withdrawal from all agents
168
189
  const results = await sdk.withdraw({ asset: "USDC" });
169
- console.log(results.agentResult.zyfai.type); // "full"
170
- console.log(results.agentResult.sail.type); // "full"
190
+ console.log(results.agentResult.zyfai.type); // "full"
191
+ console.log(results.agentResult.sail.type); // "full"
171
192
  ```
172
193
 
173
194
  ### `getBalances(agentId?)`
174
195
 
175
196
  Get the user's balances for a specific agent, or aggregated across all agents.
176
197
 
177
- | Param | Type | Description |
178
- |-------|------|-------------|
198
+ | Param | Type | Description |
199
+ | --------- | ------------------------------ | ------------------------------------ |
179
200
  | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
180
201
 
181
202
  Returns: `AgentBalance` (single agent) or `OwneyBalances` (all agents)
@@ -183,23 +204,23 @@ Returns: `AgentBalance` (single agent) or `OwneyBalances` (all agents)
183
204
  ```typescript
184
205
  // Single agent
185
206
  const balance = await sdk.getBalances("zyfai");
186
- console.log(balance.totalBalance); // "150.25"
187
- console.log(balance.smartWallet); // "0x..."
188
- console.log(balance.tokens); // [{ chain: "BASE", chainId: 8453, asset: "USDC", amount: "150.25" }]
207
+ console.log(balance.totalBalance); // "150.25"
208
+ console.log(balance.smartWallet); // "0x..."
209
+ console.log(balance.tokens); // [{ chain: "BASE", chainId: 8453, asset: "USDC", amount: "150.25" }]
189
210
 
190
211
  // All agents
191
212
  const allBalances = await sdk.getBalances();
192
- console.log(allBalances.totalBalance); // "300.50"
213
+ console.log(allBalances.totalBalance); // "300.50"
193
214
  console.log(allBalances.agentBalances.zyfai.totalBalance); // "150.25"
194
- console.log(allBalances.agentBalances.sail.totalBalance); // "150.25"
215
+ console.log(allBalances.agentBalances.sail.totalBalance); // "150.25"
195
216
  ```
196
217
 
197
218
  ### `getEarnings(agentId?)`
198
219
 
199
220
  Get the user's on-chain earnings for a specific agent, or aggregated across all agents.
200
221
 
201
- | Param | Type | Description |
202
- |-------|------|-------------|
222
+ | Param | Type | Description |
223
+ | --------- | ------------------------------ | ------------------------------------ |
203
224
  | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
204
225
 
205
226
  Returns: `AgentEarnings` (single agent) or `OwneyEarnings` (all agents)
@@ -207,12 +228,12 @@ Returns: `AgentEarnings` (single agent) or `OwneyEarnings` (all agents)
207
228
  ```typescript
208
229
  // Single agent
209
230
  const earnings = await sdk.getEarnings("zyfai");
210
- console.log(earnings.smartWallet); // "0x..."
211
- console.log(earnings.lifetimeEarnings); // 42.5
231
+ console.log(earnings.smartWallet); // "0x..."
232
+ console.log(earnings.lifetimeEarnings); // 42.5
212
233
 
213
234
  // All agents
214
235
  const allEarnings = await sdk.getEarnings();
215
- console.log(allEarnings.totalEarnings); // "85.0"
236
+ console.log(allEarnings.totalEarnings); // "85.0"
216
237
  console.log(allEarnings.agentEarnings.zyfai.lifetimeEarnings); // 42.5
217
238
  ```
218
239
 
@@ -220,37 +241,37 @@ console.log(allEarnings.agentEarnings.zyfai.lifetimeEarnings); // 42.5
220
241
 
221
242
  Get the weighted APY for the user's account. When querying all agents, the total APY is a balance-weighted average.
222
243
 
223
- | Param | Type | Description |
224
- |-------|------|-------------|
244
+ | Param | Type | Description |
245
+ | --------- | ------------------------------ | ------------------------------------------------ |
225
246
  | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for balance-weighted total. |
226
- | `days` | `"7D" \| "14D" \| "30D"` | Lookback period |
247
+ | `days` | `"7D" \| "14D" \| "30D"` | Lookback period |
227
248
 
228
249
  Returns: `AccountAgentApy` (single agent) or `OwneyAccountApy` (all agents)
229
250
 
230
251
  ```typescript
231
252
  // Single agent
232
253
  const apy = await sdk.getAccountApy({ agentId: "zyfai", days: "30D" });
233
- console.log(apy.walletAddress); // "0x..."
254
+ console.log(apy.walletAddress); // "0x..."
234
255
  console.log(apy.weightedApyAfterFee); // 5.2
235
256
  // Per chain + token breakdown, when the agent reports it
236
- console.log(apy.weightedApyAfterFeeDetails?.apyPerAsset[8453]?.USDC); // 5.4
257
+ console.log(apy.weightedApyAfterFeeDetails?.apyPerAsset[8453]?.USDC); // 5.4
237
258
 
238
259
  // All agents (balance-weighted)
239
260
  const allApy = await sdk.getAccountApy({ days: "30D" });
240
- console.log(allApy.totalApy); // "5.6"
261
+ console.log(allApy.totalApy); // "5.6"
241
262
  console.log(allApy.agentApy.zyfai.weightedApyAfterFee); // 6.0
242
- console.log(allApy.agentApy.sail.weightedApyAfterFee); // 4.0
263
+ console.log(allApy.agentApy.sail.weightedApyAfterFee); // 4.0
243
264
  ```
244
265
 
245
266
  ### `getHistory({ agentId?, filters? })`
246
267
 
247
268
  Get transaction history for a specific agent, or all agents. When querying all agents, results are merged into a single list sorted by date (newest first). Each entry includes the originating `agent` and a `transactions` array with typed on-chain transaction details.
248
269
 
249
- | Param | Type | Description |
250
- |-------|------|-------------|
251
- | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
252
- | `filters.fromDate` | `string` (optional) | Start date (`YYYY-MM-DD`) |
253
- | `filters.toDate` | `string` (optional) | End date (`YYYY-MM-DD`) |
270
+ | Param | Type | Description |
271
+ | ------------------ | ------------------------------ | ------------------------------------ |
272
+ | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
273
+ | `filters.fromDate` | `string` (optional) | Start date (`YYYY-MM-DD`) |
274
+ | `filters.toDate` | `string` (optional) | End date (`YYYY-MM-DD`) |
254
275
 
255
276
  Returns: `OwneyAgentHistory`
256
277
 
@@ -260,65 +281,65 @@ const history = await sdk.getHistory({
260
281
  agentId: "zyfai",
261
282
  filters: { fromDate: "2025-01-01" },
262
283
  });
263
- console.log(history.total); // 42
264
- console.log(history.data[0].agent); // "zyfai"
265
- console.log(history.data[0].action); // "Rebalance"
266
- console.log(history.data[0].date); // "2025-03-15T12:00:00Z"
267
- console.log(history.data[0].transactions[0].txHashes); // ["0x..."]
268
- console.log(history.data[0].transactions[0].amount); // "100.00"
284
+ console.log(history.total); // 42
285
+ console.log(history.data[0].agent); // "zyfai"
286
+ console.log(history.data[0].action); // "Rebalance"
287
+ console.log(history.data[0].date); // "2025-03-15T12:00:00Z"
288
+ console.log(history.data[0].transactions[0].txHashes); // ["0x..."]
289
+ console.log(history.data[0].transactions[0].amount); // "100.00"
269
290
  console.log(history.data[0].transactions[0].tokenSymbol); // "USDC"
270
291
 
271
292
  // Rebalance logs show fund movement between protocols
272
293
  console.log(history.data[0].rebalanceLog[0].fromProtocol); // "Aave V3"
273
- console.log(history.data[0].rebalanceLog[0].toProtocol); // "Morpho Blue"
274
- console.log(history.data[0].rebalanceLog[0].tokenSymbol); // "USDC"
275
- console.log(history.data[0].rebalanceLog[0].amount); // "100.00"
276
- console.log(history.data[0].rebalanceLog[0].status); // "success"
294
+ console.log(history.data[0].rebalanceLog[0].toProtocol); // "Morpho Blue"
295
+ console.log(history.data[0].rebalanceLog[0].tokenSymbol); // "USDC"
296
+ console.log(history.data[0].rebalanceLog[0].amount); // "100.00"
297
+ console.log(history.data[0].rebalanceLog[0].status); // "success"
277
298
 
278
299
  // All agents (merged and sorted by date)
279
300
  const allHistory = await sdk.getHistory();
280
- console.log(allHistory.total); // 57
281
- console.log(allHistory.data[0].agent); // "sail" (most recent entry)
282
- console.log(allHistory.data[0].action); // "Rebalance"
301
+ console.log(allHistory.total); // 57
302
+ console.log(allHistory.data[0].agent); // "sail" (most recent entry)
303
+ console.log(allHistory.data[0].action); // "Rebalance"
283
304
  ```
284
305
 
285
306
  ### `pauseAgent(agentId)`
286
307
 
287
308
  Pause an agent's automated operations. The agent will stop rebalancing until resumed.
288
309
 
289
- | Param | Type | Description |
290
- |-------|------|-------------|
310
+ | Param | Type | Description |
311
+ | --------- | ------------------- | -------------- |
291
312
  | `agentId` | `"zyfai" \| "sail"` | Agent to pause |
292
313
 
293
314
  Returns: `OwneyAgentStatus`
294
315
 
295
316
  ```typescript
296
317
  const status = await sdk.pauseAgent("zyfai");
297
- console.log(status.success); // true
318
+ console.log(status.success); // true
298
319
  ```
299
320
 
300
321
  ### `resumeAgent(agentId)`
301
322
 
302
323
  Resume an agent's automated operations.
303
324
 
304
- | Param | Type | Description |
305
- |-------|------|-------------|
325
+ | Param | Type | Description |
326
+ | --------- | ------------------- | --------------- |
306
327
  | `agentId` | `"zyfai" \| "sail"` | Agent to resume |
307
328
 
308
329
  Returns: `OwneyAgentStatus`
309
330
 
310
331
  ```typescript
311
332
  const status = await sdk.resumeAgent("zyfai");
312
- console.log(status.success); // true
313
- console.log(status.protocols); // ["aave", "compound"]
333
+ console.log(status.success); // true
334
+ console.log(status.protocols); // ["aave", "compound"]
314
335
  ```
315
336
 
316
337
  ### `getUserProfile(agentId?)`
317
338
 
318
339
  Get the user's profile for a specific agent, or all agents.
319
340
 
320
- | Param | Type | Description |
321
- |-------|------|-------------|
341
+ | Param | Type | Description |
342
+ | --------- | ------------------------------ | ------------------------------------ |
322
343
  | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
323
344
 
324
345
  Returns: `AgentUserProfile` (single agent) or `OwneyUserProfile` (all agents)
@@ -326,28 +347,28 @@ Returns: `AgentUserProfile` (single agent) or `OwneyUserProfile` (all agents)
326
347
  ```typescript
327
348
  // Single agent
328
349
  const profile = await sdk.getUserProfile("zyfai");
329
- console.log(profile.address); // "0x..."
330
- console.log(profile.smartWallet); // "0x..."
331
- console.log(profile.chains); // [8453]
350
+ console.log(profile.address); // "0x..."
351
+ console.log(profile.smartWallet); // "0x..."
352
+ console.log(profile.chains); // [8453]
332
353
  console.log(profile.hasActiveSessionKey); // true
333
- console.log(profile.protocols); // ["aave", "compound"]
354
+ console.log(profile.protocols); // ["aave", "compound"]
334
355
 
335
356
  // All agents
336
357
  const allProfiles = await sdk.getUserProfile();
337
358
  console.log(allProfiles.agentUserProfile.zyfai.smartWallet); // "0x..."
338
- console.log(allProfiles.agentUserProfile.sail.smartWallet); // "0x..."
359
+ console.log(allProfiles.agentUserProfile.sail.smartWallet); // "0x..."
339
360
  ```
340
361
 
341
362
  ### `getAgentApy({ agentId?, days, tokenSymbol?, chainId? })`
342
363
 
343
364
  Get the agent's average APY performance over a time period. Does not require a wallet connection.
344
365
 
345
- | Param | Type | Description |
346
- |-------|------|-------------|
347
- | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
348
- | `days` | `"7D" \| "14D" \| "30D"` | Lookback period |
349
- | `tokenSymbol` | `string` (optional) | Asset symbol (e.g. `"USDC"`, `"WETH"`). Scopes the upstream request to a specific asset when the agent's backend supports it. Zyfai forwards this; Sail currently ignores it at the API level. |
350
- | `chainId` | `number` (optional) | Chain id. Typically paired with `tokenSymbol` for per-asset+chain APY. Zyfai forwards this; Sail currently ignores it at the API level. |
366
+ | Param | Type | Description |
367
+ | ------------- | ------------------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
368
+ | `agentId` | `"zyfai" \| "sail"` (optional) | Agent to query. Omit for all agents. |
369
+ | `days` | `"7D" \| "14D" \| "30D"` | Lookback period |
370
+ | `tokenSymbol` | `string` (optional) | Asset symbol (e.g. `"USDC"`, `"WETH"`). Scopes the upstream request to a specific asset when the agent's backend supports it. Zyfai forwards this; Sail currently ignores it at the API level. |
371
+ | `chainId` | `number` (optional) | Chain id. Typically paired with `tokenSymbol` for per-asset+chain APY. Zyfai forwards this; Sail currently ignores it at the API level. |
351
372
 
352
373
  Returns: `AgentApy` (single agent) or `OwneyAgentApy` (all agents)
353
374
 
@@ -359,13 +380,13 @@ returns.
359
380
  ```typescript
360
381
  // Single agent
361
382
  const apy = await sdk.getAgentApy({ agentId: "zyfai", days: "30D" });
362
- console.log(apy.averageApy); // 8.5
383
+ console.log(apy.averageApy); // 8.5
363
384
  console.log(apy.detailedApys?.apyPerAsset[8453]?.USDC); // 8.7
364
385
 
365
386
  // All agents
366
387
  const allApy = await sdk.getAgentApy({ days: "30D" });
367
388
  console.log(allApy.agentApy.zyfai.averageApy); // 8.5
368
- console.log(allApy.agentApy.sail.averageApy); // 6.2
389
+ console.log(allApy.agentApy.sail.averageApy); // 6.2
369
390
  console.log(allApy.agentApy.sail.detailedApys?.apyPerAsset[42161]?.USDT); // 6.4
370
391
 
371
392
  // Scope the upstream query to USDC on Base (Zyfai-aware; Sail ignores the filter)
@@ -385,7 +406,7 @@ Returns: `OwneyAgentAllocation`
385
406
 
386
407
  ```typescript
387
408
  const allocation = await sdk.getAgentAllocation();
388
- console.log(allocation.agentAllocation); // { zyfai: 75, sail: 25 }
409
+ console.log(allocation.agentAllocation); // { zyfai: 75, sail: 25 }
389
410
  ```
390
411
 
391
412
  ## Types
@@ -408,6 +429,10 @@ type AgentSupportedAssets = {
408
429
 
409
430
  interface OwneySDKConfig {
410
431
  apiKey: string;
432
+ zyfaiRpcUrls?: {
433
+ 8453?: string;
434
+ 42161?: string;
435
+ };
411
436
  }
412
437
 
413
438
  interface ConnectionState {
@@ -417,8 +442,8 @@ interface ConnectionState {
417
442
  }
418
443
 
419
444
  type HistoryFilters = {
420
- fromDate?: string; // YYYY-MM-DD
421
- toDate?: string; // YYYY-MM-DD
445
+ fromDate?: string; // YYYY-MM-DD
446
+ toDate?: string; // YYYY-MM-DD
422
447
  };
423
448
 
424
449
  type HistoryOptions = {
@@ -447,8 +472,8 @@ type AccountApyOptions = {
447
472
  type AgentsApyOptions = {
448
473
  agentId?: AgentId;
449
474
  days: DailyApyDays;
450
- tokenSymbol?: string; // e.g. "USDC", "WETH"
451
- chainId?: number; // typically paired with tokenSymbol
475
+ tokenSymbol?: string; // e.g. "USDC", "WETH"
476
+ chainId?: number; // typically paired with tokenSymbol
452
477
  };
453
478
  ```
454
479
 
@@ -603,13 +628,83 @@ type DepositCallback = (
603
628
  ) => Promise<`0x${string}`> | `0x${string}`;
604
629
  ```
605
630
 
606
- ### Error Classes
631
+ ### Error Handling
632
+
633
+ All errors thrown by the SDK are instances of `OwneyError` (which extends `Error`), each carrying a stable `code` string and optional `details` object for programmatic handling.
634
+
635
+ ```typescript
636
+ import { OwneyError } from "@owney/sdk";
637
+
638
+ try {
639
+ await sdk.getBalances();
640
+ } catch (error) {
641
+ if (error instanceof OwneyError) {
642
+ switch (error.code) {
643
+ case "NOT_CONNECTED":
644
+ // prompt user to connect wallet
645
+ break;
646
+ case "NO_ACTIVE_CHAIN":
647
+ // prompt user to activate an agent
648
+ break;
649
+ case "BALANCE_ALL_FAILED":
650
+ // all agents failed to return balances
651
+ break;
652
+ default:
653
+ console.error(`[${error.code}] ${error.message}`, error.details);
654
+ }
655
+ }
656
+ }
657
+ ```
658
+
659
+ ```typescript
660
+ type OwneyErrorCode =
661
+ // Connection & wallet
662
+ | "NOT_CONNECTED" // Wallet-dependent method called before connect()
663
+ | "NO_ACTIVE_CHAIN" // Method called before activateAgent()
664
+ | "WALLET_NO_ACCOUNTS" // Provider returned no accounts during connect()
665
+ | "WALLET_ADDRESS_REQUIRED" // Wallet address missing during agent auth
666
+ // Agent resolution
667
+ | "AGENT_NOT_FOUND" // Unknown agent ID passed
668
+ | "AGENT_CHAIN_INCOMPATIBLE" // Agent(s) don't support the given chain
669
+ | "AGENT_EMPTY_LIST" // Empty agentId array passed to activateAgent()
670
+ // Chain
671
+ | "CHAIN_UNSUPPORTED" // Chain ID not in supported list (8453, 42161)
672
+ | "CHAIN_NO_COMPATIBLE_AGENTS" // No agents support the given chain
673
+ // Asset
674
+ | "ASSET_UNSUPPORTED" // Agent doesn't support the asset on the active chain
675
+ | "ASSET_NO_COMPATIBLE_AGENTS" // No agents support the asset on the active chain
676
+ // Deposit
677
+ | "DEPOSIT_AMOUNT_BELOW_MINIMUM" // Amount below an agent's required minimum deposit
678
+ | "DEPOSIT_CALLBACK_REQUIRED" // Sail agent requires a depositCallback
679
+ | "DEPOSIT_CALLBACK_INVALID" // depositCallback didn't return a tx hash
680
+ | "DEPOSIT_NO_PERMITTED_TOKENS" // No permitted tokens available for deposit
681
+ // Withdraw
682
+ | "WITHDRAW_NO_PERMITTED_TOKENS" // No permitted tokens available for withdrawal
683
+ // API
684
+ | "API_ROUTING_ERROR" // Routing API returned a non-OK HTTP status
685
+ | "API_ROUTING_FAILED" // Routing API returned { success: false }
686
+ | "API_SAIL_ERROR" // Sail API returned a non-OK HTTP status
687
+ | "API_SAIL_TIMEOUT" // Sail API request timed out
688
+ | "API_NO_AGENTS" // No supported agents returned by routing API
689
+ // Aggregation
690
+ | "BALANCE_ALL_FAILED" // All agents failed to return balances
691
+ | "ALLOCATION_ALL_FAILED" // All agents failed to return allocation data
692
+ // Validation
693
+ | "VALIDATION_INVALID_DAYS"; // Invalid days value (expected "7D", "14D", or "30D")
694
+
695
+ class OwneyError extends Error {
696
+ readonly code: OwneyErrorCode;
697
+ readonly details?: Record<string, unknown>;
698
+ }
699
+ ```
700
+
701
+ The three convenience subclasses extend `OwneyError` and remain backwards-compatible:
607
702
 
608
- | Error | Thrown when |
609
- |-------|------------|
610
- | `NotConnectedError` | A wallet-dependent method is called before `connect()` |
611
- | `AgentNotFoundError` | An unknown agent ID is passed (e.g. a typo) |
612
- | `AgentChainIncompatibleError` | `activateAgent` is called with agents that don't support the given chain. Exposes `incompatibleAgents` and `connectedChainId` properties for programmatic handling. |
703
+ | Class | Code | Extra properties |
704
+ | ----------------------------- | -------------------------- | ---------------------------------------- |
705
+ | `NotConnectedError` | `NOT_CONNECTED` | — |
706
+ | `AgentNotFoundError` | `AGENT_NOT_FOUND` | — |
707
+ | `AgentChainIncompatibleError` | `AGENT_CHAIN_INCOMPATIBLE` | `incompatibleAgents`, `connectedChainId` |
613
708
 
614
709
  ## License
615
710