diff --git a/lib/modules/technical/blockchainInfo.js b/lib/modules/technical/blockchainInfo.js index 403013f..7a9c5bf 100644 --- a/lib/modules/technical/blockchainInfo.js +++ b/lib/modules/technical/blockchainInfo.js @@ -1,9 +1,7 @@ 'use strict'; -var async = require('async'), - _ = require('lodash'), - request = require('request'), - +var Bluebird = require('bluebird'), + request = require('../../utils/request'), Module =require('../../Module'); module.exports = Module.extend({ @@ -26,54 +24,29 @@ module.exports = Module.extend({ updateTechnicalStats: function () { var self = this; - async.parallel([ - function (callback) { - request({ - uri: 'http://blockchain.info/stats?format=json', - json: true - }, function (err, res) { callback(err, res); }); - }, - function (callback) { - request({ - uri: 'http://blockchain.info/q/bcperblock', - json: true - }, function (err, res) { callback(err, res); }); - } - ], function (err, responses) { + Bluebird.all([ + request('https://blockchain.info/stats?format=json'), + request('https://blockchain.info/q/bcperblock') + ]).then(function (responses) { /*jshint sub:true*/ - - var allRequestsSucceeded, - difficulty; - - if (err) { - self.app.logger.info('%s - error fetching data from blockchain.info', self.id, err); - return; - } - self.app.logger.debug( '%s - fetched data from blockchain.info', self.id, - JSON.stringify(_.pluck(responses, 'statusCode')), - JSON.stringify(_.pluck(responses, 'body')) + JSON.stringify(responses) ); - allRequestsSucceeded = _.all(responses, function (res) { - return res.statusCode === 200; - }); - if (!allRequestsSucceeded) { - return; - } - difficulty = responses[0].body.difficulty; self.set({ - blockReward: responses[1].body / 1e8, - probability: 1 / (4295032833 * difficulty), - difficulty: difficulty, - networkHashrate: responses[0].body['hash_rate'] * 1e3, - blockChainLength: responses[0].body['n_blocks_total'], - timeBetweenBlocks: responses[0].body['minutes_between_blocks'], - numberOfTransactions: responses[0].body['n_tx'], - totalTransactionValue: responses[0].body['total_btc_sent'] + blockReward: responses[1] / 1e8, + probability: 1 / (4295032833 * responses[0].difficulty), + difficulty: responses[0].difficulty, + networkHashrate: responses[0]['hash_rate'] * 1e3, + blockChainLength: responses[0]['n_blocks_total'], + timeBetweenBlocks: responses[0]['minutes_between_blocks'], + numberOfTransactions: responses[0]['n_tx'], + totalTransactionValue: responses[0]['total_btc_sent'] }); + }).catch(function (err) { + self.app.logger.info('%s - error fetching data from blockchain.info', self.id, err.toString()); }); } diff --git a/test/specs/lib/modules/technical/blockchainInfoSpec.js b/test/specs/lib/modules/technical/blockchainInfoSpec.js index 221850c..682623a 100644 --- a/test/specs/lib/modules/technical/blockchainInfoSpec.js +++ b/test/specs/lib/modules/technical/blockchainInfoSpec.js @@ -5,8 +5,8 @@ var chai = require('chai'), sinonChai = require('sinon-chai'), expect = chai.expect, SandboxedModule = require('sandboxed-module'), + Bluebird = require('bluebird'), - responses = {}, statsAnswer = { 'n_blocks_total': 123, 'minutes_between_blocks': 12, @@ -15,90 +15,75 @@ var chai = require('chai'), difficulty: 100 * (1 / 4295032833), 'hash_rate': 123 }, - btcPerBlockAnswer = 2500000000, - BlockchainInfo = SandboxedModule.require('../../../../../lib/modules/technical/blockchainInfo', { - requires: { - request: require('../../../../utils/requestStub')(responses) - } - }); + btcPerBlockAnswer = 2500000000; chai.use(sinonChai); describe('modules/technical/blockchainInfo', function () { - var app; + var BlockchainInfo, + app, + requestStub; beforeEach(function () { + requestStub = sinon.stub(); + requestStub.withArgs('https://blockchain.info/stats?format=json').returns(Bluebird.resolve(statsAnswer)); + requestStub.withArgs('https://blockchain.info/q/bcperblock').returns(Bluebird.resolve(btcPerBlockAnswer)); + + BlockchainInfo = SandboxedModule.require('../../../../../lib/modules/technical/blockchainInfo', { + requires: { + '../../utils/request': requestStub + } + }); app = { logger: { debug: sinon.stub(), info: sinon.stub() } }; - responses['http://blockchain.info/stats?format=json'] = { - statusCode: 200, - body: statsAnswer - }; - responses['http://blockchain.info/q/bcperblock'] = { - statusCode: 200, - body: btcPerBlockAnswer - }; }); it('should get data from blockchainInfo correctly', function (done) { - var blockchainInfo = new BlockchainInfo(app); + var blockchainInfo; + blockchainInfo = new BlockchainInfo(app); blockchainInfo.on('change', function () { - expect(blockchainInfo.toJSON()).to.deep.equal({ - blockReward: 25, - probability: 0.01, - difficulty: 100 * (1 / 4295032833), - networkHashrate: 123000, - blockChainLength: 123, - timeBetweenBlocks: 12, - numberOfTransactions: 10, - totalTransactionValue: 1 + setImmediate(function () { + expect(blockchainInfo.toJSON()).to.deep.equal({ + blockReward: 25, + probability: 0.01, + difficulty: 100 * (1 / 4295032833), + networkHashrate: 123000, + blockChainLength: 123, + timeBetweenBlocks: 12, + numberOfTransactions: 10, + totalTransactionValue: 1 + }); + + expect(app.logger.debug).to.have.been.calledOnce; + expect(app.logger.debug).to.have.been.calledWith( + '%s - fetched data from blockchain.info', + blockchainInfo.id, + JSON.stringify([ statsAnswer, btcPerBlockAnswer ]) + ); + + done(); }); - expect(app.logger.debug).to.have.been.calledOnce; - expect(app.logger.debug).to.have.been.calledWith( - '%s - fetched data from blockchain.info', - blockchainInfo.id, - JSON.stringify([ 200, 200 ]), - JSON.stringify([ statsAnswer, btcPerBlockAnswer ]) - ); - done(); }); }); [ - 'http://blockchain.info/stats?format=json', - 'http://blockchain.info/q/bcperblock' - ].forEach(function (url) { - it('should not throw an error if the request to ' + url + 'fails with an error and log the incident', function (done) { - var blockchainInfo; + 'https://blockchain.info/stats?format=json', + 'https://blockchain.info/q/bcperblock' + ].forEach(function (testCase) { + it('should log the incident if the request to ' + testCase.failing + 'fails with an error', function (done) { + var error = new Error('Test Error'), + blockchainInfo; - responses[url] = null; + requestStub.withArgs(testCase).returns(Bluebird.reject(error)); blockchainInfo = new BlockchainInfo(app); - setTimeout(function () { expect(blockchainInfo.toJSON()).to.be.empty; expect(app.logger.info).to.have.been.calledOnce; - expect(app.logger.info).to.have.been.calledWith('%s - error fetching data from blockchain.info', blockchainInfo.id, new Error('Test Error')); - done(); - }, 50); - }); - - it('should not throw an error if the request to ' + url + 'returns a non 200 http status code and no data', function (done) { - var blockchainInfo; - - responses[url] = { - statusCode: 500, - body: 'Internal Server Error' - }; - - blockchainInfo = new BlockchainInfo(app); - - setTimeout(function () { - expect(blockchainInfo.toJSON()).to.be.empty; + expect(app.logger.info).to.have.been.calledWith('%s - error fetching data from blockchain.info', blockchainInfo.id, error.toString()); done(); - }, 50); + }, 10); }); - }); it('should have the title set correctly', function () {