Skip to content

Instantly share code, notes, and snippets.

@whiteyhat
Last active August 28, 2019 16:51
Show Gist options
  • Save whiteyhat/19bbc5ba2397bca1fc7116c10f15dad3 to your computer and use it in GitHub Desktop.
Save whiteyhat/19bbc5ba2397bca1fc7116c10f15dad3 to your computer and use it in GitHub Desktop.
File that runs on startup to subscribe to LN and ONCHAIN transactions
"use strict";
const User = use("App/Models/User");
const Invoice = use("App/Models/Invoice");
const Refill = use("App/Models/Refill");
const lnService = require("ln-service");
const { subscribeToInvoices } = require("ln-service");
const { subscribeToTransactions } = require("ln-service");
const { getChainTransactions } = require("ln-service");
const LndService = use("App/Services/LndService");
const Logger = use("Logger");
const Ws = use("Ws");
const Database = use("Database");
const axios = require("axios");
const localUrl = "http://localhost:3000";
// Create a channel to handle invoice requests
Ws.channel("invoice", "InvoiceController");
let suscriptionsLN;
let suscriptionsBTC;
let transactionsc;
const initWS = async () => {
try {
suscriptionsLN = subscribeToInvoices({ lnd: LndService.getLndInstance() });
suscriptionsBTC = subscribeToTransactions({ lnd: LndService.getLndInstance() });
setTimeout(async function() {
const { transactions } = await getChainTransactions({ lnd: LndService.getLndInstance() });
transactionsc = transactions;
}, 800);
} catch (error) {
console.log(error)
}
// Since BTCPay Server closes WS every 90 seconds it must be looped
try {
// Instantiate LN daemon
try {
suscriptionsLN.on("error", async err => {
// recursive call
try {
await initWS();
} catch (err) {
Logger.error(err);
}
});
} catch (error) {
Logger.error(error)
}
try {
suscriptionsBTC.on("error", async err => {
// recursive call
try {
await initWS();
} catch (err) {
Logger.error(err);
}
});
} catch (error) {
Logger.error(error)
}
try {
// When a LN invoice is created
suscriptionsLN.on("invoice_updated", async invoiceSubscribed => {
// If invoice is paid
if (invoiceSubscribed.is_confirmed) {
try {
const invoice = await Invoice.findBy(
"invoiceId",
invoiceSubscribed.id
);
const socketId = `invoice#${invoice.socketId}`;
setTimeout(async function(){
if (!invoice.paid) {
invoice.is_paid = true;
await invoice.save();
console.log(invoiceSubscribed.description);
if (invoiceSubscribed.description.includes("Refill APItoshi")) {
await Refill.create({ user_id: invoice.user_id, invoice_id: invoice.id, tokens: invoiceSubscribed.tokens})
}
const { data } = await axios({
method: "post",
url: localUrl + "/pay/" + invoiceSubscribed.id
});
return Ws.getChannel("invoice").topic("invoice").emitTo("invoicePaid",{ valid: true, type: "success", msg: "Payment confirmed" },[socketId]);
}
}, 800);
} catch (error) {
Logger.error(error);
}
}else {
Logger.notice('Invoice created for: ' + invoiceSubscribed.description)
}
});
} catch (error) {
Logger.error(error)
}
try {
// When a BTC on-chain invoice is created
suscriptionsBTC.on("chain_transaction", async onchainTx => {
// If invoice is paid
if (onchainTx.is_confirmed) {
const txs = transactionsc.transactions;
const tx = txs.find(x => x.id === onchainTx.id);
if (!tx) {
throw new Error("Transaction provided has not been found");
}
const invoice = await Invoice.findBy("wallet", tx.output_addresses[0]);
const socketId = `invoice#${invoice.socketId}`;
if (!invoice.paid) {
setTimeout(async function(){
invoice.is_paid = true;
await invoice.save();
const { data } = await axios({
method: "post",
url: localUrl + "/pay/" + onchainTx.id
});
Ws.getChannel("invoice").topic("invoice").emitTo("invoicePaid",{valid: true,type: "success",msg: "Payment confirmed",success_url: data},[socketId])
}, 800)
}
}
});
} catch (error) {
Logger.error(error)
}
} catch (error) {
Logger.error(error);
}
};
// Since BTCPay Server closes WS every 90 seconds it must be looped
try {
initWS();
} catch (error) {
console.log(error)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment