@aspan/sdk 0.4.4 → 0.4.6
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 +8 -0
- package/dist/index.d.mts +116 -1
- package/dist/index.d.ts +116 -1
- package/dist/index.js +289 -14
- package/dist/index.mjs +289 -14
- package/package.json +1 -1
- package/src/__tests__/read-client.test.ts +212 -0
- package/src/abi/diamond.ts +36 -0
- package/src/abi/sApUSD.ts +36 -0
- package/src/client.ts +160 -14
package/README.md
CHANGED
|
@@ -347,6 +347,13 @@ const hash = await client.deposit({ apUSDAmount: parseAmount("1000") });
|
|
|
347
347
|
const position = await client.getUserStabilityPoolPosition(account.address);
|
|
348
348
|
console.log("sApUSD Balance:", formatAmount(position.balance));
|
|
349
349
|
console.log("Earned:", formatAmount(position.balance - position.deposited));
|
|
350
|
+
|
|
351
|
+
// Preview withdrawal (supports dirty pools with apUSD + xBNB)
|
|
352
|
+
const preview = await client.previewRedeemMulti(position.shares);
|
|
353
|
+
console.log("Will receive apUSD:", formatAmount(preview.apUSD));
|
|
354
|
+
if (preview.hasXBNB) {
|
|
355
|
+
console.log("Will also receive xBNB:", formatAmount(preview.xBNB));
|
|
356
|
+
}
|
|
350
357
|
```
|
|
351
358
|
|
|
352
359
|
### 5. Quick Exit: apUSD/xBNB → USDT
|
|
@@ -539,6 +546,7 @@ console.log("Leverage:", formatAmount(stats.effectiveLeverage), "x");
|
|
|
539
546
|
| `redeemXBNB(params)` | Redeem xBNB for LST |
|
|
540
547
|
| `deposit(params)` | Deposit apUSD to stability pool |
|
|
541
548
|
| `withdraw(params)` | Withdraw from stability pool |
|
|
549
|
+
| `previewRedeemMulti(shares)` | Preview multi-asset withdrawal (apUSD + xBNB) |
|
|
542
550
|
| `harvestYield()` | Trigger yield distribution |
|
|
543
551
|
|
|
544
552
|
---
|
package/dist/index.d.mts
CHANGED
|
@@ -457,11 +457,30 @@ declare class AspanReadClient {
|
|
|
457
457
|
getOracleBounds(priceFeed: Address): Promise<OracleBounds>;
|
|
458
458
|
getShares(user: Address): Promise<bigint>;
|
|
459
459
|
getBalance(user: Address): Promise<bigint>;
|
|
460
|
+
/**
|
|
461
|
+
* Get user's underlying balances (apUSD + xBNB) from sApUSD vault
|
|
462
|
+
*/
|
|
463
|
+
getBalanceMulti(user: Address): Promise<{
|
|
464
|
+
apUSDBalance: bigint;
|
|
465
|
+
xBNBBalance: bigint;
|
|
466
|
+
}>;
|
|
460
467
|
getUserStabilityPoolPosition(user: Address): Promise<UserStabilityPoolPosition>;
|
|
461
468
|
getExchangeRate(): Promise<bigint>;
|
|
462
469
|
getTotalStaked(): Promise<bigint>;
|
|
463
470
|
previewDeposit(assets: bigint): Promise<bigint>;
|
|
464
|
-
|
|
471
|
+
/**
|
|
472
|
+
* Preview withdraw with multi-asset support (apUSD + xBNB)
|
|
473
|
+
* Replaces previewRedeem — works for both clean and dirty pools.
|
|
474
|
+
* @param shares Amount of sApUSD shares to redeem
|
|
475
|
+
* @returns Object with apUSD and xBNB amounts, plus whether vault has xBNB
|
|
476
|
+
*/
|
|
477
|
+
previewRedeemMulti(shares: bigint): Promise<{
|
|
478
|
+
apUSD: bigint;
|
|
479
|
+
xBNB: bigint;
|
|
480
|
+
hasXBNB: boolean;
|
|
481
|
+
assets: Address[];
|
|
482
|
+
amounts: bigint[];
|
|
483
|
+
}>;
|
|
465
484
|
getPendingYield(): Promise<bigint>;
|
|
466
485
|
getTotalYieldGenerated(): Promise<bigint>;
|
|
467
486
|
getLSTYieldInfo(lstToken: Address): Promise<LSTYieldInfo>;
|
|
@@ -474,6 +493,39 @@ declare class AspanReadClient {
|
|
|
474
493
|
getTreasury(): Promise<Address>;
|
|
475
494
|
getFeeTierCount(): Promise<bigint>;
|
|
476
495
|
getFeeTier(index: bigint): Promise<FeeTier>;
|
|
496
|
+
/**
|
|
497
|
+
* Get all fee tiers
|
|
498
|
+
* @returns Array of fee tiers sorted by minCR descending
|
|
499
|
+
*/
|
|
500
|
+
getAllFeeTiers(): Promise<FeeTier[]>;
|
|
501
|
+
/**
|
|
502
|
+
* Get comprehensive vault (sApUSD) info for frontend display
|
|
503
|
+
* @returns Vault state including TVL, exchange rate, xBNB status
|
|
504
|
+
*/
|
|
505
|
+
getVaultInfo(): Promise<{
|
|
506
|
+
totalSupply: bigint;
|
|
507
|
+
totalAssets: bigint;
|
|
508
|
+
exchangeRate: bigint;
|
|
509
|
+
hasXBNB: boolean;
|
|
510
|
+
xBNBAmount: bigint;
|
|
511
|
+
}>;
|
|
512
|
+
/**
|
|
513
|
+
* Get full protocol dashboard data in one call (for frontend overview page)
|
|
514
|
+
* Batches all key metrics into a single multicall
|
|
515
|
+
*/
|
|
516
|
+
getProtocolOverview(): Promise<{
|
|
517
|
+
collateralRatio: bigint;
|
|
518
|
+
tvlBNB: bigint;
|
|
519
|
+
tvlUSD: bigint;
|
|
520
|
+
apUSDSupply: bigint;
|
|
521
|
+
xBNBSupply: bigint;
|
|
522
|
+
xBNBPriceUSD: bigint;
|
|
523
|
+
xBNBPriceBNB: bigint;
|
|
524
|
+
bnbPriceUSD: bigint;
|
|
525
|
+
currentFees: CurrentFeeTier;
|
|
526
|
+
stabilityMode: StabilityModeInfo;
|
|
527
|
+
totalStaked: bigint;
|
|
528
|
+
}>;
|
|
477
529
|
getCurrentFeeTier(): Promise<CurrentFeeTier>;
|
|
478
530
|
getMaxPriceAge(): Promise<bigint>;
|
|
479
531
|
getMinDepositPeriod(): Promise<bigint>;
|
|
@@ -1377,6 +1429,24 @@ declare const DiamondABI: readonly [{
|
|
|
1377
1429
|
readonly internalType: "uint256";
|
|
1378
1430
|
}];
|
|
1379
1431
|
readonly stateMutability: "view";
|
|
1432
|
+
}, {
|
|
1433
|
+
readonly type: "function";
|
|
1434
|
+
readonly name: "previewRedeemMulti";
|
|
1435
|
+
readonly inputs: readonly [{
|
|
1436
|
+
readonly name: "_shares";
|
|
1437
|
+
readonly type: "uint256";
|
|
1438
|
+
readonly internalType: "uint256";
|
|
1439
|
+
}];
|
|
1440
|
+
readonly outputs: readonly [{
|
|
1441
|
+
readonly name: "assets";
|
|
1442
|
+
readonly type: "address[]";
|
|
1443
|
+
readonly internalType: "address[]";
|
|
1444
|
+
}, {
|
|
1445
|
+
readonly name: "amounts";
|
|
1446
|
+
readonly type: "uint256[]";
|
|
1447
|
+
readonly internalType: "uint256[]";
|
|
1448
|
+
}];
|
|
1449
|
+
readonly stateMutability: "view";
|
|
1380
1450
|
}, {
|
|
1381
1451
|
readonly type: "function";
|
|
1382
1452
|
readonly name: "getPendingYield";
|
|
@@ -1529,6 +1599,16 @@ declare const DiamondABI: readonly [{
|
|
|
1529
1599
|
readonly internalType: "address";
|
|
1530
1600
|
}];
|
|
1531
1601
|
readonly stateMutability: "view";
|
|
1602
|
+
}, {
|
|
1603
|
+
readonly type: "function";
|
|
1604
|
+
readonly name: "setSApUSD";
|
|
1605
|
+
readonly inputs: readonly [{
|
|
1606
|
+
readonly name: "_sApUSD";
|
|
1607
|
+
readonly type: "address";
|
|
1608
|
+
readonly internalType: "address";
|
|
1609
|
+
}];
|
|
1610
|
+
readonly outputs: readonly [];
|
|
1611
|
+
readonly stateMutability: "nonpayable";
|
|
1532
1612
|
}, {
|
|
1533
1613
|
readonly type: "function";
|
|
1534
1614
|
readonly name: "getStabilityPool";
|
|
@@ -1559,6 +1639,41 @@ declare const DiamondABI: readonly [{
|
|
|
1559
1639
|
readonly internalType: "uint256";
|
|
1560
1640
|
}];
|
|
1561
1641
|
readonly stateMutability: "view";
|
|
1642
|
+
}, {
|
|
1643
|
+
readonly type: "function";
|
|
1644
|
+
readonly name: "getAllFeeTiers";
|
|
1645
|
+
readonly inputs: readonly [];
|
|
1646
|
+
readonly outputs: readonly [{
|
|
1647
|
+
readonly name: "";
|
|
1648
|
+
readonly type: "tuple[]";
|
|
1649
|
+
readonly internalType: "struct LibAppStorage.FeeTier[]";
|
|
1650
|
+
readonly components: readonly [{
|
|
1651
|
+
readonly name: "minCR";
|
|
1652
|
+
readonly type: "uint256";
|
|
1653
|
+
readonly internalType: "uint256";
|
|
1654
|
+
}, {
|
|
1655
|
+
readonly name: "apUSDMintFee";
|
|
1656
|
+
readonly type: "uint16";
|
|
1657
|
+
readonly internalType: "uint16";
|
|
1658
|
+
}, {
|
|
1659
|
+
readonly name: "apUSDRedeemFee";
|
|
1660
|
+
readonly type: "uint16";
|
|
1661
|
+
readonly internalType: "uint16";
|
|
1662
|
+
}, {
|
|
1663
|
+
readonly name: "xBNBMintFee";
|
|
1664
|
+
readonly type: "uint16";
|
|
1665
|
+
readonly internalType: "uint16";
|
|
1666
|
+
}, {
|
|
1667
|
+
readonly name: "xBNBRedeemFee";
|
|
1668
|
+
readonly type: "uint16";
|
|
1669
|
+
readonly internalType: "uint16";
|
|
1670
|
+
}, {
|
|
1671
|
+
readonly name: "apUSDMintDisabled";
|
|
1672
|
+
readonly type: "bool";
|
|
1673
|
+
readonly internalType: "bool";
|
|
1674
|
+
}];
|
|
1675
|
+
}];
|
|
1676
|
+
readonly stateMutability: "view";
|
|
1562
1677
|
}, {
|
|
1563
1678
|
readonly type: "function";
|
|
1564
1679
|
readonly name: "getFeeTier";
|
package/dist/index.d.ts
CHANGED
|
@@ -457,11 +457,30 @@ declare class AspanReadClient {
|
|
|
457
457
|
getOracleBounds(priceFeed: Address): Promise<OracleBounds>;
|
|
458
458
|
getShares(user: Address): Promise<bigint>;
|
|
459
459
|
getBalance(user: Address): Promise<bigint>;
|
|
460
|
+
/**
|
|
461
|
+
* Get user's underlying balances (apUSD + xBNB) from sApUSD vault
|
|
462
|
+
*/
|
|
463
|
+
getBalanceMulti(user: Address): Promise<{
|
|
464
|
+
apUSDBalance: bigint;
|
|
465
|
+
xBNBBalance: bigint;
|
|
466
|
+
}>;
|
|
460
467
|
getUserStabilityPoolPosition(user: Address): Promise<UserStabilityPoolPosition>;
|
|
461
468
|
getExchangeRate(): Promise<bigint>;
|
|
462
469
|
getTotalStaked(): Promise<bigint>;
|
|
463
470
|
previewDeposit(assets: bigint): Promise<bigint>;
|
|
464
|
-
|
|
471
|
+
/**
|
|
472
|
+
* Preview withdraw with multi-asset support (apUSD + xBNB)
|
|
473
|
+
* Replaces previewRedeem — works for both clean and dirty pools.
|
|
474
|
+
* @param shares Amount of sApUSD shares to redeem
|
|
475
|
+
* @returns Object with apUSD and xBNB amounts, plus whether vault has xBNB
|
|
476
|
+
*/
|
|
477
|
+
previewRedeemMulti(shares: bigint): Promise<{
|
|
478
|
+
apUSD: bigint;
|
|
479
|
+
xBNB: bigint;
|
|
480
|
+
hasXBNB: boolean;
|
|
481
|
+
assets: Address[];
|
|
482
|
+
amounts: bigint[];
|
|
483
|
+
}>;
|
|
465
484
|
getPendingYield(): Promise<bigint>;
|
|
466
485
|
getTotalYieldGenerated(): Promise<bigint>;
|
|
467
486
|
getLSTYieldInfo(lstToken: Address): Promise<LSTYieldInfo>;
|
|
@@ -474,6 +493,39 @@ declare class AspanReadClient {
|
|
|
474
493
|
getTreasury(): Promise<Address>;
|
|
475
494
|
getFeeTierCount(): Promise<bigint>;
|
|
476
495
|
getFeeTier(index: bigint): Promise<FeeTier>;
|
|
496
|
+
/**
|
|
497
|
+
* Get all fee tiers
|
|
498
|
+
* @returns Array of fee tiers sorted by minCR descending
|
|
499
|
+
*/
|
|
500
|
+
getAllFeeTiers(): Promise<FeeTier[]>;
|
|
501
|
+
/**
|
|
502
|
+
* Get comprehensive vault (sApUSD) info for frontend display
|
|
503
|
+
* @returns Vault state including TVL, exchange rate, xBNB status
|
|
504
|
+
*/
|
|
505
|
+
getVaultInfo(): Promise<{
|
|
506
|
+
totalSupply: bigint;
|
|
507
|
+
totalAssets: bigint;
|
|
508
|
+
exchangeRate: bigint;
|
|
509
|
+
hasXBNB: boolean;
|
|
510
|
+
xBNBAmount: bigint;
|
|
511
|
+
}>;
|
|
512
|
+
/**
|
|
513
|
+
* Get full protocol dashboard data in one call (for frontend overview page)
|
|
514
|
+
* Batches all key metrics into a single multicall
|
|
515
|
+
*/
|
|
516
|
+
getProtocolOverview(): Promise<{
|
|
517
|
+
collateralRatio: bigint;
|
|
518
|
+
tvlBNB: bigint;
|
|
519
|
+
tvlUSD: bigint;
|
|
520
|
+
apUSDSupply: bigint;
|
|
521
|
+
xBNBSupply: bigint;
|
|
522
|
+
xBNBPriceUSD: bigint;
|
|
523
|
+
xBNBPriceBNB: bigint;
|
|
524
|
+
bnbPriceUSD: bigint;
|
|
525
|
+
currentFees: CurrentFeeTier;
|
|
526
|
+
stabilityMode: StabilityModeInfo;
|
|
527
|
+
totalStaked: bigint;
|
|
528
|
+
}>;
|
|
477
529
|
getCurrentFeeTier(): Promise<CurrentFeeTier>;
|
|
478
530
|
getMaxPriceAge(): Promise<bigint>;
|
|
479
531
|
getMinDepositPeriod(): Promise<bigint>;
|
|
@@ -1377,6 +1429,24 @@ declare const DiamondABI: readonly [{
|
|
|
1377
1429
|
readonly internalType: "uint256";
|
|
1378
1430
|
}];
|
|
1379
1431
|
readonly stateMutability: "view";
|
|
1432
|
+
}, {
|
|
1433
|
+
readonly type: "function";
|
|
1434
|
+
readonly name: "previewRedeemMulti";
|
|
1435
|
+
readonly inputs: readonly [{
|
|
1436
|
+
readonly name: "_shares";
|
|
1437
|
+
readonly type: "uint256";
|
|
1438
|
+
readonly internalType: "uint256";
|
|
1439
|
+
}];
|
|
1440
|
+
readonly outputs: readonly [{
|
|
1441
|
+
readonly name: "assets";
|
|
1442
|
+
readonly type: "address[]";
|
|
1443
|
+
readonly internalType: "address[]";
|
|
1444
|
+
}, {
|
|
1445
|
+
readonly name: "amounts";
|
|
1446
|
+
readonly type: "uint256[]";
|
|
1447
|
+
readonly internalType: "uint256[]";
|
|
1448
|
+
}];
|
|
1449
|
+
readonly stateMutability: "view";
|
|
1380
1450
|
}, {
|
|
1381
1451
|
readonly type: "function";
|
|
1382
1452
|
readonly name: "getPendingYield";
|
|
@@ -1529,6 +1599,16 @@ declare const DiamondABI: readonly [{
|
|
|
1529
1599
|
readonly internalType: "address";
|
|
1530
1600
|
}];
|
|
1531
1601
|
readonly stateMutability: "view";
|
|
1602
|
+
}, {
|
|
1603
|
+
readonly type: "function";
|
|
1604
|
+
readonly name: "setSApUSD";
|
|
1605
|
+
readonly inputs: readonly [{
|
|
1606
|
+
readonly name: "_sApUSD";
|
|
1607
|
+
readonly type: "address";
|
|
1608
|
+
readonly internalType: "address";
|
|
1609
|
+
}];
|
|
1610
|
+
readonly outputs: readonly [];
|
|
1611
|
+
readonly stateMutability: "nonpayable";
|
|
1532
1612
|
}, {
|
|
1533
1613
|
readonly type: "function";
|
|
1534
1614
|
readonly name: "getStabilityPool";
|
|
@@ -1559,6 +1639,41 @@ declare const DiamondABI: readonly [{
|
|
|
1559
1639
|
readonly internalType: "uint256";
|
|
1560
1640
|
}];
|
|
1561
1641
|
readonly stateMutability: "view";
|
|
1642
|
+
}, {
|
|
1643
|
+
readonly type: "function";
|
|
1644
|
+
readonly name: "getAllFeeTiers";
|
|
1645
|
+
readonly inputs: readonly [];
|
|
1646
|
+
readonly outputs: readonly [{
|
|
1647
|
+
readonly name: "";
|
|
1648
|
+
readonly type: "tuple[]";
|
|
1649
|
+
readonly internalType: "struct LibAppStorage.FeeTier[]";
|
|
1650
|
+
readonly components: readonly [{
|
|
1651
|
+
readonly name: "minCR";
|
|
1652
|
+
readonly type: "uint256";
|
|
1653
|
+
readonly internalType: "uint256";
|
|
1654
|
+
}, {
|
|
1655
|
+
readonly name: "apUSDMintFee";
|
|
1656
|
+
readonly type: "uint16";
|
|
1657
|
+
readonly internalType: "uint16";
|
|
1658
|
+
}, {
|
|
1659
|
+
readonly name: "apUSDRedeemFee";
|
|
1660
|
+
readonly type: "uint16";
|
|
1661
|
+
readonly internalType: "uint16";
|
|
1662
|
+
}, {
|
|
1663
|
+
readonly name: "xBNBMintFee";
|
|
1664
|
+
readonly type: "uint16";
|
|
1665
|
+
readonly internalType: "uint16";
|
|
1666
|
+
}, {
|
|
1667
|
+
readonly name: "xBNBRedeemFee";
|
|
1668
|
+
readonly type: "uint16";
|
|
1669
|
+
readonly internalType: "uint16";
|
|
1670
|
+
}, {
|
|
1671
|
+
readonly name: "apUSDMintDisabled";
|
|
1672
|
+
readonly type: "bool";
|
|
1673
|
+
readonly internalType: "bool";
|
|
1674
|
+
}];
|
|
1675
|
+
}];
|
|
1676
|
+
readonly stateMutability: "view";
|
|
1562
1677
|
}, {
|
|
1563
1678
|
readonly type: "function";
|
|
1564
1679
|
readonly name: "getFeeTier";
|
package/dist/index.js
CHANGED
|
@@ -363,6 +363,16 @@ var DiamondABI = [
|
|
|
363
363
|
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
364
364
|
stateMutability: "view"
|
|
365
365
|
},
|
|
366
|
+
{
|
|
367
|
+
type: "function",
|
|
368
|
+
name: "previewRedeemMulti",
|
|
369
|
+
inputs: [{ name: "_shares", type: "uint256", internalType: "uint256" }],
|
|
370
|
+
outputs: [
|
|
371
|
+
{ name: "assets", type: "address[]", internalType: "address[]" },
|
|
372
|
+
{ name: "amounts", type: "uint256[]", internalType: "uint256[]" }
|
|
373
|
+
],
|
|
374
|
+
stateMutability: "view"
|
|
375
|
+
},
|
|
366
376
|
{
|
|
367
377
|
type: "function",
|
|
368
378
|
name: "getPendingYield",
|
|
@@ -463,6 +473,13 @@ var DiamondABI = [
|
|
|
463
473
|
outputs: [{ name: "", type: "address", internalType: "address" }],
|
|
464
474
|
stateMutability: "view"
|
|
465
475
|
},
|
|
476
|
+
{
|
|
477
|
+
type: "function",
|
|
478
|
+
name: "setSApUSD",
|
|
479
|
+
inputs: [{ name: "_sApUSD", type: "address", internalType: "address" }],
|
|
480
|
+
outputs: [],
|
|
481
|
+
stateMutability: "nonpayable"
|
|
482
|
+
},
|
|
466
483
|
{
|
|
467
484
|
type: "function",
|
|
468
485
|
name: "getStabilityPool",
|
|
@@ -484,6 +501,25 @@ var DiamondABI = [
|
|
|
484
501
|
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
485
502
|
stateMutability: "view"
|
|
486
503
|
},
|
|
504
|
+
{
|
|
505
|
+
type: "function",
|
|
506
|
+
name: "getAllFeeTiers",
|
|
507
|
+
inputs: [],
|
|
508
|
+
outputs: [{
|
|
509
|
+
name: "",
|
|
510
|
+
type: "tuple[]",
|
|
511
|
+
internalType: "struct LibAppStorage.FeeTier[]",
|
|
512
|
+
components: [
|
|
513
|
+
{ name: "minCR", type: "uint256", internalType: "uint256" },
|
|
514
|
+
{ name: "apUSDMintFee", type: "uint16", internalType: "uint16" },
|
|
515
|
+
{ name: "apUSDRedeemFee", type: "uint16", internalType: "uint16" },
|
|
516
|
+
{ name: "xBNBMintFee", type: "uint16", internalType: "uint16" },
|
|
517
|
+
{ name: "xBNBRedeemFee", type: "uint16", internalType: "uint16" },
|
|
518
|
+
{ name: "apUSDMintDisabled", type: "bool", internalType: "bool" }
|
|
519
|
+
]
|
|
520
|
+
}],
|
|
521
|
+
stateMutability: "view"
|
|
522
|
+
},
|
|
487
523
|
{
|
|
488
524
|
type: "function",
|
|
489
525
|
name: "getFeeTier",
|
|
@@ -677,6 +713,138 @@ var DiamondABI = [
|
|
|
677
713
|
}
|
|
678
714
|
];
|
|
679
715
|
|
|
716
|
+
// src/abi/sApUSD.ts
|
|
717
|
+
var SApUSDABI = [
|
|
718
|
+
// ============ View Functions ============
|
|
719
|
+
{
|
|
720
|
+
type: "function",
|
|
721
|
+
name: "totalAssets",
|
|
722
|
+
inputs: [],
|
|
723
|
+
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
724
|
+
stateMutability: "view"
|
|
725
|
+
},
|
|
726
|
+
{
|
|
727
|
+
type: "function",
|
|
728
|
+
name: "totalSupply",
|
|
729
|
+
inputs: [],
|
|
730
|
+
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
731
|
+
stateMutability: "view"
|
|
732
|
+
},
|
|
733
|
+
{
|
|
734
|
+
type: "function",
|
|
735
|
+
name: "balanceOf",
|
|
736
|
+
inputs: [{ name: "account", type: "address", internalType: "address" }],
|
|
737
|
+
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
738
|
+
stateMutability: "view"
|
|
739
|
+
},
|
|
740
|
+
{
|
|
741
|
+
type: "function",
|
|
742
|
+
name: "previewRedeemMulti",
|
|
743
|
+
inputs: [
|
|
744
|
+
{ name: "shares", type: "uint256", internalType: "uint256" }
|
|
745
|
+
],
|
|
746
|
+
outputs: [
|
|
747
|
+
{ name: "assets", type: "address[]", internalType: "address[]" },
|
|
748
|
+
{ name: "amounts", type: "uint256[]", internalType: "uint256[]" }
|
|
749
|
+
],
|
|
750
|
+
stateMutability: "view"
|
|
751
|
+
},
|
|
752
|
+
{
|
|
753
|
+
type: "function",
|
|
754
|
+
name: "hasStabilityConversion",
|
|
755
|
+
inputs: [],
|
|
756
|
+
outputs: [
|
|
757
|
+
{ name: "hasXBNB", type: "bool", internalType: "bool" },
|
|
758
|
+
{ name: "xBNBAmount", type: "uint256", internalType: "uint256" }
|
|
759
|
+
],
|
|
760
|
+
stateMutability: "view"
|
|
761
|
+
},
|
|
762
|
+
{
|
|
763
|
+
type: "function",
|
|
764
|
+
name: "totalValue",
|
|
765
|
+
inputs: [],
|
|
766
|
+
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
767
|
+
stateMutability: "view"
|
|
768
|
+
},
|
|
769
|
+
{
|
|
770
|
+
type: "function",
|
|
771
|
+
name: "underlyingBalances",
|
|
772
|
+
inputs: [{ name: "_user", type: "address", internalType: "address" }],
|
|
773
|
+
outputs: [
|
|
774
|
+
{ name: "apUSDBalance", type: "uint256", internalType: "uint256" },
|
|
775
|
+
{ name: "xBNBBalance", type: "uint256", internalType: "uint256" }
|
|
776
|
+
],
|
|
777
|
+
stateMutability: "view"
|
|
778
|
+
},
|
|
779
|
+
{
|
|
780
|
+
type: "function",
|
|
781
|
+
name: "xBNBToApUSDRate",
|
|
782
|
+
inputs: [],
|
|
783
|
+
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
784
|
+
stateMutability: "view"
|
|
785
|
+
},
|
|
786
|
+
{
|
|
787
|
+
type: "function",
|
|
788
|
+
name: "exchangeRate",
|
|
789
|
+
inputs: [],
|
|
790
|
+
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
791
|
+
stateMutability: "view"
|
|
792
|
+
},
|
|
793
|
+
{
|
|
794
|
+
type: "function",
|
|
795
|
+
name: "previewCleanXBNB",
|
|
796
|
+
inputs: [
|
|
797
|
+
{ name: "_xBNBAmount", type: "uint256", internalType: "uint256" },
|
|
798
|
+
{ name: "_router", type: "address", internalType: "address" },
|
|
799
|
+
{ name: "_path", type: "address[]", internalType: "address[]" }
|
|
800
|
+
],
|
|
801
|
+
outputs: [{ name: "expectedApUSD", type: "uint256", internalType: "uint256" }],
|
|
802
|
+
stateMutability: "view"
|
|
803
|
+
},
|
|
804
|
+
{
|
|
805
|
+
type: "function",
|
|
806
|
+
name: "KEEPER_ROLE",
|
|
807
|
+
inputs: [],
|
|
808
|
+
outputs: [{ name: "", type: "bytes32", internalType: "bytes32" }],
|
|
809
|
+
stateMutability: "view"
|
|
810
|
+
},
|
|
811
|
+
{
|
|
812
|
+
type: "function",
|
|
813
|
+
name: "hasRole",
|
|
814
|
+
inputs: [
|
|
815
|
+
{ name: "role", type: "bytes32", internalType: "bytes32" },
|
|
816
|
+
{ name: "account", type: "address", internalType: "address" }
|
|
817
|
+
],
|
|
818
|
+
outputs: [{ name: "", type: "bool", internalType: "bool" }],
|
|
819
|
+
stateMutability: "view"
|
|
820
|
+
},
|
|
821
|
+
// ============ Keeper Functions ============
|
|
822
|
+
{
|
|
823
|
+
type: "function",
|
|
824
|
+
name: "cleanXBNB",
|
|
825
|
+
inputs: [
|
|
826
|
+
{ name: "_xBNBAmount", type: "uint256", internalType: "uint256" },
|
|
827
|
+
{ name: "_minApUSDOut", type: "uint256", internalType: "uint256" },
|
|
828
|
+
{ name: "_router", type: "address", internalType: "address" },
|
|
829
|
+
{ name: "_path", type: "address[]", internalType: "address[]" },
|
|
830
|
+
{ name: "_deadline", type: "uint256", internalType: "uint256" }
|
|
831
|
+
],
|
|
832
|
+
outputs: [{ name: "apUSDReceived", type: "uint256", internalType: "uint256" }],
|
|
833
|
+
stateMutability: "nonpayable"
|
|
834
|
+
},
|
|
835
|
+
// ============ Events ============
|
|
836
|
+
{
|
|
837
|
+
type: "event",
|
|
838
|
+
name: "VaultCleaned",
|
|
839
|
+
inputs: [
|
|
840
|
+
{ name: "xBNBSold", type: "uint256", indexed: false, internalType: "uint256" },
|
|
841
|
+
{ name: "apUSDReceived", type: "uint256", indexed: false, internalType: "uint256" },
|
|
842
|
+
{ name: "keeper", type: "address", indexed: true, internalType: "address" }
|
|
843
|
+
],
|
|
844
|
+
anonymous: false
|
|
845
|
+
}
|
|
846
|
+
];
|
|
847
|
+
|
|
680
848
|
// src/client.ts
|
|
681
849
|
var pharosTestnet = {
|
|
682
850
|
id: 688689,
|
|
@@ -1070,6 +1238,19 @@ var AspanReadClient = class _AspanReadClient {
|
|
|
1070
1238
|
args: [user]
|
|
1071
1239
|
});
|
|
1072
1240
|
}
|
|
1241
|
+
/**
|
|
1242
|
+
* Get user's underlying balances (apUSD + xBNB) from sApUSD vault
|
|
1243
|
+
*/
|
|
1244
|
+
async getBalanceMulti(user) {
|
|
1245
|
+
const sApUSDAddress = await this.getSApUSD();
|
|
1246
|
+
const [apUSDBalance, xBNBBalance] = await this.publicClient.readContract({
|
|
1247
|
+
address: sApUSDAddress,
|
|
1248
|
+
abi: SApUSDABI,
|
|
1249
|
+
functionName: "underlyingBalances",
|
|
1250
|
+
args: [user]
|
|
1251
|
+
});
|
|
1252
|
+
return { apUSDBalance, xBNBBalance };
|
|
1253
|
+
}
|
|
1073
1254
|
async getUserStabilityPoolPosition(user) {
|
|
1074
1255
|
const [shares, balance] = await Promise.all([
|
|
1075
1256
|
this.getShares(user),
|
|
@@ -1120,20 +1301,27 @@ var AspanReadClient = class _AspanReadClient {
|
|
|
1120
1301
|
throw error;
|
|
1121
1302
|
}
|
|
1122
1303
|
}
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1304
|
+
/**
|
|
1305
|
+
* Preview withdraw with multi-asset support (apUSD + xBNB)
|
|
1306
|
+
* Replaces previewRedeem — works for both clean and dirty pools.
|
|
1307
|
+
* @param shares Amount of sApUSD shares to redeem
|
|
1308
|
+
* @returns Object with apUSD and xBNB amounts, plus whether vault has xBNB
|
|
1309
|
+
*/
|
|
1310
|
+
async previewRedeemMulti(shares) {
|
|
1311
|
+
const [assets, amounts] = await this.publicClient.readContract({
|
|
1312
|
+
address: this.diamondAddress,
|
|
1313
|
+
abi: DiamondABI,
|
|
1314
|
+
functionName: "previewRedeemMulti",
|
|
1315
|
+
args: [shares]
|
|
1316
|
+
});
|
|
1317
|
+
const hasXBNB = amounts.length > 1 && amounts[1] > 0n;
|
|
1318
|
+
return {
|
|
1319
|
+
apUSD: amounts[0] ?? 0n,
|
|
1320
|
+
xBNB: amounts[1] ?? 0n,
|
|
1321
|
+
hasXBNB,
|
|
1322
|
+
assets,
|
|
1323
|
+
amounts
|
|
1324
|
+
};
|
|
1137
1325
|
}
|
|
1138
1326
|
async getPendingYield() {
|
|
1139
1327
|
try {
|
|
@@ -1288,6 +1476,93 @@ var AspanReadClient = class _AspanReadClient {
|
|
|
1288
1476
|
apUSDMintDisabled: result[5]
|
|
1289
1477
|
};
|
|
1290
1478
|
}
|
|
1479
|
+
/**
|
|
1480
|
+
* Get all fee tiers
|
|
1481
|
+
* @returns Array of fee tiers sorted by minCR descending
|
|
1482
|
+
*/
|
|
1483
|
+
async getAllFeeTiers() {
|
|
1484
|
+
const result = await this.publicClient.readContract({
|
|
1485
|
+
address: this.diamondAddress,
|
|
1486
|
+
abi: DiamondABI,
|
|
1487
|
+
functionName: "getAllFeeTiers"
|
|
1488
|
+
});
|
|
1489
|
+
return result.map((tier) => ({
|
|
1490
|
+
minCR: tier.minCR,
|
|
1491
|
+
apUSDMintFee: tier.apUSDMintFee,
|
|
1492
|
+
apUSDRedeemFee: tier.apUSDRedeemFee,
|
|
1493
|
+
xBNBMintFee: tier.xBNBMintFee,
|
|
1494
|
+
xBNBRedeemFee: tier.xBNBRedeemFee,
|
|
1495
|
+
apUSDMintDisabled: tier.apUSDMintDisabled
|
|
1496
|
+
}));
|
|
1497
|
+
}
|
|
1498
|
+
/**
|
|
1499
|
+
* Get comprehensive vault (sApUSD) info for frontend display
|
|
1500
|
+
* @returns Vault state including TVL, exchange rate, xBNB status
|
|
1501
|
+
*/
|
|
1502
|
+
async getVaultInfo() {
|
|
1503
|
+
const sApUSDAddress = await this.getSApUSD();
|
|
1504
|
+
const [totalSupply, totalAssets, exchangeRate, conversion] = await Promise.all([
|
|
1505
|
+
this.publicClient.readContract({
|
|
1506
|
+
address: sApUSDAddress,
|
|
1507
|
+
abi: SApUSDABI,
|
|
1508
|
+
functionName: "totalSupply"
|
|
1509
|
+
}),
|
|
1510
|
+
this.publicClient.readContract({
|
|
1511
|
+
address: sApUSDAddress,
|
|
1512
|
+
abi: SApUSDABI,
|
|
1513
|
+
functionName: "totalAssets"
|
|
1514
|
+
}),
|
|
1515
|
+
this.publicClient.readContract({
|
|
1516
|
+
address: sApUSDAddress,
|
|
1517
|
+
abi: SApUSDABI,
|
|
1518
|
+
functionName: "exchangeRate"
|
|
1519
|
+
}),
|
|
1520
|
+
this.publicClient.readContract({
|
|
1521
|
+
address: sApUSDAddress,
|
|
1522
|
+
abi: SApUSDABI,
|
|
1523
|
+
functionName: "hasStabilityConversion"
|
|
1524
|
+
})
|
|
1525
|
+
]);
|
|
1526
|
+
return {
|
|
1527
|
+
totalSupply,
|
|
1528
|
+
totalAssets,
|
|
1529
|
+
exchangeRate,
|
|
1530
|
+
hasXBNB: conversion[0],
|
|
1531
|
+
xBNBAmount: conversion[1]
|
|
1532
|
+
};
|
|
1533
|
+
}
|
|
1534
|
+
/**
|
|
1535
|
+
* Get full protocol dashboard data in one call (for frontend overview page)
|
|
1536
|
+
* Batches all key metrics into a single multicall
|
|
1537
|
+
*/
|
|
1538
|
+
async getProtocolOverview() {
|
|
1539
|
+
const [cr, tvlBNB, tvlUSD, apUSD, xBNB, xPriceUSD, xPriceBNB, bnbPrice, fees, sm, staked] = await Promise.all([
|
|
1540
|
+
this.getCollateralRatio(),
|
|
1541
|
+
this.getTVLInBNB(),
|
|
1542
|
+
this.getTVLInUSD(),
|
|
1543
|
+
this.getApUSDSupply(),
|
|
1544
|
+
this.getXBNBSupply(),
|
|
1545
|
+
this.getXBNBPriceUSD(),
|
|
1546
|
+
this.getXBNBPriceBNB(),
|
|
1547
|
+
this.getBNBPriceUSD(),
|
|
1548
|
+
this.getCurrentFeeTier(),
|
|
1549
|
+
this.getStabilityMode(),
|
|
1550
|
+
this.getTotalStaked()
|
|
1551
|
+
]);
|
|
1552
|
+
return {
|
|
1553
|
+
collateralRatio: cr,
|
|
1554
|
+
tvlBNB,
|
|
1555
|
+
tvlUSD,
|
|
1556
|
+
apUSDSupply: apUSD,
|
|
1557
|
+
xBNBSupply: xBNB,
|
|
1558
|
+
xBNBPriceUSD: xPriceUSD,
|
|
1559
|
+
xBNBPriceBNB: xPriceBNB,
|
|
1560
|
+
bnbPriceUSD: bnbPrice,
|
|
1561
|
+
currentFees: fees,
|
|
1562
|
+
stabilityMode: sm,
|
|
1563
|
+
totalStaked: staked
|
|
1564
|
+
};
|
|
1565
|
+
}
|
|
1291
1566
|
async getCurrentFeeTier() {
|
|
1292
1567
|
try {
|
|
1293
1568
|
const result = await this.publicClient.readContract({
|