config: update configuration options for exec path
- config options for bitcoind to specify exec path of bitcoind - config options to connect to multiple bitcoind processes - systemd and upstart preferred methods to daemonize
This commit is contained in:
parent
5932b34a1f
commit
0f24dd5f49
|
@ -28,7 +28,6 @@ var errors = require('./errors');
|
|||
*
|
||||
* @param {Object} config - The configuration of the node
|
||||
* @param {Array} config.services - The array of services
|
||||
* @param {String} config.datadir - The directory for data (e.g. bitcoind datadir)
|
||||
* @param {Number} config.port - The HTTP port for services
|
||||
* @param {Boolean} config.https - Enable https
|
||||
* @param {Object} config.httpsOptions - Options for https
|
||||
|
@ -52,8 +51,6 @@ function Node(config) {
|
|||
$.checkArgument(Array.isArray(config.services));
|
||||
this._unloadedServices = config.services;
|
||||
}
|
||||
$.checkState(config.datadir, 'Node config expects "datadir"');
|
||||
this.datadir = config.datadir;
|
||||
this.port = config.port;
|
||||
this.https = config.https;
|
||||
this.httpsOptions = config.httpsOptions;
|
||||
|
|
|
@ -15,10 +15,15 @@ function getDefaultBaseConfig(options) {
|
|||
return {
|
||||
path: process.cwd(),
|
||||
config: {
|
||||
datadir: options.datadir || path.resolve(process.env.HOME, '.bitcoin'),
|
||||
network: options.network || 'livenet',
|
||||
port: 3001,
|
||||
services: ['bitcoind', 'db', 'address', 'web']
|
||||
services: ['bitcoind', 'web'],
|
||||
servicesConfig: {
|
||||
bitcoind: {
|
||||
datadir: options.datadir || path.resolve(process.env.HOME, '.bitcoin'),
|
||||
exec: path.resolve(__dirname, '../../dist/bitcoind')
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -24,17 +24,22 @@ function getDefaultConfig(options) {
|
|||
mkdirp.sync(defaultPath);
|
||||
}
|
||||
|
||||
var defaultServices = ['bitcoind', 'db', 'address', 'web'];
|
||||
var defaultServices = ['bitcoind', 'web'];
|
||||
if (options.additionalServices) {
|
||||
defaultServices = defaultServices.concat(options.additionalServices);
|
||||
}
|
||||
|
||||
if (!fs.existsSync(defaultConfigFile)) {
|
||||
var defaultConfig = {
|
||||
datadir: path.resolve(defaultPath, './data'),
|
||||
network: 'livenet',
|
||||
port: 3001,
|
||||
services: defaultServices
|
||||
services: defaultServices,
|
||||
servicesConfig: {
|
||||
bitcoind: {
|
||||
datadir: path.resolve(defaultPath, './data'),
|
||||
exec: path.resolve(__dirname, '../../dist/bitcoind')
|
||||
}
|
||||
}
|
||||
};
|
||||
fs.writeFileSync(defaultConfigFile, JSON.stringify(defaultConfig, null, 2));
|
||||
}
|
||||
|
|
|
@ -201,11 +201,6 @@ function start(options) {
|
|||
}
|
||||
|
||||
fullConfig.services = start.setupServices(require, servicesPath, options.config);
|
||||
fullConfig.datadir = path.resolve(options.path, options.config.datadir);
|
||||
|
||||
if (fullConfig.daemon) {
|
||||
start.spawnChildProcess(fullConfig.datadir, process);
|
||||
}
|
||||
|
||||
var node = new BitcoreNode(fullConfig);
|
||||
|
||||
|
@ -237,46 +232,9 @@ function start(options) {
|
|||
|
||||
}
|
||||
|
||||
/**
|
||||
* This function will fork the passed in process and exit the parent process
|
||||
* in order to daemonize the process. If there is already a daemon for this pid (process),
|
||||
* then the function just returns. Stdout and stderr both append to one file, 'bitcore-node.log'
|
||||
* located in the datadir.
|
||||
* @param {String} datadir - The data directory where the bitcoin blockchain and config live.
|
||||
* @param {Object} _process - The process that needs to fork a child and then, itself, exit.
|
||||
*/
|
||||
function spawnChildProcess(datadir, _process) {
|
||||
|
||||
if (_process.env.__bitcore_node) {
|
||||
return _process.pid;
|
||||
}
|
||||
|
||||
var args = [].concat(_process.argv);
|
||||
args.shift();
|
||||
var script = args.shift();
|
||||
var env = _process.env;
|
||||
var cwd = _process.cwd();
|
||||
env.__bitcore_node = true;
|
||||
|
||||
var stderr = fs.openSync(datadir + '/bitcore-node.log', 'a+');
|
||||
var stdout = stderr;
|
||||
|
||||
var cp_opt = {
|
||||
stdio: ['ignore', stdout, stderr],
|
||||
env: env,
|
||||
cwd: cwd,
|
||||
detached: true
|
||||
};
|
||||
|
||||
var child = child_process.spawn(_process.execPath, [script].concat(args), cp_opt);
|
||||
child.unref();
|
||||
return _process.exit();
|
||||
}
|
||||
|
||||
module.exports = start;
|
||||
module.exports.registerExitHandlers = registerExitHandlers;
|
||||
module.exports.exitHandler = exitHandler;
|
||||
module.exports.registerSyncHandlers = registerSyncHandlers;
|
||||
module.exports.setupServices = setupServices;
|
||||
module.exports.spawnChildProcess = spawnChildProcess;
|
||||
module.exports.cleanShutdown = cleanShutdown;
|
||||
|
|
|
@ -6,7 +6,6 @@ var spawn = require('child_process').spawn;
|
|||
var util = require('util');
|
||||
var mkdirp = require('mkdirp');
|
||||
var bitcore = require('bitcore-lib');
|
||||
var Address = bitcore.Address;
|
||||
var zmq = require('zmq');
|
||||
var async = require('async');
|
||||
var LRU = require('lru-cache');
|
||||
|
@ -27,12 +26,11 @@ var Transaction = require('../transaction');
|
|||
* @param {Node} options.node - A reference to the node
|
||||
*/
|
||||
function Bitcoin(options) {
|
||||
/* jshint maxstatements: 20 */
|
||||
if (!(this instanceof Bitcoin)) {
|
||||
return new Bitcoin(options);
|
||||
}
|
||||
|
||||
this._reindex = false;
|
||||
this._reindexWait = 1000;
|
||||
Service.call(this, options);
|
||||
|
||||
// caches valid until there is a new block
|
||||
|
@ -41,15 +39,32 @@ function Bitcoin(options) {
|
|||
this.balanceCache = LRU(50000);
|
||||
this.summaryCache = LRU(50000);
|
||||
|
||||
// caches valid indefinetly
|
||||
// caches valid indefinitely
|
||||
this.transactionCache = LRU(100000);
|
||||
this.transactionInfoCache = LRU(100000);
|
||||
this.blockCache = LRU(144);
|
||||
this.blockHeaderCache = LRU(288);
|
||||
this.zmqKnownTransactions = LRU(50);
|
||||
|
||||
this.options = options;
|
||||
|
||||
// bitcoind child process
|
||||
this.spawn = false;
|
||||
|
||||
// available bitcoind nodes
|
||||
this.nodes = [];
|
||||
this.nodesIndex = 0;
|
||||
Object.defineProperty(this, 'client', {
|
||||
get: function() {
|
||||
var client = this.nodes[this.nodesIndex].client;
|
||||
this.nodesIndex = (this.nodesIndex + 1) % this.nodes.length;
|
||||
return client;
|
||||
},
|
||||
enumerable: true,
|
||||
configurable: false
|
||||
});
|
||||
|
||||
$.checkState(this.node.datadir, 'Node is missing datadir property');
|
||||
}
|
||||
|
||||
util.inherits(Bitcoin, Service);
|
||||
|
||||
Bitcoin.dependencies = [];
|
||||
|
@ -77,15 +92,24 @@ Bitcoin.prototype.getAPIMethods = function() {
|
|||
return methods;
|
||||
};
|
||||
|
||||
Bitcoin.prototype._loadConfiguration = function() {
|
||||
Bitcoin.prototype._loadSpawnConfiguration = function(node) {
|
||||
/* jshint maxstatements: 25 */
|
||||
|
||||
$.checkArgument(this.node.datadir, 'Please specify "datadir" in configuration options');
|
||||
var configPath = this.node.datadir + '/bitcoin.conf';
|
||||
this.configuration = {};
|
||||
$.checkArgument(this.options.spawn, 'Please specify "spawn" in bitcoind config options');
|
||||
$.checkArgument(this.options.spawn.datadir, 'Please specify "spawn.datadir" in bitcoind config options');
|
||||
$.checkArgument(this.options.spawn.exec, 'Please specify "spawn.exec" in bitcoind config options');
|
||||
|
||||
if (!fs.existsSync(this.node.datadir)) {
|
||||
mkdirp.sync(this.node.datadir);
|
||||
var spawnOptions = this.options.spawn;
|
||||
var configPath = spawnOptions.datadir + '/bitcoin.conf';
|
||||
|
||||
this.spawn = {};
|
||||
this.spawn.datadir = this.options.spawn.datadir;
|
||||
this.spawn.exec = this.options.spawn.exec;
|
||||
this.spawn.configPath = configPath;
|
||||
this.spawn.config = {};
|
||||
|
||||
if (!fs.existsSync(spawnOptions.datadir)) {
|
||||
mkdirp.sync(spawnOptions.datadir);
|
||||
}
|
||||
|
||||
var file = fs.readFileSync(configPath);
|
||||
|
@ -100,48 +124,50 @@ Bitcoin.prototype._loadConfiguration = function() {
|
|||
} else {
|
||||
value = option[1];
|
||||
}
|
||||
this.configuration[option[0]] = value;
|
||||
this.spawn.config[option[0]] = value;
|
||||
}
|
||||
}
|
||||
|
||||
var spawnConfig = this.spawn.config;
|
||||
|
||||
$.checkState(
|
||||
this.configuration.txindex && this.configuration.txindex === 1,
|
||||
spawnConfig.txindex && spawnConfig.txindex === 1,
|
||||
'"txindex" option is required in order to use transaction query features of bitcore-node. ' +
|
||||
'Please add "txindex=1" to your configuration and reindex an existing database if ' +
|
||||
'necessary with reindex=1'
|
||||
);
|
||||
|
||||
$.checkState(
|
||||
this.configuration.addressindex && this.configuration.addressindex === 1,
|
||||
spawnConfig.addressindex && spawnConfig.addressindex === 1,
|
||||
'"addressindex" option is required in order to use address query features of bitcore-node. ' +
|
||||
'Please add "addressindex=1" to your configuration and reindex an existing database if ' +
|
||||
'necessary with reindex=1'
|
||||
);
|
||||
|
||||
$.checkState(
|
||||
this.configuration.server && this.configuration.server === 1,
|
||||
spawnConfig.server && spawnConfig.server === 1,
|
||||
'"server" option is required to communicate to bitcoind from bitcore. ' +
|
||||
'Please add "server=1" to your configuration and restart'
|
||||
);
|
||||
|
||||
$.checkState(
|
||||
this.configuration.zmqpubrawtx,
|
||||
spawnConfig.zmqpubrawtx,
|
||||
'"zmqpubrawtx" option is required to get event updates from bitcoind. ' +
|
||||
'Please add "zmqpubrawtx=tcp://127.0.0.1:<port>" to your configuration and restart'
|
||||
);
|
||||
|
||||
$.checkState(
|
||||
this.configuration.zmqpubhashblock,
|
||||
spawnConfig.zmqpubhashblock,
|
||||
'"zmqpubhashblock" option is required to get event updates from bitcoind. ' +
|
||||
'Please add "zmqpubhashblock=tcp://127.0.0.1:<port>" to your configuration and restart'
|
||||
);
|
||||
|
||||
if (this.configuration.reindex && this.configuration.reindex === 1) {
|
||||
if (spawnConfig.reindex && spawnConfig.reindex === 1) {
|
||||
log.warn('Reindex option is currently enabled. This means that bitcoind is undergoing a reindex. ' +
|
||||
'The reindex flag will start the index from beginning every time the node is started, so it ' +
|
||||
'should be removed after the reindex has been initiated. Once the reindex is complete, the rest ' +
|
||||
'of bitcore-node services will start.');
|
||||
this._reindex = true;
|
||||
'The reindex flag will start the index from beginning every time the node is started, so it ' +
|
||||
'should be removed after the reindex has been initiated. Once the reindex is complete, the rest ' +
|
||||
'of bitcore-node services will start.');
|
||||
node._reindex = true;
|
||||
}
|
||||
|
||||
};
|
||||
|
@ -153,67 +179,37 @@ Bitcoin.prototype._resetCaches = function() {
|
|||
this.summaryCache.reset();
|
||||
};
|
||||
|
||||
Bitcoin.prototype._registerEventHandlers = function() {
|
||||
Bitcoin.prototype._initChain = function(callback) {
|
||||
var self = this;
|
||||
|
||||
this.zmqSubSocket.subscribe('hashblock');
|
||||
this.zmqSubSocket.subscribe('rawtx');
|
||||
|
||||
this.zmqSubSocket.on('message', function(topic, message) {
|
||||
var topicString = topic.toString('utf8');
|
||||
if (topicString === 'rawtx') {
|
||||
self.emit('tx', message);
|
||||
} else if (topicString === 'hashblock') {
|
||||
self._resetCaches();
|
||||
self.tiphash = message.toString('hex');
|
||||
self.client.getBlock(self.tiphash, function(err, response) {
|
||||
if (err) {
|
||||
return log.error(err);
|
||||
}
|
||||
self.height = response.result.height;
|
||||
$.checkState(self.height >= 0);
|
||||
self.emit('tip', self.height);
|
||||
});
|
||||
|
||||
if(!self.node.stopping) {
|
||||
self.syncPercentage(function(err, percentage) {
|
||||
if (err) {
|
||||
return log.error(err);
|
||||
}
|
||||
log.info('Bitcoin Height:', self.height, 'Percentage:', percentage.toFixed(2));
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
};
|
||||
|
||||
Bitcoin.prototype._onReady = function(result, callback) {
|
||||
var self = this;
|
||||
|
||||
self._registerEventHandlers();
|
||||
|
||||
self.client.getInfo(function(err, response) {
|
||||
self.client.getBestBlockHash(function(err, response) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
self.height = response.result.blocks;
|
||||
|
||||
self.client.getBlockHash(0, function(err, response) {
|
||||
self.client.getBlock(response.result, function(err, response) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
var blockhash = response.result;
|
||||
self.getBlock(blockhash, function(err, block) {
|
||||
|
||||
self.height = response.result.height;
|
||||
|
||||
self.client.getBlockHash(0, function(err, response) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
self.tiphash = block.hash;
|
||||
self.genesisBuffer = block.toBuffer();
|
||||
self.emit('ready', result);
|
||||
log.info('Bitcoin Daemon Ready');
|
||||
callback();
|
||||
var blockhash = response.result;
|
||||
self.getBlock(blockhash, function(err, block) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
self.genesisBuffer = block.toBuffer();
|
||||
self.emit('ready');
|
||||
log.info('Bitcoin Daemon Ready');
|
||||
callback();
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
};
|
||||
|
@ -229,27 +225,139 @@ Bitcoin.prototype._getNetworkOption = function() {
|
|||
return networkOption;
|
||||
};
|
||||
|
||||
/**
|
||||
* Called by Node to start the service
|
||||
* @param {Function} callback
|
||||
*/
|
||||
Bitcoin.prototype.start = function(callback) {
|
||||
Bitcoin.prototype._zmqBlockHandler = function(node, message) {
|
||||
var self = this;
|
||||
var hex = message.toString('hex');
|
||||
if (hex !== self.tiphash) {
|
||||
self._resetCaches();
|
||||
self.tiphash = message.toString('hex');
|
||||
node.client.getBlock(self.tiphash, function(err, response) {
|
||||
if (err) {
|
||||
return log.error(err);
|
||||
}
|
||||
self.height = response.result.height;
|
||||
$.checkState(self.height >= 0);
|
||||
self.emit('tip', self.height);
|
||||
});
|
||||
|
||||
if(!self.node.stopping) {
|
||||
self.syncPercentage(function(err, percentage) {
|
||||
if (err) {
|
||||
return log.error(err);
|
||||
}
|
||||
log.info('Bitcoin Height:', self.height, 'Percentage:', percentage.toFixed(2));
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
Bitcoin.prototype._zmqTransactionHandler = function(node, message) {
|
||||
var self = this;
|
||||
var id = message.toString('binary');
|
||||
if (!self.zmqKnownTransactions[id]) {
|
||||
self.zmqKnownTransactions[id] = true;
|
||||
self.emit('tx', message);
|
||||
}
|
||||
};
|
||||
|
||||
Bitcoin.prototype._subscribeZmqEvents = function(node) {
|
||||
var self = this;
|
||||
node.zmqSubSocket.subscribe('hashblock');
|
||||
node.zmqSubSocket.subscribe('rawtx');
|
||||
node.zmqSubSocket.on('message', function(topic, message) {
|
||||
var topicString = topic.toString('utf8');
|
||||
if (topicString === 'rawtx') {
|
||||
self._zmqTransactionHandler(node, message);
|
||||
} else if (topicString === 'hashblock') {
|
||||
self._zmqBlockHandler(node, message);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
Bitcoin.prototype._initZmqSubSocket = function(node, zmqUrl) {
|
||||
var self = this;
|
||||
node.zmqSubSocket = zmq.socket('sub');
|
||||
|
||||
node.zmqSubSocket.on('monitor_error', function(err) {
|
||||
log.error('Error in monitoring: %s, will restart monitoring in 5 seconds', err);
|
||||
setTimeout(function() {
|
||||
self.zmqSubSocket.monitor(500, 0);
|
||||
}, 5000);
|
||||
});
|
||||
|
||||
node.zmqSubSocket.monitor(500, 0);
|
||||
node.zmqSubSocket.connect(zmqUrl);
|
||||
};
|
||||
|
||||
Bitcoin.prototype._checkReindex = function(node, callback) {
|
||||
var self = this;
|
||||
if (node._reindex) {
|
||||
var interval = setInterval(function() {
|
||||
node.client.syncPercentage(function(err, percentSynced) {
|
||||
if (err) {
|
||||
return log.error(err);
|
||||
}
|
||||
log.info('Bitcoin Core Daemon Reindex Percentage: ' + percentSynced.toFixed(2));
|
||||
if (Math.round(percentSynced) >= 100) {
|
||||
node._reindex = false;
|
||||
self._subscribeZmqEvents(node);
|
||||
callback();
|
||||
clearInterval(interval);
|
||||
}
|
||||
});
|
||||
}, self._reindexWait);
|
||||
|
||||
} else {
|
||||
self._subscribeZmqEvents(node);
|
||||
callback();
|
||||
}
|
||||
};
|
||||
|
||||
Bitcoin.prototype._loadTipFromNode = function(node, callback) {
|
||||
var self = this;
|
||||
node.client.getBestBlockHash(function(err, response) {
|
||||
if (err) {
|
||||
if (!(err instanceof Error)) {
|
||||
log.warn(err.message);
|
||||
}
|
||||
return callback(new Error('Could not connect to bitcoind RPC'));
|
||||
}
|
||||
node.client.getBlock(response.result, function(err, response) {
|
||||
if (err) {
|
||||
return done(err);
|
||||
}
|
||||
self.height = response.result.height;
|
||||
$.checkState(self.height >= 0);
|
||||
self.emit('tip', self.height);
|
||||
callback();
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
Bitcoin.prototype._spawnChildProcess = function(callback) {
|
||||
var self = this;
|
||||
|
||||
self._loadConfiguration();
|
||||
var node = {};
|
||||
node._reindex = false;
|
||||
node._reindexWait = 1000;
|
||||
|
||||
try {
|
||||
self._loadSpawnConfiguration(node);
|
||||
} catch(e) {
|
||||
return callback(e);
|
||||
}
|
||||
|
||||
var options = [
|
||||
'--conf=' + path.resolve(this.node.datadir, './bitcoin.conf'),
|
||||
'--datadir=' + this.node.datadir,
|
||||
'--conf=' + path.resolve(this.spawn.configPath),
|
||||
'--datadir=' + this.spawn.datadir,
|
||||
];
|
||||
|
||||
if (self._getNetworkOption()) {
|
||||
options.push(self._getNetworkOption());
|
||||
}
|
||||
self.spawn.process = spawn(this.spawn.exec, options, {stdio: 'inherit'});
|
||||
|
||||
self.process = spawn('bitcoind', options, {stdio: 'inherit'});
|
||||
|
||||
self.process.on('error', function(err) {
|
||||
self.spawn.process.on('error', function(err) {
|
||||
log.error(err);
|
||||
});
|
||||
|
||||
|
@ -258,67 +366,104 @@ Bitcoin.prototype.start = function(callback) {
|
|||
return done(new Error('Stopping while trying to connect to bitcoind.'));
|
||||
}
|
||||
|
||||
self.client = new BitcoinRPC({
|
||||
node.client = new BitcoinRPC({
|
||||
protocol: 'http',
|
||||
host: '127.0.0.1',
|
||||
port: self.configuration.rpcport,
|
||||
user: self.configuration.rpcuser,
|
||||
pass: self.configuration.rpcpassword
|
||||
port: self.spawn.config.rpcport,
|
||||
user: self.spawn.config.rpcuser,
|
||||
pass: self.spawn.config.rpcpassword
|
||||
});
|
||||
|
||||
self.client.getBestBlockHash(function(err, response) {
|
||||
if (err) {
|
||||
if (!(err instanceof Error)) {
|
||||
log.warn(err.message);
|
||||
}
|
||||
return done(new Error('Could not connect to bitcoind RPC'));
|
||||
}
|
||||
self.client.getBlock(response.result, function(err, response) {
|
||||
if (err) {
|
||||
return done(err);
|
||||
}
|
||||
self.height = response.result.height;
|
||||
$.checkState(self.height >= 0);
|
||||
self.emit('tip', self.height);
|
||||
done();
|
||||
});
|
||||
});
|
||||
self._loadTipFromNode(node, done);
|
||||
|
||||
}, function ready(err, result) {
|
||||
}, function(err) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
|
||||
self.zmqSubSocket = zmq.socket('sub');
|
||||
self._initZmqSubSocket(node, self.spawn.config.zmqpubrawtx);
|
||||
|
||||
self.zmqSubSocket.on('monitor_error', function(err) {
|
||||
log.error('Error in monitoring: %s, will restart monitoring in 5 seconds', err);
|
||||
setTimeout(function() {
|
||||
self.zmqSubSocket.monitor(500, 0);
|
||||
}, 5000);
|
||||
self._checkReindex(node, function() {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
callback(null, node);
|
||||
});
|
||||
|
||||
self.zmqSubSocket.monitor(500, 0);
|
||||
self.zmqSubSocket.connect(self.configuration.zmqpubrawtx);
|
||||
});
|
||||
};
|
||||
|
||||
if (self._reindex) {
|
||||
var interval = setInterval(function() {
|
||||
self.syncPercentage(function(err, percentSynced) {
|
||||
if (err) {
|
||||
return log.error(err);
|
||||
}
|
||||
log.info('Bitcoin Core Daemon Reindex Percentage: ' + percentSynced.toFixed(2));
|
||||
if (Math.round(percentSynced) >= 100) {
|
||||
self._reindex = false;
|
||||
self._onReady(result, callback);
|
||||
clearInterval(interval);
|
||||
}
|
||||
});
|
||||
}, self._reindexWait);
|
||||
Bitcoin.prototype._connectProcess = function(config, callback) {
|
||||
var self = this;
|
||||
var node = {};
|
||||
|
||||
} else {
|
||||
self._onReady(result, callback);
|
||||
async.retry({times: 60, interval: 5000}, function(done) {
|
||||
if (self.node.stopping) {
|
||||
return done(new Error('Stopping while trying to connect to bitcoind.'));
|
||||
}
|
||||
|
||||
node.client = new BitcoinRPC({
|
||||
protocol: config.rpcprotocol || 'http',
|
||||
host: config.rpchost || '127.0.0.1',
|
||||
port: config.rpcport,
|
||||
user: config.rpcuser,
|
||||
pass: config.rpcpassword
|
||||
});
|
||||
|
||||
self._loadTipFromNode(node, done);
|
||||
|
||||
}, function(err) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
|
||||
self._initZmqSubSocket(node, config.zmqpubrawtx);
|
||||
|
||||
callback(null, node);
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* Called by Node to start the service
|
||||
* @param {Function} callback
|
||||
*/
|
||||
Bitcoin.prototype.start = function(callback) {
|
||||
var self = this;
|
||||
|
||||
async.series([
|
||||
function(next) {
|
||||
if (self.options.spawn) {
|
||||
self._spawnChildProcess(function(err, node) {
|
||||
if (err) {
|
||||
return next(err);
|
||||
}
|
||||
self.nodes.push(node);
|
||||
next();
|
||||
});
|
||||
} else {
|
||||
next();
|
||||
}
|
||||
},
|
||||
function(next) {
|
||||
if (self.options.connect) {
|
||||
async.map(self.options.connect, self._connectProcess.bind(self), function(err, nodes) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
for(var i = 0; i < nodes.length; i++) {
|
||||
self.nodes.push(nodes[i]);
|
||||
}
|
||||
next();
|
||||
});
|
||||
} else {
|
||||
next();
|
||||
}
|
||||
}
|
||||
], function(err) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
}
|
||||
self._initChain(callback);
|
||||
});
|
||||
|
||||
};
|
||||
|
@ -950,15 +1095,15 @@ Bitcoin.prototype.getInfo = function(callback) {
|
|||
* @param {Function} callback
|
||||
*/
|
||||
Bitcoin.prototype.stop = function(callback) {
|
||||
if (this.process) {
|
||||
this.process.once('exit', function(err, status) {
|
||||
if (this.spawn && this.spawn.process) {
|
||||
this.spawn.process.once('exit', function(err, status) {
|
||||
if (err) {
|
||||
return callback(err);
|
||||
} else {
|
||||
return callback();
|
||||
}
|
||||
});
|
||||
this.process.kill('SIGHUP');
|
||||
this.spawn.process.kill('SIGHUP');
|
||||
} else {
|
||||
callback();
|
||||
}
|
||||
|
|
|
@ -40,7 +40,6 @@
|
|||
],
|
||||
"dependencies": {
|
||||
"async": "^1.3.0",
|
||||
"bindings": "^1.2.1",
|
||||
"bitcoind-rpc": "^0.3.0",
|
||||
"bitcore-lib": "^0.13.13",
|
||||
"body-parser": "^1.13.3",
|
||||
|
@ -50,7 +49,6 @@
|
|||
"express": "^4.13.3",
|
||||
"liftoff": "^2.2.0",
|
||||
"lru-cache": "^4.0.1",
|
||||
"memdown": "^1.0.0",
|
||||
"mkdirp": "0.5.0",
|
||||
"npm": "^2.14.1",
|
||||
"semver": "^5.0.1",
|
||||
|
|
Loading…
Reference in New Issue