@subwallet/extension-base 1.3.50-0 → 1.3.52-0

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.
Files changed (63) hide show
  1. package/cjs/constants/environment.js +3 -1
  2. package/cjs/koni/background/handlers/State.js +1 -5
  3. package/cjs/packageInfo.js +1 -1
  4. package/cjs/services/balance-service/index.js +3 -4
  5. package/cjs/services/balance-service/transfer/cardano-transfer.js +43 -11
  6. package/cjs/services/balance-service/transfer/xcm/acrossBridge/index.js +13 -92
  7. package/cjs/services/balance-service/transfer/xcm/index.js +12 -4
  8. package/cjs/services/chain-service/handler/bitcoin/BitcoinApi.js +3 -1
  9. package/cjs/services/chain-service/utils/patch.js +3 -2
  10. package/cjs/services/earning-service/handlers/native-staking/dtao.js +28 -301
  11. package/cjs/services/earning-service/handlers/native-staking/relay-chain.js +4 -4
  12. package/cjs/services/earning-service/handlers/native-staking/tao.js +174 -148
  13. package/cjs/services/earning-service/handlers/nomination-pool/index.js +11 -5
  14. package/cjs/services/earning-service/service.js +5 -2
  15. package/cjs/services/fee-service/utils/tokenPayFee.js +17 -13
  16. package/cjs/services/price-service/coingecko.js +3 -3
  17. package/cjs/services/swap-service/handler/base-handler.js +5 -2
  18. package/cjs/services/swap-service/handler/chainflip-handler.js +35 -12
  19. package/cjs/services/swap-service/handler/hydradx-handler.js +19 -13
  20. package/cjs/services/swap-service/index.js +8 -5
  21. package/cjs/services/transaction-service/utils.js +31 -22
  22. package/cjs/utils/account/common.js +1 -0
  23. package/cjs/utils/account/transform.js +1 -1
  24. package/cjs/utils/index.js +12 -0
  25. package/cjs/utils/setup-api-sdk.js +27 -0
  26. package/constants/environment.d.ts +1 -0
  27. package/constants/environment.js +1 -0
  28. package/koni/background/handlers/State.js +3 -7
  29. package/package.json +13 -7
  30. package/packageInfo.js +1 -1
  31. package/services/balance-service/index.js +3 -4
  32. package/services/balance-service/transfer/cardano-transfer.js +42 -10
  33. package/services/balance-service/transfer/xcm/acrossBridge/index.js +14 -93
  34. package/services/balance-service/transfer/xcm/index.js +12 -4
  35. package/services/chain-service/handler/bitcoin/BitcoinApi.js +3 -1
  36. package/services/chain-service/utils/patch.d.ts +1 -0
  37. package/services/chain-service/utils/patch.js +1 -1
  38. package/services/earning-service/handlers/native-staking/dtao.d.ts +4 -36
  39. package/services/earning-service/handlers/native-staking/dtao.js +24 -298
  40. package/services/earning-service/handlers/native-staking/relay-chain.d.ts +1 -2
  41. package/services/earning-service/handlers/native-staking/relay-chain.js +4 -4
  42. package/services/earning-service/handlers/native-staking/tao.d.ts +25 -5
  43. package/services/earning-service/handlers/native-staking/tao.js +169 -149
  44. package/services/earning-service/handlers/nomination-pool/index.d.ts +1 -2
  45. package/services/earning-service/handlers/nomination-pool/index.js +11 -5
  46. package/services/earning-service/service.d.ts +1 -0
  47. package/services/earning-service/service.js +4 -2
  48. package/services/fee-service/utils/tokenPayFee.js +17 -13
  49. package/services/price-service/coingecko.js +2 -3
  50. package/services/swap-service/handler/base-handler.js +6 -3
  51. package/services/swap-service/handler/chainflip-handler.js +34 -13
  52. package/services/swap-service/handler/hydradx-handler.js +19 -13
  53. package/services/swap-service/index.js +8 -5
  54. package/services/transaction-service/utils.d.ts +0 -1
  55. package/services/transaction-service/utils.js +31 -21
  56. package/types/swap/index.d.ts +1 -1
  57. package/types/yield/info/chain/info.d.ts +1 -0
  58. package/utils/account/common.js +1 -0
  59. package/utils/account/transform.js +1 -1
  60. package/utils/index.d.ts +1 -0
  61. package/utils/index.js +2 -1
  62. package/utils/setup-api-sdk.d.ts +1 -0
  63. package/utils/setup-api-sdk.js +20 -0
@@ -3,7 +3,7 @@
3
3
 
4
4
  import { COMMON_CHAIN_SLUGS } from '@subwallet/chain-list';
5
5
  import { _isAcrossBridgeXcm } from '@subwallet/extension-base/core/substrate/xcm-parser';
6
- import subwalletApiSdk from '@subwallet/subwallet-api-sdk';
6
+ import subwalletApiSdk from '@subwallet-monorepos/subwallet-services-sdk';
7
7
  // Across Bridge
