www/listeners/monero.js

76 lines
2.5 KiB
JavaScript

'use strict'
require('dotenv').config()
const formatUSD = (v) => v.toLocaleString(undefined, {
style: 'currency', currency: 'USD' })
const fs = require('fs').promises
const axios = require('axios')
const ORDERS_DIR = `${__dirname}/../orders`
// Monero price
let XMR_PRICE
const getXmrPrice = async () => {
let res; try {
//res = await axios('https://localmonero.co/web/ticker?currencyCode=USD')
res = await axios('https://api.coingecko.com/api/v3/simple/price?ids=monero&vs_currencies=usd')
} catch (err) { return console.error(`Failed to fetch CoinGecko price: ${err}`) }
console.log(`Monero is now worth ${formatUSD(res.data.monero.usd)}`)
if (res.data.monero.usd)
return XMR_PRICE = Number(res.data.monero.usd)
else return
}; getXmrPrice()
setInterval(getXmrPrice,1000*Number(process.env.MONERO_PRICECHECK_SEC))
const xmrToUsd = (xmr) => Number(xmr * XMR_PRICE)
const xmrPaidCheck = async (order) => {
if (order.paidDate!=null) return clearInterval(interval)
console.log(`Checking if order ${order.id} (${order.totalxmr} XMR) is paid`)
// Get status from MoneroPay
let res; try {
res = await axios.get(`${process.env.MONEROPAY_URL}/receive/${order.xmr_address}`)
} catch (err) {
return console.error(`Failed to get update about xmr address ${order.xmr_address}\n${err}`)
}
// Throw hook if paid
if (res.data.amount!=null) if (res.data.amount.expected<=res.data.amount.covered.unlocked && order.paidDate==null) {
console.log(`Order ${order.id} has been paid with ${res.data.amount.expected/1000000000000} XMR`)
// Save payment data to order
order.paidDate = new Date()
order.xmr_txs = res.data.transactions.map((tx) => {
tx.fee_usd = xmrToUsd(tx.fee)
})
const orderFile = `${ORDERS_DIR}/${order.id}.json`
try {
console.log(JSON.stringify(order,null,2))
await fs.writeFile(orderFile, JSON.stringify(order,null,2))
} catch (err) {
console.error(`Failed to write paidDate to ${orderFile}:\n${err}`)
}
// Email customer
require('../hooks/email-customer')(order)
// Ntfy sales team
require('../hooks/ntfy-sales')(order)
// Email sales team
require('../hooks/email-sales')(order)
// Remove single products from store
require('../hooks/remove-sid')(order)
// Remove this listener
clearInterval(interval)
}
}
let interval
module.exports = (order) => {
if (order.paymentMethod!=='XMR')
return console.log(`Invalid paymentMethod: ${order.paymentMethod}`)
interval = setInterval(()=>xmrPaidCheck(order), 1000*process.env.MONERO_PRICECHECK_SEC)
}