define([
'angular', 'lodash', 'config'
], function (angular, _, config) {
'use strict'; var module = angular.module('kibana.services'); module.service('esVersion', function($http, alertSrv, esMinVersion, $q, ejsResource) { this.versions = []; var ejs = ejsResource(config.elasticsearch); // save a reference to this var self = this, defer = $q.defer(); this.init = function() { getVersions(); }; var getVersions = function() { if(self.versions.length !== 0) { defer.resolve(self.versions); return defer.promise; } else { var nodeInfo = ejs.client.get('/_nodes', undefined, undefined, function(data, status) { if(_.isUndefined(status)) { alertSrv.set('Error',"Could not contact Elasticsearch at "+ejs.client.server()+ ". Please ensure that Elasticsearch is reachable from your system." ,'error'); } else { alertSrv.set('Error',"Could not reach "+ejs.client.server()+"/_nodes. If you"+ " are using a proxy, ensure it is configured correctly",'error'); } return; }); return nodeInfo.then(function(p) { _.each(p.nodes, function(v) { self.versions.push(v.version.split('-')[0]); }); self.versions = sortVersions(_.uniq(self.versions)); return self.versions; }); } }; // Get the max version in this cluster this.max = function(versions) { return _.last(versions); }; // Return the lowest version in the cluster this.min = function(versions) { return _.first(versions); }; // Sort versions from lowest to highest var sortVersions = function(versions) { var _versions = _.clone(versions), _r = []; while(_r.length < versions.length) { var _h = "0"; /*jshint -W083 */ _.each(_versions,function(v){ if(self.compare(_h,v)) { _h = v; } }); _versions = _.without(_versions,_h); _r.push(_h); } return _r.reverse(); }; /* Takes a version string with one of the following optional comparison prefixes: >,>=,<.<= and evaluates if the cluster meets the requirement. If the prefix is omitted exact match is assumed */ this.is = function(equation) { var _v = equation, _cf; if(_v.charAt(0) === '>') { _cf = _v.charAt(1) === '=' ? self.gte(_v.slice(2)) : self.gt(_v.slice(1)); } else if (_v.charAt(0) === '<') { _cf = _v.charAt(1) === '=' ? self.lte(_v.slice(2)) : self.lt(_v.slice(1)); } else { _cf = self.eq(_v); } return _cf; }; this.isMinimum = function() { return self.gte(esMinVersion); }; // check if lowest version in cluster = `version` this.eq = function(version) { return getVersions().then(function(v) { return version === self.min(v) ? true : false; }); }; // version > lowest version in cluster? this.gt = function(version) { return getVersions().then(function(v) { return version === self.min(v) ? false : self.gte(version); }); }; // version < highest version in cluster? this.lt = function(version) { return getVersions().then(function(v) { return version === self.max(v) ? false : self.lte(version); }); }; // Check if the lowest version in the cluster is >= to `version` this.gte = function(version) { return getVersions().then(function(v) { return self.compare(version,self.min(v)); }); }; // Check if the highest version in the cluster is <= to `version` this.lte = function(version) { return getVersions().then(function(v) { return self.compare(self.max(v),version); }); }; // Determine if a specific version is greater than or equal to another this.compare = function (required,installed) { if(_.isUndefined(installed)) { return; } if(!required || !installed) { return undefined; } var a = installed.split('.'); var b = required.split('.'); var i; // leave suffixes as is ("RC1 or -SNAPSHOT") for (i = 0; i < Math.min(a.length, 3); ++i) { a[i] = Number(a[i]); } for (i = 0; i < Math.min(b.length, 3); ++i) { b[i] = Number(b[i]); } if (a.length === 2) { a[2] = 0; } if (a[0] > b[0]){return true;} if (a[0] < b[0]){return false;} if (a[1] > b[1]){return true;} if (a[1] < b[1]){return false;} if (a[2] > b[2]){return true;} if (a[2] < b[2]){return false;} if (a.length > 3) { // rc/beta suffix if (b.length <= 3) { return false; } // no suffix on b -> a<b return a[3] >= b[3]; } if (b.length > 3) { // b has a suffix but a not -> a>b return true; } return true; }; this.init(); });
});