UNPKG

matrixbitcore-wallet-service

Version:
188 lines (150 loc) 5.03 kB
'use strict'; var _ = require('lodash'); var $ = require('preconditions').singleton(); var async = require('async'); var log = require('npmlog'); log.debug = log.verbose; var request = require('request'); var Common = require('./common'); var Defaults = Common.Defaults; var Storage = require('./storage'); var Model = require('./model'); function FiatRateService() {}; FiatRateService.prototype.init = function(opts, cb) { var self = this; opts = opts || {}; self.request = opts.request || request; self.defaultProvider = opts.defaultProvider || Defaults.FIAT_RATE_PROVIDER; async.parallel([ function(done) { if (opts.storage) { self.storage = opts.storage; done(); } else { self.storage = new Storage(); self.storage.connect(opts.storageOpts, done); } }, ], function(err) { if (err) { log.error(err); } return cb(err); }); }; FiatRateService.prototype.startCron = function(opts, cb) { var self = this; opts = opts || {}; self.providers = _.values(require('./fiatrateproviders')); var interval = opts.fetchInterval || Defaults.FIAT_RATE_FETCH_INTERVAL; if (interval) { self._fetch(); setInterval(function() { self._fetch(); }, interval * 60 * 1000); } return cb(); }; FiatRateService.prototype._fetch = function(cb) { var self = this; cb = cb || function() {}; async.each(self.providers, function(provider, next) { self._retrieve(provider, function(err, res) { if (err) { log.warn('Error retrieving data for ' + provider.name, err); return next(); } self.storage.storeFiatRate(provider.name, res, function(err) { if (err) { log.warn('Error storing data for ' + provider.name, err); } return next(); }); }); }, cb); }; FiatRateService.prototype._retrieve = function(provider, cb) { var self = this; async.waterfall([ function(callback){ log.debug('Fetching data for CoinMarketCap'); self.request.get({ url: 'https://api.coinmarketcap.com/v1/ticker/bitcoin/?convert=USD', json: true }, function(err, res, body) { if (err || !body) { callback(err, null); } log.debug('Data for CoinMarketCap fetched successfully'); var xrate = body; var nrate = parseFloat(xrate[0].price_usd.replace(/'/g, '')) * 0.000029; var mxbit = [ { 'id': 'matrixbit', 'name': 'Matrixbit', 'symbol': 'MXBIT', 'rank': '0', 'price_usd': nrate, 'price_btc': 0.000029, '24h_volume_usd': 0, 'market_cap_usd': 0, 'available_supply': 1000000, 'total_supply':1000000, 'max_supply': 150000000.0, 'percent_change_1h': xrate[0].percent_change_1h, 'percent_change_24h': xrate[0].percent_change_24h, 'percent_change_7d': xrate[0].percent_change_7d, 'last_updated': xrate[0].last_updated } ]; callback(null, mxbit); }); }, function(data, callback){ log.debug('Fetching data for ' + provider.name); self.request.get({ url: provider.url, json: true }, function(err, res, body) { if (err || !body) { callback(err, null); } log.debug('Data for ' + provider.name + ' fetched successfully'); if (!provider.parseFn) { return cb(new Error('No parse function for provider ' + provider.name)); } var rates = provider.parseFn(body, data); callback(null, rates); }); } ], function (err, result) { if (err || !result) { return cb(err); } return cb(null, result); }); }; FiatRateService.prototype.getRate = function(opts, cb) { var self = this; $.shouldBeFunction(cb); opts = opts || {}; var now = Date.now(); var provider = opts.provider || self.defaultProvider; var ts = (_.isNumber(opts.ts) || _.isArray(opts.ts)) ? opts.ts : now; async.map([].concat(ts), function(ts, cb) { self.storage.fetchFiatRate(provider, opts.code, ts, function(err, rate) { if (err) return cb(err); if (rate && (ts - rate.ts) > Defaults.FIAT_RATE_MAX_LOOK_BACK_TIME * 60 * 1000) rate = null; return cb(null, { ts: +ts, rate: rate ? rate.value : undefined, fetchedOn: rate ? rate.ts : undefined, }); }); }, function(err, res) { if (err) return cb(err); if (!_.isArray(ts)) res = res[0]; return cb(null, res); }); }; module.exports = FiatRateService;