@scallop-io/sui-scallop-sdk 2.0.8-emerging-asset-alpha.1 → 2.0.8

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@scallop-io/sui-scallop-sdk",
3
- "version": "2.0.8-emerging-asset-alpha.1",
3
+ "version": "2.0.8",
4
4
  "description": "Typescript sdk for interacting with Scallop contract on SUI",
5
5
  "keywords": [
6
6
  "sui",
@@ -1001,89 +1001,80 @@ export class ScallopClient {
1001
1001
  */
1002
1002
  public async migrateAllMarketCoin<S extends boolean>(
1003
1003
  includeStakePool: boolean = true,
1004
- sign: S = true as S
1004
+ sign: S = true as S,
1005
+ walletAddress?: string
1005
1006
  ): Promise<ScallopClientFnReturnType<S>> {
1007
+ const sender = walletAddress ?? this.walletAddress;
1006
1008
  const txBlock = this.builder.createTxBlock();
1007
- txBlock.setSender(this.walletAddress);
1009
+ txBlock.setSender(sender);
1008
1010
 
1009
1011
  const toTransfer: SuiObjectArg[] = [];
1010
- await Promise.all(
1011
- [...this.constants.whitelist.scoin].map(async (sCoinName) => {
1012
- /**
1013
- * First check marketCoin inside mini wallet
1014
- * Then check stakedMarketCoin inside spool
1015
- */
1016
- const sCoins: SuiObjectArg[] = [];
1017
- let toDestroyMarketCoin: SuiObjectArg | undefined;
1018
-
1019
- // check market coin in mini wallet
1020
- try {
1021
- const marketCoins = await this.utils.selectCoins(
1022
- Number.MAX_SAFE_INTEGER,
1023
- this.utils.parseMarketCoinType(sCoinName as string),
1024
- this.walletAddress
1025
- ); // throw error no coins found
1026
-
1027
- toDestroyMarketCoin = marketCoins[0];
1028
- if (marketCoins.length > 1) {
1029
- txBlock.mergeCoins(toDestroyMarketCoin, marketCoins.slice(1));
1030
- }
1031
- } catch (e: any) {
1032
- // Ignore
1033
- const errMsg = e.toString() as String;
1034
- if (!errMsg.includes('No valid coins found for the transaction'))
1035
- throw e;
1036
- }
1037
-
1038
- // if market coin found, mint sCoin
1039
- if (toDestroyMarketCoin) {
1012
+ for (const sCoinName of this.constants.whitelist.scoin) {
1013
+ /**
1014
+ * First check marketCoin inside mini wallet
1015
+ * Then check stakedMarketCoin inside spool
1016
+ */
1017
+ const sCoins: SuiObjectArg[] = [];
1018
+
1019
+ // check market coin in mini wallet
1020
+ try {
1021
+ const { takeCoin } = await this.builder.selectMarketCoin(
1022
+ txBlock,
1023
+ sCoinName,
1024
+ Number.MAX_SAFE_INTEGER,
1025
+ sender
1026
+ ); // throw error no coins found
1027
+
1028
+ if (takeCoin) {
1040
1029
  // mint new sCoin
1041
- const sCoin = txBlock.mintSCoin(
1042
- sCoinName as string,
1043
- toDestroyMarketCoin
1044
- );
1045
-
1046
- const sCoinType = this.utils.parseSCoinType(sCoinName as string);
1047
- if (!sCoinType) throw new Error('Invalid sCoin type');
1048
- // Merge with existing sCoin
1049
- await this.utils.mergeSimilarCoins(
1050
- txBlock,
1051
- sCoin,
1052
- sCoinType,
1053
- requireSender(txBlock)
1054
- );
1030
+ const sCoin = txBlock.mintSCoin(sCoinName as string, takeCoin);
1055
1031
  sCoins.push(sCoin);
1056
1032
  }
1057
- if (includeStakePool) {
1058
- // check for staked market coin in spool
1059
- if (this.constants.whitelist.spool.has(sCoinName as string)) {
1060
- try {
1061
- const sCoin = await txBlock.unstakeQuick(
1062
- Number.MAX_SAFE_INTEGER,
1063
- sCoinName as string
1064
- );
1065
- if (sCoin) {
1066
- sCoins.push(sCoin);
1067
- }
1068
- } catch (_e: any) {
1069
- // ignore
1033
+ } catch (e: any) {
1034
+ // Ignore
1035
+ const errMsg = e.toString() as String;
1036
+ if (!errMsg.includes('No valid coins found for the transaction'))
1037
+ throw e;
1038
+ }
1039
+
1040
+ // if market coin found, mint sCoin
1041
+ if (includeStakePool) {
1042
+ // check for staked market coin in spool
1043
+ if (this.constants.whitelist.spool.has(sCoinName as string)) {
1044
+ try {
1045
+ const sCoin = await txBlock.unstakeQuick(
1046
+ Number.MAX_SAFE_INTEGER,
1047
+ sCoinName as string
1048
+ );
1049
+ if (sCoin) {
1050
+ sCoins.push(sCoin);
1070
1051
  }
1052
+ } catch (_e: any) {
1053
+ // ignore
1071
1054
  }
1072
1055
  }
1056
+ }
1073
1057
 
1074
- if (sCoins.length > 0) {
1075
- const mergedSCoin = sCoins[0];
1076
- if (sCoins.length > 1) {
1077
- txBlock.mergeCoins(mergedSCoin, sCoins.slice(1));
1078
- }
1079
-
1080
- toTransfer.push(mergedSCoin);
1058
+ if (sCoins.length > 0) {
1059
+ const mergedSCoin = sCoins[0];
1060
+ if (sCoins.length > 1) {
1061
+ txBlock.mergeCoins(mergedSCoin, sCoins.slice(1));
1081
1062
  }
1082
- })
1083
- );
1063
+ const sCoinType = this.utils.parseSCoinType(sCoinName as string);
1064
+
1065
+ // Merge with existing sCoin in wallet
1066
+ await this.utils.mergeSimilarCoins(
1067
+ txBlock,
1068
+ mergedSCoin,
1069
+ sCoinType,
1070
+ sender
1071
+ );
1072
+ toTransfer.push(mergedSCoin);
1073
+ }
1074
+ }
1084
1075
 
1085
1076
  if (toTransfer.length > 0) {
1086
- txBlock.transferObjects(toTransfer, this.walletAddress);
1077
+ txBlock.transferObjects(toTransfer, sender);
1087
1078
  }
1088
1079
 
1089
1080
  if (sign) {
@@ -1101,15 +1092,18 @@ export class ScallopClient {
1101
1092
  */
1102
1093
  public async claimAllUnlockedSca(): Promise<SuiTransactionBlockResponse>;
1103
1094
  public async claimAllUnlockedSca<S extends boolean>(
1095
+ walletAddress?: string,
1104
1096
  sign?: S
1105
1097
  ): Promise<ScallopClientVeScaReturnType<S>>;
1106
1098
  public async claimAllUnlockedSca<S extends boolean>(
1099
+ walletAddress?: string,
1107
1100
  sign: S = true as S
1108
1101
  ): Promise<ScallopClientVeScaReturnType<S>> {
1102
+ const sender = walletAddress ?? this.walletAddress;
1109
1103
  // get all veSca keys
1110
1104
  const veScaKeys = (
1111
1105
  (await this.query.getVeScas({
1112
- walletAddress: this.walletAddress,
1106
+ walletAddress: sender,
1113
1107
  })) ?? []
1114
1108
  ).map(({ keyObject }) => keyObject);
1115
1109
  if (veScaKeys.length === 0) {
@@ -1118,7 +1112,7 @@ export class ScallopClient {
1118
1112
 
1119
1113
  const scaCoins: TransactionResult[] = [];
1120
1114
  const tx = this.builder.createTxBlock();
1121
- tx.setSender(this.walletAddress);
1115
+ tx.setSender(sender);
1122
1116
 
1123
1117
  await Promise.all(
1124
1118
  veScaKeys.map(async (key) => {
@@ -1139,12 +1133,7 @@ export class ScallopClient {
1139
1133
  if (scaCoins.length > 1) {
1140
1134
  tx.mergeCoins(scaCoins[0], scaCoins.slice(1));
1141
1135
  }
1142
- await this.utils.mergeSimilarCoins(
1143
- tx,
1144
- scaCoins[0],
1145
- 'sca',
1146
- this.walletAddress
1147
- );
1136
+ await this.utils.mergeSimilarCoins(tx, scaCoins[0], 'sca', sender);
1148
1137
 
1149
1138
  if (sign) {
1150
1139
  return (await this.suiKit.signAndSendTxn(
@@ -42,7 +42,6 @@ export class ScallopConstants {
42
42
  oracles: new Set(),
43
43
  pythEndpoints: new Set(),
44
44
  deprecated: new Set(),
45
- emerging: new Set(),
46
45
  };
47
46
 
48
47
  private _coinDecimals: Record<string, number | undefined> = {};
@@ -230,6 +230,7 @@ const queryRequiredMarketObjects = async (
230
230
  borrowFeeKey: query.constants.poolAddresses[t]?.borrowFeeKey,
231
231
  supplyLimitKey: query.constants.poolAddresses[t]?.supplyLimitKey,
232
232
  borrowLimitKey: query.constants.poolAddresses[t]?.borrowLimitKey,
233
+ isolatedAssetKey: query.constants.poolAddresses[t]?.isolatedAssetKey,
233
234
  }));
234
235
 
235
236
  // Query all objects for each key in parallel
@@ -242,6 +243,7 @@ const queryRequiredMarketObjects = async (
242
243
  borrowFeeObjects,
243
244
  supplyLimitObjects,
244
245
  borrowLimitObjects,
246
+ isolatedAssetObjects,
245
247
  ] = await Promise.all([
246
248
  queryMultipleObjects(
247
249
  query.cache,
@@ -275,14 +277,15 @@ const queryRequiredMarketObjects = async (
275
277
  query.cache,
276
278
  tasks.map((task) => task.borrowLimitKey).filter((t): t is string => !!t)
277
279
  ),
280
+ queryMultipleObjects(
281
+ query.cache,
282
+ tasks.map((task) => task.isolatedAssetKey).filter((t): t is string => !!t)
283
+ ),
278
284
  ]);
279
285
 
280
286
  // Map the results back to poolCoinNames
281
287
  const mapObjects = (
282
- tasks: {
283
- poolCoinName: string;
284
- [key: string]: string | undefined;
285
- }[],
288
+ tasks: { poolCoinName: string; [key: string]: string | undefined }[],
286
289
  fetchedObjects: SuiObjectData[],
287
290
  keyValue: string
288
291
  ) => {
@@ -335,11 +338,11 @@ const queryRequiredMarketObjects = async (
335
338
  borrowLimitObjects,
336
339
  'borrowLimitKey'
337
340
  );
338
- // const isolatedAssetMap = mapObjects(
339
- // tasks,
340
- // isolatedAssetObjects,
341
- // 'isolatedAssetKey'
342
- // );
341
+ const isolatedAssetMap = mapObjects(
342
+ tasks,
343
+ isolatedAssetObjects,
344
+ 'isolatedAssetKey'
345
+ );
343
346
  // Construct the final requiredObjects result
344
347
  const result = poolCoinNames.reduce(
345
348
  (acc, name) => {
@@ -352,8 +355,7 @@ const queryRequiredMarketObjects = async (
352
355
  borrowFeeKey: borrowFeeMap[name],
353
356
  supplyLimitKey: supplyLimitMap[name],
354
357
  borrowLimitKey: borrowLimitMap[name],
355
- isolatedAssetKey:
356
- query.constants.poolAddresses[name]?.isolatedAssetKey ?? false,
358
+ isolatedAssetKey: isolatedAssetMap[name],
357
359
  };
358
360
  return acc;
359
361
  },
@@ -368,7 +370,7 @@ const queryRequiredMarketObjects = async (
368
370
  borrowFeeKey: SuiObjectData;
369
371
  supplyLimitKey: SuiObjectData;
370
372
  borrowLimitKey: SuiObjectData;
371
- isolatedAssetKey: boolean;
373
+ isolatedAssetKey: SuiObjectData;
372
374
  }
373
375
  >
374
376
  );
@@ -482,7 +484,7 @@ const parseMarketPoolObjects = ({
482
484
  borrowFeeKey?: SuiObjectData;
483
485
  supplyLimitKey?: SuiObjectData;
484
486
  borrowLimitKey?: SuiObjectData;
485
- isolatedAssetKey: boolean;
487
+ isolatedAssetKey: SuiObjectData;
486
488
  }): OriginMarketPoolData & {
487
489
  parsedOriginMarketCollateral?: OriginMarketCollateralData;
488
490
  } => {
@@ -509,7 +511,7 @@ const parseMarketPoolObjects = ({
509
511
  _riskModel && _collateralStat
510
512
  ? {
511
513
  type: _interestModel.type.fields,
512
- isIsolated: isolatedAssetKey,
514
+ isIsolated: !!isolatedAssetKey,
513
515
  collateralFactor: _riskModel.collateral_factor.fields,
514
516
  liquidationFactor: _riskModel.liquidation_factor.fields,
515
517
  liquidationPenalty: _riskModel.liquidation_penalty.fields,
@@ -570,7 +572,7 @@ export const getMarketPool = async (
570
572
  borrowFeeKey: SuiObjectData;
571
573
  supplyLimitKey: SuiObjectData;
572
574
  borrowLimitKey: SuiObjectData;
573
- isolatedAssetKey: boolean;
575
+ isolatedAssetKey: SuiObjectData;
574
576
  }
575
577
  ): Promise<
576
578
  { marketPool: MarketPool; collateral?: MarketCollateral } | undefined
@@ -90,7 +90,7 @@ export const isIsolatedAsset = async (
90
90
  ): Promise<boolean> => {
91
91
  const assetInPoolAddresses = utils.constants.poolAddresses[coinName];
92
92
  if (assetInPoolAddresses) {
93
- return assetInPoolAddresses.isolatedAssetKey;
93
+ return !!assetInPoolAddresses.isolatedAssetKey;
94
94
  }
95
95
 
96
96
  const marketObject = utils.address.get('core.market');
@@ -1,4 +1,4 @@
1
- import { getFullnodeUrl, SuiClient, SuiParsedData } from '@mysten/sui/client';
1
+ import { getFullnodeUrl, SuiClient } from '@mysten/sui/client';
2
2
  import { AddressesInterface, OptionalKeys, PoolAddress } from 'src/types';
3
3
 
4
4
  const RPC_PROVIDERS = [
@@ -62,31 +62,6 @@ const queryFlashloanFeeObjectIds = async (
62
62
  return flashloanFeeObjectIds;
63
63
  };
64
64
 
65
- type FetchDynamicObjectReturnType<T extends boolean> = T extends true
66
- ? string | undefined
67
- : (SuiParsedData & { dataType: 'moveObject' }) | null | undefined;
68
-
69
- const fetchDynamicObject = async <S extends boolean>(
70
- parentId: string,
71
- type: string,
72
- value: any,
73
- returnObjId: S = true as S
74
- ): Promise<FetchDynamicObjectReturnType<S>> => {
75
- const res = (
76
- await tryRequest(async (client) => {
77
- return await client.getDynamicFieldObject({
78
- parentId,
79
- name: {
80
- type,
81
- value,
82
- },
83
- });
84
- })
85
- ).data;
86
- if (returnObjId) return res?.objectId as FetchDynamicObjectReturnType<S>;
87
- else return res?.content as FetchDynamicObjectReturnType<S>;
88
- };
89
-
90
65
  export const getPoolAddresses = async (
91
66
  addressId: string,
92
67
  poolNames: string[] = []
@@ -158,6 +133,23 @@ export const getPoolAddresses = async (
158
133
  const SUPPLY_LIMIT_TYPE = `0x6e641f0dca8aedab3101d047e96439178f16301bf0b57fe8745086ff1195eb3e::market_dynamic_keys::SupplyLimitKey`;
159
134
  const BORROW_LIMIT_TYPE = `0xe7dbb371a9595631f7964b7ece42255ad0e738cc85fe6da26c7221b220f01af6::market_dynamic_keys::BorrowLimitKey`; // prod
160
135
  const ISOLATED_ASSET_KEY = `0xe7dbb371a9595631f7964b7ece42255ad0e738cc85fe6da26c7221b220f01af6::market_dynamic_keys::IsolatedAssetKey`;
136
+ const fetchDynamicObject = async (
137
+ parentId: string,
138
+ type: string,
139
+ value: any
140
+ ) => {
141
+ return (
142
+ await tryRequest(async (client) => {
143
+ return await client.getDynamicFieldObject({
144
+ parentId,
145
+ name: {
146
+ type,
147
+ value,
148
+ },
149
+ });
150
+ })
151
+ ).data?.objectId;
152
+ };
161
153
 
162
154
  // query flashloan fee objects first
163
155
  const flashloanFeeObjectIds = await tryRequest(async (client) => {
@@ -171,50 +163,25 @@ export const getPoolAddresses = async (
171
163
  coinTypesPairs.map(async ([coinName, coinType]) => {
172
164
  const coinTypeKey = coinType.slice(2);
173
165
  const addresses = await Promise.all([
174
- fetchDynamicObject(
175
- balanceSheetParentId,
176
- ADDRESS_TYPE,
177
- {
178
- name: coinTypeKey,
179
- },
180
- true
181
- ),
182
- fetchDynamicObject(
183
- collateralStatsParentId,
184
- ADDRESS_TYPE,
185
- {
186
- name: coinTypeKey,
187
- },
188
- true
189
- ),
190
- fetchDynamicObject(
191
- borrowDynamicsParentid,
192
- ADDRESS_TYPE,
193
- {
194
- name: coinTypeKey,
195
- },
196
- true
197
- ),
198
- fetchDynamicObject(
199
- interestModelParentId,
200
- ADDRESS_TYPE,
201
- {
202
- name: coinTypeKey,
203
- },
204
- true
205
- ),
206
- fetchDynamicObject(
207
- riskModelParentId,
208
- ADDRESS_TYPE,
209
- {
210
- name: coinTypeKey,
211
- },
212
- true
213
- ),
214
- fetchDynamicObject(marketId, BORROW_FEE_TYPE, coinTypeKey, true),
215
- fetchDynamicObject(marketId, SUPPLY_LIMIT_TYPE, coinTypeKey, true),
216
- fetchDynamicObject(marketId, BORROW_LIMIT_TYPE, coinTypeKey, true),
217
- fetchDynamicObject(marketId, ISOLATED_ASSET_KEY, coinTypeKey, false),
166
+ fetchDynamicObject(balanceSheetParentId, ADDRESS_TYPE, {
167
+ name: coinTypeKey,
168
+ }),
169
+ fetchDynamicObject(collateralStatsParentId, ADDRESS_TYPE, {
170
+ name: coinTypeKey,
171
+ }),
172
+ fetchDynamicObject(borrowDynamicsParentid, ADDRESS_TYPE, {
173
+ name: coinTypeKey,
174
+ }),
175
+ fetchDynamicObject(interestModelParentId, ADDRESS_TYPE, {
176
+ name: coinTypeKey,
177
+ }),
178
+ fetchDynamicObject(riskModelParentId, ADDRESS_TYPE, {
179
+ name: coinTypeKey,
180
+ }),
181
+ fetchDynamicObject(marketId, BORROW_FEE_TYPE, coinTypeKey),
182
+ fetchDynamicObject(marketId, SUPPLY_LIMIT_TYPE, coinTypeKey),
183
+ fetchDynamicObject(marketId, BORROW_LIMIT_TYPE, coinTypeKey),
184
+ fetchDynamicObject(marketId, ISOLATED_ASSET_KEY, coinTypeKey),
218
185
  ]);
219
186
 
220
187
  // @ts-ignore
@@ -296,7 +263,7 @@ export const getPoolAddresses = async (
296
263
  borrowFeeKey: addresses[5] ?? '',
297
264
  supplyLimitKey: addresses[6] ?? '',
298
265
  borrowLimitKey: addresses[7] ?? '',
299
- isolatedAssetKey: (addresses[8]?.fields as any)?.value ?? false,
266
+ isolatedAssetKey: addresses[8] ?? '',
300
267
  ...spoolData,
301
268
  ...sCoinData,
302
269
  sCoinName,
@@ -22,7 +22,7 @@ export type PoolAddress = {
22
22
  sCoinSymbol?: string;
23
23
  sCoinMetadataId?: string;
24
24
  sCoinTreasury?: string;
25
- isolatedAssetKey: boolean;
25
+ isolatedAssetKey?: string;
26
26
  spool?: string;
27
27
  spoolReward?: string;
28
28
  spoolName?: string;
@@ -42,7 +42,6 @@ export type Whitelist = {
42
42
  rewardsAsPoint: Set<string>;
43
43
  pythEndpoints: Set<string>;
44
44
  deprecated: Set<string>;
45
- emerging: Set<string>;
46
45
  };
47
46
 
48
47
  export type CoinWrappedType =