8
8
  const acrossPairsMap = new Map([[COMMON_CHAIN_SLUGS.ETHEREUM, new Set(['optimism', 'base_mainnet', 'arbitrum_one'])], ['optimism', new Set([COMMON_CHAIN_SLUGS.ETHEREUM, 'base_mainnet', 'arbitrum_one'])], ['base_mainnet', new Set([COMMON_CHAIN_SLUGS.ETHEREUM, 'optimism', 'arbitrum_one'])], ['arbitrum_one', new Set([COMMON_CHAIN_SLUGS.ETHEREUM, 'optimism', 'base_mainnet'])], [COMMON_CHAIN_SLUGS.ETHEREUM_SEPOLIA, new Set(['base_sepolia', 'arbitrum_sepolia'])],
9
9
  // TESTNET START HERE
@@ -37,100 +37,21 @@ export const getAcrossQuote = async ({
37
37
  throw new Error('Sender is required');
38
38
  }
39
39
  try {
40
- var _subwalletApiSdk$xcmA;
41
- const data = await ((_subwalletApiSdk$xcmA = subwalletApiSdk.xcmApi) === null || _subwalletApiSdk$xcmA === void 0 ? void 0 : _subwalletApiSdk$xcmA.fetchXcmData(sender, originTokenInfo.slug, destinationTokenInfo.slug, recipient, sendingValue));
40
+ const data = await subwalletApiSdk.xcmApi.fetchXcmData({
41
+ address: sender,
42
+ from: originTokenInfo.slug,
43
+ to: destinationTokenInfo.slug,
44
+ recipient,
45
+ value: sendingValue
46
+ });
42
47
  if (!data) {
43
- throw new Error('Failed to fetch Across Bridge Data. Please try again later');
48
+ return Promise.reject(new Error('Failed to fetch Across Bridge Data. Please try again later'));
44
49
  }
45
50
  return data;
46
51
  } catch (error) {
47
- return Promise.reject(error);
52
+ if (error instanceof SyntaxError) {
53
+ return Promise.reject(new Error('Unable to perform this transaction at the moment. Try again later'));
54
+ }
55
+ return Promise.reject(new Error((error === null || error === void 0 ? void 0 : error.message) || 'Unable to perform this transaction at the moment. Try again later'));
48
56
  }
49
- };
50
-
51
- // export const SpokePoolMapping: Record<number, { SpokePool: { address: string; blockNumber: number } }> = {
52
- // 1: {
53
- // SpokePool: { address: '0x5c7BCd6E7De5423a257D81B442095A1a6ced35C5', blockNumber: 17117454 }
54
- // },
55
- // 10: {
56
- // SpokePool: { address: '0x6f26Bf09B1C792e3228e5467807a900A503c0281', blockNumber: 93903076 }
57
- // },
58
- // 11155111: {
59
- // SpokePool: { address: '0x5ef6C01E11889d86803e0B23e3cB3F9E9d97B662', blockNumber: 5288470 }
60
- // },
61
- // 11155420: {
62
- // SpokePool: { address: '0x4e8E101924eDE233C13e2D8622DC8aED2872d505', blockNumber: 7762656 }
63
- // },
64
- // 1135: {
65
- // SpokePool: { address: '0x9552a0a6624A23B848060AE5901659CDDa1f83f8', blockNumber: 2602337 }
66
- // },
67
- // 130: {
68
- // SpokePool: { address: '0x09aea4b2242abC8bb4BB78D537A67a245A7bEC64', blockNumber: 7915488 }
69
- // },
70
- // 137: {
71
- // SpokePool: { address: '0x9295ee1d8C5b022Be115A2AD3c30C72E34e7F096', blockNumber: 41908657 }
72
- // },
73
- // 168587773: {
74
- // SpokePool: { address: '0x5545092553Cf5Bf786e87a87192E902D50D8f022', blockNumber: 7634204 }
75
- // },
76
- // 1868: {
77
- // SpokePool: { address: '0x3baD7AD0728f9917d1Bf08af5782dCbD516cDd96', blockNumber: 1709997 }
78
- // },
79
- // 288: {
80
- // SpokePool: { address: '0xBbc6009fEfFc27ce705322832Cb2068F8C1e0A58', blockNumber: 619993 }
81
- // },
82
- // 324: {
83
- // SpokePool: { address: '0xE0B015E54d54fc84a6cB9B666099c46adE9335FF', blockNumber: 10352565 }
84
- // },
85
- // 34443: {
86
- // SpokePool: { address: '0x3baD7AD0728f9917d1Bf08af5782dCbD516cDd96', blockNumber: 8043187 }
87
- // },
88
- // 37111: {
89
- // SpokePool: { address: '0x6A0a7f39530923911832Dd60667CE5da5449967B', blockNumber: 156275 }
90
- // },
91
- // 41455: {
92
- // SpokePool: { address: '0x13fDac9F9b4777705db45291bbFF3c972c6d1d97', blockNumber: 4240318 }
93
- // },
94
- // 4202: {
95
- // SpokePool: { address: '0xeF684C38F94F48775959ECf2012D7E864ffb9dd4', blockNumber: 7267988 }
96
- // },
97
- // 42161: {
98
- // SpokePool: { address: '0xe35e9842fceaCA96570B734083f4a58e8F7C5f2A', blockNumber: 83868041 }
99
- // },
100
- // 421614: {
101
- // SpokePool: { address: '0x7E63A5f1a8F0B4d0934B2f2327DAED3F6bb2ee75', blockNumber: 12411026 }
102
- // },
103
- // 480: {
104
- // SpokePool: { address: '0x09aea4b2242abC8bb4BB78D537A67a245A7bEC64', blockNumber: 4524742 }
105
- // },
106
- // 534352: {
107
- // SpokePool: { address: '0x3baD7AD0728f9917d1Bf08af5782dCbD516cDd96', blockNumber: 7489705 }
108
- // },
109
- // 57073: {
110
- // SpokePool: { address: '0xeF684C38F94F48775959ECf2012D7E864ffb9dd4', blockNumber: 1139240 }
111
- // },
112
- // 59144: {
113
- // SpokePool: { address: '0x7E63A5f1a8F0B4d0934B2f2327DAED3F6bb2ee75', blockNumber: 2721169 }
114
- // },
115
- // 690: {
116
- // SpokePool: { address: '0x13fDac9F9b4777705db45291bbFF3c972c6d1d97', blockNumber: 5512122 }
117
- // },
118
- // 7777777: {
119
- // SpokePool: { address: '0x13fDac9F9b4777705db45291bbFF3c972c6d1d97', blockNumber: 18382867 }
120
- // },
121
- // 80002: {
122
- // SpokePool: { address: '0xd08baaE74D6d2eAb1F3320B2E1a53eeb391ce8e5', blockNumber: 7529960 }
123
- // },
124
- // 81457: {
125
- // SpokePool: { address: '0x2D509190Ed0172ba588407D4c2df918F955Cc6E1', blockNumber: 5574280 }
126
- // },
127
- // 8453: {
128
- // SpokePool: { address: '0x09aea4b2242abC8bb4BB78D537A67a245A7bEC64', blockNumber: 2164878 }
129
- // },
130
- // 84532: {
131
- // SpokePool: { address: '0x82B564983aE7274c86695917BBf8C99ECb6F0F8F', blockNumber: 6082004 }
132
- // },
133
- // 919: {
134
- // SpokePool: { address: '0xbd886FC0725Cc459b55BbFEb3E4278610331f83b', blockNumber: 13999465 }
135
- // }
136
- // };
57
+ };
@@ -12,7 +12,7 @@ import { getExtrinsicByXtokensPallet } from '@subwallet/extension-base/services/
12
12
  import { _XCM_CHAIN_GROUP } from '@subwallet/extension-base/services/chain-service/constants';
13
13
  import { _isNativeToken } from '@subwallet/extension-base/services/chain-service/utils';
14
14
  import { combineEthFee } from '@subwallet/extension-base/utils';
15
- import subwalletApiSdk from '@subwallet/subwallet-api-sdk';
15
+ import subwalletApiSdk from '@subwallet-monorepos/subwallet-services-sdk';
16
16
  import { _createPosBridgeL1toL2Extrinsic, _createPosBridgeL2toL1Extrinsic } from "./posBridge.js";
17
17
  // SnowBridge
18
18
  export const createSnowBridgeExtrinsic = async ({
@@ -175,8 +175,13 @@ export const createAcrossBridgeExtrinsic = async ({
175
175
  throw new Error('Sender is required');
176
176
  }
177
177
  try {
178
- var _subwalletApiSdk$xcmA;
179
- const data = await ((_subwalletApiSdk$xcmA = subwalletApiSdk.xcmApi) === null || _subwalletApiSdk$xcmA === void 0 ? void 0 : _subwalletApiSdk$xcmA.fetchXcmData(sender, originTokenInfo.slug, destinationTokenInfo.slug, recipient, sendingValue));
178
+ const data = await subwalletApiSdk.xcmApi.fetchXcmData({
179
+ address: sender,
180
+ from: originTokenInfo.slug,
181
+ to: destinationTokenInfo.slug,
182
+ recipient,
183
+ value: sendingValue
184
+ });
180
185
  const _feeCustom = feeCustom;
181
186
  const feeCombine = combineEthFee(feeInfo, feeOption, _feeCustom);
182
187
  if (!data) {
@@ -193,6 +198,9 @@ export const createAcrossBridgeExtrinsic = async ({
193
198
  transactionConfig.gas = gasLimit.toString();
194
199
  return transactionConfig;
195
200
  } catch (error) {
196
- return Promise.reject(error);
201
+ if (error instanceof SyntaxError) {
202
+ return Promise.reject(new Error('Unable to perform this transaction at the moment. Try again later'));
203
+ }
204
+ return Promise.reject(new Error((error === null || error === void 0 ? void 0 : error.message) || 'Unable to perform this transaction at the moment. Try again later'));
197
205
  }
198
206
  };
@@ -31,10 +31,11 @@ export class BitcoinApi {
31
31
  return this.isApiConnectedSubject.getValue();
32
32
  }
33
33
  createApiStrategy(apiUrl) {
34
+ const _apiUrl = 'https://blockstream.info/testnet/api/'; // todo: for test
34
35
  const isTestnet = apiUrl.includes('testnet');
35
36
  const isBlockstreamUrl = apiUrl.includes('blockstream');
36
37
  if (isTestnet) {
37
- return isBlockstreamUrl ? new BlockStreamTestnetRequestStrategy(apiUrl) : new MempoolTestnetRequestStrategy(apiUrl);
38
+ return isBlockstreamUrl ? new BlockStreamTestnetRequestStrategy(_apiUrl) : new MempoolTestnetRequestStrategy(_apiUrl);
38
39
  }
39
40
  return new SubWalletMainnetRequestStrategy(apiUrl);
40
41
  }
@@ -51,6 +52,7 @@ export class BitcoinApi {
51
52
  }
52
53
  }
53
54
  get isReady() {
55
+ // todo: recheck if bitcoinApi need this
54
56
  return this.isReadyHandler.promise;
55
57
  }
56
58
  async updateApiUrl(apiUrl) {
@@ -1,4 +1,5 @@
1
1
  import { _ChainAsset, _ChainInfo, _MultiChainAsset } from '@subwallet/chain-list/types';
2
+ export declare const ChainListVersion = "0.2.111";
2
3
  export interface PatchInfo {
3
4
  patchVersion: string;
4
5
  appliedVersion: string;
@@ -5,7 +5,7 @@ const PRODUCTION_BRANCHES = ['master', 'webapp', 'webapp-dev'];
5
5
  const branchName = process.env.BRANCH_NAME || 'subwallet-dev';
6
6
  const fetchDomain = PRODUCTION_BRANCHES.indexOf(branchName) > -1 ? 'https://chain-list-assets.subwallet.app' : 'https://dev.sw-chain-list-assets.pages.dev';
7
7
  const fetchFile = PRODUCTION_BRANCHES.indexOf(branchName) > -1 ? 'list.json' : 'preview.json';
8
- const ChainListVersion = '0.2.110'; // update this when build chainlist
8
+ export const ChainListVersion = '0.2.111'; // update this when build chain-list
9
9
 
10
10
  // todo: move this interface to chainlist
11
11
 
@@ -1,10 +1,7 @@
1
1
  import { _ChainInfo } from '@subwallet/chain-list/types';
2
- import { TransactionError } from '@subwallet/extension-base/background/errors/TransactionError';
3
- import { ExtrinsicType } from '@subwallet/extension-base/background/KoniTypes';
4
2
  import KoniState from '@subwallet/extension-base/koni/background/handlers/State';
5
- import BaseParaStakingPoolHandler from '@subwallet/extension-base/services/earning-service/handlers/native-staking/base-para';
6
- import { BaseYieldPositionInfo, OptimalYieldPath, RequestEarningSlippage, StakeCancelWithdrawalParams, SubmitBittensorChangeValidatorStaking, SubmitJoinNativeStaking, TransactionData, UnstakingInfo, ValidatorInfo, YieldPoolInfo, YieldPoolMethodInfo, YieldPoolType, YieldPositionInfo, YieldTokenBaseInfo } from '@subwallet/extension-base/types';
7
- import BigN from 'bignumber.js';
3
+ import { BaseYieldPositionInfo, RequestEarningSlippage, YieldPoolInfo, YieldPoolType, YieldPositionInfo } from '@subwallet/extension-base/types';
4
+ import TaoNativeStakingPoolHandler, { TaoStakingStakeOption } from './tao';
8
5
  export interface SubnetData {
9
6
  netuid: number;
10
7
  name: string;
@@ -14,12 +11,6 @@ export interface SubnetData {
14
11
  taoIn: number;
15
12
  taoInEmission: number;
16
13
  }
17
- interface TaoStakingStakeOption {
18
- owner: string;
19
- amount: string;
20
- rate?: BigN;
21
- identity?: string;
22
- }
23
14
  export interface RawDelegateState {
24
15
  data: Array<{
25
16
  hotkey_name: string;
@@ -29,46 +20,23 @@ export interface RawDelegateState {
29
20
  stake: string;
30
21
  }>;
31
22
  }
32
- declare type Nominators = [Array<[number, number]>];
33
- export interface TestnetBittensorDelegateInfo {
34
- delegateSs58: string;
35
- take: number;
36
- nominators: Nominators;
37
- returnPer1000: number;
38
- }
39
23
  export interface EarningSlippageResult {
40
24
  slippage: number;
41
25
  rate: number;
42
26
  }
43
- export declare const DEFAULT_DTAO_MINBOND = "21000000";
44
- export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHandler {
45
- handleYieldWithdraw(address: string, unstakingInfo: UnstakingInfo): Promise<TransactionData>;
46
- handleYieldCancelUnstake(params: StakeCancelWithdrawalParams): Promise<TransactionData>;
27
+ export default class SubnetTaoStakingPoolHandler extends TaoNativeStakingPoolHandler {
47
28
  readonly type = YieldPoolType.SUBNET_STAKING;
48
29
  slug: string;
49
30
  protected name: string;
50
31
  protected shortName: string;
51
32
  subnetData: SubnetData[];
52
33
  private isInit;
53
- private bittensorCache;
54
- readonly availableMethod: YieldPoolMethodInfo;
55
34
  constructor(state: KoniState, chain: string);
56
35
  canHandleSlug(slug: string): boolean;
57
36
  getEarningSlippage(params: RequestEarningSlippage): Promise<EarningSlippageResult>;
58
- get maintainBalance(): string;
59
37
  private init;
60
38
  protected getDescription(): string;
61
39
  subscribePoolInfo(callback: (data: YieldPoolInfo) => void): Promise<VoidFunction>;
62
- parseNominatorMetadata(chainInfo: _ChainInfo, address: string, delegatorState: TaoStakingStakeOption[]): Promise<Omit<YieldPositionInfo, keyof BaseYieldPositionInfo>>;
40
+ parseNominatorMetadata(chainInfo: _ChainInfo, delegatorState: TaoStakingStakeOption[], netuid?: number): Promise<Omit<YieldPositionInfo, keyof BaseYieldPositionInfo>>;
63
41
  subscribePoolPosition(useAddresses: string[], rsCallback: (rs: YieldPositionInfo) => void): Promise<VoidFunction>;
64
- checkAccountHaveStake(useAddresses: string[]): Promise<string[]>;
65
- private getDevnetPoolTargets;
66
- private getMainnetPoolTargets;
67
- getPoolTargets(netuid: number): Promise<ValidatorInfo[]>;
68
- createJoinExtrinsic(data: SubmitJoinNativeStaking, positionInfo?: YieldPositionInfo, bondDest?: string): Promise<[TransactionData, YieldTokenBaseInfo]>;
69
- validateYieldJoin(data: SubmitJoinNativeStaking, path: OptimalYieldPath): Promise<TransactionError[]>;
70
- handleYieldUnstake(amount: string, address: string, selectedTarget?: string, netuid?: number, slippage?: number): Promise<[ExtrinsicType, TransactionData]>;
71
- validateYieldLeave(amount: string, address: string, fastLeave: boolean, selectedTarget?: string, slug?: string, poolInfo?: YieldPoolInfo): Promise<TransactionError[]>;
72
- handleChangeEarningValidator(data: SubmitBittensorChangeValidatorStaking): Promise<TransactionData>;
73
42
  }
74
- export {};
@@ -1,20 +1,13 @@
1
1
  // Copyright 2019-2022 @subwallet/extension-base
2
2
  // SPDX-License-Identifier: Apache-2.0
3
3
 
4
- import { TransactionError } from '@subwallet/extension-base/background/errors/TransactionError';
5
4
  import { ExtrinsicType } from '@subwallet/extension-base/background/KoniTypes';
6
5
  import { BITTENSOR_REFRESH_STAKE_APY, BITTENSOR_REFRESH_STAKE_INFO } from '@subwallet/extension-base/constants';
7
- import { getEarningStatusByNominations } from '@subwallet/extension-base/koni/api/staking/bonding/utils';
8
- import { _getAssetDecimals, _getAssetSymbol } from '@subwallet/extension-base/services/chain-service/utils';
9
- import BaseParaStakingPoolHandler from '@subwallet/extension-base/services/earning-service/handlers/native-staking/base-para';
10
- import { BasicTxErrorType, EarningStatus, StakingTxErrorType, YieldPoolType } from '@subwallet/extension-base/types';
11
- import { formatNumber, reformatAddress } from '@subwallet/extension-base/utils';
6
+ import { EarningStatus, YieldPoolType } from '@subwallet/extension-base/types';
7
+ import { reformatAddress } from '@subwallet/extension-base/utils';
12
8
  import BigN from 'bignumber.js';
13
- import { t } from 'i18next';
14
9
  import { BN, BN_ZERO } from '@polkadot/util';
15
- import { BittensorCache } from "./tao.js";
16
- const DEFAULT_BITTENSOR_SLIPPAGE = 0.005;
17
- export const DEFAULT_DTAO_MINBOND = '21000000';
10
+ import TaoNativeStakingPoolHandler, { DEFAULT_DTAO_MINBOND } from "./tao.js";
18
11
  const getAlphaToTaoMapping = async substrateApi => {
19
12
  const allSubnets = (await substrateApi.api.call.subnetInfoRuntimeApi.getAllDynamicInfo()).toJSON();
20
13
  if (!allSubnets || allSubnets.length === 0) {
@@ -32,47 +25,18 @@ const getAlphaToTaoMapping = async substrateApi => {
32
25
  }
33
26
  return result;
34
27
  };
35
- const getAlphaToTaoRate = async (substrateApi, netuid) => {
36
- const subnetInfo = (await substrateApi.api.call.subnetInfoRuntimeApi.getDynamicInfo(netuid)).toJSON();
37
- if (!subnetInfo) {
38
- return '1';
39
- }
40
- const taoIn = subnetInfo.taoIn ? new BigN(subnetInfo.taoIn) : new BigN(0);
41
- const alphaIn = subnetInfo.alphaIn ? new BigN(subnetInfo.alphaIn) : new BigN(0);
42
- return netuid === 0 || alphaIn.lte(0) ? '1' : taoIn.dividedBy(alphaIn).toString();
43
- };
44
- export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHandler {
45
- /* Unimplemented function */
46
- handleYieldWithdraw(address, unstakingInfo) {
47
- throw new Error('Method not implemented.');
48
- }
49
- handleYieldCancelUnstake(params) {
50
- throw new Error('Method not implemented.');
51
- }
52
- /* Unimplemented function */
53
-
28
+ export default class SubnetTaoStakingPoolHandler extends TaoNativeStakingPoolHandler {
54
29
  // @ts-ignore
55
30
  type = YieldPoolType.SUBNET_STAKING;
56
31
  subnetData = [];
57
32
  isInit = false;
58
- availableMethod = {
59
- join: true,
60
- defaultUnstake: true,
61
- fastUnstake: false,
62
- cancelUnstake: false,
63
- withdraw: false,
64
- claimReward: false,
65
- changeValidator: true
66
- };
67
33
  constructor(state, chain) {
68
34
  super(state, chain);
69
- const _chainAsset = this.nativeToken;
70
- const _chainInfo = this.chainInfo;
71
- const symbol = _chainAsset.symbol;
72
- this.slug = this.slug = `${symbol}___subnet_staking___${_chainInfo.slug}`;
35
+ const symbol = this.nativeToken.symbol;
36
+ const chainSlug = this.chainInfo.slug;
37
+ this.slug = `${symbol}___subnet_staking___${chainSlug}`;
73
38
  this.name = 'Subnet Tao Staking';
74
39
  this.shortName = 'dTAO Staking';
75
- this.bittensorCache = BittensorCache.getInstance();
76
40
  }
77
41
  canHandleSlug(slug) {
78
42
  return slug.startsWith(`${this.slug}__`);
@@ -111,15 +75,9 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
111
75
  rate: 1
112
76
  };
113
77
  }
114
- get maintainBalance() {
115
- const ed = new BigN(this.nativeToken.minAmount || '0');
116
- const calculateMaintainBalance = new BigN(15).multipliedBy(ed).dividedBy(10);
117
- const maintainBalance = calculateMaintainBalance;
118
- return maintainBalance.toString();
119
- }
120
- async init() {
78
+ async init(forceRefresh = false) {
121
79
  try {
122
- if (this.isInit || !this.substrateApi) {
80
+ if (this.isInit && !forceRefresh || !this.substrateApi) {
123
81
  return;
124
82
  }
125
83
  const substrateApi = await this.substrateApi.isReady;
@@ -159,20 +117,20 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
159
117
  /* Subscribe pool info */
160
118
 
161
119
  async subscribePoolInfo(callback) {
162
- await this.init();
120
+ await this.substrateApi.isReady;
163
121
  let cancel = false;
164
122
  const updateStakingInfo = async () => {
165
- await this.substrateApi.isReady;
123
+ await this.init(true);
124
+ if (cancel) {
125
+ return;
126
+ }
166
127
  try {
167
- if (cancel) {
168
- return;
169
- }
170
- this.subnetData.forEach(subnet => {
128
+ for (const subnet of this.subnetData) {
171
129
  const netuid = subnet.netuid.toString().padStart(2, '0');
172
- const subnetSlug = `${this.slug}__subnet_${netuid.padStart(2, '0')}`;
130
+ const subnetSlug = `${this.slug}__subnet_${netuid}`;
173
131
  const subnetName = `${subnet.name || 'Unknown'} ${netuid}`;
174
132
  const bnTaoIn = new BigN(subnet.taoIn);
175
- const emission = new BigN(subnet.taoInEmission).dividedBy(new BigN(10).pow(new BigN(7)));
133
+ const emission = new BigN(subnet.taoInEmission).dividedBy(new BigN(10).pow(7));
176
134
  const data = {
177
135
  ...this.baseInfo,
178
136
  type: this.type,
@@ -185,7 +143,8 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
185
143
  subnetData: {
186
144
  netuid: subnet.netuid,
187
145
  subnetSymbol: subnet.symbol || 'dTAO'
188
- }
146
+ },
147
+ minValidate: DEFAULT_DTAO_MINBOND
189
148
  },
190
149
  statistic: {
191
150
  assetEarning: [{
@@ -206,7 +165,7 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
206
165
  }
207
166
  };
208
167
  callback(data);
209
- });
168
+ }
210
169
  } catch (error) {
211
170
  console.error('Error updating staking info:', error);
212
171
  }
@@ -224,39 +183,9 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
224
183
 
225
184
  /* Subscribe pool position */
226
185
 
227
- async parseNominatorMetadata(chainInfo, address, delegatorState) {
228
- await this.substrateApi.isReady;
229
- const nominationList = [];
230
- let allActiveStake = BN_ZERO;
231
- for (const delegate of delegatorState) {
232
- const stake = new BigN(delegate.amount);
233
- const originActiveStake = stake.multipliedBy(delegate.rate || new BigN(1)).toFixed(0).toString();
234
- const bnActiveStake = new BN(originActiveStake);
235
- if (bnActiveStake.gt(BN_ZERO)) {
236
- const delegationStatus = EarningStatus.EARNING_REWARD;
237
- allActiveStake = allActiveStake.add(bnActiveStake);
238
- nominationList.push({
239
- status: delegationStatus,
240
- chain: chainInfo.slug,
241
- validatorAddress: delegate.owner,
242
- activeStake: delegate.amount,
243
- validatorMinStake: DEFAULT_DTAO_MINBOND,
244
- originActiveStake: originActiveStake,
245
- validatorIdentity: delegate.identity
246
- });
247
- }
248
- }
249
- const stakingStatus = getEarningStatusByNominations(allActiveStake, nominationList);
250
- return {
251
- status: stakingStatus,
252
- balanceToken: this.nativeToken.slug,
253
- totalStake: allActiveStake.toString(),
254
- activeStake: allActiveStake.toString(),
255
- unstakeBalance: '0',
256
- isBondedBefore: true,
257
- nominations: nominationList,
258
- unstakings: []
259
- };
186
+ async parseNominatorMetadata(chainInfo, delegatorState, netuid) {
187
+ const bnMinBond = await this.getMinBond(netuid);
188
+ return this.parseNominatorMetadataBase(chainInfo, delegatorState, bnMinBond.toString(), true);
260
189
  }
261
190
  async subscribePoolPosition(useAddresses, rsCallback) {
262
191
  await this.init();
@@ -309,7 +238,7 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
309
238
  originalTotalStake = BN_ZERO
310
239
  } = subnetPositions[netuid] || {};
311
240
  if (delegatorState.length > 0) {
312
- this.parseNominatorMetadata(chainInfo, owner, delegatorState).then(nominatorMetadata => {
241
+ this.parseNominatorMetadata(chainInfo, delegatorState, netuid).then(nominatorMetadata => {
313
242
  rsCallback({
314
243
  ...defaultInfo,
315
244
  ...nominatorMetadata,
@@ -364,208 +293,5 @@ export default class SubnetTaoStakingPoolHandler extends BaseParaStakingPoolHand
364
293
  };
365
294
  }
366
295
 
367
- // Because not have subscan api
368
- async checkAccountHaveStake(useAddresses) {
369
- return Promise.resolve([]);
370
- }
371
-
372
296
  /* Subscribe pool position */
373
-
374
- /* Get pool targets */
375
- // eslint-disable-next-line @typescript-eslint/require-await
376
- async getDevnetPoolTargets() {
377
- const testnetDelegate = (await this.substrateApi.api.call.delegateInfoRuntimeApi.getDelegates()).toJSON();
378
- const bnMinBond = new BigN(DEFAULT_DTAO_MINBOND);
379
- const filteredDelegates = testnetDelegate.filter(delegate => {
380
- return delegate.returnPer1000 !== 0;
381
- });
382
- return filteredDelegates.map(delegate => ({
383
- address: delegate.delegateSs58,
384
- totalStake: '0',
385
- ownStake: '0',
386
- otherStake: '0',
387
- minBond: bnMinBond.toString(),
388
- nominatorCount: delegate.nominators.length,
389
- commission: delegate.take / 1000,
390
- blocked: false,
391
- isVerified: false,
392
- chain: this.chain,
393
- isCrowded: false
394
- }));
395
- }
396
- async getMainnetPoolTargets(netuid) {
397
- const _topValidator = await this.bittensorCache.get();
398
- const topValidator = _topValidator;
399
- const bnMinBond = new BigN(DEFAULT_DTAO_MINBOND);
400
- const validatorList = topValidator.data;
401
- const aprResponse = await this.bittensorCache.fetchApr(netuid);
402
- const aprMap = {};
403
- aprResponse.data.forEach(item => {
404
- aprMap[item.hotkey.ss58] = item.thirty_day_apy;
405
- });
406
- const results = await Promise.all(validatorList.map(validator => {
407
- const address = validator.hotkey.ss58;
408
- // With bittensor we use total weight, root weight and alpha staked insted of total stake, own stake and other stake
409
- const bnTotalWeightStake = new BigN(validator.global_weighted_stake);
410
- const bnRootWeightStake = new BigN(validator.weighted_root_stake);
411
- const bnAlphaStake = new BigN(validator.global_alpha_stake_as_tao);
412
- const nominatorCount = validator.global_nominators;
413
- const commission = validator.take;
414
- const roundedCommission = (parseFloat(commission) * 100).toFixed(0);
415
- const apr = aprMap[address];
416
- const expectedReturn = apr ? new BigN(apr).multipliedBy(100).toFixed(2) : '0';
417
- const name = validator.name || address;
418
- return {
419
- address: address,
420
- totalStake: bnTotalWeightStake.toString(),
421
- ownStake: bnRootWeightStake.toString(),
422
- otherStake: bnAlphaStake.toString(),
423
- minBond: bnMinBond.toString(),
424
- nominatorCount: nominatorCount,
425
- commission: roundedCommission,
426
- expectedReturn: expectedReturn,
427
- blocked: false,
428
- isVerified: false,
429
- chain: this.chain,
430
- isCrowded: false,
431
- identity: name
432
- };
433
- }));
434
- return results;
435
- }
436
- async getPoolTargets(netuid) {
437
- await this.init();
438
- if (this.chain === 'bittensor') {
439
- return this.getMainnetPoolTargets(netuid);
440
- } else {
441
- return this.getDevnetPoolTargets();
442
- }
443
- }
444
-
445
- /* Get pool targets */
446
-
447
- /* Join pool action */
448
-
449
- async createJoinExtrinsic(data, positionInfo, bondDest = 'Staked') {
450
- const {
451
- amount,
452
- selectedValidators: targetValidators,
453
- subnetData
454
- } = data;
455
- if (!subnetData) {
456
- throw new Error(BasicTxErrorType.INVALID_PARAMS);
457
- }
458
- const {
459
- netuid,
460
- slippage
461
- } = subnetData;
462
- const chainApi = await this.substrateApi.isReady;
463
- const binaryAmount = new BigN(amount);
464
- const alphaToTaoPrice = new BigN(await getAlphaToTaoRate(this.substrateApi, netuid));
465
- const limitPrice = alphaToTaoPrice.multipliedBy(10 ** _getAssetDecimals(this.nativeToken)).multipliedBy(1 + (slippage || DEFAULT_BITTENSOR_SLIPPAGE));
466
- const BNlimitPrice = new BigN(limitPrice.integerValue(BigN.ROUND_CEIL).toFixed());
467
-
468
- // Bittensor only supports changing 1 validator at a time, not multiple
469
- const selectedValidatorInfo = targetValidators[0];
470
- const hotkey = selectedValidatorInfo.address;
471
- const extrinsic = chainApi.api.tx.subtensorModule.addStakeLimit(hotkey, netuid, binaryAmount.toFixed(), BNlimitPrice.toFixed(), false);
472
- return [extrinsic, {
473
- slug: this.nativeToken.slug,
474
- amount: '0'
475
- }];
476
- }
477
-
478
- // Validate for case stake more
479
- async validateYieldJoin(data, path) {
480
- const baseErrors = await super.validateYieldJoin(data, path);
481
- if (baseErrors.length > 0) {
482
- return baseErrors;
483
- }
484
- const {
485
- amount
486
- } = data;
487
- if (new BigN(amount).lt(new BigN(DEFAULT_DTAO_MINBOND))) {
488
- return [new TransactionError(BasicTxErrorType.INVALID_PARAMS, t(`Insufficient stake. You need to stake at least ${formatNumber(DEFAULT_DTAO_MINBOND, _getAssetDecimals(this.nativeToken))} ${_getAssetSymbol(this.nativeToken)} to earn rewards`))];
489
- }
490
- return baseErrors;
491
- }
492
-
493
- /* Join pool action */
494
-
495
- /* Leave pool action */
496
-
497
- async handleYieldUnstake(amount, address, selectedTarget, netuid, slippage) {
498
- const apiPromise = await this.substrateApi.isReady;
499
- if (!selectedTarget) {
500
- return Promise.reject(new TransactionError(BasicTxErrorType.INVALID_PARAMS));
501
- }
502
- const binaryAmount = new BigN(amount);
503
- const alphaToTaoPrice = new BigN(await getAlphaToTaoRate(this.substrateApi, netuid || 0));
504
- const limitPrice = alphaToTaoPrice.multipliedBy(10 ** _getAssetDecimals(this.nativeToken)).multipliedBy(1 - (slippage || DEFAULT_BITTENSOR_SLIPPAGE));
505
- const BNlimitPrice = new BigN(limitPrice.integerValue(BigN.ROUND_CEIL).toFixed());
506
- const extrinsic = apiPromise.api.tx.subtensorModule.removeStakeLimit(selectedTarget, netuid, binaryAmount.toFixed(), BNlimitPrice.toFixed(), false);
507
- return [ExtrinsicType.STAKING_UNBOND, extrinsic];
508
- }
509
- async validateYieldLeave(amount, address, fastLeave, selectedTarget, slug, poolInfo) {
510
- var _poolInfo$metadata$su;
511
- const baseErrors = await super.validateYieldLeave(amount, address, fastLeave, selectedTarget, slug);
512
- if (baseErrors.length > 0) {
513
- return baseErrors;
514
- }
515
- if (!poolInfo) {
516
- return [new TransactionError(BasicTxErrorType.INVALID_PARAMS)];
517
- }
518
- const netuid = (_poolInfo$metadata$su = poolInfo.metadata.subnetData) === null || _poolInfo$metadata$su === void 0 ? void 0 : _poolInfo$metadata$su.netuid;
519
- const alphaToTaoPrice = new BigN(await getAlphaToTaoRate(this.substrateApi, netuid || 0));
520
- const minUnstake = new BigN(DEFAULT_DTAO_MINBOND).dividedBy(alphaToTaoPrice);
521
- const formattedMinUnstake = minUnstake.dividedBy(1000000).integerValue(BigN.ROUND_CEIL).dividedBy(1000);
522
- if (new BigN(amount).lt(formattedMinUnstake.multipliedBy(10 ** _getAssetDecimals(this.nativeToken)))) {
523
- var _poolInfo$metadata$su2;
524
- return [new TransactionError(BasicTxErrorType.INVALID_PARAMS, t(`Amount too low. You need to unstake at least ${formattedMinUnstake.toString()} ${((_poolInfo$metadata$su2 = poolInfo.metadata.subnetData) === null || _poolInfo$metadata$su2 === void 0 ? void 0 : _poolInfo$metadata$su2.subnetSymbol) || ''}`))];
525
- }
526
- return baseErrors;
527
- }
528
-
529
- /* Leave pool action */
530
-
531
- /* Change validator */
532
- async handleChangeEarningValidator(data) {
533
- const chainApi = await this.substrateApi.isReady;
534
- const {
535
- amount,
536
- maxAmount,
537
- metadata,
538
- originValidator,
539
- selectedValidators: targetValidators,
540
- subnetData
541
- } = data;
542
- if (!subnetData || !originValidator) {
543
- return Promise.reject(new TransactionError(BasicTxErrorType.INVALID_PARAMS));
544
- }
545
- const {
546
- netuid
547
- } = subnetData;
548
- const selectedValidatorInfo = targetValidators[0];
549
- const destValidator = selectedValidatorInfo.address;
550
- if (new BigN(amount).lte(0)) {
551
- return Promise.reject(new TransactionError(BasicTxErrorType.INVALID_PARAMS, t('Amount must be greater than 0')));
552
- }
553
- if (originValidator === destValidator) {
554
- return Promise.reject(new TransactionError(BasicTxErrorType.INVALID_PARAMS, 'From validator is the same with to validator'));
555
- }
556
- const alphaToTaoPrice = new BigN(await getAlphaToTaoRate(this.substrateApi, netuid || 0));
557
- const minUnstake = new BigN(DEFAULT_DTAO_MINBOND).dividedBy(alphaToTaoPrice);
558
- const formattedMinUnstake = minUnstake.dividedBy(1000000).integerValue(BigN.ROUND_CEIL).dividedBy(1000);
559
- const bnMinUnstake = formattedMinUnstake.multipliedBy(10 ** _getAssetDecimals(this.nativeToken));
560
- if (new BigN(maxAmount).lt(bnMinUnstake)) {
561
- return Promise.reject(new TransactionError(BasicTxErrorType.INVALID_PARAMS, t(`Amount too low. You need to move at least ${formattedMinUnstake.toString()} ${(metadata === null || metadata === void 0 ? void 0 : metadata.subnetSymbol) || ''}`)));
562
- }
563
-
564
- // Avoid remaining amount too low -> can't do anything with that amount
565
- if (!(maxAmount === amount) && new BigN(maxAmount).minus(new BigN(amount)).lt(bnMinUnstake)) {
566
- return Promise.reject(new TransactionError(StakingTxErrorType.REMAINING_AMOUNT_TOO_LOW, t(`Your remaining stake on the initial validator will fall below minimum active stake and cannot be unstaked if you proceed with the chosen amount. Hit "Move all" to move all ${formatNumber(maxAmount, _getAssetDecimals(this.nativeToken))} ${(metadata === null || metadata === void 0 ? void 0 : metadata.subnetSymbol) || ''} to the new validator, or "Cancel" and lower the amount, then try again`)));
567
- }
568
- const extrinsic = chainApi.api.tx.subtensorModule.moveStake(originValidator, destValidator, netuid, netuid, amount);
569
- return extrinsic;
570
- }
571
297
  }