fix(electrumx config): Passing electrum server info as env var

This commit is contained in:
Chris Troutner
2020-04-12 18:14:02 -07:00
parent 769fd5919f
commit 4eadea6d88
7 changed files with 86 additions and 131 deletions
-37
View File
@@ -1,37 +0,0 @@
/*
Config settings for working with an ElectrumX or Fulcrum server.
*/
const config = {
port: 8000,
electrum: {
application: 'bch-api',
version: '1.4.1',
confidence: 2,
distribution: 3,
// servers: [
// 'fulcrum.fountainhead.cash:50002',
// 'electrum.imaginary.cash:50002',
// 'bch.imaginary.cash:50002',
// 'electroncash.de:50002',
// 'electroncash.dk:50002',
// 'electron.jochen-hoenicke.de:51002'
// ]
serverUrl: 'fulcrum.fountainhead.cash',
serverPort: '50002'
},
ratelimit: {
windowMs: 1 * 60 * 1000,
max: 100
}
}
if (process.env.NETWORK === 'testnet') {
config.electrum.serverUrl = 'blackie.c3-soft.com'
config.electrum.serverPort = '60002'
// config.electrum.serverUrl = '192.168.0.6'
// config.electrum.serverPort = '50001'
}
module.exports = config
+1 -4
View File
@@ -2,11 +2,8 @@
Common configuration settings.
*/
const electrumxConfig = require('./electrumx')
const config = {
apiTokenSecret: process.env.TOKENSECRET ? process.env.TOKENSECRET : 'secret-jwt-token',
electrumx: electrumxConfig
apiTokenSecret: process.env.TOKENSECRET ? process.env.TOKENSECRET : 'secret-jwt-token'
}
module.exports = config
+28
View File
@@ -0,0 +1,28 @@
#!/bin/bash
# test
# Full node
export RPC_BASEURL=http://142.93.13.2:8332/
export RPC_USERNAME=bitcoin
export RPC_PASSWORD=password
export NETWORK=mainnet
# SLPDB
#export SLPDB_URL=https://slpdb.bitcoin.com/
#export SLPDB_URL=http://172.17.0.1:12300/
export SLPDB_URL=https://slpdb2.bchtest.net/
export SLPDB_PASS=owmvgnsksoapwhrnvu
# Blockbook Indexer
export BLOCKBOOK_URL=https://157.230.214.175:9131/
# Allow node.js to make network calls to https using self-signed certificate.
export NODE_TLS_REJECT_UNAUTHORIZED=0
export JWT_AUTH_SERVER=http://172.17.0.1:5001/
# Redis DB
export REDIS_PORT=6379
export REDIS_HOST=172.17.0.1
npm start
+1 -1
View File
@@ -16,7 +16,7 @@
"dev": "nodemon ./dist/app.js",
"test": "npm run lint && npm run test-v3",
"lint": "standard --env mocha --fix",
"test-v3": "export NETWORK=mainnet && nyc --reporter=text mocha --timeout 60000 test/v3/",
"test-v3": "export NETWORK=mainnet && nyc --reporter=text mocha --timeout 60000 test/v3/electrumx.js",
"test:temp": "export NETWORK=mainnet && mocha --timeout 25000 test/v3/blockchain.js",
"test:integration": "mocha test/v3/integration",
"coverage": "nyc report --reporter=text-lcov | coveralls",
+35 -26
View File
@@ -33,10 +33,10 @@ class Electrum {
_this.bitcore = bitcore
_this.electrumx = new ElectrumCash(
config.electrumx.electrum.application,
config.electrumx.electrum.version,
config.electrumx.electrum.serverUrl,
config.electrumx.electrum.serverPort
'bch-api',
'1.4.1',
process.env.FULCRUM_URL,
process.env.FULCRUM_PORT
)
_this.isReady = false
@@ -61,12 +61,12 @@ class Electrum {
// Set the connection flag.
_this.isReady = true
console.log(`...Successfully connected to ElectrumX server.`)
console.log('...Successfully connected to ElectrumX server.')
// console.log(`_this.isReady: ${_this.isReady}`)
return _this.isReady
} catch (err) {
console.log(`err: `, err)
console.log('err: ', err)
wlogger.error('Error in electrumx.js/connect(): ', err)
// throw err
}
@@ -118,11 +118,34 @@ class Electrum {
return res.json({ status: 'electrumx' })
}
async utxosFromElectrumx (address) {
// Returns a promise that resolves to UTXO data for an address. Expects input
// to be a cash address, and input validation to have already been done by
// calling function.
async _utxosFromElectrumx (address) {
try {
// Convert the address to a scripthash.
const scripthash = _this.addressToScripthash(address)
if (!_this.isReady) {
throw new Error(
'ElectrumX server connection is not ready. Call await connectToServer() first.'
)
}
// Query the utxos from the ElectrumX server.
const electrumResponse = await _this.electrumx.request(
'blockchain.scripthash.listunspent',
scripthash
)
// console.log(
// `electrumResponse: ${JSON.stringify(electrumResponse, null, 2)}`
// )
return electrumResponse
} catch (err) {
// Write out error to error log.
wlogger.error('Error in elecrumx.js/_utxosFromElectrumx().')
throw err
}
}
@@ -164,25 +187,11 @@ class Electrum {
})
}
wlogger.debug('Executing electrumx/getUtxos with this address: ', address)
wlogger.debug('Executing electrumx/getUtxos with this address: ', cashAddr)
// Convert the address to a scripthash.
const scripthash = _this.addressToScripthash(cashAddr)
if (!_this.isReady) {
throw new Error(
'ElectrumX server connection is not ready. Call await connectToServer() first.'
)
}
// Query the utxos from the ElectrumX server.
var electrumResponse = await _this.electrumx.request(
'blockchain.scripthash.listunspent',
scripthash
)
// console.log(
// `electrumResponse: ${JSON.stringify(electrumResponse, null, 2)}`
// )
// Get data from ElectrumX server.
const electrumResponse = await _this._utxosFromElectrumx(cashAddr)
console.log(`electrumResponse: ${JSON.stringify(electrumResponse, null, 2)}`)
// Pass the error message if ElectrumX reports an error.
if (Object.prototype.hasOwnProperty.call(electrumResponse, 'code')) {
+6
View File
@@ -14,4 +14,10 @@ export BLOCKBOOK_URL=https://<Blockbook IP>:9131/
# Allow node.js to make network calls to https using self-signed certificate.
export NODE_TLS_REJECT_UNAUTHORIZED=0
# Mainnet Fulcrum / ElectrumX
export FULCRUM_URL=192.168.0.6
export FULCRUM_PORT=50002
export TOKENSECRET=somelongpassword
npm start
+15 -63
View File
@@ -135,8 +135,7 @@ describe('#ElectrumX Router', () => {
})
it('should throw an error for an invalid address', async () => {
req.params.address =
'02v05l7qs5s24srqju498qu55dwuj0cx5ehjm2c'
req.params.address = '02v05l7qs5s24srqju498qu55dwuj0cx5ehjm2c'
const result = await electrumxRoute.getUtxos(req, res)
// console.log(`result: ${util.inspect(result)}`)
@@ -151,8 +150,7 @@ describe('#ElectrumX Router', () => {
})
it('should detect a network mismatch', async () => {
req.params.address =
'bchtest:qq89kjkeqz9mngp8kl3dpmu43y2wztdjqu500gn4c4'
req.params.address = 'bchtest:qq89kjkeqz9mngp8kl3dpmu43y2wztdjqu500gn4c4'
const result = await electrumxRoute.getUtxos(req, res)
// console.log(`result: ${util.inspect(result)}`)
@@ -165,68 +163,22 @@ describe('#ElectrumX Router', () => {
assert.property(result, 'success')
assert.equal(result.success, false)
})
})
// it('should throw 500 when network issues', async () => {
// const savedUrl = process.env.BLOCKBOOK_URL
//
// try {
// req.params.address = 'qzs02v05l7qs5s24srqju498qu55dwuj0cx5ehjm2c'
//
// // Switch the Insight URL to something that will error out.
// process.env.BLOCKBOOK_URL = 'http://fakeurl/api/'
//
// const result = await blockbookRoute.balanceSingle(req, res)
//
// // Restore the saved URL.
// process.env.BLOCKBOOK_URL = savedUrl
//
// assert.equal(res.statusCode, 500, 'HTTP status code 500 expected.')
// assert.include(result.error, 'ENOTFOUND', 'Error message expected')
// } catch (err) {
// // Restore the saved URL.
// process.env.BLOCKBOOK_URL = savedUrl
// }
// })
describe('#_utxosFromElectrumx', () => {
// Unit test only.
if (process.env.TEST === 'unit') {
it('should pass errors from ElectrumX to user', async () => {
req.params.address =
'bitcoincash:qrdka2205f4hyukutc2g0s6lykperc8nsu5u2ddpqf'
// it('returns proper error when downstream service stalls', async () => {
// req.params.address =
// 'bitcoincash:qrdka2205f4hyukutc2g0s6lykperc8nsu5u2ddpqf'
//
// // Mock the timeout error.
// sandbox.stub(blockbookRoute.axios, 'request').throws({
// code: 'ECONNABORTED'
// })
//
// const result = await blockbookRoute.balanceSingle(req, res)
// // console.log(`result: ${JSON.stringify(result, null, 2)}`)
//
// assert.isAbove(res.statusCode, 499, 'HTTP status code 503 expected.')
// assert.include(
// result.error,
// 'Could not communicate with full node',
// 'Error message expected'
// )
// })
electrumxRoute.isReady = true // Force flag.
// it('returns proper error when downstream service is down', async () => {
// req.params.address =
// 'bitcoincash:qrdka2205f4hyukutc2g0s6lykperc8nsu5u2ddpqf'
//
// // Mock the timeout error.
// sandbox.stub(blockbookRoute.axios, 'request').throws({
// code: 'ECONNREFUSED'
// })
//
// const result = await blockbookRoute.balanceSingle(req, res)
// // console.log(`result: ${JSON.stringify(result, null, 2)}`)
//
// assert.isAbove(res.statusCode, 499, 'HTTP status code 503 expected.')
// assert.include(
// result.error,
// 'Could not communicate with full node',
// 'Error message expected'
// )
// })
sandbox
.stub(electrumxRoute.electrumx, 'request')
.resolves(mockData.utxos)
})
}
it('should get balance for a single address', async () => {
req.params.address =