From 427c896f42e8fff18f41531b5643e5fecf21d618 Mon Sep 17 00:00:00 2001 From: Daniel Lugo Date: Wed, 13 Jan 2021 17:34:38 -0400 Subject: [PATCH] new "addInvoice()" --- src/routes.js | 82 ++++++++++---------------------- utils/lightningServices/types.ts | 28 +++++++++++ utils/lightningServices/v2.js | 37 +++++++++++++- 3 files changed, 89 insertions(+), 58 deletions(-) diff --git a/src/routes.js b/src/routes.js index 9697d46d..e38e0afa 100644 --- a/src/routes.js +++ b/src/routes.js @@ -1709,64 +1709,32 @@ module.exports = async ( }) // addinvoice - app.post('/api/lnd/addinvoice', (req, res) => { - const { lightning } = LightningServices.services - const invoiceRequest = { memo: req.body.memo, private: true } - if (req.body.value) { - invoiceRequest.value = req.body.value - } - if (req.body.expiry) { - invoiceRequest.expiry = req.body.expiry - } - lightning.addInvoice(invoiceRequest, async (err, newInvoice) => { - if (err) { - logger.debug('AddInvoice Error:', err) - const health = await checkHealth() - if (health.LNDStatus.success) { - res.status(400).json({ - field: 'addInvoice', - errorMessage: sanitizeLNDError(err.message) - }) - } else { - res.status(500) - res.json({ errorMessage: 'LND is down' }) + app.post('/api/lnd/addinvoice', async (req, res) => { + const { expiry, value, memo } = req.body + const addInvoiceRes = await LV2.addInvoice(value, memo, true, expiry) + + if (value) { + const channelsList = await LV2.listChannels({ active_only: true }) + let remoteBalance = Big(0) + channelsList.forEach(element => { + const remB = Big(element.remote_balance) + if (remB.gt(remoteBalance)) { + remoteBalance = remB } - return err - } - logger.debug('AddInvoice:', newInvoice) - if (req.body.value) { - logger.debug('AddInvoice liquidity check:') - lightning.listChannels({ active_only: true }, async (err, response) => { - if (err) { - logger.debug('ListChannels Error:', err) - const health = await checkHealth() - if (health.LNDStatus.success) { - res.status(400).json({ - field: 'listChannels', - errorMessage: sanitizeLNDError(err.message) - }) - } else { - res.status(500) - res.json({ errorMessage: 'LND is down' }) - } - } - logger.debug('ListChannels:', response) - const channelsList = response.channels - let remoteBalance = Big(0) - channelsList.forEach(element => { - const remB = Big(element.remote_balance) - if (remB.gt(remoteBalance)) { - remoteBalance = remB - } - }) - newInvoice.liquidityCheck = remoteBalance > req.body.value - //newInvoice.remoteBalance = remoteBalance - res.json(newInvoice) - }) - } else { - res.json(newInvoice) - } - }) + }) + + addInvoiceRes.liquidityCheck = remoteBalance > value + //newInvoice.remoteBalance = remoteBalance + } + + try { + return res.json(addInvoiceRes) + } catch (e) { + console.log(e) + return res.status(500).json({ + errorMessage: e.message + }) + } }) // signmessage diff --git a/utils/lightningServices/types.ts b/utils/lightningServices/types.ts index c390d545..ca0d034f 100644 --- a/utils/lightningServices/types.ts +++ b/utils/lightningServices/types.ts @@ -166,3 +166,31 @@ export interface PendingChannelsRes { */ waiting_close_channels: Common.WaitingCloseChannel[] } + +/** + * https://github.com/lightningnetwork/lnd/blob/daf7c8a85420fc67fffa18fa5f7d08c2040946e4/lnrpc/rpc.proto#L2948 + */ +export interface AddInvoiceRes { + /** + * + */ + r_hash: Common.Bytes + /** + * A bare-bones invoice for a payment within the Lightning Network. With the + * details of the invoice, the sender has all the data necessary to send a + * payment to the recipient. + */ + payment_request: string + /** + * The "add" index of this invoice. Each newly created invoice will increment + * this index making it monotonically increasing. Callers to the + * SubscribeInvoices call can use this to instantly get notified of all added + * invoices with an add_index greater than this one. + */ + add_index: string + /** + * The payment address of the generated invoice. This value should be used in + * all payments for this invoice as we require it for end to end security. + */ + payment_addr: Common.Bytes +} diff --git a/utils/lightningServices/v2.js b/utils/lightningServices/v2.js index 07c5574a..b933c63b 100644 --- a/utils/lightningServices/v2.js +++ b/utils/lightningServices/v2.js @@ -537,6 +537,40 @@ const pendingChannels = () => }) }) +/** + * @typedef {import('./types').AddInvoiceRes} AddInvoiceRes + */ +/** + * https://api.lightning.community/#addinvoice + * @param {number} value + * @param {string=} memo + * @param {boolean=} confidential Alias for `private`. + * @param {number=} expiry + * @returns {Promise} + */ +const addInvoice = (value, memo = '', confidential = true, expiry = 180) => + Common.makePromise((res, rej) => { + const { lightning } = lightningServices.getServices() + + lightning.addInvoice( + { + value, + memo, + private: confidential, + expiry + }, + (err, resp) => { + if (err) { + rej(new Error(err.message)) + } else { + // Needs cast because typescript refuses to assign Record + // to an actual object :shrugs + res(/** @type {AddInvoiceRes} */ (resp)) + } + } + ) + }) + module.exports = { sendPaymentV2Keysend, sendPaymentV2Invoice, @@ -547,5 +581,6 @@ module.exports = { listChannels, getChanInfo, listPeers, - pendingChannels + pendingChannels, + addInvoice }