@xchainjs/xchain-thorchain-amm 0.8.21 → 1.0.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.
- package/lib/index.d.ts +10 -1
- package/lib/index.esm.js +371 -895
- package/lib/index.js +358 -883
- package/lib/thorchain-action.d.ts +21 -0
- package/lib/thorchain-amm.d.ts +78 -71
- package/lib/types.d.ts +38 -0
- package/lib/utils.d.ts +19 -0
- package/package.json +12 -18
- package/lib/utils/evm-helper.d.ts +0 -25
- package/lib/utils/index.d.ts +0 -1
- package/lib/wallet.d.ts +0 -173
package/lib/index.esm.js
CHANGED
|
@@ -1,19 +1,19 @@
|
|
|
1
|
-
import { Client as Client$
|
|
2
|
-
import { Client as Client$
|
|
3
|
-
import { Client
|
|
4
|
-
import { Client, defaultBchParams
|
|
5
|
-
import { Client as Client$
|
|
6
|
-
import { Protocol,
|
|
7
|
-
import { Client as Client$
|
|
8
|
-
import { Client as Client$
|
|
9
|
-
import { Client as Client$
|
|
10
|
-
import { Client as Client$
|
|
11
|
-
import { Client as Client$
|
|
12
|
-
import {
|
|
13
|
-
import {
|
|
14
|
-
import { abi
|
|
1
|
+
import { AssetAVAX, Client as Client$5, defaultAvaxParams } from '@xchainjs/xchain-avax';
|
|
2
|
+
import { AssetBNB, Client as Client$8 } from '@xchainjs/xchain-binance';
|
|
3
|
+
import { Client, defaultBTCParams } from '@xchainjs/xchain-bitcoin';
|
|
4
|
+
import { Client as Client$1, defaultBchParams } from '@xchainjs/xchain-bitcoincash';
|
|
5
|
+
import { AssetBSC, Client as Client$6, defaultBscParams } from '@xchainjs/xchain-bsc';
|
|
6
|
+
import { Protocol, Network } from '@xchainjs/xchain-client';
|
|
7
|
+
import { AssetATOM, Client as Client$7 } from '@xchainjs/xchain-cosmos';
|
|
8
|
+
import { Client as Client$3, defaultDogeParams } from '@xchainjs/xchain-doge';
|
|
9
|
+
import { AssetETH, Client as Client$4, defaultEthParams } from '@xchainjs/xchain-ethereum';
|
|
10
|
+
import { Client as Client$2, defaultLtcParams } from '@xchainjs/xchain-litecoin';
|
|
11
|
+
import { THORChain, Client as Client$9, defaultClientConfig } from '@xchainjs/xchain-thorchain';
|
|
12
|
+
import { ThorchainQuery, ThorchainCache, Thornode } from '@xchainjs/xchain-thorchain-query';
|
|
13
|
+
import { Wallet } from '@xchainjs/xchain-wallet';
|
|
14
|
+
import { abi } from '@xchainjs/xchain-evm';
|
|
15
|
+
import { getContractAddressFromAsset } from '@xchainjs/xchain-util';
|
|
15
16
|
import { ethers } from 'ethers';
|
|
16
|
-
import { ThorchainQuery } from '@xchainjs/xchain-thorchain-query';
|
|
17
17
|
|
|
18
18
|
/******************************************************************************
|
|
19
19
|
Copyright (c) Microsoft Corporation.
|
|
@@ -40,803 +40,128 @@ function __awaiter(thisArg, _arguments, P, generator) {
|
|
|
40
40
|
});
|
|
41
41
|
}
|
|
42
42
|
|
|
43
|
-
const FIFTEEN_MIN_IN_SECS = 15 * 60;
|
|
44
|
-
class EvmHelper {
|
|
45
|
-
constructor(client, thorchainCache) {
|
|
46
|
-
this.evmClient = client;
|
|
47
|
-
this.client = client;
|
|
48
|
-
this.thorchainCache = thorchainCache;
|
|
49
|
-
}
|
|
50
|
-
/**
|
|
51
|
-
* Transaction to THORChain inbound address.
|
|
52
|
-
*
|
|
53
|
-
* @param {DepositParams} params The transaction options.
|
|
54
|
-
* @returns {TxHash} The transaction hash.
|
|
55
|
-
*
|
|
56
|
-
* @throws {"halted chain"} Thrown if chain is halted.
|
|
57
|
-
* @throws {"halted trading"} Thrown if trading is halted.
|
|
58
|
-
* @throws {"amount is not approved"} Thrown if the amount is not allowed to spend
|
|
59
|
-
* @throws {"router address is not defined"} Thrown if router address is not defined
|
|
60
|
-
*/
|
|
61
|
-
sendDeposit(params) {
|
|
62
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
63
|
-
const inboundAsgard = (yield this.thorchainCache.getInboundDetails())[params.asset.chain];
|
|
64
|
-
if (!(inboundAsgard === null || inboundAsgard === void 0 ? void 0 : inboundAsgard.router)) {
|
|
65
|
-
throw new Error('router address is not defined');
|
|
66
|
-
}
|
|
67
|
-
if (!(inboundAsgard === null || inboundAsgard === void 0 ? void 0 : inboundAsgard.address)) {
|
|
68
|
-
throw new Error('Vault address is not defined');
|
|
69
|
-
}
|
|
70
|
-
const address = yield this.client.getAddressAsync(params.walletIndex);
|
|
71
|
-
const gasPrice = yield this.evmClient.estimateGasPrices(Protocol.THORCHAIN);
|
|
72
|
-
if (eqAsset(params.asset, this.evmClient.config.gasAsset)) {
|
|
73
|
-
// simple transfer
|
|
74
|
-
return yield this.evmClient.transfer({
|
|
75
|
-
walletIndex: params.walletIndex || 0,
|
|
76
|
-
asset: params.asset,
|
|
77
|
-
amount: params.amount,
|
|
78
|
-
recipient: inboundAsgard.address,
|
|
79
|
-
memo: params.memo,
|
|
80
|
-
gasPrice: gasPrice.fast,
|
|
81
|
-
});
|
|
82
|
-
}
|
|
83
|
-
else {
|
|
84
|
-
//erc-20 must be depsited to the router
|
|
85
|
-
const isApprovedResult = yield this.isTCRouterApprovedToSpend(params.asset, params.amount, params.walletIndex);
|
|
86
|
-
if (!isApprovedResult) {
|
|
87
|
-
throw new Error('The amount is not allowed to spend');
|
|
88
|
-
}
|
|
89
|
-
const contractAddress = getContractAddressFromAsset(params.asset);
|
|
90
|
-
const checkSummedContractAddress = ethers.utils.getAddress(contractAddress);
|
|
91
|
-
const latestBlockTimeUnixSecs = (yield this.evmClient.getProvider().getBlock('latest')).timestamp;
|
|
92
|
-
const expiry = latestBlockTimeUnixSecs + FIFTEEN_MIN_IN_SECS;
|
|
93
|
-
const depositParams = [
|
|
94
|
-
inboundAsgard.address,
|
|
95
|
-
checkSummedContractAddress,
|
|
96
|
-
params.amount.amount().toFixed(),
|
|
97
|
-
params.memo,
|
|
98
|
-
expiry,
|
|
99
|
-
];
|
|
100
|
-
const routerContract = new ethers.Contract(inboundAsgard.router, abi.router);
|
|
101
|
-
const gasLimit = '160000';
|
|
102
|
-
const unsignedTx = yield routerContract.populateTransaction.depositWithExpiry(...depositParams, {
|
|
103
|
-
from: address,
|
|
104
|
-
value: 0,
|
|
105
|
-
gasPrice: gasPrice.fast.amount().toFixed(),
|
|
106
|
-
gasLimit: gasLimit,
|
|
107
|
-
});
|
|
108
|
-
const { hash } = yield this.evmClient.getWallet(params.walletIndex).sendTransaction(unsignedTx);
|
|
109
|
-
return hash;
|
|
110
|
-
}
|
|
111
|
-
});
|
|
112
|
-
}
|
|
113
|
-
isTCRouterApprovedToSpend(asset, amount, walletIndex = 0) {
|
|
114
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
115
|
-
const router = yield this.thorchainCache.getRouterAddressForChain(asset.chain);
|
|
116
|
-
const contractAddress = getContractAddressFromAsset(asset);
|
|
117
|
-
return yield this.evmClient.isApproved({
|
|
118
|
-
amount: amount,
|
|
119
|
-
spenderAddress: router,
|
|
120
|
-
contractAddress,
|
|
121
|
-
walletIndex: walletIndex,
|
|
122
|
-
});
|
|
123
|
-
});
|
|
124
|
-
}
|
|
125
|
-
approveTCRouterToSpend(asset, amount = MAX_APPROVAL, walletIndex = 0) {
|
|
126
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
127
|
-
const contractAddress = getContractAddressFromAsset(asset);
|
|
128
|
-
const router = yield this.thorchainCache.getRouterAddressForChain(asset.chain);
|
|
129
|
-
const decimals = yield this.thorchainCache.midgardQuery.getDecimalForAsset(asset);
|
|
130
|
-
const approveParams = {
|
|
131
|
-
contractAddress,
|
|
132
|
-
spenderAddress: router,
|
|
133
|
-
amount: baseAmount(amount.toString(), decimals),
|
|
134
|
-
walletIndex,
|
|
135
|
-
};
|
|
136
|
-
return yield this.evmClient.approve(approveParams);
|
|
137
|
-
});
|
|
138
|
-
}
|
|
139
|
-
}
|
|
140
|
-
|
|
141
43
|
/**
|
|
142
|
-
*
|
|
44
|
+
* Check if a chain is EVM and supported by the protocol
|
|
45
|
+
* @param {Chain} chain to check
|
|
46
|
+
* @returns true if chain is EVM, otherwise, false
|
|
143
47
|
*/
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
};
|
|
169
|
-
this.evmHelpers = {
|
|
170
|
-
ETH: new EvmHelper(this.clients.ETH, this.thorchainQuery.thorchainCache),
|
|
171
|
-
BSC: new EvmHelper(this.clients.BSC, this.thorchainQuery.thorchainCache),
|
|
172
|
-
AVAX: new EvmHelper(this.clients.AVAX, this.thorchainQuery.thorchainCache),
|
|
173
|
-
};
|
|
174
|
-
}
|
|
175
|
-
/**
|
|
176
|
-
* Fetch balances for all wallets
|
|
177
|
-
*
|
|
178
|
-
* @returns AllBalances[]
|
|
179
|
-
*/
|
|
180
|
-
getAllBalances() {
|
|
181
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
182
|
-
const allBalances = [];
|
|
183
|
-
for (const [chain, client] of Object.entries(this.clients)) {
|
|
184
|
-
const address = yield client.getAddressAsync(0);
|
|
185
|
-
try {
|
|
186
|
-
const balances = yield client.getBalance(address);
|
|
187
|
-
allBalances.push({ chain, address, balances });
|
|
188
|
-
}
|
|
189
|
-
catch (err) {
|
|
190
|
-
allBalances.push({ chain, address, balances: err.message });
|
|
191
|
-
}
|
|
192
|
-
}
|
|
193
|
-
return allBalances;
|
|
194
|
-
});
|
|
195
|
-
}
|
|
196
|
-
/**
|
|
197
|
-
* Executes a Swap from THORChainAMM.doSwap()
|
|
198
|
-
*
|
|
199
|
-
* @param swap object with all the required details for a swap.
|
|
200
|
-
* @returns transaction details and explorer url
|
|
201
|
-
* @see ThorchainAMM.doSwap()
|
|
202
|
-
*/
|
|
203
|
-
executeSwap(swap) {
|
|
204
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
205
|
-
yield this.validateSwap(swap);
|
|
206
|
-
if (swap.input.asset.chain === THORChain || swap.input.asset.synth) {
|
|
207
|
-
return yield this.swapRuneTo(swap);
|
|
208
|
-
}
|
|
209
|
-
else {
|
|
210
|
-
return yield this.swapNonRune(swap);
|
|
211
|
-
}
|
|
212
|
-
});
|
|
213
|
-
}
|
|
214
|
-
/** Validate swap object
|
|
215
|
-
*
|
|
216
|
-
* @param swap - swap parameters
|
|
217
|
-
*/
|
|
218
|
-
validateSwap(swap) {
|
|
219
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
220
|
-
const errors = [];
|
|
221
|
-
const isThorchainDestinationAsset = swap.destinationAsset.synth || swap.destinationAsset.chain === THORChain;
|
|
222
|
-
const chain = isThorchainDestinationAsset ? THORChain : swap.destinationAsset.chain;
|
|
223
|
-
// check address
|
|
224
|
-
if (swap.destinationAddress && !this.clients[chain].validateAddress(swap.destinationAddress)) {
|
|
225
|
-
errors.push(`destinationAddress ${swap.destinationAddress} is not a valid address`);
|
|
226
|
-
}
|
|
227
|
-
// Affiliate address should be THORName or THORAddress
|
|
228
|
-
const checkAffiliateAddress = swap.memo.split(':');
|
|
229
|
-
if (checkAffiliateAddress.length > 4) {
|
|
230
|
-
const affiliateAddress = checkAffiliateAddress[4];
|
|
231
|
-
if (affiliateAddress.length > 0) {
|
|
232
|
-
const isValidThorchainAddress = this.clients[THORChain].validateAddress(affiliateAddress);
|
|
233
|
-
const isValidThorname = this.isThorname(affiliateAddress);
|
|
234
|
-
if (!(isValidThorchainAddress || isValidThorname))
|
|
235
|
-
errors.push(`affiliateAddress ${affiliateAddress} is not a valid THOR address`);
|
|
236
|
-
}
|
|
237
|
-
}
|
|
238
|
-
// if input == synth return errors.
|
|
239
|
-
if (swap.input.asset.synth)
|
|
240
|
-
return errors;
|
|
241
|
-
if (this.isERC20Asset(swap.input.asset)) {
|
|
242
|
-
const isApprovedResult = yield this.evmHelpers[swap.input.asset.chain].isTCRouterApprovedToSpend(swap.input.asset, swap.input.baseAmount, swap.walletIndex);
|
|
243
|
-
if (!isApprovedResult) {
|
|
244
|
-
errors.push('TC router has not been approved to spend this amount');
|
|
245
|
-
}
|
|
246
|
-
}
|
|
247
|
-
return errors;
|
|
248
|
-
});
|
|
249
|
-
}
|
|
250
|
-
isThorname(name) {
|
|
251
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
252
|
-
const thornameDetails = yield this.thorchainQuery.thorchainCache.midgardQuery.midgardCache.midgard.getTHORNameDetails(name); // Update when thorchainCache expose getTHORNameDetails method
|
|
253
|
-
return thornameDetails !== undefined;
|
|
254
|
-
});
|
|
255
|
-
}
|
|
256
|
-
/** Function handles all swaps from Rune to asset
|
|
257
|
-
*
|
|
258
|
-
* @param swap - swap parameters
|
|
259
|
-
* @returns - tx submitted object
|
|
260
|
-
*/
|
|
261
|
-
swapRuneTo(swap) {
|
|
262
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
263
|
-
const thorClient = this.clients.THOR;
|
|
264
|
-
const hash = yield thorClient.deposit({
|
|
265
|
-
amount: swap.input.baseAmount,
|
|
266
|
-
asset: swap.input.asset,
|
|
267
|
-
memo: swap.memo,
|
|
268
|
-
});
|
|
269
|
-
return { hash, url: this.clients.THOR.getExplorerTxUrl(hash) };
|
|
270
|
-
});
|
|
271
|
-
}
|
|
272
|
-
/** Function handles all swaps from Non Rune
|
|
273
|
-
*
|
|
274
|
-
* @param swap - swap object
|
|
275
|
-
* @returns - TxSubmitted object
|
|
276
|
-
*/
|
|
277
|
-
swapNonRune(swap) {
|
|
278
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
279
|
-
const client = this.clients[swap.input.asset.chain];
|
|
280
|
-
const inbound = (yield this.thorchainQuery.thorchainCache.getInboundDetails())[swap.input.asset.chain];
|
|
281
|
-
if (!(inbound === null || inbound === void 0 ? void 0 : inbound.address))
|
|
282
|
-
throw Error(`no asgard address found for ${swap.input.asset.chain}`);
|
|
283
|
-
if (this.isEVMChain(swap.input.asset)) {
|
|
284
|
-
const params = {
|
|
285
|
-
walletIndex: 0,
|
|
286
|
-
asset: swap.input.asset,
|
|
287
|
-
amount: swap.input.baseAmount,
|
|
288
|
-
feeOption: swap.feeOption || FeeOption.Fast,
|
|
289
|
-
memo: swap.memo,
|
|
290
|
-
};
|
|
291
|
-
const hash = yield this.evmHelpers[swap.input.asset.chain].sendDeposit(params);
|
|
292
|
-
return { hash, url: client.getExplorerTxUrl(hash) };
|
|
293
|
-
}
|
|
294
|
-
else {
|
|
295
|
-
const params = {
|
|
296
|
-
walletIndex: 0,
|
|
297
|
-
asset: swap.input.asset,
|
|
298
|
-
amount: swap.input.baseAmount,
|
|
299
|
-
recipient: inbound.address,
|
|
300
|
-
memo: swap.memo,
|
|
301
|
-
};
|
|
302
|
-
const hash = yield client.transfer(params);
|
|
303
|
-
return { hash, url: client.getExplorerTxUrl(hash) };
|
|
304
|
-
}
|
|
305
|
-
});
|
|
306
|
-
}
|
|
307
|
-
/** Function handles liquidity Add
|
|
308
|
-
* BASED OFF https://dev.thorchain.or›g/thorchain-dev/network/memos
|
|
309
|
-
* @param params input parameters needed to add liquidity
|
|
310
|
-
* @returns transaction details submitted
|
|
311
|
-
*/
|
|
312
|
-
addLiquidity(params) {
|
|
313
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
314
|
-
const assetClient = this.clients[params.asset.asset.chain];
|
|
315
|
-
const inboundAsgard = (yield this.thorchainQuery.thorchainCache.getInboundDetails())[params.asset.asset.chain]
|
|
316
|
-
.address;
|
|
317
|
-
const thorchainClient = this.clients[params.rune.asset.chain];
|
|
318
|
-
const addressRune = yield thorchainClient.getAddressAsync();
|
|
319
|
-
const addressAsset = yield assetClient.getAddressAsync();
|
|
320
|
-
// const waitTimeSeconds = params.waitTimeSeconds
|
|
321
|
-
let constructedMemo = '';
|
|
322
|
-
const txSubmitted = [];
|
|
323
|
-
// symmetrical add
|
|
324
|
-
if (params.asset.assetAmount.gt(0) && params.rune.assetAmount.gt(0)) {
|
|
325
|
-
constructedMemo = `+:${params.assetPool}:${addressRune}`;
|
|
326
|
-
txSubmitted.push(yield this.addAssetLP(params, constructedMemo, assetClient, inboundAsgard));
|
|
327
|
-
constructedMemo = `+:${params.assetPool}:${addressAsset}`;
|
|
328
|
-
txSubmitted.push(yield this.addRuneLP(params, constructedMemo, thorchainClient));
|
|
329
|
-
return txSubmitted;
|
|
330
|
-
}
|
|
331
|
-
else if (params.asset.assetAmount.gt(0) && params.rune.assetAmount.eq(0)) {
|
|
332
|
-
// asymmetrical asset only
|
|
333
|
-
constructedMemo = `+:${params.assetPool}`;
|
|
334
|
-
txSubmitted.push(yield this.addAssetLP(params, constructedMemo, assetClient, inboundAsgard));
|
|
335
|
-
return txSubmitted;
|
|
336
|
-
}
|
|
337
|
-
else {
|
|
338
|
-
// asymmetrical rune only
|
|
339
|
-
constructedMemo = `+:${params.assetPool}`;
|
|
340
|
-
txSubmitted.push(yield this.addRuneLP(params, constructedMemo, thorchainClient));
|
|
341
|
-
return txSubmitted;
|
|
342
|
-
}
|
|
343
|
-
});
|
|
344
|
-
}
|
|
345
|
-
/** Function handles liquidity Withdraw
|
|
346
|
-
*
|
|
347
|
-
* @param params - parameters required for liquidity position
|
|
348
|
-
* @returns object with tx response, url and wait time in seconds
|
|
349
|
-
*/
|
|
350
|
-
withdrawLiquidity(params) {
|
|
351
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
352
|
-
const assetClient = this.clients[params.assetFee.asset.chain];
|
|
353
|
-
const inboundAsgard = (yield this.thorchainQuery.thorchainCache.getInboundDetails())[params.assetFee.asset.chain]
|
|
354
|
-
.address;
|
|
355
|
-
// const waitTimeSeconds = params.waitTimeSeconds
|
|
356
|
-
const thorchainClient = this.clients[params.runeFee.asset.chain];
|
|
357
|
-
const basisPoints = (params.percentage * 100).toFixed(); // convert to basis points
|
|
358
|
-
let constructedMemo = '';
|
|
359
|
-
const txSubmitted = [];
|
|
360
|
-
if (params.assetAddress && params.runeAddress) {
|
|
361
|
-
constructedMemo = `-:${params.assetPool}:${basisPoints}`;
|
|
362
|
-
txSubmitted.push(yield this.withdrawAssetLP(params, constructedMemo, assetClient, inboundAsgard));
|
|
363
|
-
constructedMemo = `-:${params.assetPool}:${basisPoints}`;
|
|
364
|
-
txSubmitted.push(yield this.withdrawRuneLP(params, constructedMemo, thorchainClient));
|
|
365
|
-
return txSubmitted;
|
|
366
|
-
}
|
|
367
|
-
else if (params.assetAddress && !params.runeAddress) {
|
|
368
|
-
// asymmetrical asset only
|
|
369
|
-
constructedMemo = `-:${params.assetPool}:${basisPoints}`;
|
|
370
|
-
txSubmitted.push(yield this.withdrawAssetLP(params, constructedMemo, assetClient, inboundAsgard));
|
|
371
|
-
return txSubmitted;
|
|
372
|
-
}
|
|
373
|
-
else {
|
|
374
|
-
// asymmetrical rune only
|
|
375
|
-
constructedMemo = `-:${params.assetPool}:${basisPoints}`;
|
|
376
|
-
txSubmitted.push(yield this.withdrawRuneLP(params, constructedMemo, thorchainClient));
|
|
377
|
-
return txSubmitted;
|
|
378
|
-
}
|
|
379
|
-
});
|
|
380
|
-
}
|
|
381
|
-
/**
|
|
382
|
-
*
|
|
383
|
-
* @param assetAmount - amount to add
|
|
384
|
-
* @param memo - memo required
|
|
385
|
-
* @param waitTimeSeconds - expected wait for the transaction to be processed
|
|
386
|
-
* @returns
|
|
387
|
-
*/
|
|
388
|
-
addSavers(assetAmount, memo, toAddress) {
|
|
389
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
390
|
-
const assetClient = this.clients[assetAmount.asset.chain];
|
|
391
|
-
if (this.isEVMChain(assetAmount.asset)) {
|
|
392
|
-
const addParams = {
|
|
393
|
-
wallIndex: 0,
|
|
394
|
-
asset: assetAmount.asset,
|
|
395
|
-
amount: assetAmount.baseAmount,
|
|
396
|
-
feeOption: FeeOption.Fast,
|
|
397
|
-
memo: memo,
|
|
398
|
-
};
|
|
399
|
-
const evmHelper = new EvmHelper(assetClient, this.thorchainQuery.thorchainCache);
|
|
400
|
-
const hash = yield evmHelper.sendDeposit(addParams);
|
|
401
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
402
|
-
}
|
|
403
|
-
else if (this.isUTXOChain(assetAmount.asset)) {
|
|
404
|
-
const feeRates = yield assetClient.getFeeRates(Protocol.THORCHAIN);
|
|
405
|
-
const addParams = {
|
|
406
|
-
wallIndex: 0,
|
|
407
|
-
asset: assetAmount.asset,
|
|
408
|
-
amount: assetAmount.baseAmount,
|
|
409
|
-
recipient: toAddress,
|
|
410
|
-
memo: memo,
|
|
411
|
-
feeRate: feeRates.fast,
|
|
412
|
-
};
|
|
413
|
-
try {
|
|
414
|
-
const hash = yield assetClient.transfer(addParams);
|
|
415
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
416
|
-
}
|
|
417
|
-
catch (err) {
|
|
418
|
-
const hash = JSON.stringify(err);
|
|
419
|
-
return { hash, url: assetClient.getExplorerAddressUrl(assetClient.getAddress()) };
|
|
420
|
-
}
|
|
421
|
-
}
|
|
422
|
-
else {
|
|
423
|
-
const addParams = {
|
|
424
|
-
wallIndex: 0,
|
|
425
|
-
asset: assetAmount.asset,
|
|
426
|
-
amount: assetAmount.baseAmount,
|
|
427
|
-
recipient: toAddress,
|
|
428
|
-
memo: memo,
|
|
429
|
-
};
|
|
430
|
-
try {
|
|
431
|
-
const hash = yield assetClient.transfer(addParams);
|
|
432
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
433
|
-
}
|
|
434
|
-
catch (err) {
|
|
435
|
-
const hash = JSON.stringify(err);
|
|
436
|
-
return { hash, url: assetClient.getExplorerAddressUrl(assetClient.getAddress()) };
|
|
437
|
-
}
|
|
438
|
-
}
|
|
439
|
-
});
|
|
440
|
-
}
|
|
441
|
-
/**
|
|
442
|
-
*
|
|
443
|
-
* @param assetAmount - amount to withdraw
|
|
444
|
-
* @param memo - memo required
|
|
445
|
-
* @param waitTimeSeconds - expected wait for the transaction to be processed
|
|
446
|
-
* @returns
|
|
447
|
-
*/
|
|
448
|
-
withdrawSavers(assetAmount, memo, toAddress) {
|
|
48
|
+
const isProtocolEVMChain = (chain) => {
|
|
49
|
+
return [AssetETH.chain, AssetBSC.chain, AssetAVAX.chain].includes(chain);
|
|
50
|
+
};
|
|
51
|
+
/**
|
|
52
|
+
* Check if asset is ERC20
|
|
53
|
+
* @param {Asset} asset to check
|
|
54
|
+
* @returns true if asset is ERC20, otherwise, false
|
|
55
|
+
*/
|
|
56
|
+
const isProtocolERC20Asset = (asset) => {
|
|
57
|
+
return isProtocolEVMChain(asset.chain)
|
|
58
|
+
? ![AssetETH.symbol, AssetAVAX.symbol, AssetBSC.symbol].includes(asset.symbol)
|
|
59
|
+
: false;
|
|
60
|
+
};
|
|
61
|
+
/**
|
|
62
|
+
* Check if a chain is EVM and supported by the protocol
|
|
63
|
+
* @param {Chain} chain to check
|
|
64
|
+
* @returns true if chain is EVM, otherwise, false
|
|
65
|
+
*/
|
|
66
|
+
const isProtocolBFTChain = (chain) => {
|
|
67
|
+
return [AssetBNB.chain, AssetATOM.chain].includes(chain);
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
class ThorchainAction {
|
|
71
|
+
static makeAction(actionParams) {
|
|
449
72
|
return __awaiter(this, void 0, void 0, function* () {
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
wallIndex: 0,
|
|
454
|
-
asset: assetAmount.asset,
|
|
455
|
-
amount: assetAmount.baseAmount,
|
|
456
|
-
feeOption: FeeOption.Fast,
|
|
457
|
-
memo: memo,
|
|
458
|
-
};
|
|
459
|
-
const evmHelper = new EvmHelper(assetClient, this.thorchainQuery.thorchainCache);
|
|
460
|
-
const hash = yield evmHelper.sendDeposit(addParams);
|
|
461
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
462
|
-
}
|
|
463
|
-
else if (this.isUTXOChain(assetAmount.asset)) {
|
|
464
|
-
const feeRates = yield assetClient.getFeeRates(Protocol.THORCHAIN);
|
|
465
|
-
const addParams = {
|
|
466
|
-
wallIndex: 0,
|
|
467
|
-
asset: assetAmount.asset,
|
|
468
|
-
amount: assetAmount.baseAmount,
|
|
469
|
-
recipient: toAddress,
|
|
470
|
-
memo: memo,
|
|
471
|
-
feeRate: feeRates.fast,
|
|
472
|
-
};
|
|
473
|
-
try {
|
|
474
|
-
const hash = yield assetClient.transfer(addParams);
|
|
475
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
476
|
-
}
|
|
477
|
-
catch (err) {
|
|
478
|
-
const hash = JSON.stringify(err);
|
|
479
|
-
return { hash, url: yield assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
480
|
-
}
|
|
481
|
-
}
|
|
482
|
-
else {
|
|
483
|
-
const addParams = {
|
|
484
|
-
wallIndex: 0,
|
|
485
|
-
asset: assetAmount.asset,
|
|
486
|
-
amount: assetAmount.baseAmount,
|
|
487
|
-
recipient: toAddress,
|
|
488
|
-
memo: memo,
|
|
489
|
-
};
|
|
490
|
-
try {
|
|
491
|
-
const hash = yield assetClient.transfer(addParams);
|
|
492
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
493
|
-
}
|
|
494
|
-
catch (err) {
|
|
495
|
-
const hash = JSON.stringify(err);
|
|
496
|
-
return { hash, url: yield assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
497
|
-
}
|
|
498
|
-
}
|
|
73
|
+
return this.isNonProtocolParams(actionParams)
|
|
74
|
+
? this.makeNonProtocolAction(actionParams)
|
|
75
|
+
: this.makeProtocolAction(actionParams);
|
|
499
76
|
});
|
|
500
77
|
}
|
|
501
|
-
|
|
78
|
+
static makeProtocolAction({ wallet, assetAmount, memo }) {
|
|
502
79
|
return __awaiter(this, void 0, void 0, function* () {
|
|
503
|
-
const
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
amount: params.amount.baseAmount,
|
|
509
|
-
feeOption: FeeOption.Fast,
|
|
510
|
-
memo: params.memo,
|
|
511
|
-
};
|
|
512
|
-
const evmHelper = new EvmHelper(assetClient, this.thorchainQuery.thorchainCache);
|
|
513
|
-
const hash = yield evmHelper.sendDeposit(addParams);
|
|
514
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
515
|
-
}
|
|
516
|
-
else if (this.isUTXOChain(params.amount.asset)) {
|
|
517
|
-
const feeRates = yield assetClient.getFeeRates(Protocol.THORCHAIN);
|
|
518
|
-
const addParams = {
|
|
519
|
-
wallIndex: 0,
|
|
520
|
-
asset: params.amount.asset,
|
|
521
|
-
amount: params.amount.baseAmount,
|
|
522
|
-
recipient: params.toAddress,
|
|
523
|
-
memo: params.memo,
|
|
524
|
-
feeRate: feeRates.fast,
|
|
525
|
-
};
|
|
526
|
-
try {
|
|
527
|
-
const hash = yield assetClient.transfer(addParams);
|
|
528
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
529
|
-
}
|
|
530
|
-
catch (err) {
|
|
531
|
-
const hash = JSON.stringify(err);
|
|
532
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
533
|
-
}
|
|
534
|
-
}
|
|
535
|
-
else {
|
|
536
|
-
const addParams = {
|
|
537
|
-
wallIndex: 0,
|
|
538
|
-
asset: params.amount.asset,
|
|
539
|
-
amount: params.amount.baseAmount,
|
|
540
|
-
recipient: params.toAddress,
|
|
541
|
-
memo: params.memo,
|
|
542
|
-
};
|
|
543
|
-
try {
|
|
544
|
-
const hash = yield assetClient.transfer(addParams);
|
|
545
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
546
|
-
}
|
|
547
|
-
catch (err) {
|
|
548
|
-
const hash = JSON.stringify(err);
|
|
549
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
550
|
-
}
|
|
551
|
-
}
|
|
80
|
+
const hash = yield wallet.deposit({ asset: assetAmount.asset, amount: assetAmount.baseAmount, memo });
|
|
81
|
+
return {
|
|
82
|
+
hash,
|
|
83
|
+
url: yield wallet.getExplorerTxUrl(assetAmount.asset.chain, hash),
|
|
84
|
+
};
|
|
552
85
|
});
|
|
553
86
|
}
|
|
554
|
-
|
|
555
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
556
|
-
|
|
557
|
-
if (
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
else if (this.isUTXOChain(params.amount.asset)) {
|
|
570
|
-
const feeRates = yield assetClient.getFeeRates(Protocol.THORCHAIN);
|
|
571
|
-
const addParams = {
|
|
572
|
-
wallIndex: 0,
|
|
573
|
-
asset: params.amount.asset,
|
|
574
|
-
amount: params.amount.baseAmount,
|
|
575
|
-
recipient: params.toAddress,
|
|
576
|
-
memo: params.memo,
|
|
577
|
-
feeRate: feeRates.average,
|
|
578
|
-
};
|
|
579
|
-
try {
|
|
580
|
-
const hash = yield assetClient.transfer(addParams);
|
|
581
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
582
|
-
}
|
|
583
|
-
catch (err) {
|
|
584
|
-
const hash = JSON.stringify(err);
|
|
585
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
87
|
+
static makeNonProtocolAction({ wallet, assetAmount, recipient, memo, }) {
|
|
88
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
89
|
+
// Non ERC20 swaps
|
|
90
|
+
if (!isProtocolERC20Asset(assetAmount.asset)) {
|
|
91
|
+
if (isProtocolBFTChain(assetAmount.asset.chain)) {
|
|
92
|
+
const hash = yield wallet.transfer({
|
|
93
|
+
asset: assetAmount.asset,
|
|
94
|
+
amount: assetAmount.baseAmount,
|
|
95
|
+
recipient,
|
|
96
|
+
memo,
|
|
97
|
+
});
|
|
98
|
+
return {
|
|
99
|
+
hash,
|
|
100
|
+
url: yield wallet.getExplorerTxUrl(assetAmount.asset.chain, hash),
|
|
101
|
+
};
|
|
586
102
|
}
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
103
|
+
const feeRates = yield wallet.getFeeRates(assetAmount.asset.chain, Protocol.THORCHAIN);
|
|
104
|
+
const hash = yield wallet.transfer(isProtocolEVMChain(assetAmount.asset.chain)
|
|
105
|
+
? {
|
|
106
|
+
asset: assetAmount.asset,
|
|
107
|
+
amount: assetAmount.baseAmount,
|
|
108
|
+
recipient,
|
|
109
|
+
memo,
|
|
110
|
+
gasPrice: feeRates.fast,
|
|
111
|
+
}
|
|
112
|
+
: {
|
|
113
|
+
asset: assetAmount.asset,
|
|
114
|
+
amount: assetAmount.baseAmount,
|
|
115
|
+
recipient,
|
|
116
|
+
memo,
|
|
117
|
+
feeRate: feeRates.fast,
|
|
118
|
+
});
|
|
119
|
+
return {
|
|
120
|
+
hash,
|
|
121
|
+
url: yield wallet.getExplorerTxUrl(assetAmount.asset.chain, hash),
|
|
595
122
|
};
|
|
596
|
-
try {
|
|
597
|
-
const hash = yield assetClient.transfer(addParams);
|
|
598
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
599
|
-
}
|
|
600
|
-
catch (err) {
|
|
601
|
-
const hash = JSON.stringify(err);
|
|
602
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
603
|
-
}
|
|
604
|
-
}
|
|
605
|
-
});
|
|
606
|
-
}
|
|
607
|
-
/**
|
|
608
|
-
* Register a THORName with a default expirity of one year. By default chain and chainAddress is getting from wallet instance and is BTC.
|
|
609
|
-
* By default owner is getting from wallet
|
|
610
|
-
* @param thorname - Name to register
|
|
611
|
-
* @param chain - Chain to add alias
|
|
612
|
-
* @param chainAddress - Address to add to chain alias
|
|
613
|
-
* @param owner - Owner address (rune address)
|
|
614
|
-
* @param preferredAsset - referred asset
|
|
615
|
-
* @param expirity - expirity of the domain in MILLISECONDS
|
|
616
|
-
* @param isUpdate - true only if the domain is already register and you want to update its data
|
|
617
|
-
* @returns memo and value of deposit
|
|
618
|
-
*/
|
|
619
|
-
registerThorname(params) {
|
|
620
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
621
|
-
const chainClient = this.clients[params.chain || BTCChain];
|
|
622
|
-
const thorClient = this.clients.THOR;
|
|
623
|
-
if (!chainClient || !thorClient) {
|
|
624
|
-
throw Error('Can not find a wallet client');
|
|
625
123
|
}
|
|
626
|
-
|
|
627
|
-
const
|
|
628
|
-
const
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
124
|
+
// ERC20 swaps
|
|
125
|
+
const thorchainQuery = new ThorchainQuery(new ThorchainCache(new Thornode(wallet.getNetwork())));
|
|
126
|
+
const inboundDetails = yield thorchainQuery.getChainInboundDetails(assetAmount.asset.chain);
|
|
127
|
+
if (!inboundDetails.router)
|
|
128
|
+
throw Error(`Unknown router for ${assetAmount.asset.chain} chain`);
|
|
129
|
+
const contractAddress = getContractAddressFromAsset(assetAmount.asset);
|
|
130
|
+
const checkSummedContractAddress = ethers.utils.getAddress(contractAddress);
|
|
131
|
+
const expiration = Math.floor(new Date(new Date().getTime() + 15 * 60000).getTime() / 1000);
|
|
132
|
+
const depositParams = [
|
|
133
|
+
recipient,
|
|
134
|
+
checkSummedContractAddress,
|
|
135
|
+
assetAmount.baseAmount.amount().toFixed(),
|
|
136
|
+
memo,
|
|
137
|
+
expiration,
|
|
138
|
+
];
|
|
139
|
+
const routerContract = new ethers.Contract(inboundDetails.router, abi.router);
|
|
140
|
+
const chainWallet = wallet.getChainWallet(assetAmount.asset.chain);
|
|
141
|
+
const gasPrices = yield wallet.getFeeRates(assetAmount.asset.chain);
|
|
142
|
+
const unsignedTx = yield routerContract.populateTransaction.depositWithExpiry(...depositParams, {
|
|
143
|
+
from: wallet.getAddress(assetAmount.asset.chain),
|
|
144
|
+
value: 0,
|
|
145
|
+
gasPrice: gasPrices.fast.amount().toFixed(),
|
|
146
|
+
gasLimit: '160000',
|
|
632
147
|
});
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
* Register a THORName with a default expirity of one year. By default chain and chainAddress is getting from wallet instance and is BTC.
|
|
638
|
-
* By default owner is getting from wallet
|
|
639
|
-
* @param thorname - Name to register
|
|
640
|
-
* @param chain - Chain to add alias
|
|
641
|
-
* @param chainAddress - Address to add to chain alias
|
|
642
|
-
* @param owner - Owner address (rune address)
|
|
643
|
-
* @param preferredAsset - referred asset
|
|
644
|
-
* @param expirity - expirity of the domain in MILLISECONDS
|
|
645
|
-
* @returns memo and value of deposit
|
|
646
|
-
*/
|
|
647
|
-
updateThorname(params) {
|
|
648
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
649
|
-
const chainClient = this.clients[params.chain || BTCChain];
|
|
650
|
-
const thorClient = this.clients.THOR;
|
|
651
|
-
if (!chainClient || !thorClient) {
|
|
652
|
-
throw Error('Can not find a wallet client');
|
|
653
|
-
}
|
|
654
|
-
const thornameDetail = yield this.thorchainQuery.getThornameDetails(params.thorname);
|
|
655
|
-
if ((thornameDetail === null || thornameDetail === void 0 ? void 0 : thornameDetail.owner) !== (yield thorClient.getAddressAsync())) {
|
|
656
|
-
throw Error('You cannot update a domain that is not yours');
|
|
657
|
-
}
|
|
658
|
-
const thornameEstimation = yield this.thorchainQuery.estimateThorname(Object.assign(Object.assign({}, params), { chain: params.chain || BTCChain, isUpdate: true, preferredAsset: params.preferredAsset || assetFromString(thornameDetail.preferredAsset), chainAddress: params.chainAddress || (yield chainClient.getAddressAsync()) }));
|
|
659
|
-
const castedThorClient = thorClient;
|
|
660
|
-
const result = yield castedThorClient.deposit({
|
|
661
|
-
asset: thornameEstimation.value.asset,
|
|
662
|
-
amount: thornameEstimation.value.baseAmount,
|
|
663
|
-
memo: thornameEstimation.memo,
|
|
664
|
-
});
|
|
665
|
-
return result;
|
|
666
|
-
});
|
|
667
|
-
}
|
|
668
|
-
/** Function handles liquidity add for all non rune assets
|
|
669
|
-
*
|
|
670
|
-
* @param params - parameters for add liquidity
|
|
671
|
-
* @param constructedMemo - memo needed for thorchain
|
|
672
|
-
* @param waitTimeSeconds - wait time for the tx to be confirmed
|
|
673
|
-
* @param assetClient - passing XchainClient
|
|
674
|
-
* @param inboundAsgard - inbound Asgard address for the LP
|
|
675
|
-
* @returns - tx object
|
|
676
|
-
*/
|
|
677
|
-
addAssetLP(params, constructedMemo, assetClient, inboundAsgard) {
|
|
678
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
679
|
-
if (this.isEVMChain(params.asset.asset)) {
|
|
680
|
-
const addParams = {
|
|
681
|
-
wallIndex: 0,
|
|
682
|
-
asset: params.asset.asset,
|
|
683
|
-
amount: params.asset.baseAmount,
|
|
684
|
-
feeOption: FeeOption.Fast,
|
|
685
|
-
memo: constructedMemo,
|
|
686
|
-
};
|
|
687
|
-
const evmHelper = new EvmHelper(assetClient, this.thorchainQuery.thorchainCache);
|
|
688
|
-
const hash = yield evmHelper.sendDeposit(addParams);
|
|
689
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
690
|
-
}
|
|
691
|
-
else if (this.isUTXOChain(params.asset.asset)) {
|
|
692
|
-
const feeRates = yield assetClient.getFeeRates(Protocol.THORCHAIN);
|
|
693
|
-
const addParams = {
|
|
694
|
-
wallIndex: 0,
|
|
695
|
-
asset: params.asset.asset,
|
|
696
|
-
amount: params.asset.baseAmount,
|
|
697
|
-
recipient: inboundAsgard,
|
|
698
|
-
memo: constructedMemo,
|
|
699
|
-
feeRate: feeRates.fast,
|
|
700
|
-
};
|
|
701
|
-
try {
|
|
702
|
-
const hash = yield assetClient.transfer(addParams);
|
|
703
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
704
|
-
}
|
|
705
|
-
catch (err) {
|
|
706
|
-
const hash = JSON.stringify(err);
|
|
707
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
708
|
-
}
|
|
709
|
-
}
|
|
710
|
-
else {
|
|
711
|
-
const addParams = {
|
|
712
|
-
wallIndex: 0,
|
|
713
|
-
asset: params.asset.asset,
|
|
714
|
-
amount: params.asset.baseAmount,
|
|
715
|
-
recipient: inboundAsgard,
|
|
716
|
-
memo: constructedMemo,
|
|
717
|
-
};
|
|
718
|
-
try {
|
|
719
|
-
const hash = yield assetClient.transfer(addParams);
|
|
720
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
721
|
-
}
|
|
722
|
-
catch (err) {
|
|
723
|
-
const hash = JSON.stringify(err);
|
|
724
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
725
|
-
}
|
|
726
|
-
}
|
|
727
|
-
});
|
|
728
|
-
}
|
|
729
|
-
/** Function handles liquidity Withdraw for Non rune assets
|
|
730
|
-
*
|
|
731
|
-
* @param params - parameters for withdraw liquidity
|
|
732
|
-
* @param constructedMemo - memo needed for thorchain execution
|
|
733
|
-
* @param assetClient - asset client to call transfer
|
|
734
|
-
* @param waitTimeSeconds - return back estimated wait
|
|
735
|
-
* @param inboundAsgard - destination address
|
|
736
|
-
* @returns - tx object
|
|
737
|
-
*/
|
|
738
|
-
withdrawAssetLP(params, constructedMemo, assetClient, inboundAsgard) {
|
|
739
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
740
|
-
if (this.isEVMChain(params.assetFee.asset)) {
|
|
741
|
-
const withdrawParams = {
|
|
742
|
-
wallIndex: 0,
|
|
743
|
-
asset: params.assetFee.asset,
|
|
744
|
-
amount: params.assetFee.baseAmount,
|
|
745
|
-
feeOption: FeeOption.Fast,
|
|
746
|
-
memo: constructedMemo,
|
|
747
|
-
};
|
|
748
|
-
const evmHelper = new EvmHelper(assetClient, this.thorchainQuery.thorchainCache);
|
|
749
|
-
const hash = yield evmHelper.sendDeposit(withdrawParams);
|
|
750
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
751
|
-
}
|
|
752
|
-
else if (this.isUTXOChain(params.assetFee.asset)) {
|
|
753
|
-
const feeRates = yield assetClient.getFeeRates(Protocol.THORCHAIN);
|
|
754
|
-
const withdrawParams = {
|
|
755
|
-
wallIndex: 0,
|
|
756
|
-
asset: params.assetFee.asset,
|
|
757
|
-
amount: params.assetFee.baseAmount,
|
|
758
|
-
recipient: inboundAsgard,
|
|
759
|
-
memo: constructedMemo,
|
|
760
|
-
feeRate: feeRates.fast,
|
|
761
|
-
};
|
|
762
|
-
try {
|
|
763
|
-
const hash = yield assetClient.transfer(withdrawParams);
|
|
764
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
765
|
-
}
|
|
766
|
-
catch (err) {
|
|
767
|
-
const hash = JSON.stringify(err);
|
|
768
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
769
|
-
}
|
|
770
|
-
}
|
|
771
|
-
else {
|
|
772
|
-
const withdrawParams = {
|
|
773
|
-
wallIndex: 0,
|
|
774
|
-
asset: params.assetFee.asset,
|
|
775
|
-
amount: params.assetFee.baseAmount,
|
|
776
|
-
recipient: inboundAsgard,
|
|
777
|
-
memo: constructedMemo,
|
|
778
|
-
};
|
|
779
|
-
try {
|
|
780
|
-
const hash = yield assetClient.transfer(withdrawParams);
|
|
781
|
-
return { hash, url: assetClient.getExplorerTxUrl(hash) };
|
|
782
|
-
}
|
|
783
|
-
catch (err) {
|
|
784
|
-
const hash = JSON.stringify(err);
|
|
785
|
-
return { hash, url: assetClient.getExplorerAddressUrl(yield assetClient.getAddressAsync()) };
|
|
786
|
-
}
|
|
787
|
-
}
|
|
788
|
-
});
|
|
789
|
-
}
|
|
790
|
-
/** Function handles liquidity Add for Rune only
|
|
791
|
-
*
|
|
792
|
-
* @param params - deposit parameters
|
|
793
|
-
* @param memo - memo needed to withdraw lp
|
|
794
|
-
* @returns - tx object
|
|
795
|
-
*/
|
|
796
|
-
addRuneLP(params, memo, thorchainClient) {
|
|
797
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
798
|
-
const thorClient = this.clients.THOR;
|
|
799
|
-
const addParams = {
|
|
800
|
-
asset: params.rune.asset,
|
|
801
|
-
amount: params.rune.baseAmount,
|
|
802
|
-
memo: memo,
|
|
803
|
-
};
|
|
804
|
-
const hash = yield thorClient.deposit(addParams);
|
|
805
|
-
return { hash, url: thorchainClient.getExplorerTxUrl(hash) };
|
|
806
|
-
});
|
|
807
|
-
}
|
|
808
|
-
/** Function handles liquidity Withdraw for Rune only
|
|
809
|
-
*
|
|
810
|
-
* @param params - withdraw parameters
|
|
811
|
-
* @param memo - memo needed to withdraw lp
|
|
812
|
-
* @returns - tx object
|
|
813
|
-
*/
|
|
814
|
-
withdrawRuneLP(params, memo, thorchainClient) {
|
|
815
|
-
return __awaiter(this, void 0, void 0, function* () {
|
|
816
|
-
const thorClient = this.clients.THOR;
|
|
817
|
-
const addParams = {
|
|
818
|
-
asset: params.runeFee.asset,
|
|
819
|
-
amount: params.runeFee.baseAmount,
|
|
820
|
-
memo: memo,
|
|
148
|
+
const { hash } = yield chainWallet.sendTransaction(unsignedTx);
|
|
149
|
+
return {
|
|
150
|
+
hash,
|
|
151
|
+
url: yield wallet.getExplorerTxUrl(assetAmount.asset.chain, hash),
|
|
821
152
|
};
|
|
822
|
-
const hash = yield thorClient.deposit(addParams);
|
|
823
|
-
return { hash, url: thorchainClient.getExplorerTxUrl(hash) };
|
|
824
153
|
});
|
|
825
154
|
}
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
return
|
|
833
|
-
}
|
|
834
|
-
isUTXOChain(asset) {
|
|
835
|
-
return ['BTC', 'BCH', 'DOGE'].includes(asset.chain);
|
|
155
|
+
static isNonProtocolParams(params) {
|
|
156
|
+
if ((params.assetAmount.asset.chain === THORChain || params.assetAmount.asset.synth) &&
|
|
157
|
+
'address' in params &&
|
|
158
|
+
!!params.address) {
|
|
159
|
+
throw Error('Inconsistent params. Native actions do not support recipient');
|
|
160
|
+
}
|
|
161
|
+
return params.assetAmount.asset.chain !== THORChain && !params.assetAmount.asset.synth;
|
|
836
162
|
}
|
|
837
163
|
}
|
|
838
164
|
|
|
839
|
-
const defaultQuery = new ThorchainQuery();
|
|
840
165
|
/**
|
|
841
166
|
* THORChain Class for interacting with THORChain.
|
|
842
167
|
* Recommended main class to use for swapping with THORChain
|
|
@@ -844,79 +169,144 @@ const defaultQuery = new ThorchainQuery();
|
|
|
844
169
|
*/
|
|
845
170
|
class ThorchainAMM {
|
|
846
171
|
/**
|
|
847
|
-
*
|
|
172
|
+
* Constructor to create a ThorchainAMM instance
|
|
848
173
|
*
|
|
849
174
|
* @param thorchainQuery - an instance of the ThorchainQuery
|
|
850
175
|
* @returns ThorchainAMM
|
|
851
176
|
*/
|
|
852
|
-
constructor(thorchainQuery =
|
|
177
|
+
constructor(thorchainQuery = new ThorchainQuery(), wallet = new Wallet({
|
|
178
|
+
BTC: new Client(Object.assign(Object.assign({}, defaultBTCParams), { network: Network.Mainnet })),
|
|
179
|
+
BCH: new Client$1(Object.assign(Object.assign({}, defaultBchParams), { network: Network.Mainnet })),
|
|
180
|
+
LTC: new Client$2(Object.assign(Object.assign({}, defaultLtcParams), { network: Network.Mainnet })),
|
|
181
|
+
DOGE: new Client$3(Object.assign(Object.assign({}, defaultDogeParams), { network: Network.Mainnet })),
|
|
182
|
+
ETH: new Client$4(Object.assign(Object.assign({}, defaultEthParams), { network: Network.Mainnet })),
|
|
183
|
+
AVAX: new Client$5(Object.assign(Object.assign({}, defaultAvaxParams), { network: Network.Mainnet })),
|
|
184
|
+
BSC: new Client$6(Object.assign(Object.assign({}, defaultBscParams), { network: Network.Mainnet })),
|
|
185
|
+
GAIA: new Client$7({ network: Network.Mainnet }),
|
|
186
|
+
BNB: new Client$8({ network: Network.Mainnet }),
|
|
187
|
+
THOR: new Client$9(Object.assign(Object.assign({}, defaultClientConfig), { network: Network.Mainnet })),
|
|
188
|
+
})) {
|
|
853
189
|
this.thorchainQuery = thorchainQuery;
|
|
190
|
+
this.wallet = wallet;
|
|
854
191
|
}
|
|
855
192
|
/**
|
|
856
|
-
* Provides
|
|
857
|
-
*
|
|
858
|
-
*
|
|
859
|
-
*
|
|
193
|
+
* * Provides an estimate for a swap based on the given swap details.
|
|
194
|
+
* Checks the parameters for errors before attempting to retrieve the estimate.
|
|
195
|
+
* Utilizes current pool data to calculate inbound and outbound fees, affiliate fees,
|
|
196
|
+
* and the expected wait time for the swap (inbound and outbound).
|
|
197
|
+
* @param params Parameters for the swap, including the amount to swap.
|
|
860
198
|
|
|
861
|
-
* @returns The
|
|
199
|
+
* @returns The estimated swap details.
|
|
862
200
|
*/
|
|
863
|
-
estimateSwap({ fromAsset, amount, destinationAsset, destinationAddress, affiliateAddress = '',
|
|
201
|
+
estimateSwap({ fromAddress, fromAsset, amount, destinationAsset, destinationAddress, affiliateAddress = '', affiliateBps = 0, toleranceBps, }) {
|
|
864
202
|
return __awaiter(this, void 0, void 0, function* () {
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
waitTimeSeconds: 100,
|
|
873
|
-
walletIndex,
|
|
874
|
-
};
|
|
875
|
-
errors = yield wallet.validateSwap(params);
|
|
876
|
-
}
|
|
203
|
+
const errors = yield this.validateSwap({
|
|
204
|
+
fromAddress,
|
|
205
|
+
fromAsset,
|
|
206
|
+
amount,
|
|
207
|
+
destinationAsset,
|
|
208
|
+
destinationAddress,
|
|
209
|
+
});
|
|
877
210
|
const estimate = yield this.thorchainQuery.quoteSwap({
|
|
878
211
|
fromAsset,
|
|
879
212
|
amount,
|
|
880
213
|
destinationAsset,
|
|
881
214
|
destinationAddress,
|
|
882
215
|
affiliateAddress,
|
|
883
|
-
interfaceID,
|
|
884
216
|
affiliateBps,
|
|
885
217
|
toleranceBps,
|
|
886
218
|
});
|
|
219
|
+
// Add any validation errors to the estimate
|
|
887
220
|
estimate.txEstimate.errors.push(...errors);
|
|
888
|
-
estimate.txEstimate.canSwap = errors.length
|
|
221
|
+
estimate.txEstimate.canSwap = estimate.txEstimate.errors.length === 0;
|
|
889
222
|
return estimate;
|
|
890
223
|
});
|
|
891
224
|
}
|
|
892
225
|
/**
|
|
893
|
-
*
|
|
226
|
+
* Validate swap params
|
|
227
|
+
* @param {QuoteSwapParams} quoteSwapParams Swap params
|
|
228
|
+
* @returns {string[]} the reasons the swap can not be done. If it is empty there are no reason to avoid the swap
|
|
229
|
+
*/
|
|
230
|
+
validateSwap({ fromAsset, fromAddress, destinationAsset, destinationAddress, amount, affiliateAddress, affiliateBps, }) {
|
|
231
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
232
|
+
const errors = [];
|
|
233
|
+
if (destinationAddress && !this.wallet.validateAddress(destinationAsset.chain, destinationAddress)) {
|
|
234
|
+
errors.push(`destinationAddress ${destinationAddress} is not a valid address`);
|
|
235
|
+
}
|
|
236
|
+
if (affiliateAddress) {
|
|
237
|
+
const isThorAddress = this.wallet.validateAddress(THORChain, affiliateAddress);
|
|
238
|
+
const isThorname = !!(yield this.thorchainQuery.thorchainCache.midgardQuery.midgardCache.midgard.getTHORNameDetails(affiliateAddress));
|
|
239
|
+
if (!(isThorAddress || isThorname))
|
|
240
|
+
errors.push(`affiliateAddress ${affiliateAddress} is not a valid THOR address`);
|
|
241
|
+
}
|
|
242
|
+
if (affiliateBps && (affiliateBps < 0 || affiliateBps > 10000)) {
|
|
243
|
+
errors.push(`affiliateBps ${affiliateBps} out of range [0 - 10000]`);
|
|
244
|
+
}
|
|
245
|
+
if (isProtocolERC20Asset(fromAsset) && fromAddress) {
|
|
246
|
+
const approveErrors = yield this.isRouterApprovedToSpend({
|
|
247
|
+
asset: fromAsset,
|
|
248
|
+
address: fromAddress,
|
|
249
|
+
amount,
|
|
250
|
+
});
|
|
251
|
+
errors.push(...approveErrors);
|
|
252
|
+
}
|
|
253
|
+
return errors;
|
|
254
|
+
});
|
|
255
|
+
}
|
|
256
|
+
/**
|
|
257
|
+
* Conducts a swap with the given inputs. This method should be called after estimateSwap() to ensure the swap is valid.
|
|
894
258
|
*
|
|
895
|
-
* @param wallet - wallet to use
|
|
896
|
-
* @param params - swap
|
|
897
|
-
* @returns {SwapSubmitted} -
|
|
259
|
+
* @param wallet - The wallet to use for the swap.
|
|
260
|
+
* @param params - The swap parameters.
|
|
261
|
+
* @returns {SwapSubmitted} - The transaction hash, URL of BlockExplorer, and expected wait time.
|
|
898
262
|
*/
|
|
899
|
-
doSwap(
|
|
263
|
+
doSwap({ fromAsset, fromAddress, amount, destinationAsset, destinationAddress, affiliateAddress, affiliateBps, toleranceBps, }) {
|
|
900
264
|
return __awaiter(this, void 0, void 0, function* () {
|
|
901
|
-
//
|
|
902
|
-
const txDetails = yield this.thorchainQuery.quoteSwap(
|
|
265
|
+
// Retrieve swap details from ThorchainQuery to ensure validity
|
|
266
|
+
const txDetails = yield this.thorchainQuery.quoteSwap({
|
|
267
|
+
fromAsset,
|
|
268
|
+
fromAddress,
|
|
269
|
+
amount,
|
|
270
|
+
destinationAsset,
|
|
271
|
+
destinationAddress,
|
|
272
|
+
affiliateAddress,
|
|
273
|
+
affiliateBps,
|
|
274
|
+
toleranceBps,
|
|
275
|
+
});
|
|
903
276
|
if (!txDetails.txEstimate.canSwap) {
|
|
904
277
|
throw Error(txDetails.txEstimate.errors.join('\n'));
|
|
905
278
|
}
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
|
|
279
|
+
// Execute the swap using Thorchain action
|
|
280
|
+
return ThorchainAction.makeAction({
|
|
281
|
+
wallet: this.wallet,
|
|
282
|
+
assetAmount: amount,
|
|
910
283
|
memo: txDetails.memo,
|
|
911
|
-
|
|
912
|
-
feeOption: params.feeOption,
|
|
284
|
+
recipient: txDetails.toAddress,
|
|
913
285
|
});
|
|
914
286
|
});
|
|
915
287
|
}
|
|
916
288
|
/**
|
|
917
|
-
*
|
|
918
|
-
* @param
|
|
919
|
-
*
|
|
289
|
+
* Validate if the asset router is allowed to spend the asset amount in name of the address
|
|
290
|
+
* @param {IsApprovedParams} isApprovedParams contains the asset and the amount the router is supposed to spend
|
|
291
|
+
* int name of address
|
|
292
|
+
* @returns {string[]} the reasons the router of the asset is not allowed to spend the amount. If it is empty, the asset router is allowed to spend the amount
|
|
293
|
+
*/
|
|
294
|
+
isRouterApprovedToSpend({ asset, amount, address }) {
|
|
295
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
296
|
+
const errors = [];
|
|
297
|
+
const inboundDetails = yield this.thorchainQuery.getChainInboundDetails(asset.chain);
|
|
298
|
+
if (!inboundDetails.router)
|
|
299
|
+
throw Error(`Unknown router address for ${asset.chain}`);
|
|
300
|
+
const isApprovedResult = yield this.wallet.isApproved(asset, amount.baseAmount, address, inboundDetails.router);
|
|
301
|
+
if (!isApprovedResult)
|
|
302
|
+
errors.push('Thorchain router has not been approved to spend this amount');
|
|
303
|
+
return errors;
|
|
304
|
+
});
|
|
305
|
+
}
|
|
306
|
+
/**
|
|
307
|
+
* Wraps the estimate from ThorchainQuery for adding liquidity.
|
|
308
|
+
* @param params - The parameters for estimating adding liquidity.
|
|
309
|
+
* @returns - The estimated liquidity addition object.
|
|
920
310
|
*/
|
|
921
311
|
estimateAddLiquidity(params) {
|
|
922
312
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -924,9 +314,9 @@ class ThorchainAMM {
|
|
|
924
314
|
});
|
|
925
315
|
}
|
|
926
316
|
/**
|
|
927
|
-
* Wraps estimate
|
|
928
|
-
* @param params -
|
|
929
|
-
* @returns -
|
|
317
|
+
* Wraps the estimate from ThorchainQuery for withdrawing liquidity.
|
|
318
|
+
* @param params - The parameters for estimating withdrawing liquidity.
|
|
319
|
+
* @returns - The estimated liquidity withdrawal object.
|
|
930
320
|
*/
|
|
931
321
|
estimateWithdrawLiquidity(params) {
|
|
932
322
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -934,36 +324,75 @@ class ThorchainAMM {
|
|
|
934
324
|
});
|
|
935
325
|
}
|
|
936
326
|
/**
|
|
937
|
-
*
|
|
938
|
-
* @param wallet -
|
|
939
|
-
* @param params -
|
|
327
|
+
* If there is no existing liquidity position, it is created automatically.
|
|
328
|
+
* @param wallet - Wallet class
|
|
329
|
+
* @param params - Liquidity parameter
|
|
940
330
|
* @returns
|
|
941
331
|
*/
|
|
942
|
-
addLiquidityPosition(
|
|
332
|
+
addLiquidityPosition(params) {
|
|
943
333
|
return __awaiter(this, void 0, void 0, function* () {
|
|
944
334
|
// Check amounts are greater than fees and use return estimated wait
|
|
945
335
|
const checkLPAdd = yield this.thorchainQuery.estimateAddLP(params);
|
|
946
336
|
if (!checkLPAdd.canAdd)
|
|
947
337
|
throw Error(`${checkLPAdd.errors}`);
|
|
948
|
-
|
|
338
|
+
const inboundAsgard = (yield this.thorchainQuery.thorchainCache.getInboundDetails())[params.asset.asset.chain]
|
|
339
|
+
.address;
|
|
340
|
+
const addressRune = yield this.wallet.getAddress(THORChain);
|
|
341
|
+
const addressAsset = yield this.wallet.getAddress(params.asset.asset.chain);
|
|
342
|
+
// const waitTimeSeconds = params.waitTimeSeconds
|
|
343
|
+
const txSubmitted = [];
|
|
344
|
+
const addLiquidity = {
|
|
949
345
|
asset: params.asset,
|
|
950
346
|
rune: params.rune,
|
|
951
347
|
waitTimeSeconds: checkLPAdd.estimatedWaitSeconds,
|
|
952
348
|
assetPool: checkLPAdd.assetPool,
|
|
953
|
-
}
|
|
349
|
+
};
|
|
350
|
+
// symmetrical add
|
|
351
|
+
if (params.asset.assetAmount.gt(0) && params.rune.assetAmount.gt(0)) {
|
|
352
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
353
|
+
wallet: this.wallet,
|
|
354
|
+
memo: `+:${checkLPAdd.assetPool}:${addressRune}`,
|
|
355
|
+
assetAmount: addLiquidity.asset,
|
|
356
|
+
recipient: inboundAsgard,
|
|
357
|
+
}));
|
|
358
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
359
|
+
wallet: this.wallet,
|
|
360
|
+
memo: `+:${checkLPAdd.assetPool}:${addressAsset}`,
|
|
361
|
+
assetAmount: addLiquidity.rune,
|
|
362
|
+
}));
|
|
363
|
+
return txSubmitted;
|
|
364
|
+
}
|
|
365
|
+
else if (params.asset.assetAmount.gt(0) && params.rune.assetAmount.eq(0)) {
|
|
366
|
+
// asymmetrical asset only
|
|
367
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
368
|
+
wallet: this.wallet,
|
|
369
|
+
memo: `+:${checkLPAdd.assetPool}`,
|
|
370
|
+
assetAmount: addLiquidity.asset,
|
|
371
|
+
recipient: inboundAsgard,
|
|
372
|
+
}));
|
|
373
|
+
return txSubmitted;
|
|
374
|
+
}
|
|
375
|
+
else {
|
|
376
|
+
// asymmetrical rune only
|
|
377
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
378
|
+
wallet: this.wallet,
|
|
379
|
+
memo: `+:${checkLPAdd.assetPool}`,
|
|
380
|
+
assetAmount: addLiquidity.asset,
|
|
381
|
+
}));
|
|
382
|
+
return txSubmitted;
|
|
383
|
+
}
|
|
954
384
|
});
|
|
955
385
|
}
|
|
956
386
|
/**
|
|
957
|
-
*
|
|
958
|
-
* @param params -
|
|
959
|
-
* @
|
|
960
|
-
* @return
|
|
387
|
+
* Withdraws liquidity from a position.
|
|
388
|
+
* @param params - The wallet to perform the transaction.
|
|
389
|
+
* @return - The array of transaction submissions.
|
|
961
390
|
*/
|
|
962
|
-
withdrawLiquidityPosition(
|
|
391
|
+
withdrawLiquidityPosition(params) {
|
|
963
392
|
return __awaiter(this, void 0, void 0, function* () {
|
|
964
|
-
// Caution Dust Limits: BTC,BCH,LTC chains 10k sats; DOGE 1m Sats; ETH 0 wei; THOR 0 RUNE.
|
|
393
|
+
// Caution Dust Limits: BTC, BCH, LTC chains: 10k sats; DOGE: 1m Sats; ETH: 0 wei; THOR: 0 RUNE.
|
|
965
394
|
const withdrawParams = yield this.thorchainQuery.estimateWithdrawLP(params);
|
|
966
|
-
|
|
395
|
+
const withdrawLiquidity = {
|
|
967
396
|
assetFee: withdrawParams.inbound.fees.asset,
|
|
968
397
|
runeFee: withdrawParams.inbound.fees.rune,
|
|
969
398
|
waitTimeSeconds: withdrawParams.estimatedWaitSeconds,
|
|
@@ -971,13 +400,50 @@ class ThorchainAMM {
|
|
|
971
400
|
assetPool: withdrawParams.assetPool,
|
|
972
401
|
assetAddress: withdrawParams.assetAddress,
|
|
973
402
|
runeAddress: withdrawParams.runeAddress,
|
|
974
|
-
}
|
|
403
|
+
};
|
|
404
|
+
const inboundAsgard = (yield this.thorchainQuery.thorchainCache.getInboundDetails())[withdrawLiquidity.assetFee.asset.chain].address;
|
|
405
|
+
// const waitTimeSeconds = params.waitTimeSeconds
|
|
406
|
+
const basisPoints = (withdrawLiquidity.percentage * 100).toFixed(); // convert to basis points
|
|
407
|
+
const txSubmitted = [];
|
|
408
|
+
if (withdrawLiquidity.assetAddress && withdrawLiquidity.runeAddress) {
|
|
409
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
410
|
+
wallet: this.wallet,
|
|
411
|
+
memo: `-:${withdrawLiquidity.assetPool}:${basisPoints}`,
|
|
412
|
+
assetAmount: withdrawLiquidity.assetFee,
|
|
413
|
+
recipient: inboundAsgard,
|
|
414
|
+
}));
|
|
415
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
416
|
+
wallet: this.wallet,
|
|
417
|
+
memo: `-:${withdrawLiquidity.assetPool}:${basisPoints}`,
|
|
418
|
+
assetAmount: withdrawLiquidity.runeFee,
|
|
419
|
+
}));
|
|
420
|
+
return txSubmitted;
|
|
421
|
+
}
|
|
422
|
+
else if (withdrawLiquidity.assetAddress && !withdrawLiquidity.runeAddress) {
|
|
423
|
+
// asymmetrical asset only
|
|
424
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
425
|
+
wallet: this.wallet,
|
|
426
|
+
memo: `-:${withdrawLiquidity.assetPool}:${basisPoints}`,
|
|
427
|
+
assetAmount: withdrawLiquidity.assetFee,
|
|
428
|
+
recipient: inboundAsgard,
|
|
429
|
+
}));
|
|
430
|
+
return txSubmitted;
|
|
431
|
+
}
|
|
432
|
+
else {
|
|
433
|
+
// asymmetrical rune only
|
|
434
|
+
txSubmitted.push(yield ThorchainAction.makeAction({
|
|
435
|
+
wallet: this.wallet,
|
|
436
|
+
memo: `-:${withdrawLiquidity.assetPool}:${basisPoints}`,
|
|
437
|
+
assetAmount: withdrawLiquidity.runeFee,
|
|
438
|
+
}));
|
|
439
|
+
return txSubmitted;
|
|
440
|
+
}
|
|
975
441
|
});
|
|
976
442
|
}
|
|
977
443
|
/**
|
|
978
|
-
*
|
|
979
|
-
* @param addAssetAmount
|
|
980
|
-
* @returns
|
|
444
|
+
* Estimates adding to a saver.
|
|
445
|
+
* @param addAssetAmount The amount to add to the saver.
|
|
446
|
+
* @returns The estimated addition to the saver object.
|
|
981
447
|
*/
|
|
982
448
|
estimateAddSaver(addAssetAmount) {
|
|
983
449
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -985,9 +451,9 @@ class ThorchainAMM {
|
|
|
985
451
|
});
|
|
986
452
|
}
|
|
987
453
|
/**
|
|
988
|
-
*
|
|
989
|
-
* @param withdrawParams
|
|
990
|
-
* @returns
|
|
454
|
+
* Estimates withdrawing from a saver.
|
|
455
|
+
* @param withdrawParams The parameters for withdrawing from the saver.
|
|
456
|
+
* @returns The estimated withdrawal from the saver object.
|
|
991
457
|
*/
|
|
992
458
|
estimateWithdrawSaver(withdrawParams) {
|
|
993
459
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -995,9 +461,9 @@ class ThorchainAMM {
|
|
|
995
461
|
});
|
|
996
462
|
}
|
|
997
463
|
/**
|
|
998
|
-
*
|
|
999
|
-
* @param getsaver
|
|
1000
|
-
* @returns
|
|
464
|
+
* Retrieves the position of a saver.
|
|
465
|
+
* @param getsaver The parameters to retrieve the saver position.
|
|
466
|
+
* @returns The saver position object.
|
|
1001
467
|
*/
|
|
1002
468
|
getSaverPosition(getsaver) {
|
|
1003
469
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -1005,37 +471,46 @@ class ThorchainAMM {
|
|
|
1005
471
|
});
|
|
1006
472
|
}
|
|
1007
473
|
/**
|
|
1008
|
-
*
|
|
474
|
+
* Adds assets to a saver.
|
|
1009
475
|
* @param wallet - wallet needed to execute tx
|
|
1010
|
-
* @param addAssetAmount -
|
|
1011
|
-
* @returns - submitted
|
|
476
|
+
* @param addAssetAmount - The amount to add to the saver.
|
|
477
|
+
* @returns - The submitted transaction.
|
|
1012
478
|
*/
|
|
1013
|
-
addSaver(
|
|
479
|
+
addSaver(addAssetAmount) {
|
|
1014
480
|
return __awaiter(this, void 0, void 0, function* () {
|
|
1015
481
|
const addEstimate = yield this.thorchainQuery.estimateAddSaver(addAssetAmount);
|
|
1016
482
|
if (!addEstimate.canAddSaver)
|
|
1017
483
|
throw Error(`Cannot add to savers`);
|
|
1018
|
-
return
|
|
484
|
+
return ThorchainAction.makeAction({
|
|
485
|
+
wallet: this.wallet,
|
|
486
|
+
recipient: addEstimate.toAddress,
|
|
487
|
+
assetAmount: addAssetAmount,
|
|
488
|
+
memo: addEstimate.memo,
|
|
489
|
+
});
|
|
1019
490
|
});
|
|
1020
491
|
}
|
|
1021
492
|
/**
|
|
1022
|
-
*
|
|
1023
|
-
* @param
|
|
1024
|
-
* @
|
|
1025
|
-
* @returns
|
|
493
|
+
* Withdraws assets from a saver.
|
|
494
|
+
* @param withdrawParams - The parameters for withdrawing from the saver.
|
|
495
|
+
* @returns The submitted transaction.
|
|
1026
496
|
*/
|
|
1027
|
-
withdrawSaver(
|
|
497
|
+
withdrawSaver(withdrawParams) {
|
|
1028
498
|
return __awaiter(this, void 0, void 0, function* () {
|
|
1029
499
|
const withdrawEstimate = yield this.thorchainQuery.estimateWithdrawSaver(withdrawParams);
|
|
1030
500
|
if (withdrawEstimate.errors.length > 0)
|
|
1031
501
|
throw Error(`${withdrawEstimate.errors}`);
|
|
1032
|
-
return
|
|
502
|
+
return ThorchainAction.makeAction({
|
|
503
|
+
wallet: this.wallet,
|
|
504
|
+
recipient: withdrawEstimate.toAddress,
|
|
505
|
+
assetAmount: withdrawEstimate.dustAmount,
|
|
506
|
+
memo: withdrawEstimate.memo,
|
|
507
|
+
});
|
|
1033
508
|
});
|
|
1034
509
|
}
|
|
1035
510
|
/**
|
|
1036
|
-
*
|
|
1037
|
-
* @param loanOpenParams
|
|
1038
|
-
* @returns
|
|
511
|
+
* Retrieves a quote for opening a loan.
|
|
512
|
+
* @param loanOpenParams The parameters for opening the loan.
|
|
513
|
+
* @returns The quote for opening the loan.
|
|
1039
514
|
*/
|
|
1040
515
|
getLoanQuoteOpen(loanOpenParams) {
|
|
1041
516
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -1043,9 +518,9 @@ class ThorchainAMM {
|
|
|
1043
518
|
});
|
|
1044
519
|
}
|
|
1045
520
|
/**
|
|
1046
|
-
*
|
|
1047
|
-
* @param loanCloseParams
|
|
1048
|
-
* @returns
|
|
521
|
+
* Retrieves a quote for closing a loan.
|
|
522
|
+
* @param loanCloseParams The parameters for closing the loan.
|
|
523
|
+
* @returns The quote for closing the loan.
|
|
1049
524
|
*/
|
|
1050
525
|
getLoanQuoteClose(loanCloseParams) {
|
|
1051
526
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -1053,45 +528,46 @@ class ThorchainAMM {
|
|
|
1053
528
|
});
|
|
1054
529
|
}
|
|
1055
530
|
/**
|
|
1056
|
-
*
|
|
1057
|
-
* @param
|
|
1058
|
-
* @
|
|
1059
|
-
* @returns - submitted tx
|
|
531
|
+
* Opens a loan.
|
|
532
|
+
* @param loanOpenParams - The parameters for opening the loan.
|
|
533
|
+
* @returns - The submitted transaction.
|
|
1060
534
|
*/
|
|
1061
|
-
addLoan(
|
|
535
|
+
addLoan(loanOpenParams) {
|
|
1062
536
|
return __awaiter(this, void 0, void 0, function* () {
|
|
1063
537
|
const loanOpen = yield this.thorchainQuery.getLoanQuoteOpen(loanOpenParams);
|
|
1064
538
|
if (loanOpen.errors.length > 0)
|
|
1065
539
|
throw Error(`${loanOpen.errors}`);
|
|
1066
|
-
return
|
|
540
|
+
return ThorchainAction.makeAction({
|
|
541
|
+
wallet: this.wallet,
|
|
1067
542
|
memo: `${loanOpen.memo}`,
|
|
1068
|
-
|
|
1069
|
-
|
|
543
|
+
recipient: `${loanOpen.inboundAddress}`,
|
|
544
|
+
assetAmount: loanOpenParams.amount,
|
|
1070
545
|
});
|
|
1071
546
|
});
|
|
1072
547
|
}
|
|
1073
548
|
/**
|
|
1074
|
-
*
|
|
1075
|
-
* @param
|
|
1076
|
-
* @
|
|
1077
|
-
* @returns
|
|
549
|
+
* Withdraws assets from a loan.
|
|
550
|
+
* @param loanCloseParams - The parameters for withdrawing from the loan.
|
|
551
|
+
* @returns The submitted transaction.
|
|
1078
552
|
*/
|
|
1079
|
-
withdrawLoan(
|
|
553
|
+
withdrawLoan(loanCloseParams) {
|
|
1080
554
|
return __awaiter(this, void 0, void 0, function* () {
|
|
1081
555
|
const withdrawLoan = yield this.thorchainQuery.getLoanQuoteClose(loanCloseParams);
|
|
556
|
+
// Checks if there are any errors in the quote
|
|
1082
557
|
if (withdrawLoan.errors.length > 0)
|
|
1083
558
|
throw Error(`${withdrawLoan.errors}`);
|
|
1084
|
-
return
|
|
559
|
+
return ThorchainAction.makeAction({
|
|
560
|
+
wallet: this.wallet,
|
|
1085
561
|
memo: `${withdrawLoan.memo}`,
|
|
1086
|
-
|
|
1087
|
-
|
|
562
|
+
recipient: `${withdrawLoan.inboundAddress}`,
|
|
563
|
+
assetAmount: loanCloseParams.amount,
|
|
1088
564
|
});
|
|
1089
565
|
});
|
|
1090
566
|
}
|
|
1091
567
|
/**
|
|
1092
|
-
*
|
|
1093
|
-
* @param address - address
|
|
1094
|
-
* @returns
|
|
568
|
+
* Retrieves all Thornames and their associated data owned by an address.
|
|
569
|
+
* @param address - The address to retrieve Thornames for.
|
|
570
|
+
* @returns The Thornames data.
|
|
1095
571
|
*/
|
|
1096
572
|
getThornamesByAddress(address) {
|
|
1097
573
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -1100,4 +576,4 @@ class ThorchainAMM {
|
|
|
1100
576
|
}
|
|
1101
577
|
}
|
|
1102
578
|
|
|
1103
|
-
export { ThorchainAMM
|
|
579
|
+
export { ThorchainAMM };
|