mirror of
https://github.com/valitydev/wazuh-kibana-app.git
synced 2024-11-08 10:43:51 +00:00
258 lines
7.6 KiB
JavaScript
258 lines
7.6 KiB
JavaScript
module.exports = (server, options) => {
|
|
|
|
// Elastic JS Client
|
|
const elasticRequest = server.plugins.elasticsearch.getCluster('data');
|
|
|
|
//Handlers
|
|
const fetchElastic = (req, payload) => {
|
|
return elasticRequest.callWithRequest(req, 'search', {
|
|
index: 'wazuh-alerts-*',
|
|
type: 'wazuh',
|
|
body: payload
|
|
});
|
|
};
|
|
|
|
const getConfig = (callback) => {
|
|
elasticRequest
|
|
.callWithInternalUser('search', {
|
|
index: '.wazuh',
|
|
type: 'wazuh-configuration',
|
|
q: 'active:true'
|
|
})
|
|
.then((data) => {
|
|
if (data.hits.total === 1) {
|
|
callback({
|
|
'user': data.hits.hits[0]._source.api_user,
|
|
'password': Buffer.from(data.hits.hits[0]._source.api_password, 'base64').toString("ascii"),
|
|
'url': data.hits.hits[0]._source.url,
|
|
'port': data.hits.hits[0]._source.api_port,
|
|
'insecure': data.hits.hits[0]._source.insecure,
|
|
'cluster_info': data.hits.hits[0]._source.cluster_info,
|
|
'extensions': data.hits.hits[0]._source.extensions
|
|
});
|
|
} else {
|
|
callback({
|
|
'error': 'no credentials',
|
|
'error_code': 1
|
|
});
|
|
}
|
|
})
|
|
.catch((error) => {
|
|
callback({
|
|
'error': 'no elasticsearch',
|
|
'error_code': 2
|
|
});
|
|
});
|
|
};
|
|
|
|
// Returns alerts count for fields/value array between timeGTE and timeLT
|
|
const alertsCount = (req, reply) => {
|
|
|
|
var payload = {
|
|
"size": 1,
|
|
"query": {
|
|
"bool": {
|
|
"must": [],
|
|
"filter": {
|
|
"range": {
|
|
"@timestamp": {}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
};
|
|
|
|
// Set up time interval, default to Last 15m
|
|
const timeGTE = req.payload.timeinterval.gte ? req.payload.timeinterval.gte : 'now-15m';
|
|
const timeLT = req.payload.timeinterval.lt ? req.payload.timeinterval.lt : 'now';
|
|
payload.query.bool.filter.range['@timestamp']['gte'] = timeGTE;
|
|
|
|
if (timeLT !== 'now'){
|
|
payload.query.bool.filter.range['@timestamp']['lte'] = timeLT;
|
|
} else {
|
|
payload.query.bool.filter.range['@timestamp']['lt'] = timeLT;
|
|
}
|
|
|
|
// Set up match for default cluster name
|
|
payload.query.bool.must.push({
|
|
'match': {
|
|
'cluster.name': req.payload.cluster
|
|
}
|
|
});
|
|
|
|
// Set up match for different pairs field/value
|
|
for(let item of req.payload.fields){
|
|
let obj = {};
|
|
obj[item.field] = item.value;
|
|
payload.query.bool.must.push({ 'match': obj });
|
|
}
|
|
|
|
fetchElastic(req, payload)
|
|
.then((data) => {
|
|
reply({
|
|
'statusCode': 200,
|
|
'data': data.hits.total
|
|
});
|
|
})
|
|
.catch((error) => {
|
|
reply({
|
|
'statusCode': 500,
|
|
'error': 9,
|
|
'message': 'Could not get data from elasticsearch'
|
|
}).code(500);
|
|
});
|
|
};
|
|
|
|
const getFieldTop = (req, reply) => {
|
|
|
|
// Top field payload
|
|
var payload = {
|
|
"size": 1,
|
|
"query": {
|
|
"bool": {
|
|
"must": [],
|
|
"filter": {
|
|
"range": {
|
|
"@timestamp": {}
|
|
}
|
|
}
|
|
}
|
|
},
|
|
"aggs": {
|
|
"2": {
|
|
"terms": {
|
|
"field": "",
|
|
"size": 1,
|
|
"order": {
|
|
"_count": "desc"
|
|
}
|
|
}
|
|
}
|
|
}
|
|
};
|
|
|
|
// Set up time interval, default to Last 24h
|
|
const timeGTE = 'now-1d';
|
|
const timeLT = 'now';
|
|
payload.query.bool.filter.range['@timestamp']['gte'] = timeGTE;
|
|
payload.query.bool.filter.range['@timestamp']['lt'] = timeLT;
|
|
|
|
// Set up match for default cluster name
|
|
payload.query.bool.must.push({
|
|
"match": {
|
|
"cluster.name": req.params.cluster
|
|
}
|
|
});
|
|
payload.aggs['2'].terms.field = req.params.field;
|
|
|
|
fetchElastic(req, payload)
|
|
.then((data) => {
|
|
|
|
if (data.hits.total === 0 || typeof data.aggregations['2'].buckets[0] === 'undefined'){
|
|
reply({
|
|
'statusCode': 200,
|
|
'data': ''
|
|
});
|
|
} else {
|
|
reply({
|
|
'statusCode': 200,
|
|
'data': data.aggregations['2'].buckets[0].key
|
|
});
|
|
}
|
|
})
|
|
.catch((error) => {
|
|
reply({
|
|
'statusCode': 500,
|
|
'error': 9,
|
|
'message': 'Could not get data from elasticsearch'
|
|
}).code(500);
|
|
});
|
|
};
|
|
|
|
const getSetupInfo = (req, reply) => {
|
|
elasticRequest
|
|
.callWithInternalUser('search', {
|
|
index: '.wazuh-version',
|
|
type: 'wazuh-version'
|
|
})
|
|
.then((data) => {
|
|
if (data.hits.total === 0) {
|
|
reply({
|
|
'statusCode': 200,
|
|
'data': ''
|
|
});
|
|
} else {
|
|
reply({
|
|
'statusCode': 200,
|
|
'data': data.hits.hits[0]._source
|
|
});
|
|
}
|
|
})
|
|
.catch((error) => {
|
|
reply({
|
|
'statusCode': 500,
|
|
'error': 9,
|
|
'message': 'Could not get data from elasticsearch'
|
|
}).code(500);
|
|
});
|
|
};
|
|
|
|
module.exports = getConfig;
|
|
|
|
//Server routes
|
|
|
|
/*
|
|
* GET /api/wazuh-elastic/top/{cluster}/{field}/{time?}
|
|
* Returns the agent with most alerts
|
|
*
|
|
**/
|
|
server.route({
|
|
method: 'GET',
|
|
path: '/api/wazuh-elastic/top/{cluster}/{field}/{time?}',
|
|
handler: getFieldTop
|
|
});
|
|
|
|
/*
|
|
* GET /api/wazuh-elastic/top/{cluster}/{field}/{fieldFilter}/{fieldValue}/{time?}
|
|
* Returns the agent with most alerts
|
|
*
|
|
**/
|
|
server.route({
|
|
method: 'GET',
|
|
path: '/api/wazuh-elastic/top/{cluster}/{field}/{fieldFilter}/{fieldValue}/{time?}',
|
|
handler: getFieldTop
|
|
});
|
|
|
|
/*
|
|
* GET /api/wazuh-elastic/top/{cluster}/{field}/{fieldFilter}/{fieldValue}/{fieldFilter}/{fieldValue}/{time?}
|
|
* Returns the agent with most alerts
|
|
*
|
|
**/
|
|
server.route({
|
|
method: 'GET',
|
|
path: '/api/wazuh-elastic/top/{cluster}/{field}/{fieldFilter}/{fieldValue}/{fieldFilter2}/{fieldValue2}/{time?}',
|
|
handler: getFieldTop
|
|
});
|
|
|
|
/*
|
|
* /api/wazuh-elastic/alerts-count
|
|
* Returns alerts count for fields/value array between timeGTE and timeLT
|
|
* @params: fields[{field,value}], cluster, timeinterval{gte,lte}
|
|
**/
|
|
server.route({
|
|
method: 'POST',
|
|
path: '/api/wazuh-elastic/alerts-count/',
|
|
handler: alertsCount
|
|
});
|
|
|
|
/*
|
|
* GET /api/wazuh-elastic/setup
|
|
* Return Wazuh Appsetup info
|
|
*
|
|
**/
|
|
server.route({
|
|
method: 'GET',
|
|
path: '/api/wazuh-elastic/setup',
|
|
handler: getSetupInfo
|
|
});
|
|
}; |