Skip to content

Commit

Permalink
add transfer check (#496)
Browse files Browse the repository at this point in the history
* init payment sdk

* update payment sdk draft

* get payment method

* update

* update

* update

* add transfer-check in wallete sdk

* fix lint
  • Loading branch information
qwer951123 committed Jul 27, 2023
1 parent f949e63 commit bbcf15f
Show file tree
Hide file tree
Showing 5 changed files with 49 additions and 12 deletions.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -35,5 +35,5 @@
"typescript": "^5.0.4"
},
"packageManager": "yarn@3.5.0",
"stableVersion": "4.1.9-2"
"stableVersion": "4.1.9-3"
}
9 changes: 3 additions & 6 deletions packages/sdk-payment/src/Payment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -87,14 +87,11 @@ export class Payment {
// remove token when token is exist in globalFeePaths
if (globalFeePaths.find(([key]) => this.wallet.getToken(key.args[0]).isEqual(token))) continue;

const path = paths[0][1][1];
const xpath = paths?.[0]?.[0]?.[1];

if (isEmpty(path)) continue;
if (isEmpty(xpath)) continue;

paymentMethods.push({
type: PaymentMethodTypes.SWAP,
path
});
paymentMethods.push({ type: PaymentMethodTypes.SWAP, path: xpath });
}

return paymentMethods;
Expand Down
2 changes: 2 additions & 0 deletions packages/sdk-payment/src/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export * from './Payment';
export * from './types';
11 changes: 11 additions & 0 deletions packages/sdk/src/errors.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import { Token } from '@acala-network/sdk-core';

export class MethodNotFound extends Error {
readonly section: string;
readonly method: string;
Expand All @@ -21,3 +23,12 @@ export class SDKNotReady extends Error {
this.name = 'SDKNotReady';
}
}

export class BelowExistentialDeposit extends Error {
constructor(address: string, token: Token) {
super();

this.name = 'BelowExistentialDeposit';
this.message = `The ${address}'s ${token.display} balance may below the existential deposit after this action`;
}
}
37 changes: 32 additions & 5 deletions packages/sdk/src/wallet/wallet.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,9 @@ import {
} from '@acala-network/sdk-core';
import { BehaviorSubject, combineLatest, Observable, of, firstValueFrom } from 'rxjs';
import { map, switchMap, filter, catchError } from 'rxjs/operators';
import { FrameSystemAccountInfo } from '@polkadot/types/lookup';
import { TokenRecord, WalletConsts, BalanceData, PresetTokens, WalletConfigs, PriceProviders } from './types';
import { ChainType, Homa, Liquidity, SDKNotReady } from '..';
import { BelowExistentialDeposit, ChainType, Homa, Liquidity, SDKNotReady } from '..';
import { getMaxAvailableBalance } from './utils/get-max-available-balance';
import { MarketPriceProvider } from './price-provider/market-price-provider';
import { OraclePriceProvider } from './price-provider/oracle-price-provider';
Expand Down Expand Up @@ -215,16 +216,12 @@ export class Wallet implements BaseSDK {
const providers = accountInfo.providers.toBigInt();
const consumers = accountInfo.consumers.toBigInt();
const nativeFreeBalance = FN.fromInner(accountInfo.data.free.toString(), nativeToken.decimals);
// native locked balance = max(accountInfo.data.miscFrozen, accountInfo.data.feeFrozen)
const nativeLockedBalance = FN.fromInner(
accountInfo.data.miscFrozen.toString(),
nativeToken.decimals
).max(FN.fromInner(accountInfo.data.feeFrozen.toString(), nativeToken.decimals));
const isDefaultFee = forceToCurrencyName(feeToken) === nativeToken.name;
const feeFreeBalance = isDefaultFee ? nativeFreeBalance : feeInfo.free;
// const feeLockedBalance =
// forceToCurrencyName(feeToken) === nativeToken.name ? nativeLockedBalance : feeInfo.locked;

const targetFreeBalance: FixedPointNumber = isNativeToken ? nativeFreeBalance : tokenInfo.free;
const targetLockedBalance: FixedPointNumber = isNativeToken ? nativeLockedBalance : tokenInfo.locked;
const ed = token.ed;
Expand Down Expand Up @@ -357,4 +354,34 @@ export class Wallet implements BaseSDK {
public getPrice(token: MaybeCurrency, type?: PriceProviderType): Promise<FN> {
return firstValueFrom(this.subscribePrice(token, type));
}

public async checkTransfer(address: string, currency: MaybeCurrency, amount: FN, direction: 'from' | 'to' = 'to') {
const { nativeToken } = this.getPresetTokens();
const token = this.getToken(currency);
const tokenName = forceToCurrencyName(currency);
const isNativeToken = nativeToken.isEqual(token);
const accountInfo = (await this.api.query.system.account(address)) as unknown as FrameSystemAccountInfo;
const balance = await this.getBalance(currency, address);

let needCheck = true;

// always check ED if the direction is `to`
if (direction === 'to' && balance.free.add(amount).lt(token.ed || FN.ZERO)) {
throw new BelowExistentialDeposit(address, token);
}

if (direction === 'from') {
if (isNativeToken) {
needCheck = !(accountInfo.consumers.toBigInt() === BigInt(0));
} else {
needCheck = !(accountInfo.providers.toBigInt() > BigInt(0) || accountInfo.consumers.toBigInt() === BigInt(0));
}

if (needCheck && balance.free.minus(amount).lt(token.ed || FN.ZERO)) {
throw new BelowExistentialDeposit(address, token);
}
}

return true;
}
}

0 comments on commit bbcf15f

Please sign in to comment.