Skip to content

Commit

Permalink
Add webhook mediatype for Zabbix 6.0 or higher
Browse files Browse the repository at this point in the history
  • Loading branch information
masa-orca committed Nov 10, 2023
1 parent 5dfbc6f commit 3422a75
Show file tree
Hide file tree
Showing 9 changed files with 407 additions and 64 deletions.
18 changes: 17 additions & 1 deletion .circleci/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ executors:
default: latest
docker:
- image: circleci/ruby:2.7.2-buster
- image: mysql:5.7
- image: mysql:<< parameters.mysql_tag >>
environment:
MYSQL_DATABASE: zabbix
MYSQL_USER: zabbix
Expand All @@ -43,6 +43,7 @@ jobs:
integration_test_with_zabbix_32:
executor:
name: zabbix
mysql_tag: 5.7
tag: ubuntu-3.2-latest
working_directory: ~/repo
environment:
Expand All @@ -53,13 +54,27 @@ jobs:
integration_test_with_zabbix_40:
executor:
name: zabbix
mysql_tag: 5.7
tag: ubuntu-4.0-latest
working_directory: ~/repo
environment:
ZABBIX_API: http://localhost:8080/
steps:
- integration_test_with_zabbix

integration_test_with_zabbix_60:
executor:
name: zabbix
mysql_tag: 8.2
tag: ubuntu-6.0-latest
working_directory: ~/repo
environment:
ZABBIX_API: http://localhost:8080/
ZABBIX_USER: Admin
ZABBIX_DISPATCHER_MEDIA_TYPE: webhook
steps:
- integration_test_with_zabbix

circleci_is_disabled_job:
docker:
- image: cimg/base:stable
Expand All @@ -74,6 +89,7 @@ workflows:
jobs:
- integration_test_with_zabbix_32
- integration_test_with_zabbix_40
- integration_test_with_zabbix_60
circleci_is_disabled:
jobs:
- circleci_is_disabled_job
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# Change Log

## 1.1.0

- Add webhook media_type for Zabbix 6.0 or higher

## 1.0.0

- Drop python 2.7 support.
Expand Down
28 changes: 26 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,14 @@ This README explains how this integration works, and how to configure it.
![Internal construction of this pack](./images/internal_construction.png)

# Requirements
## st2 pack
* Zabbix >=3.0. It has been tested with v3.0, v3.2 and v4.0.

* Zabbix >3.0. It has been tested with v3.0, v3.2 and v4.0.
## script type distpacher
* Zabbix >=3.0. It has been tested with v3.0, v3.2 and v4.0.

## webhook type dispatcher
* Zabbix >=6.0. It has been tested with v6.0.

# Installation
Install the pack:
Expand All @@ -34,6 +40,13 @@ Options:
-s Z_SENDTO, --sendto=Z_SENDTO
Address, user name or other identifier of the
recipient
-s Z_DISPATCHERTYPE, --type=Z_DISPATCHERTYPE
Type of way to dispatch. If you select script,
the Zabbix will use st2_dispatcher. On the
other hand, if you select webhook, this command
will import a webhook dispathcer mediatype which
is defined in media_stackstorm.yml

