UNPKG

bitcore-wallet-service

Version:
296 lines 10.5 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.SolChain = void 0; const crypto_wallet_core_1 = require("crypto-wallet-core"); const lodash_1 = __importDefault(require("lodash")); const defaults_1 = require("../../common/defaults"); const errordefinitions_1 = require("../../errors/errordefinitions"); const logger_1 = __importDefault(require("../../logger")); class SolChain { constructor() { this.chain = 'SOL'; } convertBitcoreBalance(bitcoreBalance, locked) { const { unconfirmed, confirmed, balance } = bitcoreBalance; const convertedBalance = { totalAmount: balance, totalConfirmedAmount: confirmed, lockedAmount: locked, lockedConfirmedAmount: locked, availableAmount: balance - locked, availableConfirmedAmount: confirmed - locked, byAddress: [] }; return convertedBalance; } getWalletBalance(server, wallet, opts, cb) { const bc = server._getBlockchainExplorer(wallet.chain || wallet.coin, wallet.network); if (opts.tokenAddress) { wallet.tokenAddress = opts.tokenAddress; } bc.getBalance(wallet, (err, balance) => { if (err) { return cb(err); } server.getPendingTxs(opts, (err, txps) => { if (err) return cb(err); const { fees, amounts } = txps.reduce((acc, txp) => { if (!opts.tokenAddress) { acc.fees += txp.fee || 0; } if (!(txp.tokenAddress && !opts.tokenAddress)) { acc.amounts += txp.amount; } return acc; }, { fees: 0, amounts: 0 }); const lockedSum = (amounts + fees) || 0; const convertedBalance = this.convertBitcoreBalance(balance, lockedSum); server.storage.fetchAddresses(server.walletId, (err, addresses) => { if (err) return cb(err); if (addresses.length > 0) { const byAddress = [ { address: addresses[0].address, path: addresses[0].path, amount: convertedBalance.totalAmount } ]; convertedBalance.byAddress = byAddress; } return cb(null, convertedBalance); }); }); }); } getFee(server, wallet, opts) { return new Promise(resolve => { const numSignatures = opts.signatures || 1; return resolve({ fee: 5000 * numSignatures }); }); } getBitcoreTx(txp, opts = { signed: true }) { const { data, outputs, payProUrl, tokenAddress, isTokenSwap, multiTx } = txp; if (multiTx) { throw errordefinitions_1.Errors.MULTI_TX_UNSUPPORTED; } const isSPL = tokenAddress && !payProUrl && !isTokenSwap; const chain = isSPL ? `${this.chain}SPL` : this.chain; const recipients = outputs.map(output => { return { amount: output.amount, address: output.toAddress, data: output.data }; }); if (data) { recipients[0].data = data; } const unsignedTxs = []; for (let index = 0; index < recipients.length; index++) { let params = { ...recipients[index], recipients: [recipients[index]] }; unsignedTxs.push(crypto_wallet_core_1.Transactions.create({ ...txp, chain, ...params })); } const tx = { uncheckedSerialize: () => unsignedTxs, txid: () => txp.txid, toObject: () => { let ret = lodash_1.default.clone(txp); ret.outputs[0].satoshis = ret.outputs[0].amount; return ret; }, getFee: () => { return txp.fee; }, getChangeOutput: () => null }; if (opts.signed) { const sigs = txp.getCurrentSignatures(); for (const x of sigs) { this.addSignaturesToBitcoreTx(tx, txp.inputs, txp.inputPaths, x.signatures, x.xpub); } } return tx; } addSignaturesToBitcoreTx(tx, inputs, inputPaths, signatures, xpub) { if (signatures.length === 0) { throw new Error('Signatures Required'); } const unsignedTxs = tx.uncheckedSerialize(); const signedTxs = []; for (let index = 0; index < signatures.length; index++) { const signed = crypto_wallet_core_1.Transactions.applySignature({ chain: this.chain, tx: unsignedTxs[index], signature: signatures[index] }); signedTxs.push(signed); tx.id = crypto_wallet_core_1.Transactions.getHash({ tx: signed, chain: this.chain }); } tx.uncheckedSerialize = () => signedTxs; } getTransactionCount(server, wallet, from) { return new Promise((resolve, reject) => { server._getTransactionCount(wallet, from, (err, count) => { if (err) return reject(err); return resolve(count); }); }); } getWalletSendMaxInfo(server, wallet, opts, cb) { server.getBalance({}, (err, balance) => { if (err) return cb(err); const { availableAmount } = balance; const sigs = opts.signatures || 1; let fee = sigs * 5000; return cb(null, { utxosBelowFee: 0, amountBelowFee: 0, amount: availableAmount - fee, feePerKb: opts.feePerKb, fee }); }); } checkValidTxAmount(output) { try { if (output.amount == null || output.amount < 0 || isNaN(output.amount) || crypto_wallet_core_1.Web3.utils.toBN(BigInt(output.amount).toString()).toString() !== BigInt(output.amount).toString()) { logger_1.default.warn('output.amount is not a valid value: ' + output.amount); return false; } return true; } catch (err) { logger_1.default.warn(`Invalid output amount (${output.amount}) in checkValidTxAmount: $o`, err); return false; } } checkTx(txp) { try { const tx = this.getBitcoreTx(txp); } catch (ex) { logger_1.default.debug('Error building Bitcore transaction: %o', ex); return ex; } return null; } selectTxInputs(server, txp, wallet, _opts, cb) { server.getBalance({ wallet }, (err, balance) => { if (err) return cb(err); const { totalAmount, availableAmount } = balance; const minRentException = defaults_1.Defaults.MIN_SOL_BALANCE; if (totalAmount - minRentException < txp.getTotalAmount()) { return cb(errordefinitions_1.Errors.INSUFFICIENT_FUNDS); } else if (availableAmount < txp.getTotalAmount()) { return cb(errordefinitions_1.Errors.LOCKED_FUNDS); } else { return cb(this.checkTx(txp)); } }); } validateAddress(wallet, inaddr, opts) { const chain = this.chain.toLowerCase(); const isValidTo = crypto_wallet_core_1.Validation.validateAddress(chain, wallet.network, inaddr); if (!isValidTo) { throw errordefinitions_1.Errors.INVALID_ADDRESS; } const isValidFrom = crypto_wallet_core_1.Validation.validateAddress(chain, wallet.network, opts.from); if (!isValidFrom) { throw errordefinitions_1.Errors.INVALID_ADDRESS; } return; } addressFromStorageTransform(network, address) { if (network != 'livenet') { const x = address.address.indexOf(':' + network); if (x >= 0) { address.address = address.address.substr(0, x); } } } addressToStorageTransform(network, address) { if (network != 'livenet') address.address += ':' + network; } getMinimumRent(server, wallet, cb) { const bc = server._getBlockchainExplorer(wallet.chain || wallet.coin, wallet.network); bc.getReserve((err, reserve) => { if (err) { return cb(err); } return cb(null, reserve); }); } refreshTxData(server, txp, _opts, cb) { if ((txp.blockHeight || txp.blockHash) && txp.isRepublishEnabled()) { server._getBlockchainHeight(txp.chain, txp.network, (err, height, hash) => { if (err) return cb(err); txp.blockHeight = height; txp.blockHash = hash; return cb(null, txp); }); } else { return cb(null, txp); } } getReserve(server, wallet, cb) { return cb(null, 0); } getSizeSafetyMargin() { return 0; } getInputSizeSafetyMargin() { return 0; } notifyConfirmations() { return false; } supportsMultisig() { return false; } isUTXOChain() { return false; } isSingleAddress() { return true; } getDustAmountValue() { return 0; } getChangeAddress() { } checkDust(_output, _opts) { } checkScriptOutput(output) { } onCoin(coin) { return null; } convertFeePerKb(p, feePerKb) { return [p, feePerKb]; } checkTxUTXOs(server, txp, opts, cb) { return cb(); } checkUtxos(opts) { } onTx(tx) { return null; } } exports.SolChain = SolChain; //# sourceMappingURL=index.js.map