UNPKG

tokenlon-sdk

Version:

imToken Tokenlon API for node

182 lines 10.1 kB
"use strict"; var __assign = (this && this.__assign) || Object.assign || function(t) { for (var s, i = 1, n = arguments.length; i < n; i++) { s = arguments[i]; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p]; } return t; }; Object.defineProperty(exports, "__esModule", { value: true }); var _ = require("lodash"); var constants_1 = require("../constants"); var helper_1 = require("./helper"); var math_1 = require("./math"); var format_1 = require("./format"); var types_1 = require("../types"); var _0x_js_1 = require("0x.js"); var sign_1 = require("./sign"); var assert_1 = require("./assert"); var pair_1 = require("./pair"); // generate a dex order without salt by simple order exports.generateDexOrderWithoutSalt = function (params) { var simpleOrder = params.simpleOrder, pair = params.pair, config = params.config; var base = pair.base, quote = pair.quote; var side = simpleOrder.side, price = simpleOrder.price, amount = simpleOrder.amount, expirationUnixTimestampSec = simpleOrder.expirationUnixTimestampSec; var isBuy = side === 'BUY'; var baseTokenAmountUnit = amount; var quoteTokenAmountUnit = math_1.toBN(price).times(amount); return { maker: helper_1.lowerCase(config.wallet.address), taker: helper_1.lowerCase(constants_1.ETH_CONTRACT), makerTokenAmount: isBuy ? format_1.fromUnitToDecimalBN(quoteTokenAmountUnit, quote.decimal) : format_1.fromUnitToDecimalBN(baseTokenAmountUnit, base.decimal), takerTokenAmount: isBuy ? format_1.fromUnitToDecimalBN(baseTokenAmountUnit, base.decimal) : format_1.fromUnitToDecimalBN(quoteTokenAmountUnit, quote.decimal), makerTokenAddress: helper_1.lowerCase(isBuy ? quote.contractAddress : base.contractAddress), takerTokenAddress: helper_1.lowerCase(isBuy ? base.contractAddress : quote.contractAddress), // 智能合约上的判断 因此 expirationUnixTimestampSec 为必填项 未设置情况下设置到明年今日 // if(block.timestamp >= order.expirationTimestampInSec) { // LogError(uint8(Errors.ORDER_EXPIRED), order.orderHash); // return 0; // } expirationUnixTimestampSec: math_1.toBN(expirationUnixTimestampSec || helper_1.getTimestamp() + 86400 * 365), exchangeContractAddress: helper_1.lowerCase(config.zeroEx.exchangeContractAddress), feeRecipient: constants_1.FEE_RECIPIENT, // TODO setting fees makerFee: math_1.toBN(0), takerFee: math_1.toBN(0), }; }; // use 0x.js and privateKey's personal sign, to generate a dex order exports.getSignedOrder = function (orderWithoutSalt, config) { var order = __assign({}, orderWithoutSalt, { salt: _0x_js_1.ZeroEx.generatePseudoRandomSalt() }); var hash = _0x_js_1.ZeroEx.getOrderHashHex(order); return __assign({}, order, { ecSignature: sign_1.personalECSignHex(config.wallet.privateKey, hash) }); }; var translateValueHelper = function (obj, check, operate) { var result = {}; _.keys(obj).forEach(function (key) { var v = obj[key]; result[key] = check(v) ? operate(v) : v; }); return result; }; // translate a dex order with bigNumber to string exports.orderBNToString = function (order) { var result = {}; result = translateValueHelper(order, math_1.isBigNumber, function (v) { return v.toString(); }); return result; }; exports.orderStringToBN = function (order) { var result = {}; var check = function (v) { return _.isString(v) && !v.startsWith('0x'); }; result = translateValueHelper(order, check, math_1.toBN); return result; }; exports.getAmountTotal = function (params) { var order = params.order, pair = params.pair; var base = pair.base, quote = pair.quote, precision = pair.precision; var formatPrice = format_1.formatNumHelper(precision); var makerTokenAddress = order.makerTokenAddress, makerTokenAmount = order.makerTokenAmount, takerTokenAddress = order.takerTokenAddress, takerTokenAmount = order.takerTokenAmount; var isBuy = helper_1.helpCompareStr(base.contractAddress, takerTokenAddress) && helper_1.helpCompareStr(quote.contractAddress, makerTokenAddress); var baseTokenAmountBN = isBuy ? format_1.fromDecimalToUnit(takerTokenAmount, base.decimal) : format_1.fromDecimalToUnit(makerTokenAmount, base.decimal); var amountTotal = math_1.toBN(formatPrice(baseTokenAmountBN.toString(), false)).toNumber(); return amountTotal; }; // translate dex order to simple order, for us to check which order we want to fill exports.getSimpleOrder = function (params) { var order = params.order, pair = params.pair, amountRemaining = params.amountRemaining; var base = pair.base, quote = pair.quote, precision = pair.precision; var formatPrice = format_1.formatNumHelper(precision); var expirationUnixTimestampSec = order.expirationUnixTimestampSec, makerTokenAddress = order.makerTokenAddress, makerTokenAmount = order.makerTokenAmount, takerTokenAddress = order.takerTokenAddress, takerTokenAmount = order.takerTokenAmount; var isBuy = helper_1.helpCompareStr(base.contractAddress, takerTokenAddress) && helper_1.helpCompareStr(quote.contractAddress, makerTokenAddress); var side = isBuy ? 'BUY' : 'SELL'; var baseTokenAmountBN = isBuy ? format_1.fromDecimalToUnit(takerTokenAmount, base.decimal) : format_1.fromDecimalToUnit(makerTokenAmount, base.decimal); var quoteTokenAmountBN = isBuy ? format_1.fromDecimalToUnit(makerTokenAmount, quote.decimal) : format_1.fromDecimalToUnit(takerTokenAmount, quote.decimal); var amountRemainingBN = amountRemaining && math_1.toBN(amountRemaining).lt(baseTokenAmountBN) ? math_1.toBN(amountRemaining) : baseTokenAmountBN; var price = math_1.toBN(formatPrice(quoteTokenAmountBN.dividedBy(baseTokenAmountBN).toString(), false)).toNumber(); var amount = math_1.toBN(formatPrice(amountRemainingBN.toString(), false)).toNumber(); return { side: side, price: price, amount: amount, expirationUnixTimestampSec: math_1.toBN(expirationUnixTimestampSec).toNumber(), }; }; exports.getSimpleOrderWithBaseQuoteBySignedOrder = function (order, pairs) { var pair = pair_1.getPairBySignedOrder(order, pairs); var simpleOrder = exports.getSimpleOrder({ order: order, pair: pair, }); return __assign({ base: pair.base.symbol.toUpperCase(), quote: pair.quote.symbol.toUpperCase() }, simpleOrder); }; exports.translateOrderBookToSimple = function (params) { var orderbookItems = params.orderbookItems, pair = params.pair, wallet = params.wallet; return orderbookItems.map(function (item) { var amountRemaining = item.amountRemaining, payload = item.payload; return __assign({}, exports.getSimpleOrder({ pair: pair, order: payload, amountRemaining: amountRemaining, }), { amountTotal: exports.getAmountTotal({ pair: pair, order: payload }), isMaker: !!wallet && helper_1.helpCompareStr(wallet.address, payload.maker), rawOrder: JSON.stringify(payload) }); }); }; // fill order need to change side // if is buy, then maker token is weth, so we use quote decimal exports.getFillTakerTokenAmountBN = function (side, amount, price, pair) { return side === 'SELL' ? format_1.fromUnitToDecimalBN(amount, pair.base.decimal) : format_1.fromUnitToDecimalBN(math_1.toBN(amount).times(price).toNumber(), pair.quote.decimal); }; exports.getFillTakerTokenAmountBNByUpToOrders = function (side, amount, simpleOrders, pair) { if (side === 'SELL') { return format_1.fromUnitToDecimalBN(amount, pair.base.decimal); } var remainedAmountBN = math_1.toBN(amount); var takerTokenAmountBN = math_1.toBN(0); simpleOrders.some(function (so) { var orderPrice = so.price; var orderAmount = so.amount; // if base amount is too large, then set takerTokenAmount as orders quote amounts if (remainedAmountBN.gt(math_1.toBN(orderAmount))) { takerTokenAmountBN = takerTokenAmountBN.plus(exports.getFillTakerTokenAmountBN('BUY', orderAmount, orderPrice, pair)); remainedAmountBN = remainedAmountBN.minus(math_1.toBN(orderAmount)); // // if orders quote amount larger then base amount, then set takerTokenAmount as calculated amount } else { takerTokenAmountBN = takerTokenAmountBN.plus(exports.getFillTakerTokenAmountBN('BUY', remainedAmountBN, orderPrice, pair)); return true; } }); return takerTokenAmountBN; }; exports.getOrderFillRequest = function (params, pairs) { var rawOrder = params.rawOrder, price = params.price, amount = params.amount, side = params.side, base = params.base, quote = params.quote; assert_1.assert.isValidrawOrder(rawOrder); assert_1.assert.isValidBaseQuote(params, pairs); var order = JSON.parse(rawOrder); var isBuy = side === 'BUY'; var pair = pair_1.getPairByContractAddress(isBuy ? { base: order.makerTokenAddress, quote: order.takerTokenAddress, } : { base: order.takerTokenAddress, quote: order.makerTokenAddress, }, pairs); if (!helper_1.helpCompareStr(pair.base.symbol, base) || !helper_1.helpCompareStr(pair.quote.symbol, quote)) { throw helper_1.newError(types_1.TokenlonError.UnsupportedPair); } assert_1.assert.isValidSimpleOrder(params, pair.precision); var simpleOrder = exports.getSimpleOrder({ order: order, pair: pair, }); var formatPrice = format_1.formatNumHelper(pair.precision); if (formatPrice(simpleOrder.price, false) !== formatPrice(price, false)) { throw helper_1.newError(types_1.TokenlonError.InvalidPriceWithToBeFilledOrder); } var takerTokenAmountBN = exports.getFillTakerTokenAmountBN(side, amount, price, pair); return { signedOrder: exports.orderStringToBN(order), takerTokenFillAmount: takerTokenAmountBN, }; }; //# sourceMappingURL=dex.js.map