From acb06712228e3387b355503b39115c1afad45bf3 Mon Sep 17 00:00:00 2001 From: naftalimurgor Date: Wed, 25 Jan 2023 11:36:45 +0300 Subject: [PATCH 1/2] update Docker config --- docker/Dockerfile | 32 +++++++++++++++++++++++--------- 1 file changed, 23 insertions(+), 9 deletions(-) diff --git a/docker/Dockerfile b/docker/Dockerfile index 1f4bdfd..1c0fe7a 100644 --- a/docker/Dockerfile +++ b/docker/Dockerfile @@ -1,15 +1,29 @@ -FROM debian:bullseye-slim +FROM ubuntu:20.04 as builder -RUN apt-get update -y \ - && apt-get install curl ca-certificates apt-transport-https bash perl -y \ - && apt-get clean +ARG VERSION=0.1.9 -RUN curl -L "http://security.ubuntu.com/ubuntu/pool/main/p/perl/perl-modules-5.30_5.30.0-9ubuntu0.2_all.deb" -o "/var/tmp/perl-modules.deb" \ - && curl -L "https://github.com/BitgesellOfficial/bitgesell/releases/download/0.1.7/bitgesell_0.1.7_amd64.deb" -o "/var/tmp/bitgesell.deb" \ - && dpkg -i "/var/tmp/perl-modules.deb" \ - && dpkg -i "/var/tmp/bitgesell.deb" \ +RUN apt update \ + && apt install -y --no-install-recommends \ + libatomic1 \ + wget \ + ca-certificates \ + apt-transport-https + +RUN cd /tmp/ \ + && wget https://github.com/BitgesellOfficial/bitgesell/releases/download/${VERSION}/bitgesell_${VERSION}_amd64.deb \ + && wget http://ports.ubuntu.com/pool/main/p/perl/perl-modules-5.30_5.30.0-9build1_all.deb \ + && dpkg -i perl-modules-5.30_5.30.0-9build1_all.deb \ + && dpkg -i bitgesell_${VERSION}_amd64.deb \ + && apt-get install -y -f \ + && apt clean && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* + +RUN cd /tmp/ \ + && wget https://github.com/BitgesellOfficial/bitgesell/releases/download/${VERSION}/bitgesell_${VERSION}_amd64.deb \ + && wget http://ports.ubuntu.com/pool/main/p/perl/perl-modules-5.30_5.30.0-9build1_all.deb \ + && dpkg -i perl-modules-5.30_5.30.0-9build1_all.deb \ + && dpkg -i bitgesell_${VERSION}_amd64.deb \ && apt-get install -y -f \ - && rm -rf "/var/tmp/*" + && apt clean && rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* WORKDIR "/root/.BGL" From d6674d710e1b46fb006240741a0f50f5a707d629 Mon Sep 17 00:00:00 2001 From: naftalimurgor Date: Wed, 25 Jan 2023 15:31:29 +0300 Subject: [PATCH 2/2] reftactor: add file-system level logging to service ( #21 #22 ) --- app/src/utils/index.js | 37 ++++++++++++--------- service/package.json | 3 +- service/src/controllers/SubmitController.js | 13 ++++++++ service/src/modules/bsc.js | 20 +++++++---- service/src/modules/chores.js | 21 ++++++++++++ service/src/modules/rpc.js | 23 +++++++++++-- service/src/utils/logger.js | 29 ++++++++++++++++ 7 files changed, 121 insertions(+), 25 deletions(-) create mode 100644 service/src/utils/logger.js diff --git a/app/src/utils/index.js b/app/src/utils/index.js index ef216b3..3c3996c 100644 --- a/app/src/utils/index.js +++ b/app/src/utils/index.js @@ -1,20 +1,24 @@ -import {isTest, serviceUrl} from './config' +import { isTest, serviceUrl } from './config' -export const url = path => serviceUrl + path +export const url = (path) => serviceUrl + path -export const fetcher = url => fetch(url).then(res => res.json()) +export const fetcher = (url) => fetch(url).then((res) => res.json()) export const post = async (url, data) => { - const response = await fetch(url, { - method: 'POST', - mode: 'cors', - cache: 'no-cache', - headers: { - 'Content-Type': 'application/json', - }, - body: JSON.stringify(data), - }) - return response.json() + try { + const response = await fetch(url, { + method: 'POST', + mode: 'cors', + cache: 'no-cache', + headers: { + 'Content-Type': 'application/json', + }, + body: JSON.stringify(data), + }) + return await response.json() + } catch (error) { + return error.message + } } export function chainLabel(chainId) { @@ -32,10 +36,13 @@ export function chainLabel(chainId) { } export function isChainValid(chainId) { - return isTest ? [3, 97, '0x3', '0x61'].includes(chainId) : [1, 56, '0x1', '0x38'].includes(chainId) + return isTest + ? [3, 97, '0x3', '0x61'].includes(chainId) + : [1, 56, '0x1', '0x38'].includes(chainId) } -export const isChainBsc = chainId => (typeof chainId == 'string' ? ['0x38', '0x61'] : [56, 97]).includes(chainId) +export const isChainBsc = (chainId) => + (typeof chainId == 'string' ? ['0x38', '0x61'] : [56, 97]).includes(chainId) let contracts export async function getTokenAddress(chainId) { diff --git a/service/package.json b/service/package.json index 50dd1f1..058e21a 100644 --- a/service/package.json +++ b/service/package.json @@ -22,7 +22,8 @@ "ethereumjs-tx": "^2.1.2", "express": "^4.17.1", "mongoose": "^5.12.10", - "web3": "^1.3.6" + "web3": "^1.3.6", + "winston": "^3.8.2" }, "devDependencies": { "eslint": "^8.12.0", diff --git a/service/src/controllers/SubmitController.js b/service/src/controllers/SubmitController.js index 5d4795b..dcbe933 100644 --- a/service/src/controllers/SubmitController.js +++ b/service/src/controllers/SubmitController.js @@ -2,6 +2,7 @@ import Transfer from "../models/Transfer.js"; import { RPC, Eth, Bsc } from "../modules/index.js"; import { bsc, eth, feePercentage } from "../utils/config.js"; import { isValidBglAddress, isValidEthAddress, sha3 } from "../utils/index.js"; +import { logger } from "../utils/logger.js"; export const bglToWbgl = async (req, res) => { const data = req.body; @@ -22,6 +23,7 @@ export const bglToWbgl = async (req, res) => { chain, to: data.address, }).exec(); + if (!transfer) { const bglAddress = await RPC.createAddress(); transfer = new Transfer({ @@ -32,6 +34,7 @@ export const bglToWbgl = async (req, res) => { to: data.address, }); } + transfer.markModified("type"); await transfer.save(); @@ -42,8 +45,11 @@ export const bglToWbgl = async (req, res) => { balance: await Chain.getWBGLBalance(), feePercentage: feePercentage, }); + } catch (e) { console.error(`Error: couldn't reach either RPC server or mongodb `, e); + logger.error(`Error: couldn't reach either RPC server or mongodb `, e); + res.status(400).json({ status: "error", message: "Network is likely to be down.", @@ -130,6 +136,7 @@ export const wbglToBgl = async (req, res) => { }); } catch (e) { console.error(`Error: network related error `, e); + logger.error(`Error: network related error `, e); res.status(400).json({ status: "error", message: "Network is likely to be down.", @@ -137,3 +144,9 @@ export const wbglToBgl = async (req, res) => { return; } }; + + +// Borrow from: +// - coinbase +// - Binance bridge +// - base off issues \ No newline at end of file diff --git a/service/src/modules/bsc.js b/service/src/modules/bsc.js index 36f1a7d..62e4b49 100644 --- a/service/src/modules/bsc.js +++ b/service/src/modules/bsc.js @@ -4,17 +4,25 @@ import Web3Base from "./web3.js"; class Bsc extends Web3Base { async getNetworkId() { - if (!this.networkId) { - this.networkId = await this.web3.eth.net.getId(); + try { + if (!this.networkId) { + this.networkId = await this.web3.eth.net.getId(); + } + return this.networkId; + } catch (error) { + return null; } - return this.networkId; } async getChainId() { - if (!this.chainId) { - this.chainId = await this.web3.eth.getChainId(); + try { + if (!this.chainId) { + this.chainId = await this.web3.eth.getChainId(); + } + return this.chainId; + } catch (error) { + return null } - return this.chainId; } async transactionOpts() { diff --git a/service/src/modules/chores.js b/service/src/modules/chores.js index 30de7d9..480daf2 100644 --- a/service/src/modules/chores.js +++ b/service/src/modules/chores.js @@ -3,6 +3,7 @@ import { Data, RPC, Eth, Bsc } from "./index.js"; import Transaction from "../models/Transaction.js"; import Transfer from "../models/Transfer.js"; import Conversion from "../models/Conversion.js"; +import {logger} from "../utils/logger.js" let ethNonce = 0; let bscNonce = 0; @@ -36,6 +37,11 @@ async function returnBGL(conversion, address) { conversion.returnTxid = await RPC.send(address, conversion.amount); await conversion.save(); } catch (e) { + logger.error( + `Error returning BGL to ${address}, conversion ID: ${conversion._id}.`, + e, + ); + console.error( `Error returning BGL to ${address}, conversion ID: ${conversion._id}.`, e, @@ -59,6 +65,10 @@ async function returnWBGL(Chain, conversion, address) { `Error returning WBGL (${Chain.id}) to ${address}, conversion ID: ${conversion._id}.`, e, ); + logger.error( + `Error returning WBGL (${Chain.id}) to ${address}, conversion ID: ${conversion._id}.`, + e, + ); conversion.status = "error"; await conversion.save(); } @@ -156,6 +166,8 @@ async function checkBglTransactions() { await Data.set("lastBglBlockHash", result["lastblock"]); } catch (e) { console.error("Error: checkBglTransactions function failed. Check network"); + logger.error("Error: checkBglTransactions function failed. Check network"); + } setTimeout(checkBglTransactions, 60000); @@ -236,6 +248,11 @@ export async function checkWbglTransfers(Chain = Eth, prefix = "Eth") { `Error sending ${sendAmount} BGL to ${transfer.to}`, e, ); + + logger.error( + `Error sending ${sendAmount} BGL to ${transfer.to}`, + e, + ); conversion.status = "error"; await conversion.save(); @@ -248,6 +265,7 @@ export async function checkWbglTransfers(Chain = Eth, prefix = "Eth") { }); } catch (e) { console.error("Error: checkWbglTransfers function failed. Check network"); + logger.error("Error: checkWbglTransfers function failed. Check network"); } setTimeout(() => checkWbglTransfers(Chain, prefix), 60000); @@ -282,6 +300,9 @@ async function checkPendingConversions(Chain) { console.error( "Error: checkPendingConversions function failed. Check chain network or mongodb", ); + logger.error( + "Error: checkPendingConversions function failed. Check chain network or mongodb", + ); } setTimeout(() => checkPendingConversions(Chain), 60000); } diff --git a/service/src/modules/rpc.js b/service/src/modules/rpc.js index 99d14f0..a2b3b98 100644 --- a/service/src/modules/rpc.js +++ b/service/src/modules/rpc.js @@ -1,5 +1,6 @@ import Client from "bitcoin-core"; import { rpc, confirmations } from "../utils/config.js"; +import { logger } from "../utils/logger.js"; let client; @@ -31,19 +32,35 @@ export const listSinceBlock = async ( blockHash, confirmation = confirmations.bgl, ) => { + try { return await getClient().command( "listsinceblock", blockHash ? blockHash : undefined, confirmation, ); + } catch(error) { + console.error('Failed to list since block', e) + logger.error('Failed to list since block', e) + } }; export const getTransactionFromAddress = async (txid) => { + try { const rawTx = await getClient().command("getrawtransaction", txid, true); const vin = rawTx["vin"][0]; const txIn = await getClient().command("getrawtransaction", vin.txid, true); return txIn["vout"][vin["vout"]]["scriptPubKey"]["address"]; -}; + } catch (e) { + return null + } +} + +export const send = async (address, amount) => { + try { + await getClient().command("sendtoaddress", address, amount); -export const send = async (address, amount) => - await getClient().command("sendtoaddress", address, amount); + } catch (e) { + console.error('Failed to send', e) + logger.error(`Failed to send ${amount} to ${address}`, e) + } +} diff --git a/service/src/utils/logger.js b/service/src/utils/logger.js new file mode 100644 index 0000000..e26603d --- /dev/null +++ b/service/src/utils/logger.js @@ -0,0 +1,29 @@ +import winston from "winston" + +const options = { + file: { + level: "info", + filename: "./logs/service.log", + handleExceptions: true, + json: true, + maxsize: 5242880, // 5MB + maxFiles: 5, + colorize: false, + }, + console: { + level: "debug", + handleExceptions: true, + json: false, + colorize: true, + }, +} + +export const logger = winston.createLogger({ + levels: winston.config.npm.levels, + transports: [ + new winston.transports.File(options.file), + new winston.transports.Console(options.console), + ], + exitOnError: false, +}) +