Zabbix API: add types

This commit is contained in:
Alexander Zobnin
2020-05-18 11:37:22 +03:00
parent a3f45f1bb8
commit d7a96f06ee
6 changed files with 83 additions and 41 deletions

View File

@@ -165,6 +165,8 @@ export class ZabbixDatasource {
return this.queryNumericData(target, timeRange, useTrends, options);
} else if (target.queryType === c.MODE_TEXT) {
return this.queryTextData(target, timeRange);
} else {
return [];
}
} else if (target.queryType === c.MODE_ITEMID) {
// Item ID query

View File

@@ -0,0 +1,42 @@
export interface JSONRPCRequest {
jsonrpc: '2.0' | string;
method: string;
id: number;
auth?: string | null;
params?: JSONRPCRequestParams;
}
export interface JSONRPCResponse<T> {
jsonrpc: '2.0' | string;
id: number;
result?: T;
error?: JSONRPCError;
}
export interface JSONRPCError {
code?: number;
message?: string;
data?: string;
}
export interface GFHTTPRequest {
method: HTTPMethod;
url: string;
data?: any;
headers?: {[key: string]: string};
withCredentials?: boolean;
}
export type JSONRPCRequestParams = {[key: string]: any};
export type HTTPMethod = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' | 'HEAD' | 'CONNECT' | 'OPTIONS' | 'TRACE';
export type GFRequestOptions = {[key: string]: any};
export interface ZabbixRequestResponse {
data?: JSONRPCResponse<any>;
}
export type ZabbixAPIResponse<T> = T;
export type APILoginResponse = string;

View File

@@ -5,6 +5,7 @@ import * as utils from '../../../utils';
import { ZabbixAPICore } from './zabbixAPICore';
import { ZBX_ACK_ACTION_NONE, ZBX_ACK_ACTION_ACK, ZBX_ACK_ACTION_ADD_MESSAGE, MIN_SLA_INTERVAL } from '../../../constants';
import { ShowProblemTypes, ZBXProblem } from '../../../types';
import { JSONRPCRequestParams } from './types';
const DEFAULT_ZABBIX_VERSION = '3.0.0';
@@ -14,20 +15,20 @@ const DEFAULT_ZABBIX_VERSION = '3.0.0';
* Wraps API calls and provides high-level methods.
*/
export class ZabbixAPIConnector {
url: any;
username: any;
password: any;
url: string;
username: string;
password: string;
auth: string;
requestOptions: { basicAuth: any; withCredentials: any; };
loginPromise: any;
requestOptions: { basicAuth: any; withCredentials: boolean; };
loginPromise: Promise<string>;
loginErrorCount: number;
maxLoginAttempts: number;
zabbixAPICore: ZabbixAPICore;
getTrend: (items: any, timeFrom: any, timeTill: any) => Promise<any[]>;
version: any;
getVersionPromise: any;
version: string;
getVersionPromise: Promise<string>;
constructor(api_url, username, password, basicAuth, withCredentials) {
constructor(api_url: string, username: string, password: string, basicAuth: any, withCredentials: boolean) {
this.url = api_url;
this.username = username;
this.password = password;
@@ -54,7 +55,7 @@ export class ZabbixAPIConnector {
// Core method wrappers //
//////////////////////////
request(method, params) {
request(method: string, params: JSONRPCRequestParams): Promise<any> {
if (!this.version) {
return this.initVersion().then(() => this.request(method, params));
}
@@ -81,9 +82,8 @@ export class ZabbixAPIConnector {
* When API unauthenticated or auth token expired each request produce login()
* call. But auth token is common to all requests. This function wraps login() method
* and call it once. If login() already called just wait for it (return its promise).
* @return login promise
*/
loginOnce() {
loginOnce(): Promise<string> {
if (!this.loginPromise) {
this.loginPromise = Promise.resolve(
this.login().then(auth => {
@@ -99,7 +99,7 @@ export class ZabbixAPIConnector {
/**
* Get authentication token.
*/
login() {
login(): Promise<string> {
return this.zabbixAPICore.login(this.url, this.username, this.password, this.requestOptions);
}
@@ -110,7 +110,7 @@ export class ZabbixAPIConnector {
return this.zabbixAPICore.getVersion(this.url, this.requestOptions);
}
initVersion() {
initVersion(): Promise<string> {
if (!this.getVersionPromise) {
this.getVersionPromise = Promise.resolve(
this.getVersion().then(version => {
@@ -166,7 +166,7 @@ export class ZabbixAPIConnector {
return this.request('host.get', params);
}
getApps(hostids) {
getApps(hostids): Promise<any[]> {
const params = {
output: 'extend',
hostids: hostids

View File

@@ -2,19 +2,15 @@
* General Zabbix API methods
*/
import { getBackendSrv } from '@grafana/runtime';
import { JSONRPCRequest, ZabbixRequestResponse, JSONRPCError, APILoginResponse, GFHTTPRequest, GFRequestOptions } from './types';
export class ZabbixAPICore {
/** @ngInject */
constructor() {
}
/**
* Request data from Zabbix API
* @return {object} response.result
*/
request(api_url, method, params, options, auth?) {
const requestData: any = {
request(api_url: string, method: string, params: any, options: GFRequestOptions, auth?: string) {
const requestData: JSONRPCRequest = {
jsonrpc: '2.0',
method: method,
params: params,
@@ -29,7 +25,7 @@ export class ZabbixAPICore {
requestData.auth = auth;
}
const requestOptions: any = {
const requestOptions: GFHTTPRequest = {
method: 'POST',
url: api_url,
data: requestData,
@@ -51,7 +47,7 @@ export class ZabbixAPICore {
datasourceRequest(requestOptions) {
return getBackendSrv().datasourceRequest(requestOptions)
.then((response) => {
.then((response: ZabbixRequestResponse) => {
if (!response?.data) {
return Promise.reject(new ZabbixAPIError({data: "General Error, no data"}));
} else if (response?.data.error) {
@@ -69,7 +65,7 @@ export class ZabbixAPICore {
* Get authentication token.
* @return {string} auth token
*/
login(api_url, username, password, options) {
login(api_url: string, username: string, password: string, options: GFRequestOptions): Promise<APILoginResponse> {
const params = {
user: username,
password: password
@@ -81,7 +77,7 @@ export class ZabbixAPICore {
* Get Zabbix API version
* Matches the version of Zabbix starting from Zabbix 2.0.4
*/
getVersion(api_url, options) {
getVersion(api_url: string, options: GFRequestOptions): Promise<string> {
return this.request(api_url, 'apiinfo.version', [], options).catch(err => {
console.error(err);
return undefined;
@@ -91,12 +87,12 @@ export class ZabbixAPICore {
// Define zabbix API exception type
export class ZabbixAPIError {
code: any;
name: any;
data: any;
code: number;
name: string;
data: string;
message: string;
constructor(error) {
constructor(error: JSONRPCError) {
this.code = error.code || null;
this.name = error.message || "";
this.data = error.data || "";

View File

@@ -10,6 +10,11 @@ import { InfluxDBConnector } from './connectors/influxdb/influxdbConnector';
import { ZabbixConnector } from './types';
import { joinTriggersWithProblems } from '../problemsHandler';
interface AppsResponse extends Array<any> {
appFilterEmpty?: boolean;
hostids?: any[];
}
const REQUESTS_TO_PROXYFY = [
'getHistory', 'getTrend', 'getGroups', 'getHosts', 'getApps', 'getItems', 'getMacros', 'getItemsByIDs',
'getEvents', 'getAlerts', 'getHostAlerts', 'getAcknowledges', 'getITService', 'getSLA', 'getVersion', 'getProxies',
@@ -178,9 +183,9 @@ export class Zabbix implements ZabbixConnector {
return Promise.all([
this.getHosts(...filters),
this.getApps(...filters),
]).then((results) => {
// tslint:disable-next-line: prefer-const
let [hosts, apps] = results;
]).then(results => {
const hosts = results[0];
let apps: AppsResponse = results[1];
if (apps.appFilterEmpty) {
apps = [];
}
@@ -224,7 +229,7 @@ export class Zabbix implements ZabbixConnector {
});
}
getApps(groupFilter?, hostFilter?, appFilter?) {
getApps(groupFilter?, hostFilter?, appFilter?): Promise<AppsResponse> {
return this.getHosts(groupFilter, hostFilter)
.then(hosts => {
const hostids = _.map(hosts, 'hostid');
@@ -232,10 +237,10 @@ export class Zabbix implements ZabbixConnector {
return this.zabbixAPI.getApps(hostids)
.then(apps => filterByQuery(apps, appFilter));
} else {
return {
appFilterEmpty: true,
hostids: hostids
};
const appsResponse: AppsResponse = hostids;
appsResponse.hostids = hostids;
appsResponse.appFilterEmpty = true;
return Promise.resolve(appsResponse);
}
});
}

View File

@@ -2,10 +2,7 @@
"compilerOptions": {
"moduleResolution": "node",
"target": "es5",
"lib": [
"es6",
"dom"
],
"lib": [ "es6", "dom", "es2017" ],
"rootDir": "./src",
"jsx": "react",
"module": "esnext",