@scallop-io/sui-scallop-sdk 0.46.38 → 0.46.40
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/dist/constants/flashloan.d.ts +2 -0
- package/dist/constants/index.d.ts +1 -0
- package/dist/index.js +90 -8
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +89 -8
- package/dist/index.mjs.map +1 -1
- package/dist/models/scallopQuery.d.ts +4 -0
- package/dist/queries/coreQuery.d.ts +7 -0
- package/package.json +1 -1
- package/src/constants/flashloan.ts +18 -0
- package/src/constants/index.ts +1 -0
- package/src/models/scallopQuery.ts +11 -1
- package/src/queries/coreQuery.ts +107 -15
- package/src/queries/vescaQuery.ts +7 -9
|
@@ -401,4 +401,8 @@ export declare class ScallopQuery {
|
|
|
401
401
|
* @returns Loyalty program information
|
|
402
402
|
*/
|
|
403
403
|
getLoyaltyProgramInfos(veScaKey?: string | SuiObjectData): Promise<import("../types").LoyaltyProgramInfo | null>;
|
|
404
|
+
/**
|
|
405
|
+
* Get flashloan fee for specified assets
|
|
406
|
+
*/
|
|
407
|
+
getFlashLoanFees(assetCoinNames?: SupportAssetCoins[]): Promise<Record<"eth" | "btc" | "usdc" | "usdt" | "sui" | "apt" | "sol" | "cetus" | "afsui" | "hasui" | "vsui" | "sca", number>>;
|
|
404
408
|
}
|
|
@@ -150,3 +150,10 @@ export declare const getMarketCoinAmounts: (query: ScallopQuery, marketCoinNames
|
|
|
150
150
|
* @return Owned market coin amount.
|
|
151
151
|
*/
|
|
152
152
|
export declare const getMarketCoinAmount: (query: ScallopQuery, marketCoinName: SupportMarketCoins, ownerAddress?: string) => Promise<number>;
|
|
153
|
+
/**
|
|
154
|
+
* Get flashloan fee for specific asset
|
|
155
|
+
* @param query - The Scallop query instance.
|
|
156
|
+
* @param assetNames - Specific an array of support pool coin name.
|
|
157
|
+
* @returns Record of asset name to flashloan fee in decimal
|
|
158
|
+
*/
|
|
159
|
+
export declare const getFlashLoanFees: (query: ScallopQuery, assetNames: SupportPoolCoins[]) => Promise<Record<SupportPoolCoins, number>>;
|
package/package.json
CHANGED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { OptionalKeys, SupportPoolCoins } from 'src/types';
|
|
2
|
+
|
|
3
|
+
export const FlashLoanFeeObjectMap: OptionalKeys<
|
|
4
|
+
Record<SupportPoolCoins, string>
|
|
5
|
+
> = {
|
|
6
|
+
vsui: '0x0069cddee7a5c0b1d34beb5ef0620f978096525f1830b055f38b110f40d73fbb',
|
|
7
|
+
btc: '0x2078490aa37d8fb42b511e5c95e217cb957d141267e16980bc802d76b42719f7',
|
|
8
|
+
sui: '0x27614284a8f0a699ffd35aae8f2572c937ec76771cb21b0d7930ec4491a76ed4',
|
|
9
|
+
usdt: '0x5b61983a19b5159ca348d291e4b595f42db70ccda32852a2ed85528aa65171e4',
|
|
10
|
+
apt: '0x9d5898edcd1e4abcb044273242293a9d036f6a977bf3fe57ab71f5a87c505ee6',
|
|
11
|
+
afsui: '0xac87fde83d434554ec300c1334c9a622aa5b59e82a04334dc99e1cc1f75d4eae',
|
|
12
|
+
hasui: '0xb9f505d532de1d6c9f3a8522a2d16f2958b75c0ed939d4f80b96f584a2a8ed5e',
|
|
13
|
+
usdc: '0xd241d6a7e44ac11a6689370ed9a98eec389b98b8a6695c61fddede9fa7567b90',
|
|
14
|
+
eth: '0xd252acb058e77877810c1290564e290a8f9fcab5bc9aca2884ede8a38810cf34',
|
|
15
|
+
sca: '0xe04e46471754b6f48d81c549ecfec09de02733715a63bec02364c6ac7c4dd2dc',
|
|
16
|
+
cetus: '0xe65a73d11c31b2d323ad2b9f6b4bb0a3c0df9c1b212eef66c854941186a5ddc7',
|
|
17
|
+
sol: '0xe84bdb35b790fc7bdd1645122ac6ac0fc904531d6772c9e25904fece322c5f34',
|
|
18
|
+
};
|
package/src/constants/index.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { SuiKit } from '@scallop-io/sui-kit';
|
|
2
|
-
import { ADDRESSES_ID, SUPPORT_SPOOLS } from '../constants';
|
|
2
|
+
import { ADDRESSES_ID, SUPPORT_POOLS, SUPPORT_SPOOLS } from '../constants';
|
|
3
3
|
import {
|
|
4
4
|
queryMarket,
|
|
5
5
|
getObligations,
|
|
@@ -32,6 +32,7 @@ import {
|
|
|
32
32
|
getPythPrices,
|
|
33
33
|
getVeScaTreasuryInfo,
|
|
34
34
|
getLoyaltyProgramInformations,
|
|
35
|
+
getFlashLoanFees,
|
|
35
36
|
} from '../queries';
|
|
36
37
|
import {
|
|
37
38
|
ScallopQueryParams,
|
|
@@ -593,4 +594,13 @@ export class ScallopQuery {
|
|
|
593
594
|
public async getLoyaltyProgramInfos(veScaKey?: string | SuiObjectData) {
|
|
594
595
|
return await getLoyaltyProgramInformations(this, veScaKey);
|
|
595
596
|
}
|
|
597
|
+
|
|
598
|
+
/**
|
|
599
|
+
* Get flashloan fee for specified assets
|
|
600
|
+
*/
|
|
601
|
+
public async getFlashLoanFees(
|
|
602
|
+
assetCoinNames: SupportAssetCoins[] = [...SUPPORT_POOLS]
|
|
603
|
+
) {
|
|
604
|
+
return await getFlashLoanFees(this, assetCoinNames);
|
|
605
|
+
}
|
|
596
606
|
}
|
package/src/queries/coreQuery.ts
CHANGED
|
@@ -4,6 +4,7 @@ import {
|
|
|
4
4
|
PROTOCOL_OBJECT_ID,
|
|
5
5
|
SUPPORT_COLLATERALS,
|
|
6
6
|
BORROW_FEE_PROTOCOL_ID,
|
|
7
|
+
FlashLoanFeeObjectMap,
|
|
7
8
|
} from '../constants';
|
|
8
9
|
import {
|
|
9
10
|
parseOriginMarketPoolData,
|
|
@@ -232,7 +233,7 @@ export const getMarketPools = async (
|
|
|
232
233
|
return marketPools;
|
|
233
234
|
}
|
|
234
235
|
|
|
235
|
-
Promise.allSettled(
|
|
236
|
+
await Promise.allSettled(
|
|
236
237
|
poolCoinNames.map(async (poolCoinName) => {
|
|
237
238
|
const marketPool = await getMarketPool(
|
|
238
239
|
query,
|
|
@@ -268,19 +269,6 @@ export const getMarketPool = async (
|
|
|
268
269
|
marketObject?: SuiObjectData | null,
|
|
269
270
|
coinPrice?: number
|
|
270
271
|
) => {
|
|
271
|
-
const marketId = query.address.get('core.market');
|
|
272
|
-
marketObject =
|
|
273
|
-
marketObject ||
|
|
274
|
-
(
|
|
275
|
-
await query.cache.queryGetObject(marketId, {
|
|
276
|
-
showContent: true,
|
|
277
|
-
})
|
|
278
|
-
).data;
|
|
279
|
-
|
|
280
|
-
coinPrice =
|
|
281
|
-
coinPrice ||
|
|
282
|
-
(await query.utils.getCoinPrices([poolCoinName]))?.[poolCoinName];
|
|
283
|
-
|
|
284
272
|
let marketPool: MarketPool | undefined;
|
|
285
273
|
let balanceSheet: BalanceSheet | undefined;
|
|
286
274
|
let borrowIndex: BorrowIndex | undefined;
|
|
@@ -297,6 +285,19 @@ export const getMarketPool = async (
|
|
|
297
285
|
return marketPoolIndexer;
|
|
298
286
|
}
|
|
299
287
|
|
|
288
|
+
const marketId = query.address.get('core.market');
|
|
289
|
+
marketObject =
|
|
290
|
+
marketObject ||
|
|
291
|
+
(
|
|
292
|
+
await query.cache.queryGetObject(marketId, {
|
|
293
|
+
showContent: true,
|
|
294
|
+
})
|
|
295
|
+
).data;
|
|
296
|
+
|
|
297
|
+
coinPrice =
|
|
298
|
+
coinPrice ||
|
|
299
|
+
(await query.utils.getCoinPrices([poolCoinName]))?.[poolCoinName];
|
|
300
|
+
|
|
300
301
|
if (marketObject) {
|
|
301
302
|
if (marketObject.content && 'fields' in marketObject.content) {
|
|
302
303
|
const fields = marketObject.content.fields as any;
|
|
@@ -840,7 +841,7 @@ export const getMarketCoinAmounts = async (
|
|
|
840
841
|
const owner = ownerAddress || query.suiKit.currentAddress();
|
|
841
842
|
const marketCoins = {} as OptionalKeys<Record<SupportMarketCoins, number>>;
|
|
842
843
|
|
|
843
|
-
Promise.allSettled(
|
|
844
|
+
await Promise.allSettled(
|
|
844
845
|
marketCoinNames.map(async (marketCoinName) => {
|
|
845
846
|
const marketCoin = await getMarketCoinAmount(
|
|
846
847
|
query,
|
|
@@ -875,3 +876,94 @@ export const getMarketCoinAmount = async (
|
|
|
875
876
|
});
|
|
876
877
|
return BigNumber(amount).toNumber();
|
|
877
878
|
};
|
|
879
|
+
|
|
880
|
+
/**
|
|
881
|
+
* Get flashloan fee for specific asset
|
|
882
|
+
* @param query - The Scallop query instance.
|
|
883
|
+
* @param assetNames - Specific an array of support pool coin name.
|
|
884
|
+
* @returns Record of asset name to flashloan fee in decimal
|
|
885
|
+
*/
|
|
886
|
+
|
|
887
|
+
export const getFlashLoanFees = async (
|
|
888
|
+
query: ScallopQuery,
|
|
889
|
+
assetNames: SupportPoolCoins[]
|
|
890
|
+
): Promise<Record<SupportPoolCoins, number>> => {
|
|
891
|
+
const FEE_RATE = 1e4;
|
|
892
|
+
const missingAssets: SupportPoolCoins[] = [];
|
|
893
|
+
|
|
894
|
+
// create mapping from asset type to asset name
|
|
895
|
+
const assetTypeMap = assetNames.reduce(
|
|
896
|
+
(prev, curr) => {
|
|
897
|
+
const assetType = query.utils.parseCoinType(curr).slice(2);
|
|
898
|
+
prev[assetType] = curr;
|
|
899
|
+
return prev;
|
|
900
|
+
},
|
|
901
|
+
{} as Record<string, SupportPoolCoins>
|
|
902
|
+
);
|
|
903
|
+
|
|
904
|
+
// use the mapped object first
|
|
905
|
+
const objIds = assetNames
|
|
906
|
+
.map((assetName) => {
|
|
907
|
+
if (!FlashLoanFeeObjectMap[assetName]) {
|
|
908
|
+
missingAssets.push(assetName);
|
|
909
|
+
return null;
|
|
910
|
+
} else {
|
|
911
|
+
return FlashLoanFeeObjectMap[assetName];
|
|
912
|
+
}
|
|
913
|
+
})
|
|
914
|
+
.filter((t) => !!t) as string[];
|
|
915
|
+
|
|
916
|
+
const flashloanFeeObjects = await query.cache.queryGetObjects(objIds, {
|
|
917
|
+
showContent: true,
|
|
918
|
+
});
|
|
919
|
+
|
|
920
|
+
if (missingAssets.length > 0) {
|
|
921
|
+
// get market object
|
|
922
|
+
const marketObjectId = query.address.get('core.market');
|
|
923
|
+
const marketObjectRes = await query.cache.queryGetObject(marketObjectId, {
|
|
924
|
+
showContent: true,
|
|
925
|
+
});
|
|
926
|
+
if (marketObjectRes.data?.content?.dataType !== 'moveObject')
|
|
927
|
+
throw new Error('Failed to get market object');
|
|
928
|
+
|
|
929
|
+
// get vault
|
|
930
|
+
const vault = (marketObjectRes.data.content.fields as any).vault;
|
|
931
|
+
|
|
932
|
+
// get vault balance sheet object id
|
|
933
|
+
const flashloanFeesTableId = vault.fields.flash_loan_fees.fields.table
|
|
934
|
+
.fields.id.id as string;
|
|
935
|
+
|
|
936
|
+
// the balance sheet is a VecSet<0x1::type_name::TypeName
|
|
937
|
+
const balanceSheetDynamicFields = await query.cache.queryGetDynamicFields({
|
|
938
|
+
parentId: flashloanFeesTableId,
|
|
939
|
+
limit: 50,
|
|
940
|
+
});
|
|
941
|
+
|
|
942
|
+
// get the dynamic object ids
|
|
943
|
+
const dynamicFieldObjectIds = balanceSheetDynamicFields.data
|
|
944
|
+
.filter((field) => {
|
|
945
|
+
const assetType = (field.name.value as any).name as string;
|
|
946
|
+
return !!assetTypeMap[assetType];
|
|
947
|
+
})
|
|
948
|
+
.map((field) => field.objectId);
|
|
949
|
+
|
|
950
|
+
flashloanFeeObjects.push(
|
|
951
|
+
...(await query.cache.queryGetObjects(dynamicFieldObjectIds, {
|
|
952
|
+
showContent: true,
|
|
953
|
+
}))
|
|
954
|
+
);
|
|
955
|
+
}
|
|
956
|
+
|
|
957
|
+
return flashloanFeeObjects.reduce(
|
|
958
|
+
(prev, curr) => {
|
|
959
|
+
if (curr.content?.dataType === 'moveObject') {
|
|
960
|
+
const objectFields = curr.content.fields as any;
|
|
961
|
+
const assetType = (curr.content.fields as any).name.fields.name;
|
|
962
|
+
const feeNumerator = +objectFields.value;
|
|
963
|
+
prev[assetTypeMap[assetType]] = feeNumerator / FEE_RATE;
|
|
964
|
+
}
|
|
965
|
+
return prev;
|
|
966
|
+
},
|
|
967
|
+
{} as Record<SupportPoolCoins, number>
|
|
968
|
+
);
|
|
969
|
+
};
|
|
@@ -28,15 +28,13 @@ export const getVescaKeys = async (
|
|
|
28
28
|
let hasNextPage = false;
|
|
29
29
|
let nextCursor: string | null | undefined = null;
|
|
30
30
|
do {
|
|
31
|
-
const paginatedKeyObjectsResponse = await query.
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
cursor: nextCursor,
|
|
39
|
-
});
|
|
31
|
+
const paginatedKeyObjectsResponse = await query.cache.queryGetOwnedObjects({
|
|
32
|
+
owner,
|
|
33
|
+
filter: {
|
|
34
|
+
StructType: veScaKeyType,
|
|
35
|
+
},
|
|
36
|
+
cursor: nextCursor,
|
|
37
|
+
});
|
|
40
38
|
keyObjectsResponse.push(...paginatedKeyObjectsResponse.data);
|
|
41
39
|
if (
|
|
42
40
|
paginatedKeyObjectsResponse.hasNextPage &&
|