bancorx
Version:
BancorX Utility
219 lines • 10.5 kB
JavaScript
"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const eos_common_1 = require("eos-common");
const decimal_js_1 = __importDefault(require("decimal.js"));
/**
* Bancor Formula
*
* - token balance of EOS (eosio.token) in the relay: 77814.0638 EOS
* - token balance of BNT (bntbntbntbnt) in the relay: 429519.5539120331 BNT
*
* ```js
* Formula:
* 1.0000 / (77814.0638 + 1.0000) * 429519.5539120331
* // => 5.519748143058556
* ```
*
* @param {Asset} balanceFrom from token balance in the relay
* @param {Asset} balanceTo to token balance in the relay
* @param {Asset} amount amount to convert
* @returns {number} computed amount
* @example
*
* const balanceFrom = split(`77814.0638 EOS`);
* const balanceTo = split(`429519.5539120331 BNT`); // BNT
* const amount = split(`1.0000 EOS`);
*
* bancorx.calculateReturn(balanceFrom, balanceTo, amount)
* // => split(`5.519748143058556 BNT`)
*/
function calculateReturn(balanceFrom, balanceTo, amount) {
if (!balanceFrom.symbol.isEqual(amount.symbol))
throw new Error("From symbol does not match amount symbol");
if (amount.amount >= balanceFrom.amount)
throw new Error("Impossible to buy the entire reserve or more");
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_DOWN });
const balanceFromNumber = new decimal_js_1.default(Number(balanceFrom.amount));
const balanceToNumber = new decimal_js_1.default(Number(balanceTo.amount));
const amountNumber = new decimal_js_1.default(Number(amount.amount));
const reward = amountNumber
.div(balanceFromNumber.plus(amountNumber))
.times(balanceToNumber);
return new eos_common_1.Asset(reward
.times(Math.pow(10, balanceTo.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_DOWN)
.toNumber(), balanceTo.symbol);
}
exports.calculateReturn = calculateReturn;
/**
* Bancor Inverse Formula
*
* - token balance of EOS (eosio.token) in the relay: 77814.0638 EOS
* - token balance of BNT (bntbntbntbnt) in the relay: 429519.5539120331 BNT
*
* ```js
* Inverse Formula:
* 77814.0638 / (1.0 - 1 / 429519.5539120331) - 77814.0638
* // => 0.18116577989712823
* ```
*
* @param {Asset} balanceFrom from token balance in the relay
* @param {Asset} balanceTo to token balance in the relay
* @param {Asset} amountDesired amount to desired
* @returns {number} computed desired amount
* @example
*
* const balanceFrom = 77814.0638 // EOS
* const balanceTo = 429519.5539120331 // BNT
* const amountDesired = 1
*
* bancorx.calculateCost(balanceFrom, balanceTo, amountDesired)
* // => 0.18116577989712823
*/
function calculateCost(balanceFrom, balanceTo, amountDesired) {
if (!balanceTo.symbol.isEqual(amountDesired.symbol))
throw new Error("From symbol does not match amount symbol");
if (amountDesired.amount >= balanceTo.amount)
throw new Error("Impossible to buy the entire reserve or more");
const balanceFromNumber = new decimal_js_1.default(Number(balanceFrom.amount));
const balanceToNumber = new decimal_js_1.default(Number(balanceTo.amount));
const amountNumber = new decimal_js_1.default(Number(amountDesired.amount));
const oneNumber = new decimal_js_1.default(1);
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_UP });
const reward = balanceFromNumber
.div(oneNumber.minus(amountNumber.div(balanceToNumber)))
.minus(balanceFromNumber);
return new eos_common_1.Asset(reward
.times(Math.pow(10, balanceFrom.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_FLOOR)
.toNumber(), balanceFrom.symbol);
}
exports.calculateCost = calculateCost;
function calculateReserveToSmart(reserveAmount, reserveBalance, smartSupply, ratio = 0.5) {
const smartSupplyN = new decimal_js_1.default(Number(smartSupply.amount)).times(-1);
const balanceN = new decimal_js_1.default(Number(reserveBalance.amount));
const depositAmountN = new decimal_js_1.default(Number(reserveAmount.amount));
const one = new decimal_js_1.default(1);
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_DOWN });
const reward = smartSupplyN.times(one.minus(one.plus(depositAmountN.div(balanceN)).pow(ratio)));
return new eos_common_1.Asset(reward
.times(Math.pow(10, smartSupply.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_FLOOR)
.toNumber(), smartSupply.symbol);
}
exports.calculateReserveToSmart = calculateReserveToSmart;
function calculateSmartToReserve(smartTokens, reserveBalance, smartSupply, ratio = 0.5) {
const reserveTokensN = new decimal_js_1.default(Number(smartTokens.amount));
const reserveBalanceN = new decimal_js_1.default(Number(reserveBalance.amount));
const smartSupplyN = new decimal_js_1.default(Number(smartSupply.amount));
const one = new decimal_js_1.default(1);
const ratioN = one.div(new decimal_js_1.default(ratio));
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_DOWN });
const reward = reserveBalanceN.times(one.minus(decimal_js_1.default.pow(one.minus(reserveTokensN.div(smartSupplyN)), ratioN)));
return new eos_common_1.Asset(reward
.times(Math.pow(10, reserveBalance.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_FLOOR)
.toNumber(), reserveBalance.symbol);
}
exports.calculateSmartToReserve = calculateSmartToReserve;
/**
* Compose Memo
*
* @param {Converter[]} converters relay converters
* @param {number} minReturn minimum return
* @param {string} destAccount destination acccount
* @param {number} [version=1] bancor protocol version
* @returns {string} computed memo
* @example
*
* const CUSD = bancorx.relays.CUSD;
* const BNT = bancorx.relays.BNT;
*
* // Single converter (BNT => CUSD)
* bancorx.composeMemo([CUSD], "3.17", "<account>")
* // => "1,bancorc11144 CUSD,3.17,<account>"
*
* // Multi converter (EOS => BNT => CUSD)
* bancorx.composeMemo([BNT, CUSD], "3.17", "<account>")
* // => "1,bnt2eoscnvrt BNT bancorc11144 CUSD,3.17,<account>"
*/
function composeMemo(converters, minReturn, destAccount, version = 1) {
const receiver = converters
.map(({ extsym, symcode, contract }) => {
if (extsym)
return `${extsym.get_contract().to_string()}:${extsym.get_symbol().code().to_string()} ${symcode.to_string()}`;
return `${contract.to_string()} ${symcode.to_string()}`;
})
.join(" ");
return `${version},${receiver},${minReturn},${destAccount}`;
}
exports.composeMemo = composeMemo;
function chargeFee(asset, decimalFee, magnitude = 1) {
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_DOWN });
const assetAmount = new decimal_js_1.default(Number(asset.amount));
const one = new decimal_js_1.default(1);
const totalFee = assetAmount.times(one.minus(decimal_js_1.default.pow(one.minus(decimalFee), magnitude)));
const newAmount = assetAmount.minus(totalFee);
return new eos_common_1.Asset(newAmount
.times(Math.pow(10, asset.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_FLOOR)
.toNumber(), asset.symbol);
}
exports.chargeFee = chargeFee;
function liquidate(smartTokens, reserveBalance, smartSupply) {
const smartTokensN = new decimal_js_1.default(Number(smartTokens.amount));
const reserveBalanceN = new decimal_js_1.default(Number(reserveBalance.amount));
const smartSupplyN = new decimal_js_1.default(Number(smartSupply.amount));
const reward = smartTokensN.times(reserveBalanceN).div(smartSupplyN);
return new eos_common_1.Asset(reward
.times(Math.pow(10, reserveBalance.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_DOWN)
.toNumber(), reserveBalance.symbol);
}
exports.liquidate = liquidate;
function calculateLiquidateCost(reserveTokens, reserveBalance, smartSupply) {
const reserveTokensN = new decimal_js_1.default(Number(reserveTokens.amount));
const reserveBalanceN = new decimal_js_1.default(Number(reserveBalance.amount));
const smartSupplyN = new decimal_js_1.default(Number(smartSupply.amount));
const reward = reserveTokensN.times(smartSupplyN).div(reserveBalanceN);
return new eos_common_1.Asset(reward
.times(Math.pow(10, smartSupply.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_DOWN)
.toNumber(), smartSupply.symbol);
}
exports.calculateLiquidateCost = calculateLiquidateCost;
const bigNumber = decimal_js_1.default.pow(10, 10);
function fund(smartTokens, reserveBalance, smartSupply) {
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_DOWN });
const smartTokensN = new decimal_js_1.default(Number(smartTokens.amount));
const reserveBalanceN = new decimal_js_1.default(Number(reserveBalance.amount));
const smartSupplyN = new decimal_js_1.default(Number(smartSupply.amount));
const cost = smartTokensN.div(smartSupplyN).times(reserveBalanceN);
return new eos_common_1.Asset(cost
.times(Math.pow(10, reserveBalance.symbol.precision()))
.toDecimalPlaces(0, decimal_js_1.default.ROUND_DOWN)
.toNumber(), reserveBalance.symbol);
}
exports.fund = fund;
function calculateFundReturn(reserveTokens, reserveBalance, smartSupply) {
decimal_js_1.default.set({ precision: 15, rounding: decimal_js_1.default.ROUND_DOWN });
const reserveTokensN = new decimal_js_1.default(Number(reserveTokens.amount)).times(bigNumber);
const reserveBalanceN = new decimal_js_1.default(Number(reserveBalance.amount)).times(bigNumber);
const smartSupplyN = new decimal_js_1.default(Number(smartSupply.amount)).times(bigNumber);
const one = new decimal_js_1.default(1);
// y(s+1) + 1 / r
const reward = reserveTokensN
.times(smartSupplyN.plus(one))
.plus(one)
.div(reserveBalanceN);
return new eos_common_1.Asset(reward
.times(Math.pow(10, smartSupply.symbol.precision()))
.div(bigNumber)
.toDecimalPlaces(0, decimal_js_1.default.ROUND_DOWN)
.toNumber(), smartSupply.symbol);
}
exports.calculateFundReturn = calculateFundReturn;
//# sourceMappingURL=index.js.map