```
Example execution:
Expand All @@ -58,9 +71,12 @@ After executing the `register_st2_config_to_zabbix.py` command, you can notice t
You see following page, and you have to fill out with parameters for your st2 environment (the endpoint URLs of st2-api and st2-auth, and authentication information).
![](./images/configuration_for_mediatype2.png)
If you setup webhook dispatcher, you see following page.
![](./images/configuration_for_mediatype3.png)
You can specify additional parameters and you can handle them from the payload of the StackStorm's Trigger(`zabbix.event_handler`).
### Deploy the AlertScript
### Deploy the AlertScript for script dispatcher
The script `st2_dispatch.py` sends Zabbix events to the StackStorm server. Copy this script to the directory which Zabbix MediaType refers to. The directory is specified by the parameter of `AlertScriptsPath` in the Zabbix configuration file on the node which zabbix was installed.
```shell
Expand Down Expand Up @@ -253,6 +269,12 @@ Starting procedure to run the test is also simple, all you have to do is executi
$ bundle exec rspec
```
When you want to run test for webhook type, you have to execute following command.
```
$ ZABBIX_DISPATCHER_MEDIA_TYPE=webhook bundle exec rspec
```
# Advanced Usage
If you would prefer to use an API Key for auth in place of user/pass, you can do so by passing a JSON Dict as the first positional argument in your `Media Type` in place of:
```
Expand All @@ -277,6 +299,8 @@ This dict has the following valid keys
`api_key` will cause `st2_userid` and `st2_passwd` to be ignored (API Key prefered)
`trigger` allows you to specify your own trigger on st2 to send messages to. Default is `zabbix.event_handler`
> WARNING: webhook type dispatcher does NOT support user/pass auth, please use API Key.
### JSON Examples
API Key for Auth - `{"api_url":"https://stackstorm.yourdomain.com/api/v1", "api_key":"aaabbbccc111222333"}`
User/Pass for auth - `{"api_url":"https://stackstorm.yourdomain.com/api/v1", "auth_url":"https://stackstorm.yourdomain.com/auth", "st2_userid":"st2admin", "st2_passwd":"st2pass"}`
Expand Down
Binary file added images/configuration_for_mediatype3.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
236 changes: 236 additions & 0 deletions media_stackstorm.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,236 @@
zabbix_export:
version: '6.0'
media_types:
-
name: StackStorm
type: WEBHOOK
description: StackStorm
parameters:
-
name: alert_message
value: '{ALERT.MESSAGE}'
-
name: alert_subject
value: '{ALERT.SUBJECT}'
-
name: alert_sendto
value: '{ALERT.SENDTO}'
-
name: event_source
value: '{EVENT.SOURCE}'
-
name: st2_api_url
value: '<PLACE ST2 API URL>'
-
name: st2_api_key
value: '<PLACE ST2 API Key>'
-
name: st2_trigger
value: zabbix.event_handler
script: |
var St2 = {
params: {},
setParams: function (params) {
if (typeof params !== 'object') {
return;
}
St2.params = params;
},
setProxy: function (HTTPProxy) {
St2.HTTPProxy = HTTPProxy;
},
urlCheckFormat: function (api_url) {
if (typeof api_url === 'string' && !api_url.endsWith('/')) {
api_url += '/';
}
if (api_url.indexOf('http://') === -1 && api_url.indexOf('https://') === -1) {
api_url = 'https://' + api_url;
}
return api_url;
},
request: function (api_url, data) {
if (typeof St2.params !== 'object' || typeof St2.params['api_key'] === 'undefined' || St2.params['api_key'] === '') {
throw 'Required St2 param is not set: "api_key".';
}
var response,
request = new HttpRequest();
request.addHeader('Content-Type: application/json');
request.addHeader('St2-Api-Key: ' + St2.params.api_key);
const webhook_url = api_url + 'webhooks/st2';
if (typeof St2.HTTPProxy !== 'undefined' && St2.HTTPProxy !== '') {
request.setProxy(St2.HTTPProxy);
}
if (typeof data !== 'undefined') {
data = JSON.stringify(data);
}
Zabbix.log(4, '[ StackStorm Webhook ] Sending request: ' + webhook_url + ((typeof data === 'string')
? ('\n' + data)
: ''));
response = request.post(webhook_url, data);
Zabbix.log(4, '[ StackStorm Webhook ] Received response with status code ' +
request.getStatus() + '\n' + response);
if (response !== null) {
try {
response = JSON.parse(response);
}
catch (error) {
Zabbix.log(4, '[ StackStorm Webhook ] Failed to parse response received from StackStorm');
response = null;
}
}
if (typeof response !== 'object') {
throw 'Failed to process response received from StackStorm. Check debug log for more information.';
}
if (request.getStatus() < 200 || request.getStatus() >= 300) {
var message = 'Request failed with status code ' + request.getStatus();
if (response.message) {
message += ': ' + response.message;
}
throw message + ' Check debug log for more information.';
}
return response;
}
};
try {
var params = JSON.parse(value),
st2 = {},
data = {},
result
required_params = [
'alert_subject', 'alert_message',
'st2_api_url', 'st2_api_key', 'st2_trigger'
];
Object.keys(params)
.forEach(function (key) {
if (key.startsWith('st2_')) {
st2[key.substring(4)] = params[key];
}
else if (required_params.indexOf(key) !== -1 && params[key] === '') {
throw 'Parameter "' + key + '" can\'t be empty.';
}
});
// Check type of event. Possible values: 0 - Trigger
if (params.event_source != 0) {
throw ('Incorrect "event_source" parameter given: ' + params.event_source
+ '\nOnly trigger-based events are supported');
}
// Check for backslash in the end of url and schema.
st2.api_url = St2.urlCheckFormat(st2.api_url);
data.trigger = st2.trigger;
data.payload = {
alert_sendto: params.alert_sendto,
alert_subject: params.alert_subject,
alert_message: params.alert_message
}
St2.setParams(st2);
St2.setProxy(params.HTTPProxy);
var response = St2.request(st2.api_url, data);
Zabbix.log(4, '[ StackStorm Webhook ] Response: ' + JSON.stringify(response));
return JSON.stringify(response);
}
catch (error) {
Zabbix.log(4, '[ StackStorm Webhook ] ERROR: ' + error);
throw 'Sending failed: ' + error;
}
message_templates:
-
event_source: TRIGGERS
operation_mode: PROBLEM
subject: '[{TRIGGER.STATUS}] {TRIGGER.NAME}'
message: |
{
"event": {
"id": "{EVENT.ID}",
"time": "{EVENT.TIME}"
},
"trigger": {
"id": "{TRIGGER.ID}",
"name": "{TRIGGER.NAME}",
"status": "{TRIGGER.STATUS}"
},
"items": [
{
"name": "{ITEM.NAME1}",
"host": "{HOST.NAME1}",
"key": "{ITEM.KEY1}",
"value": "{ITEM.VALUE1}"
},
{
"name": "{ITEM.NAME2}",
"host": "{HOST.NAME2}",
"key": "{ITEM.KEY2}",
"value": "{ITEM.VALUE2}"
},
{
"name": "{ITEM.NAME3}",
"host": "{HOST.NAME3}",
"key": "{ITEM.KEY3}",
"value": "{ITEM.VALUE3}"
},
{
"name": "{ITEM.NAME4}",
"host": "{HOST.NAME4}",
"key": "{ITEM.KEY4}",
"value": "{ITEM.VALUE4}"
},
{
"name": "{ITEM.NAME5}",
"host": "{HOST.NAME5}",
"key": "{ITEM.KEY5}",
"value": "{ITEM.VALUE5}"
},
{
"name": "{ITEM.NAME6}",
"host": "{HOST.NAME6}",
"key": "{ITEM.KEY6}",
"value": "{ITEM.VALUE6}"
},
{
"name": "{ITEM.NAME7}",
"host": "{HOST.NAME7}",
"key": "{ITEM.KEY7}",
"value": "{ITEM.VALUE7}"
},
{
"name": "{ITEM.NAME8}",
"host": "{HOST.NAME8}",
"key": "{ITEM.KEY8}",
"value": "{ITEM.VALUE8}"
},
{
"name": "{ITEM.NAME9}",
"host": "{HOST.NAME9}",
"key": "{ITEM.KEY9}",
"value": "{ITEM.VALUE9}"
}
]
}
2 changes: 1 addition & 1 deletion pack.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ description: Zabbix Monitoring System
keywords:
- zabbix
- monitoring
version: 1.0.0
version: 1.1.0
author: Hiroyasu OHYAMA
email: [email protected]
python_versions:
Expand Down
2 changes: 2 additions & 0 deletions requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,5 @@ py-zabbix==1.1.3
st2client
pytz
tzlocal
looseversion
pyyaml
Loading

0 comments on commit 3422a75

Please sign in to comment.