Skip to content

Commit de34af0

Browse files
committed
Change ElasticsearchWriter to write perfdata as an array of objects
Prior to this change the ElasticsearchWriter created a new field for every metric in check command. This leads to a vast number of fields in the indices, aka a field mapping explosion. Now, it uses an array of objects. This avoids the explosion, Makes the index fields more predictable when searching and Makes the perfdata independently searchable.
1 parent f42510f commit de34af0

File tree

2 files changed

+26
-16
lines changed

2 files changed

+26
-16
lines changed

doc/14-features.md

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -370,7 +370,15 @@ See: [ElasticsearchWriter](09-object-types.md#objecttype-elasticsearchwriter)
370370
Metric values are stored like this:
371371

372372
```
373-
check_result.perfdata.<perfdata-label>.value
373+
check_result.perfdata: [
374+
{
375+
"crit": 0,
376+
"label": "example",
377+
"min": 0,
378+
"value": 0,
379+
"warn": 0
380+
}
381+
]
374382
```
375383

376384
The following characters are escaped in perfdata labels:
@@ -388,14 +396,7 @@ add more subsequent levels inside the tree.
388396
and is therefore replaced by `.`.
389397

390398
Icinga 2 automatically adds the following threshold metrics
391-
if existing:
392-
393-
```
394-
check_result.perfdata.<perfdata-label>.min
395-
check_result.perfdata.<perfdata-label>.max
396-
check_result.perfdata.<perfdata-label>.warn
397-
check_result.perfdata.<perfdata-label>.crit
398-
```
399+
if existing: min, max, warn, crit
399400

400401
Additionally it is possible to configure custom tags that are applied to the metrics via `host_tags_template` or `service_tags_template`.
401402
Depending on whether the write event was triggered on a service or host object, additional tags are added to the ElasticSearch entries.

lib/perfdata/elasticsearchwriter.cpp

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -189,6 +189,9 @@ void ElasticsearchWriter::AddCheckResult(const Dictionary::Ptr& fields, const Ch
189189

190190
if (perfdata) {
191191
ObjectLock olock(perfdata);
192+
193+
Array::Ptr perfdatapoints = new Array();
194+
192195
for (const Value& val : perfdata) {
193196
PerfdataValue::Ptr pdv;
194197

@@ -212,22 +215,28 @@ void ElasticsearchWriter::AddCheckResult(const Dictionary::Ptr& fields, const Ch
212215
boost::replace_all(escapedKey, "\\", "_");
213216
boost::algorithm::replace_all(escapedKey, "::", ".");
214217

215-
String perfdataPrefix = prefix + "perfdata." + escapedKey;
218+
Dictionary::Ptr datapoint = new Dictionary();
216219

217-
fields->Set(perfdataPrefix + ".value", pdv->GetValue());
220+
datapoint->Set("label", escapedKey);
221+
datapoint->Set("value", pdv->GetValue());
218222

219223
if (!pdv->GetMin().IsEmpty())
220-
fields->Set(perfdataPrefix + ".min", pdv->GetMin());
224+
datapoint->Set("min", pdv->GetMin());
221225
if (!pdv->GetMax().IsEmpty())
222-
fields->Set(perfdataPrefix + ".max", pdv->GetMax());
226+
datapoint->Set("max", pdv->GetMax());
223227
if (!pdv->GetWarn().IsEmpty())
224-
fields->Set(perfdataPrefix + ".warn", pdv->GetWarn());
228+
datapoint->Set("warn", pdv->GetWarn());
225229
if (!pdv->GetCrit().IsEmpty())
226-
fields->Set(perfdataPrefix + ".crit", pdv->GetCrit());
230+
datapoint->Set("crit", pdv->GetCrit());
227231

228232
if (!pdv->GetUnit().IsEmpty())
229-
fields->Set(perfdataPrefix + ".unit", pdv->GetUnit());
233+
datapoint->Set("unit", pdv->GetUnit());
234+
235+
perfdatapoints->Add(datapoint);
230236
}
237+
238+
String perfdataPrefix = prefix + "perfdata";
239+
fields->Set(perfdataPrefix, std::move(perfdatapoints));
231240
}
232241
}
233242

0 commit comments

Comments
 (0)