From 51b0a7a0eb32a218653390cc17bed676148d7b16 Mon Sep 17 00:00:00 2001 From: Alexander Zobnin Date: Sat, 23 Jan 2016 14:43:06 +0300 Subject: [PATCH] Working on new Zabbix API service. --- plugins/datasource-zabbix/datasource.js | 5 +- plugins/datasource-zabbix/zabbixAPI.js | 244 +++++++ plugins/datasource-zabbix/zabbixAPIService.js | 6 +- plugins/datasource-zabbix/zabbixAPIWrapper.js | 650 ------------------ 4 files changed, 249 insertions(+), 656 deletions(-) create mode 100644 plugins/datasource-zabbix/zabbixAPI.js delete mode 100644 plugins/datasource-zabbix/zabbixAPIWrapper.js diff --git a/plugins/datasource-zabbix/datasource.js b/plugins/datasource-zabbix/datasource.js index 6ce5a58..6225cc6 100644 --- a/plugins/datasource-zabbix/datasource.js +++ b/plugins/datasource-zabbix/datasource.js @@ -3,8 +3,7 @@ define([ 'lodash', 'app/core/utils/datemath', './directives', - './zabbixAPIWrapper', - './zabbixAPIService', + './zabbixAPI', './utils', './helperFunctions', './zabbixCacheSrv', @@ -15,7 +14,7 @@ function (angular, _, dateMath) { /** @ngInject */ function ZabbixAPIDatasource(instanceSettings, $q, backendSrv, templateSrv, alertSrv, - ZabbixAPI, Utils, zabbixHelperSrv, ZabbixCache, ZabbixAPIService) { + ZabbixAPI, Utils, zabbixHelperSrv, ZabbixCache) { // General data source settings this.name = instanceSettings.name; diff --git a/plugins/datasource-zabbix/zabbixAPI.js b/plugins/datasource-zabbix/zabbixAPI.js new file mode 100644 index 0000000..73d7a88 --- /dev/null +++ b/plugins/datasource-zabbix/zabbixAPI.js @@ -0,0 +1,244 @@ +define([ + 'angular', + 'lodash', + './zabbixAPIService' + ], +function (angular, _) { + 'use strict'; + + var module = angular.module('grafana.services'); + + module.factory('ZabbixAPI', function($q, backendSrv, ZabbixAPIService) { + + // Initialize Zabbix API. + function ZabbixAPI(api_url, username, password, basicAuth, withCredentials) { + this.url = api_url; + this.username = username; + this.password = password; + this.auth = null; + + this.requestOptions = { + basicAuth: basicAuth, + withCredentials: withCredentials + }; + } + + var p = ZabbixAPI.prototype; + + ////////////////// + // Core methods // + ////////////////// + + p.request = function(method, params) { + var self = this; + if (this.auth) { + return ZabbixAPIService._request(this.url, method, params, this.requestOptions, this.auth); + } else { + + // Login first + return ZabbixAPIService.login(this.url, this.username, this.password, this.requestOptions) + .then(function(auth) { + self.auth = auth; + return ZabbixAPIService._request(self.url, method, params, self.requestOptions, self.auth); + }); + } + }; + + /** + * Get authentication token. + */ + p.login = function() { + return ZabbixAPIService.login(this.url, this.username, this.password, this.requestOptions); + }; + + /** + * Get Zabbix API version + */ + p.getVersion = function() { + return ZabbixAPIService.getVersion(this.url, this.requestOptions); + }; + + ///////////////// + // API methods // + ///////////////// + + p.getGroups = function() { + var params = { + output: ['name'], + sortfield: 'name' + }; + + return this.request('hostgroup.get', params); + }; + + p.getHosts = function() { + var params = { + output: ['name', 'host'], + sortfield: 'name', + selectGroups: [] + }; + + return this.request('host.get', params); + }; + + p.getApplications = function() { + var params = { + output: ['name'], + sortfield: 'name', + selectHosts: [] + }; + + return this.request('application.get', params); + }; + + p.getItems = function() { + var params = { + output: ['name', 'key_', 'value_type', 'hostid', 'status', 'state'], + sortfield: 'name', + selectApplications: [] + }; + + return this.request('item.get', params); + }; + + /** + * Perform history query from Zabbix API + * + * @param {Array} items Array of Zabbix item objects + * @param {Number} start Time in seconds + * @param {Number} end Time in seconds + * @return {Array} Array of Zabbix history objects + */ + p.getHistory = function(items, start, end) { + // Group items by value type + var grouped_items = _.groupBy(items, 'value_type'); + + // Perform request for each value type + return $q.all(_.map(grouped_items, function (items, value_type) { + var itemids = _.map(items, 'itemid'); + var params = { + output: 'extend', + history: value_type, + itemids: itemids, + sortfield: 'clock', + sortorder: 'ASC', + time_from: start + }; + + // Relative queries (e.g. last hour) don't include an end time + if (end) { + params.time_till = end; + } + + return this.request('history.get', params); + }, this)).then(function (results) { + return _.flatten(results); + }); + }; + + /** + * Perform trends query from Zabbix API + * Use trends api extension from ZBXNEXT-1193 patch. + * + * @param {Array} items Array of Zabbix item objects + * @param {Number} start Time in seconds + * @param {Number} end Time in seconds + * @return {Array} Array of Zabbix trend objects + */ + p.getTrends = function(items, start, end) { + // Group items by value type + var grouped_items = _.groupBy(items, 'value_type'); + + // Perform request for each value type + return $q.all(_.map(grouped_items, function (items, value_type) { + var itemids = _.map(items, 'itemid'); + var params = { + output: 'extend', + trend: value_type, + itemids: itemids, + sortfield: 'clock', + sortorder: 'ASC', + time_from: start + }; + + // Relative queries (e.g. last hour) don't include an end time + if (end) { + params.time_till = end; + } + + return this.request('trend.get', params); + }, this)).then(function (results) { + return _.flatten(results); + }); + }; + + p.getITService = function(/* optional */ serviceids) { + var params = { + output: 'extend', + serviceids: serviceids + }; + return this.request('service.get', params); + }; + + p.getSLA = function(serviceids, from, to) { + var params = { + serviceids: serviceids, + intervals: [{ + from: from, + to: to + }] + }; + return this.request('service.getsla', params); + }; + + p.getTriggers = function(limit, sortfield, groupids, hostids, applicationids, name) { + var params = { + output: 'extend', + expandDescription: true, + expandData: true, + monitored: true, + //only_true: true, + filter: { + value: 1 + }, + search : { + description: name + }, + searchWildcardsEnabled: false, + groupids: groupids, + hostids: hostids, + applicationids: applicationids, + limit: limit, + sortfield: 'lastchange', + sortorder: 'DESC' + }; + + if (sortfield) { + params.sortfield = sortfield; + } + + return this.request('trigger.get', params); + }; + + p.getAcknowledges = function(triggerids, from) { + var params = { + output: 'extend', + objectids: triggerids, + acknowledged: true, + select_acknowledges: 'extend', + sortfield: 'clock', + sortorder: 'DESC', + time_from: from + }; + + return this.request('event.get', params) + .then(function (events) { + return _.flatten(_.map(events, 'acknowledges')); + }); + }; + + return ZabbixAPI; + + }); + +}); diff --git a/plugins/datasource-zabbix/zabbixAPIService.js b/plugins/datasource-zabbix/zabbixAPIService.js index 32e5687..2212a5a 100644 --- a/plugins/datasource-zabbix/zabbixAPIService.js +++ b/plugins/datasource-zabbix/zabbixAPIService.js @@ -86,12 +86,12 @@ function (angular) { // Define zabbix API exception type function ZabbixException(error) { this.code = error.code; - this.message = error.message; - this.data = error.data; + this.errorType = error.message; + this.message = error.data; } ZabbixException.prototype.toString = function() { - return this.name + " " + this.message; + return this.errorType + ": " + this.message; }; }); \ No newline at end of file diff --git a/plugins/datasource-zabbix/zabbixAPIWrapper.js b/plugins/datasource-zabbix/zabbixAPIWrapper.js deleted file mode 100644 index 4b3dff3..0000000 --- a/plugins/datasource-zabbix/zabbixAPIWrapper.js +++ /dev/null @@ -1,650 +0,0 @@ -define([ - 'angular', - 'lodash', - './zabbixAPIService' - ], -function (angular, _) { - 'use strict'; - - var module = angular.module('grafana.services'); - - module.factory('ZabbixAPI', function($q, backendSrv, ZabbixAPIService) { - - // Initialize Zabbix API. - function ZabbixAPI(api_url, username, password, basicAuth, withCredentials) { - this.url = api_url; - this.username = username; - this.password = password; - this.auth = null; - - this.requestOptions = { - basicAuth: basicAuth, - withCredentials: withCredentials - }; - } - - var p = ZabbixAPI.prototype; - - ////////////////// - // Core methods // - ////////////////// - - p.request = function(method, params) { - var self = this; - if (this.auth) { - return ZabbixAPIService._request(this.url, method, params, this.requestOptions, this.auth); - } else { - - // Login first - return ZabbixAPIService.login(this.url, this.username, this.password, this.requestOptions) - .then(function(auth) { - self.auth = auth; - return ZabbixAPIService._request(self.url, method, params, self.requestOptions, self.auth); - }); - } - }; - - /** - * Request data from Zabbix API - * - * @param {string} method Zabbix API method name - * @param {object} params method params - * @return {object} data.result field or [] - */ - p.performZabbixAPIRequest = function(method, params) { - var options = { - method: 'POST', - headers: { - 'Content-Type': 'application/json' - }, - url: this.url, - data: { - jsonrpc: '2.0', - method: method, - params: params, - auth: this.auth, - id: 1 - } - }; - - if (this.basicAuth || this.withCredentials) { - options.withCredentials = true; - } - if (this.basicAuth) { - options.headers.Authorization = this.basicAuth; - } - - var self = this; - return backendSrv.datasourceRequest(options).then(function (response) { - if (!response.data) { - return []; - } - // Handle Zabbix API errors - else if (response.data.error) { - - // Handle auth errors - if (response.data.error.data === "Session terminated, re-login, please." || - response.data.error.data === "Not authorised." || - response.data.error.data === "Not authorized") { - return self.performZabbixAPILogin().then(function (response) { - self.auth = response; - return self.performZabbixAPIRequest(method, params); - }); - } - } - return response.data.result; - }); - }; - - /** - * Get authentication token. - * - * @return {string} auth token - */ - p.performZabbixAPILogin = function() { - var options = { - url : this.url, - method : 'POST', - data: { - jsonrpc: '2.0', - method: 'user.login', - params: { - user: this.username, - password: this.password - }, - auth: null, - id: 1 - } - }; - - if (this.basicAuth || this.withCredentials) { - options.withCredentials = true; - } - if (this.basicAuth) { - options.headers = options.headers || {}; - options.headers.Authorization = this.basicAuth; - } - - return backendSrv.datasourceRequest(options).then(function (result) { - if (!result.data) { - return null; - } - return result.data.result; - }); - }; - - ////////////////////////// - // High-level functions // - ////////////////////////// - - p.getGroups = function() { - var params = { - output: ['name'], - sortfield: 'name' - }; - - return this.request('hostgroup.get', params).then(function(result) { - console.log("getGroups", result); - return result; - }); - }; - - p.getHosts = function() { - var params = { - output: ['name', 'host'], - sortfield: 'name', - selectGroups: [] - }; - - return this.request('host.get', params); - }; - - p.getApplications = function() { - var params = { - output: ['name'], - sortfield: 'name', - selectHosts: [] - }; - - return this.request('application.get', params); - }; - - p.getItems = function() { - var params = { - output: ['name', 'key_', 'value_type', 'hostid', 'status', 'state'], - sortfield: 'name', - selectApplications: [] - }; - - return this.request('item.get', params); - }; - - ///////////////////////// - // API method wrappers // - ///////////////////////// - - /** - * Request version of the Zabbix API. - * - * @return {string} Zabbix API version - */ - p.getZabbixAPIVersion = function() { - var options = { - method: 'POST', - headers: { - 'Content-Type': 'application/json' - }, - url: this.url, - data: { - jsonrpc: '2.0', - method: 'apiinfo.version', - params: [], - id: 1 - } - }; - - if (this.basicAuth || this.withCredentials) { - options.withCredentials = true; - } - if (this.basicAuth) { - options.headers = options.headers || {}; - options.headers.Authorization = this.basicAuth; - } - - return backendSrv.datasourceRequest(options).then(function (result) { - if (!result.data) { - return null; - } - return result.data.result; - }); - }; - - /** - * Perform history query from Zabbix API - * - * @param {Array} items Array of Zabbix item objects - * @param {Number} start Time in seconds - * @param {Number} end Time in seconds - * @return {Array} Array of Zabbix history objects - */ - p.getHistory = function(items, start, end) { - // Group items by value type - var grouped_items = _.groupBy(items, 'value_type'); - - // Perform request for each value type - return $q.all(_.map(grouped_items, function (items, value_type) { - var itemids = _.map(items, 'itemid'); - var params = { - output: 'extend', - history: value_type, - itemids: itemids, - sortfield: 'clock', - sortorder: 'ASC', - time_from: start - }; - - // Relative queries (e.g. last hour) don't include an end time - if (end) { - params.time_till = end; - } - - return this.request('history.get', params); - }, this)).then(function (results) { - return _.flatten(results); - }); - }; - - /** - * Perform trends query from Zabbix API - * Use trends api extension from ZBXNEXT-1193 patch. - * - * @param {Array} items Array of Zabbix item objects - * @param {Number} start Time in seconds - * @param {Number} end Time in seconds - * @return {Array} Array of Zabbix trend objects - */ - p.getTrends = function(items, start, end) { - // Group items by value type - var grouped_items = _.groupBy(items, 'value_type'); - - // Perform request for each value type - return $q.all(_.map(grouped_items, function (items, value_type) { - var itemids = _.map(items, 'itemid'); - var params = { - output: 'extend', - trend: value_type, - itemids: itemids, - sortfield: 'clock', - sortorder: 'ASC', - time_from: start - }; - - // Relative queries (e.g. last hour) don't include an end time - if (end) { - params.time_till = end; - } - - return this.request('trend.get', params); - }, this)).then(function (results) { - return _.flatten(results); - }); - }; - - /** - * Get the list of host groups - * - * @return {array} array of Zabbix hostgroup objects - */ - p.performHostGroupSuggestQuery = function() { - var params = { - output: ['name'], - sortfield: 'name', - // Return only host groups that contain hosts - real_hosts: true, - // Return only host groups that contain monitored hosts. - monitored_hosts: true - }; - - return this.performZabbixAPIRequest('hostgroup.get', params); - }; - - /** - * Get the list of hosts - * - * @param {string|string[]} groupids - * @return {Object} array of Zabbix host objects - */ - p.performHostSuggestQuery = function(groupids) { - var params = { - output: ['name', 'host'], - sortfield: 'name', - // Return only hosts that have items with numeric type of information. - with_simple_graph_items: true, - // Return only monitored hosts. - monitored_hosts: true - }; - // Return only hosts in given group - if (groupids) { - params.groupids = groupids; - } - return this.performZabbixAPIRequest('host.get', params); - }; - - /** - * Get the list of applications - * - * @param {array} hostids - * @param {array} groupids - * @return {Object} array of Zabbix application objects - */ - p.performAppSuggestQuery = function(hostids, /* optional */ groupids) { - var params = { - output: ['name'], - sortfield: 'name' - }; - if (hostids) { - params.hostids = hostids; - } - else if (groupids) { - params.groupids = groupids; - } - - return this.performZabbixAPIRequest('application.get', params); - }; - - /** - * Items request - * - * @param {string|string[]} hostids /////////////////////////// - * @param {string|string[]} applicationids // Zabbix API parameters // - * @param {string|string[]} groupids /////////////////////////// - * @return {string|string[]} Array of Zabbix API item objects - */ - p.performItemSuggestQuery = function(hostids, applicationids, groupids, itemtype) { - var params = { - output: ['name', 'key_', 'value_type', 'delay'], - sortfield: 'name', - //Include web items in the result - webitems: true, - // Return only numeric items - filter: { - value_type: [0, 3] - }, - // Return only enabled items - monitored: true, - searchByAny: true - }; - - if (itemtype === "text") { - params.filter.value_type = [1, 2, 4]; - } - - // Filter by hosts or by groups - if (hostids) { - params.hostids = hostids; - } else if (groupids) { - params.groupids = groupids; - } - - // If application selected return only relative items - if (applicationids) { - params.applicationids = applicationids; - } - - // Return host property for multiple hosts - if (!hostids || (_.isArray(hostids) && hostids.length > 1)) { - params.selectHosts = ['name']; - } - - return this.performZabbixAPIRequest('item.get', params); - }; - - /** - * Get groups by names - * - * @param {string or array} group group names - * @return {array} array of Zabbix API hostgroup objects - */ - p.getGroupByName = function (group) { - var params = { - output: ['name'] - }; - if (group && group[0] !== '*') { - params.filter = { - name: group - }; - } - return this.performZabbixAPIRequest('hostgroup.get', params); - }; - - /** - * Search group by name. - * - * @param {string} group group name - * @return {array} groups - */ - p.searchGroup = function (group) { - var params = { - output: ['name'], - search: { - name: group - }, - searchWildcardsEnabled: true - }; - return this.performZabbixAPIRequest('hostgroup.get', params); - }; - - /** - * Get hosts by names - * - * @param {string or array} hostnames hosts names - * @return {array} array of Zabbix API host objects - */ - p.getHostByName = function (hostnames) { - var params = { - output: ['host', 'name'] - }; - if (hostnames && hostnames[0] !== '*') { - params.filter = { - name: hostnames - }; - } - return this.performZabbixAPIRequest('host.get', params); - }; - - /** - * Get applications by names - * - * @param {string or array} application applications names - * @return {array} array of Zabbix API application objects - */ - p.getAppByName = function (application) { - var params = { - output: ['name'] - }; - if (application && application[0] !== '*') { - params.filter = { - name: application - }; - } - return this.performZabbixAPIRequest('application.get', params); - }; - - /** - * Get items belongs to passed groups, hosts and - * applications - * - * @param {string or array} groups - * @param {string or array} hosts - * @param {string or array} apps - * @return {array} array of Zabbix API item objects - */ - p.itemFindQuery = function(groups, hosts, apps, itemtype) { - var promises = []; - - // Get hostids from names - if (hosts && hosts[0] !== '*') { - promises.push(this.getHostByName(hosts)); - } - // Get groupids from names - else if (groups) { - promises.push(this.getGroupByName(groups)); - } - // Get applicationids from names - if (apps && apps[0] !== '*') { - promises.push(this.getAppByName(apps)); - } - - var self = this; - return $q.all(promises).then(function (results) { - results = _.flatten(results); - var groupids; - var hostids; - var applicationids; - if (groups) { - groupids = _.map(_.filter(results, function (object) { - return object.groupid; - }), 'groupid'); - } - if (hosts && hosts[0] !== '*') { - hostids = _.map(_.filter(results, function (object) { - return object.hostid; - }), 'hostid'); - } - if (apps && apps[0] !== '*') { - applicationids = _.map(_.filter(results, function (object) { - return object.applicationid; - }), 'applicationid'); - } - - return self.performItemSuggestQuery(hostids, applicationids, groupids, itemtype); - }); - }; - - /** - * Find applications belongs to passed groups and hosts - * - * @param {string or array} hosts - * @param {string or array} groups - * @return {array} array of Zabbix API application objects - */ - p.appFindQuery = function(hosts, groups) { - var promises = []; - - // Get hostids from names - if (hosts && hosts[0] !== '*') { - promises.push(this.getHostByName(hosts)); - } - // Get groupids from names - else if (groups) { - promises.push(this.getGroupByName(groups)); - } - - var self = this; - return $q.all(promises).then(function (results) { - results = _.flatten(results); - var groupids; - var hostids; - if (groups) { - groupids = _.map(_.filter(results, function (object) { - return object.groupid; - }), 'groupid'); - } - if (hosts && hosts[0] !== '*') { - hostids = _.map(_.filter(results, function (object) { - return object.hostid; - }), 'hostid'); - } - - return self.performAppSuggestQuery(hostids, groupids); - }); - }; - - /** - * Find hosts belongs to passed groups - * - * @param {string or array} groups - * @return {array} array of Zabbix API host objects - */ - p.hostFindQuery = function(groups) { - var self = this; - return this.getGroupByName(groups).then(function (results) { - results = _.flatten(results); - var groupids = _.map(_.filter(results, function (object) { - return object.groupid; - }), 'groupid'); - - return self.performHostSuggestQuery(groupids); - }); - }; - - p.getITService = function(/* optional */ serviceids) { - var params = { - output: 'extend', - serviceids: serviceids - }; - return this.performZabbixAPIRequest('service.get', params); - }; - - p.getSLA = function(serviceids, from, to) { - var params = { - serviceids: serviceids, - intervals: [{ - from: from, - to: to - }] - }; - return this.performZabbixAPIRequest('service.getsla', params); - }; - - p.getTriggers = function(limit, sortfield, groupids, hostids, applicationids, name) { - var params = { - output: 'extend', - expandDescription: true, - expandData: true, - monitored: true, - //only_true: true, - filter: { - value: 1 - }, - search : { - description: name - }, - searchWildcardsEnabled: false, - groupids: groupids, - hostids: hostids, - applicationids: applicationids, - limit: limit, - sortfield: 'lastchange', - sortorder: 'DESC' - }; - - if (sortfield) { - params.sortfield = sortfield; - } - - return this.performZabbixAPIRequest('trigger.get', params); - }; - - p.getAcknowledges = function(triggerids, from) { - var params = { - output: 'extend', - objectids: triggerids, - acknowledged: true, - select_acknowledges: 'extend', - sortfield: 'clock', - sortorder: 'DESC', - time_from: from - }; - - return this.performZabbixAPIRequest('event.get', params) - .then(function (events) { - return _.flatten(_.map(events, 'acknowledges')); - }); - }; - - return ZabbixAPI; - - }); - -});