@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 +194 -99
- package/dist/index.cjs +102 -146
- package/dist/index.d.cts +14 -7
- package/dist/index.d.ts +14 -7
- package/dist/index.js +102 -146
- package/package.json +4 -1
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
|
+
type ZyfaiRpcUrlsConfig = Partial<Record<(typeof SUPPORTED_CHAIN_IDS)[number], string>>;
|
|
1
2
|
interface OwneySDKConfig {
|
|
2
3
|
apiKey: string;
|
|
4
|
+
/**
|
|
5
|
+
* Optional per-chain RPC overrides for Zyfai SDK network calls.
|
|
6
|
+
* Example: { 8453: "https://...", 42161: "https://..." }
|
|
7
|
+
*/
|
|
8
|
+
zyfaiRpcUrls?: ZyfaiRpcUrlsConfig;
|
|
3
9
|
}
|
|
4
10
|
interface ConnectionState {
|
|
5
11
|
provider: any;
|
|
@@ -18,6 +24,7 @@ interface IAgent {
|
|
|
18
24
|
readonly id: string;
|
|
19
25
|
readonly supportedChainIds: readonly OwneySupportedChainId[];
|
|
20
26
|
readonly supportedAssets: readonly AgentSupportedAssets[];
|
|
27
|
+
readonly minDepositAmount: string;
|
|
21
28
|
disconnect(): Promise<void>;
|
|
22
29
|
activateAgent(state: ConnectionState, chainId: number): Promise<void>;
|
|
23
30
|
deposit(state: ConnectionState, chainId: number, amount: string, depositCallback?: DepositCallback): Promise<OwneyDepositResult>;
|
|
@@ -190,10 +197,6 @@ interface AgentApy {
|
|
|
190
197
|
interface OwneyAgentApy {
|
|
191
198
|
agentApy: Record<AgentId, AgentApy>;
|
|
192
199
|
}
|
|
193
|
-
interface OwneyRouteResponse {
|
|
194
|
-
agent: AgentId;
|
|
195
|
-
chainId: number;
|
|
196
|
-
}
|
|
197
200
|
interface OwneyAgentAllocation {
|
|
198
201
|
agentAllocation: Record<AgentId, number>;
|
|
199
202
|
}
|
|
@@ -203,6 +206,7 @@ declare class OwneySDK {
|
|
|
203
206
|
private activeAgents;
|
|
204
207
|
private state;
|
|
205
208
|
private apiKey;
|
|
209
|
+
private zyfaiRpcUrls?;
|
|
206
210
|
private initializingAgentsPromise;
|
|
207
211
|
constructor(config: OwneySDKConfig);
|
|
208
212
|
/**
|
|
@@ -231,6 +235,7 @@ declare class OwneySDK {
|
|
|
231
235
|
private getAgent;
|
|
232
236
|
private getActiveAgents;
|
|
233
237
|
private ensureAgentsInitialized;
|
|
238
|
+
private createAgent;
|
|
234
239
|
/**
|
|
235
240
|
* Activate the user's smart wallet for the specified agents, or all chain-compatible agents if omitted.
|
|
236
241
|
* Deploys the Safe contract and creates a session key if not already set up.
|
|
@@ -244,7 +249,7 @@ declare class OwneySDK {
|
|
|
244
249
|
activateAgent(chainId: number, agentId?: AgentId[]): Promise<void>;
|
|
245
250
|
/**
|
|
246
251
|
* Deposit funds into a specific agent, or split equally across all agents if agentId is omitted.
|
|
247
|
-
|
|
252
|
+
* Validates that the asset is supported and amount meets minimums for the target agent(s).
|
|
248
253
|
* @param options - Deposit parameters
|
|
249
254
|
* @param options.amount - Amount to deposit in smallest unit (e.g. "100000000" for 100 USDC)
|
|
250
255
|
* @param options.asset - Asset symbol to deposit (e.g. "USDC")
|
|
@@ -255,6 +260,8 @@ declare class OwneySDK {
|
|
|
255
260
|
* @returns {OwneyDepositResult} for a single agent, or {OwneyMultiDepositResult} with per-agent results
|
|
256
261
|
*/
|
|
257
262
|
deposit(options: DepositOptions): Promise<OwneyDepositResult | OwneyMultiDepositResult>;
|
|
263
|
+
private splitDepositAmount;
|
|
264
|
+
private validateMinDepositAmount;
|
|
258
265
|
private validateAssetSupport;
|
|
259
266
|
private getEligibleAgents;
|
|
260
267
|
/**
|
|
@@ -334,7 +341,7 @@ declare class OwneySDK {
|
|
|
334
341
|
getAgentAllocation(): Promise<OwneyAgentAllocation>;
|
|
335
342
|
}
|
|
336
343
|
|
|
337
|
-
type OwneyErrorCode = "NOT_CONNECTED" | "NO_ACTIVE_CHAIN" | "WALLET_NO_ACCOUNTS" | "WALLET_ADDRESS_REQUIRED" | "AGENT_NOT_FOUND" | "AGENT_CHAIN_INCOMPATIBLE" | "AGENT_EMPTY_LIST" | "CHAIN_UNSUPPORTED" | "CHAIN_NO_COMPATIBLE_AGENTS" | "ASSET_UNSUPPORTED" | "ASSET_NO_COMPATIBLE_AGENTS" | "
|
|
344
|
+
type OwneyErrorCode = "NOT_CONNECTED" | "NO_ACTIVE_CHAIN" | "WALLET_NO_ACCOUNTS" | "WALLET_ADDRESS_REQUIRED" | "AGENT_NOT_FOUND" | "AGENT_CHAIN_INCOMPATIBLE" | "AGENT_EMPTY_LIST" | "CHAIN_UNSUPPORTED" | "CHAIN_NO_COMPATIBLE_AGENTS" | "ASSET_UNSUPPORTED" | "ASSET_NO_COMPATIBLE_AGENTS" | "DEPOSIT_AMOUNT_BELOW_MINIMUM" | "DEPOSIT_CALLBACK_REQUIRED" | "DEPOSIT_CALLBACK_INVALID" | "DEPOSIT_NO_PERMITTED_TOKENS" | "WITHDRAW_NO_PERMITTED_TOKENS" | "API_ROUTING_ERROR" | "API_ROUTING_FAILED" | "API_SAIL_ERROR" | "API_SAIL_TIMEOUT" | "API_NO_AGENTS" | "BALANCE_ALL_FAILED" | "ALLOCATION_ALL_FAILED" | "VALIDATION_INVALID_DAYS";
|
|
338
345
|
declare class OwneyError extends Error {
|
|
339
346
|
readonly code: OwneyErrorCode;
|
|
340
347
|
readonly details?: Record<string, unknown>;
|
|
@@ -358,4 +365,4 @@ declare class AgentChainIncompatibleError extends OwneyError {
|
|
|
358
365
|
}>, connectedChainId: number);
|
|
359
366
|
}
|
|
360
367
|
|
|
361
|
-
export { AccountAgentApy, AccountApyOptions, AgentApy, AgentApyDetails, AgentBalance, AgentChainIncompatibleError, AgentEarnings, AgentHistoryEntry, AgentId, AgentNotFoundError, AgentSupportedAssets, AgentUserProfile, AgentWithdrawResult, AgentsApyOptions, Asset, ConnectionState, DailyApyDays, DepositCallback, DepositOptions, HistoryAction, HistoryFilters, HistoryOptions, HistoryTransaction, IAgent, NotConnectedError, OwneyAccountApy, OwneyAgentAllocation, OwneyAgentApy, OwneyAgentHistory, OwneyAgentStatus, OwneyBalances, OwneyDepositResult, OwneyEarnings, OwneyError, OwneyErrorCode, OwneyMultiDepositResult,
|
|
368
|
+
export { AccountAgentApy, AccountApyOptions, AgentApy, AgentApyDetails, AgentBalance, AgentChainIncompatibleError, AgentEarnings, AgentHistoryEntry, AgentId, AgentNotFoundError, AgentSupportedAssets, AgentUserProfile, AgentWithdrawResult, AgentsApyOptions, Asset, ConnectionState, DailyApyDays, DepositCallback, DepositOptions, HistoryAction, HistoryFilters, HistoryOptions, HistoryTransaction, IAgent, NotConnectedError, OwneyAccountApy, OwneyAgentAllocation, OwneyAgentApy, OwneyAgentHistory, OwneyAgentStatus, OwneyBalances, OwneyDepositResult, OwneyEarnings, OwneyError, OwneyErrorCode, OwneyMultiDepositResult, OwneySDK, OwneySDKConfig, OwneySupportedChainId, OwneySupportedChains, OwneySupportedTokens, OwneyToken, OwneyUserProfile, OwneyWithdrawResult, RebalanceLog, WithdrawOptions };
|
package/dist/index.js
CHANGED
|
@@ -273,17 +273,13 @@ function mapApyByStrategy(raw) {
|
|
|
273
273
|
}
|
|
274
274
|
|
|
275
275
|
// src/agents/zyfai/zyfai.agent.ts
|
|
276
|
-
var
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
console.log(`${ZYFAI_TIMING_PREFIX} ${label} ${elapsedMs}ms`, meta);
|
|
281
|
-
return;
|
|
282
|
-
}
|
|
283
|
-
console.log(`${ZYFAI_TIMING_PREFIX} ${label} ${elapsedMs}ms`);
|
|
284
|
-
}
|
|
276
|
+
var DEFAULT_ZYFAI_RPC_URLS = {
|
|
277
|
+
8453: "https://base-mainnet.g.alchemy.com/v2/ZWyVU-9XfS3z8Rn-xkq7V",
|
|
278
|
+
42161: "https://arb-mainnet.g.alchemy.com/v2/ZWyVU-9XfS3z8Rn-xkq7V"
|
|
279
|
+
};
|
|
285
280
|
var ZyfaiAgent = class {
|
|
286
281
|
id = "zyfai";
|
|
282
|
+
minDepositAmount = "0";
|
|
287
283
|
supportedChainIds = [8453, 42161];
|
|
288
284
|
supportedAssets = [
|
|
289
285
|
{
|
|
@@ -302,8 +298,11 @@ var ZyfaiAgent = class {
|
|
|
302
298
|
connectedChainId = null;
|
|
303
299
|
smartWalletCache = /* @__PURE__ */ new Map();
|
|
304
300
|
connectAuthPromise = null;
|
|
305
|
-
constructor(apiKey) {
|
|
306
|
-
this.sdk = new ZyfaiSDK({
|
|
301
|
+
constructor(apiKey, rpcUrls) {
|
|
302
|
+
this.sdk = new ZyfaiSDK({
|
|
303
|
+
apiKey,
|
|
304
|
+
rpcUrls: rpcUrls ?? DEFAULT_ZYFAI_RPC_URLS
|
|
305
|
+
});
|
|
307
306
|
}
|
|
308
307
|
// --- Private helpers ---
|
|
309
308
|
getAddress() {
|
|
@@ -317,17 +316,12 @@ var ZyfaiAgent = class {
|
|
|
317
316
|
}
|
|
318
317
|
/** Light connect: SIWE auth only. Re-auths if chain changed. */
|
|
319
318
|
async connectAuth(state, chainId) {
|
|
320
|
-
const startedAt = Date.now();
|
|
321
319
|
const validChainId = isValidChainId(chainId);
|
|
322
320
|
if (this.connectedAddress && this.connectedChainId === validChainId) {
|
|
323
|
-
logTiming("connectAuth cache-hit", startedAt, { chainId: validChainId });
|
|
324
321
|
return;
|
|
325
322
|
}
|
|
326
323
|
if (this.connectAuthPromise) {
|
|
327
324
|
await this.connectAuthPromise;
|
|
328
|
-
logTiming("connectAuth awaited-inflight", startedAt, {
|
|
329
|
-
chainId: validChainId
|
|
330
|
-
});
|
|
331
325
|
return;
|
|
332
326
|
}
|
|
333
327
|
this.connectAuthPromise = (async () => {
|
|
@@ -340,69 +334,40 @@ var ZyfaiAgent = class {
|
|
|
340
334
|
})();
|
|
341
335
|
try {
|
|
342
336
|
await this.connectAuthPromise;
|
|
343
|
-
logTiming("connectAuth success", startedAt, { chainId: validChainId });
|
|
344
337
|
} finally {
|
|
345
338
|
this.connectAuthPromise = null;
|
|
346
339
|
}
|
|
347
340
|
}
|
|
348
341
|
/** Full connect: SIWE auth + Safe deploy check + session key. */
|
|
349
342
|
async connectFull(state, chainId) {
|
|
350
|
-
const startedAt = Date.now();
|
|
351
343
|
await this.connectAuth(state, chainId);
|
|
352
344
|
const validChainId = isValidChainId(chainId);
|
|
353
345
|
const address = this.getAddress();
|
|
354
|
-
const walletLookupStart = Date.now();
|
|
355
346
|
const wallet = await this.sdk.getSmartWalletAddress(address, validChainId);
|
|
356
|
-
logTiming("connectFull getSmartWalletAddress", walletLookupStart, {
|
|
357
|
-
chainId: validChainId
|
|
358
|
-
});
|
|
359
347
|
this.smartWalletCache.set(`${address}_${validChainId}`, wallet.address);
|
|
360
348
|
if (!wallet.isDeployed) {
|
|
361
|
-
const deployStart = Date.now();
|
|
362
349
|
await this.sdk.deploySafe(address, validChainId, "aggressive", true);
|
|
363
|
-
logTiming("connectFull deploySafe", deployStart, {
|
|
364
|
-
chainId: validChainId
|
|
365
|
-
});
|
|
366
350
|
}
|
|
367
|
-
const userDetailsStart = Date.now();
|
|
368
351
|
const user = await this.sdk.getUserDetails();
|
|
369
|
-
logTiming("connectFull getUserDetails", userDetailsStart, {
|
|
370
|
-
chainId: validChainId
|
|
371
|
-
});
|
|
372
352
|
if (!user.hasActiveSessionKey) {
|
|
373
|
-
const sessionKeyStart = Date.now();
|
|
374
353
|
await this.sdk.createSessionKey(address, validChainId);
|
|
375
|
-
logTiming("connectFull createSessionKey", sessionKeyStart, {
|
|
376
|
-
chainId: validChainId
|
|
377
|
-
});
|
|
378
354
|
}
|
|
379
|
-
logTiming("connectFull success", startedAt, { chainId: validChainId });
|
|
380
355
|
}
|
|
381
356
|
/** Connect + resolve smart wallet address for read operations. */
|
|
382
357
|
async resolveSmartWallet(state, chainId) {
|
|
383
|
-
const startedAt = Date.now();
|
|
384
358
|
await this.connectAuth(state, chainId);
|
|
385
359
|
const validChainId = isValidChainId(chainId);
|
|
386
360
|
const ownerAddress = this.getAddress();
|
|
387
361
|
const cacheKey = `${ownerAddress}_${validChainId}`;
|
|
388
362
|
let smartWallet = this.smartWalletCache.get(cacheKey);
|
|
389
363
|
if (!smartWallet) {
|
|
390
|
-
const lookupStart = Date.now();
|
|
391
364
|
const { address } = await this.sdk.getSmartWalletAddress(
|
|
392
365
|
ownerAddress,
|
|
393
366
|
validChainId
|
|
394
367
|
);
|
|
395
|
-
logTiming("resolveSmartWallet remote-lookup", lookupStart, {
|
|
396
|
-
chainId: validChainId
|
|
397
|
-
});
|
|
398
368
|
smartWallet = address;
|
|
399
369
|
this.smartWalletCache.set(cacheKey, smartWallet);
|
|
400
|
-
} else {
|
|
401
|
-
logTiming("resolveSmartWallet cache-hit", startedAt, {
|
|
402
|
-
chainId: validChainId
|
|
403
|
-
});
|
|
404
370
|
}
|
|
405
|
-
logTiming("resolveSmartWallet ready", startedAt, { chainId: validChainId });
|
|
406
371
|
return { smartWallet, chainId: validChainId };
|
|
407
372
|
}
|
|
408
373
|
// --- IAgent: Connection lifecycle ---
|
|
@@ -462,14 +427,8 @@ var ZyfaiAgent = class {
|
|
|
462
427
|
}
|
|
463
428
|
// --- IAgent: Portfolio reads ---
|
|
464
429
|
async getBalances(state, chainId) {
|
|
465
|
-
const startedAt = Date.now();
|
|
466
430
|
const { smartWallet, chainId: validChainId } = await this.resolveSmartWallet(state, chainId);
|
|
467
|
-
const portfolioStart = Date.now();
|
|
468
431
|
const raw = await this.sdk.getPortfolio(this.getAddress());
|
|
469
|
-
logTiming("getBalances getPortfolio", portfolioStart, {
|
|
470
|
-
chainId: validChainId
|
|
471
|
-
});
|
|
472
|
-
logTiming("getBalances success", startedAt, { chainId: validChainId });
|
|
473
432
|
return mapBalances(raw, validChainId, smartWallet);
|
|
474
433
|
}
|
|
475
434
|
async getEarnings(state, chainId) {
|
|
@@ -534,13 +493,13 @@ function mapWithdraw2(raw) {
|
|
|
534
493
|
function mapPortfolioBalances(raw, smartWallet) {
|
|
535
494
|
let total = 0;
|
|
536
495
|
const tokens = [];
|
|
537
|
-
for (const item of raw.
|
|
538
|
-
total += item.
|
|
496
|
+
for (const item of raw.tokens) {
|
|
497
|
+
total += item.balanceFormatted;
|
|
539
498
|
tokens.push({
|
|
540
|
-
chain: item.chain
|
|
541
|
-
chainId: item.
|
|
542
|
-
asset: item.
|
|
543
|
-
amount:
|
|
499
|
+
chain: SUPPORTED_CHAINS[item.chain],
|
|
500
|
+
chainId: item.chain,
|
|
501
|
+
asset: item.symbol === "USD\u20AE0" ? "USDT" : item.symbol,
|
|
502
|
+
amount: item.balance
|
|
544
503
|
});
|
|
545
504
|
}
|
|
546
505
|
return {
|
|
@@ -659,7 +618,7 @@ function mapHistory2(raw) {
|
|
|
659
618
|
rewards: "Earned"
|
|
660
619
|
};
|
|
661
620
|
const filtered = raw.result.items.filter(
|
|
662
|
-
(i) => i.
|
|
621
|
+
(i) => !(i.type === "execution" && (i.status === "failed" || !i.transactions.length))
|
|
663
622
|
);
|
|
664
623
|
return {
|
|
665
624
|
total: filtered.length,
|
|
@@ -723,18 +682,10 @@ function remapApyPerAssetToSymbols(raw) {
|
|
|
723
682
|
var SAIL_API_BASE = "https://app.sail.money";
|
|
724
683
|
var PROJECT_ID = "sail";
|
|
725
684
|
var PAGE_ID = "home";
|
|
726
|
-
var SAIL_TIMING_PREFIX = "[AgentTiming][sail]";
|
|
727
685
|
var SAIL_PORTFOLIO_TIMEOUT_MS = 8e3;
|
|
728
|
-
function logTiming2(label, startedAt, meta) {
|
|
729
|
-
const elapsedMs = Date.now() - startedAt;
|
|
730
|
-
if (meta) {
|
|
731
|
-
console.log(`${SAIL_TIMING_PREFIX} ${label} ${elapsedMs}ms`, meta);
|
|
732
|
-
return;
|
|
733
|
-
}
|
|
734
|
-
console.log(`${SAIL_TIMING_PREFIX} ${label} ${elapsedMs}ms`);
|
|
735
|
-
}
|
|
736
686
|
var SailAgent = class {
|
|
737
687
|
id = "sail";
|
|
688
|
+
minDepositAmount = "4800000000";
|
|
738
689
|
supportedChainIds = [8453, 42161];
|
|
739
690
|
supportedAssets = [
|
|
740
691
|
{
|
|
@@ -805,7 +756,6 @@ var SailAgent = class {
|
|
|
805
756
|
}
|
|
806
757
|
/** Initiate SIWE and sign with the user's wallet. */
|
|
807
758
|
async signSiwe(state, chainId) {
|
|
808
|
-
const startedAt = Date.now();
|
|
809
759
|
const initiate = await this.request(
|
|
810
760
|
"POST",
|
|
811
761
|
`/api/v1/projects/${PROJECT_ID}/pages/${PAGE_ID}/auth/initiate`,
|
|
@@ -820,7 +770,6 @@ var SailAgent = class {
|
|
|
820
770
|
method: "personal_sign",
|
|
821
771
|
params: [initiate.message, state.walletAddress]
|
|
822
772
|
});
|
|
823
|
-
logTiming2("signSiwe success", startedAt, { chainId });
|
|
824
773
|
return {
|
|
825
774
|
sessionId: initiate.sessionId,
|
|
826
775
|
message: initiate.message,
|
|
@@ -829,14 +778,11 @@ var SailAgent = class {
|
|
|
829
778
|
}
|
|
830
779
|
/** Full connect: auth handles smart account creation via SIWE flow. */
|
|
831
780
|
async connectFull(state, chainId) {
|
|
832
|
-
const startedAt = Date.now();
|
|
833
781
|
if (this.connectedAddress && this.connectedChainId === chainId) {
|
|
834
|
-
logTiming2("connectFull cache-hit", startedAt, { chainId });
|
|
835
782
|
return;
|
|
836
783
|
}
|
|
837
784
|
if (this.connectPromise) {
|
|
838
785
|
await this.connectPromise;
|
|
839
|
-
logTiming2("connectFull awaited-inflight", startedAt, { chainId });
|
|
840
786
|
return;
|
|
841
787
|
}
|
|
842
788
|
if (!state.walletAddress) {
|
|
@@ -869,13 +815,11 @@ var SailAgent = class {
|
|
|
869
815
|
})();
|
|
870
816
|
try {
|
|
871
817
|
await this.connectPromise;
|
|
872
|
-
logTiming2("connectFull success", startedAt, { chainId });
|
|
873
818
|
} finally {
|
|
874
819
|
this.connectPromise = null;
|
|
875
820
|
}
|
|
876
821
|
}
|
|
877
822
|
async resolveSmartWallet(state, chainId) {
|
|
878
|
-
const startedAt = Date.now();
|
|
879
823
|
await this.connectFull(state, chainId);
|
|
880
824
|
const validChainId = isValidChainId(chainId);
|
|
881
825
|
if (!this.smartWalletAddress) {
|
|
@@ -884,7 +828,6 @@ var SailAgent = class {
|
|
|
884
828
|
"Wallet not connected. Call sdk.connect() first."
|
|
885
829
|
);
|
|
886
830
|
}
|
|
887
|
-
logTiming2("resolveSmartWallet ready", startedAt, { chainId: validChainId });
|
|
888
831
|
return {
|
|
889
832
|
smartWallet: this.smartWalletAddress,
|
|
890
833
|
chainId: validChainId
|
|
@@ -1009,13 +952,9 @@ var SailAgent = class {
|
|
|
1009
952
|
}
|
|
1010
953
|
// --- IAgent: Portfolio reads ---
|
|
1011
954
|
async getBalances(state, chainId) {
|
|
1012
|
-
const startedAt = Date.now();
|
|
1013
955
|
const { smartWallet } = await this.resolveSmartWallet(state, chainId);
|
|
1014
|
-
const portfolioStart = Date.now();
|
|
1015
956
|
try {
|
|
1016
|
-
const raw = await this.
|
|
1017
|
-
logTiming2("getBalances getMetricsPortfolio", portfolioStart, { chainId });
|
|
1018
|
-
logTiming2("getBalances success", startedAt, { chainId });
|
|
957
|
+
const raw = await this.getPortfolio();
|
|
1019
958
|
return mapPortfolioBalances(raw, smartWallet);
|
|
1020
959
|
} catch (error) {
|
|
1021
960
|
if (error instanceof OwneyError && error.code === "API_SAIL_TIMEOUT") {
|
|
@@ -1025,9 +964,8 @@ var SailAgent = class {
|
|
|
1025
964
|
chainId
|
|
1026
965
|
}
|
|
1027
966
|
);
|
|
1028
|
-
logTiming2("getBalances timeout-fallback", startedAt, { chainId });
|
|
1029
967
|
return mapPortfolioBalances(
|
|
1030
|
-
{ message: "timeout",
|
|
968
|
+
{ message: "timeout", tokens: [] },
|
|
1031
969
|
smartWallet
|
|
1032
970
|
);
|
|
1033
971
|
}
|
|
@@ -1058,6 +996,14 @@ var SailAgent = class {
|
|
|
1058
996
|
SAIL_PORTFOLIO_TIMEOUT_MS
|
|
1059
997
|
);
|
|
1060
998
|
}
|
|
999
|
+
async getPortfolio() {
|
|
1000
|
+
return this.request(
|
|
1001
|
+
"GET",
|
|
1002
|
+
`/api/v1/projects/${PROJECT_ID}/pages/${PAGE_ID}/portfolio/tokens`,
|
|
1003
|
+
void 0,
|
|
1004
|
+
SAIL_PORTFOLIO_TIMEOUT_MS
|
|
1005
|
+
);
|
|
1006
|
+
}
|
|
1061
1007
|
async getMetricsEarnings(state, chainId) {
|
|
1062
1008
|
const { smartWallet } = await this.resolveSmartWallet(state, chainId);
|
|
1063
1009
|
return this.request(
|
|
@@ -1065,7 +1011,7 @@ var SailAgent = class {
|
|
|
1065
1011
|
`/api/v1/projects/${PROJECT_ID}/pages/${PAGE_ID}/metrics/earnings?smart_account=${smartWallet}`
|
|
1066
1012
|
);
|
|
1067
1013
|
}
|
|
1068
|
-
async getMetricsBalance(state, chainId, currency) {
|
|
1014
|
+
async getMetricsBalance(state, chainId, currency = "usd") {
|
|
1069
1015
|
const { smartWallet } = await this.resolveSmartWallet(state, chainId);
|
|
1070
1016
|
return this.request(
|
|
1071
1017
|
"GET",
|
|
@@ -1213,27 +1159,16 @@ async function fetchAgentKeys(apiKey) {
|
|
|
1213
1159
|
}
|
|
1214
1160
|
|
|
1215
1161
|
// src/client.ts
|
|
1216
|
-
var AGENT_CONSTRUCTORS = {
|
|
1217
|
-
zyfai: ZyfaiAgent,
|
|
1218
|
-
sail: SailAgent
|
|
1219
|
-
};
|
|
1220
|
-
var SDK_TIMING_PREFIX = "[OwneySDKTiming]";
|
|
1221
|
-
function logTiming3(label, startedAt, meta) {
|
|
1222
|
-
const elapsedMs = Date.now() - startedAt;
|
|
1223
|
-
if (meta) {
|
|
1224
|
-
console.log(`${SDK_TIMING_PREFIX} ${label} ${elapsedMs}ms`, meta);
|
|
1225
|
-
return;
|
|
1226
|
-
}
|
|
1227
|
-
console.log(`${SDK_TIMING_PREFIX} ${label} ${elapsedMs}ms`);
|
|
1228
|
-
}
|
|
1229
1162
|
var OwneySDK = class {
|
|
1230
1163
|
agents = /* @__PURE__ */ new Map();
|
|
1231
1164
|
activeAgents = /* @__PURE__ */ new Set();
|
|
1232
1165
|
state = null;
|
|
1233
1166
|
apiKey;
|
|
1167
|
+
zyfaiRpcUrls;
|
|
1234
1168
|
initializingAgentsPromise = null;
|
|
1235
1169
|
constructor(config) {
|
|
1236
1170
|
this.apiKey = config.apiKey;
|
|
1171
|
+
this.zyfaiRpcUrls = config.zyfaiRpcUrls;
|
|
1237
1172
|
}
|
|
1238
1173
|
/**
|
|
1239
1174
|
* Establish connection state for all subsequent SDK calls.
|
|
@@ -1317,10 +1252,9 @@ var OwneySDK = class {
|
|
|
1317
1252
|
this.initializingAgentsPromise = (async () => {
|
|
1318
1253
|
const agentKeys = await fetchAgentKeys(this.apiKey);
|
|
1319
1254
|
for (const { key, agent_type } of agentKeys) {
|
|
1320
|
-
const
|
|
1321
|
-
if (!
|
|
1255
|
+
const agent = this.createAgent(agent_type, key);
|
|
1256
|
+
if (!agent)
|
|
1322
1257
|
continue;
|
|
1323
|
-
const agent = new AgentClass(key);
|
|
1324
1258
|
this.agents.set(agent_type, agent);
|
|
1325
1259
|
}
|
|
1326
1260
|
if (this.agents.size === 0) {
|
|
@@ -1337,6 +1271,15 @@ var OwneySDK = class {
|
|
|
1337
1271
|
this.initializingAgentsPromise = null;
|
|
1338
1272
|
}
|
|
1339
1273
|
}
|
|
1274
|
+
createAgent(agentId, key) {
|
|
1275
|
+
if (agentId === "zyfai") {
|
|
1276
|
+
return new ZyfaiAgent(key, this.zyfaiRpcUrls);
|
|
1277
|
+
}
|
|
1278
|
+
if (agentId === "sail") {
|
|
1279
|
+
return new SailAgent(key);
|
|
1280
|
+
}
|
|
1281
|
+
return null;
|
|
1282
|
+
}
|
|
1340
1283
|
// --- Account lifecycle ---
|
|
1341
1284
|
/**
|
|
1342
1285
|
* Activate the user's smart wallet for the specified agents, or all chain-compatible agents if omitted.
|
|
@@ -1349,7 +1292,6 @@ var OwneySDK = class {
|
|
|
1349
1292
|
* throws before activating any agent.
|
|
1350
1293
|
*/
|
|
1351
1294
|
async activateAgent(chainId, agentId) {
|
|
1352
|
-
const startedAt = Date.now();
|
|
1353
1295
|
const state = this.requireState();
|
|
1354
1296
|
await this.ensureAgentsInitialized();
|
|
1355
1297
|
if (agentId !== void 0) {
|
|
@@ -1377,20 +1319,11 @@ var OwneySDK = class {
|
|
|
1377
1319
|
state.chainId = chainId;
|
|
1378
1320
|
Promise.all(
|
|
1379
1321
|
agents.map(async (agent) => {
|
|
1380
|
-
const agentStart = Date.now();
|
|
1381
1322
|
await agent.activateAgent(state, chainId);
|
|
1382
|
-
logTiming3("activateAgent background-agent-ready", agentStart, {
|
|
1383
|
-
chainId,
|
|
1384
|
-
agentId: agent.id
|
|
1385
|
-
});
|
|
1386
1323
|
})
|
|
1387
1324
|
).catch((error) => {
|
|
1388
1325
|
console.error("activateAgent background init failed:", error);
|
|
1389
1326
|
});
|
|
1390
|
-
logTiming3("activateAgent scheduled", startedAt, {
|
|
1391
|
-
chainId,
|
|
1392
|
-
agentIds: uniqueIds
|
|
1393
|
-
});
|
|
1394
1327
|
return;
|
|
1395
1328
|
}
|
|
1396
1329
|
const compatible = [...this.agents.values()].filter(
|
|
@@ -1410,24 +1343,15 @@ var OwneySDK = class {
|
|
|
1410
1343
|
state.chainId = chainId;
|
|
1411
1344
|
Promise.all(
|
|
1412
1345
|
compatible.map(async (agent) => {
|
|
1413
|
-
const agentStart = Date.now();
|
|
1414
1346
|
await agent.activateAgent(state, chainId);
|
|
1415
|
-
logTiming3("activateAgent background-agent-ready", agentStart, {
|
|
1416
|
-
chainId,
|
|
1417
|
-
agentId: agent.id
|
|
1418
|
-
});
|
|
1419
1347
|
})
|
|
1420
1348
|
).catch((error) => {
|
|
1421
1349
|
console.error("activateAgent background init failed:", error);
|
|
1422
1350
|
});
|
|
1423
|
-
logTiming3("activateAgent scheduled", startedAt, {
|
|
1424
|
-
chainId,
|
|
1425
|
-
agentIds: compatible.map((agent) => agent.id)
|
|
1426
|
-
});
|
|
1427
1351
|
}
|
|
1428
1352
|
/**
|
|
1429
1353
|
* Deposit funds into a specific agent, or split equally across all agents if agentId is omitted.
|
|
1430
|
-
|
|
1354
|
+
* Validates that the asset is supported and amount meets minimums for the target agent(s).
|
|
1431
1355
|
* @param options - Deposit parameters
|
|
1432
1356
|
* @param options.amount - Amount to deposit in smallest unit (e.g. "100000000" for 100 USDC)
|
|
1433
1357
|
* @param options.asset - Asset symbol to deposit (e.g. "USDC")
|
|
@@ -1439,28 +1363,29 @@ var OwneySDK = class {
|
|
|
1439
1363
|
*/
|
|
1440
1364
|
async deposit(options) {
|
|
1441
1365
|
const { amount, asset, depositCallback, agentId } = options;
|
|
1366
|
+
if (BigInt(amount) === 0n) {
|
|
1367
|
+
return { agentResults: {} };
|
|
1368
|
+
}
|
|
1442
1369
|
const state = this.requireState();
|
|
1443
1370
|
const chainId = this.requireChainId();
|
|
1444
1371
|
if (agentId) {
|
|
1445
1372
|
const agent = this.getAgent(agentId);
|
|
1446
1373
|
this.validateAssetSupport(agent, chainId, asset);
|
|
1374
|
+
this.validateMinDepositAmount(agent, amount);
|
|
1447
1375
|
return agent.deposit(state, chainId, amount, depositCallback);
|
|
1448
1376
|
}
|
|
1449
|
-
const eligibleAgents = this.getEligibleAgents(chainId, asset);
|
|
1450
1377
|
const totalAmount = BigInt(amount);
|
|
1451
|
-
|
|
1378
|
+
const eligibleAgents = this.getEligibleAgents(chainId, asset);
|
|
1379
|
+
const agentAmounts = this.splitDepositAmount(totalAmount, eligibleAgents);
|
|
1380
|
+
if (agentAmounts.length === 0) {
|
|
1452
1381
|
throw new OwneyError(
|
|
1453
|
-
"
|
|
1454
|
-
`Amount "${amount}"
|
|
1455
|
-
{ amount
|
|
1382
|
+
"DEPOSIT_AMOUNT_BELOW_MINIMUM",
|
|
1383
|
+
`Amount "${amount}" cannot satisfy minimum deposit requirements for any eligible agent.`,
|
|
1384
|
+
{ amount }
|
|
1456
1385
|
);
|
|
1457
1386
|
}
|
|
1458
|
-
const perAgent = totalAmount / BigInt(eligibleAgents.length);
|
|
1459
|
-
const remainder = totalAmount % BigInt(eligibleAgents.length);
|
|
1460
1387
|
const agentResults = {};
|
|
1461
|
-
for (
|
|
1462
|
-
const agent = eligibleAgents[i];
|
|
1463
|
-
const agentAmount = i === eligibleAgents.length - 1 ? String(perAgent + remainder) : String(perAgent);
|
|
1388
|
+
for (const { agent, amount: agentAmount } of agentAmounts) {
|
|
1464
1389
|
agentResults[agent.id] = await agent.deposit(
|
|
1465
1390
|
state,
|
|
1466
1391
|
chainId,
|
|
@@ -1470,6 +1395,37 @@ var OwneySDK = class {
|
|
|
1470
1395
|
}
|
|
1471
1396
|
return { agentResults };
|
|
1472
1397
|
}
|
|
1398
|
+
splitDepositAmount(totalAmount, agents) {
|
|
1399
|
+
if (agents.length === 0)
|
|
1400
|
+
return [];
|
|
1401
|
+
const perAgent = totalAmount / BigInt(agents.length);
|
|
1402
|
+
const remainder = totalAmount % BigInt(agents.length);
|
|
1403
|
+
const splits = agents.map((agent, i) => ({
|
|
1404
|
+
agent,
|
|
1405
|
+
amount: i === agents.length - 1 ? perAgent + remainder : perAgent
|
|
1406
|
+
}));
|
|
1407
|
+
const valid = splits.filter(
|
|
1408
|
+
(s) => s.amount >= BigInt(s.agent.minDepositAmount)
|
|
1409
|
+
);
|
|
1410
|
+
if (valid.length === agents.length) {
|
|
1411
|
+
return splits.map((s) => ({ agent: s.agent, amount: String(s.amount) }));
|
|
1412
|
+
}
|
|
1413
|
+
return this.splitDepositAmount(totalAmount, valid.map((s) => s.agent));
|
|
1414
|
+
}
|
|
1415
|
+
validateMinDepositAmount(agent, amount) {
|
|
1416
|
+
const minDepositAmount = BigInt(agent.minDepositAmount);
|
|
1417
|
+
const parsedAmount = BigInt(amount);
|
|
1418
|
+
if (parsedAmount < minDepositAmount) {
|
|
1419
|
+
throw new OwneyError(
|
|
1420
|
+
"DEPOSIT_AMOUNT_BELOW_MINIMUM",
|
|
1421
|
+
`Amount "${amount}" is below the required minimum deposit for agent "${agent.id}".`,
|
|
1422
|
+
{
|
|
1423
|
+
agentId: agent.id,
|
|
1424
|
+
amount
|
|
1425
|
+
}
|
|
1426
|
+
);
|
|
1427
|
+
}
|
|
1428
|
+
}
|
|
1473
1429
|
validateAssetSupport(agent, chainId, asset) {
|
|
1474
1430
|
const chainAssets = agent.supportedAssets.find(
|
|
1475
1431
|
(sa) => sa.chainId === chainId
|
|
@@ -1548,12 +1504,10 @@ var OwneySDK = class {
|
|
|
1548
1504
|
* @returns {AgentBalance} for a single agent, or {OwneyBalances} with totalBalance and per-agent breakdown
|
|
1549
1505
|
*/
|
|
1550
1506
|
async getBalances(agentId) {
|
|
1551
|
-
const startedAt = Date.now();
|
|
1552
1507
|
const state = this.requireState();
|
|
1553
1508
|
const chainId = this.requireChainId();
|
|
1554
1509
|
if (agentId) {
|
|
1555
1510
|
const result = await this.getAgent(agentId).getBalances(state, chainId);
|
|
1556
|
-
logTiming3("getBalances single-agent", startedAt, { chainId, agentId });
|
|
1557
1511
|
return result;
|
|
1558
1512
|
}
|
|
1559
1513
|
let totalBalance = 0;
|
|
@@ -1561,12 +1515,7 @@ var OwneySDK = class {
|
|
|
1561
1515
|
const entries = [...this.getActiveAgents().entries()];
|
|
1562
1516
|
const balanceResults = await Promise.allSettled(
|
|
1563
1517
|
entries.map(async ([id, agent]) => {
|
|
1564
|
-
const agentStartedAt = Date.now();
|
|
1565
1518
|
const b = await agent.getBalances(state, chainId);
|
|
1566
|
-
logTiming3("getBalances per-agent", agentStartedAt, {
|
|
1567
|
-
chainId,
|
|
1568
|
-
agentId: id
|
|
1569
|
-
});
|
|
1570
1519
|
return [id, b];
|
|
1571
1520
|
})
|
|
1572
1521
|
);
|
|
@@ -1587,11 +1536,6 @@ var OwneySDK = class {
|
|
|
1587
1536
|
"Failed to fetch balances for all active agents."
|
|
1588
1537
|
);
|
|
1589
1538
|
}
|
|
1590
|
-
logTiming3("getBalances aggregate", startedAt, {
|
|
1591
|
-
chainId,
|
|
1592
|
-
totalAgents: entries.length,
|
|
1593
|
-
successCount
|
|
1594
|
-
});
|
|
1595
1539
|
return {
|
|
1596
1540
|
totalBalance: String(totalBalance),
|
|
1597
1541
|
agentBalances: results
|
|
@@ -1664,18 +1608,30 @@ var OwneySDK = class {
|
|
|
1664
1608
|
results[id] = apy;
|
|
1665
1609
|
}
|
|
1666
1610
|
const balances = {};
|
|
1667
|
-
let totalBalance = 0;
|
|
1668
1611
|
for (const [id, bal] of balanceResults) {
|
|
1669
1612
|
balances[id] = bal;
|
|
1670
|
-
totalBalance += bal;
|
|
1671
1613
|
}
|
|
1672
1614
|
let totalApy = 0;
|
|
1673
|
-
|
|
1615
|
+
let relevantBalance = 0;
|
|
1616
|
+
for (const id of Object.keys(results)) {
|
|
1617
|
+
const agentApy = Number(results[id].weightedApyAfterFee ?? 0);
|
|
1618
|
+
if (agentApy === 0)
|
|
1619
|
+
continue;
|
|
1620
|
+
relevantBalance += balances[id];
|
|
1621
|
+
}
|
|
1622
|
+
if (relevantBalance > 0) {
|
|
1674
1623
|
for (const id of Object.keys(results)) {
|
|
1675
|
-
const
|
|
1676
|
-
|
|
1624
|
+
const agentApy = Number(results[id].weightedApyAfterFee ?? 0);
|
|
1625
|
+
if (agentApy === 0)
|
|
1626
|
+
continue;
|
|
1627
|
+
const weight = balances[id] / relevantBalance;
|
|
1628
|
+
totalApy += agentApy * weight;
|
|
1677
1629
|
}
|
|
1678
1630
|
}
|
|
1631
|
+
console.log("account apy", {
|
|
1632
|
+
totalApy: String(totalApy),
|
|
1633
|
+
agentApy: results
|
|
1634
|
+
});
|
|
1679
1635
|
return {
|
|
1680
1636
|
totalApy: String(totalApy),
|
|
1681
1637
|
agentApy: results
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@owney/sdk",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.9",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"main": "dist/index.cjs",
|
|
6
6
|
"module": "dist/index.js",
|
|
@@ -26,5 +26,8 @@
|
|
|
26
26
|
"dotenv": "^17.3.1",
|
|
27
27
|
"tsup": "^7.0.0",
|
|
28
28
|
"typescript": "^5.0.0"
|
|
29
|
+
},
|
|
30
|
+
"publishConfig": {
|
|
31
|
+
"access": "public"
|
|
29
32
|
}
|
|
30
33
|
}
|