[EEM] Use top_metrics for identity fields lifting (#188315)

This PR converts the identity fields in the latest transform from a
`terms` aggregation to a `top_metric` aggregation in an effort to
simplify the implementation since we have to convert a terms aggregation
from keys to an array of strings. With the `top_metrics` implementation,
we just need to use the `dot_expander` processors along with a `set`
processor to get a single (non-array) field.

---------

Co-authored-by: Chris Cowan <chris@elastic.co>
This commit is contained in:
Milton Hultgren 2024-07-23 00:15:24 +02:00 committed by GitHub
parent a68f812800
commit dd126c4868
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 84 additions and 31 deletions

View file

@ -73,21 +73,27 @@ if (ctx.entity?.metadata?.sourceIndex.data != null) {
},
},
Object {
"script": Object {
"if": "ctx.entity.identity.log?.logger != null && ctx.entity.identity.log.logger.size() != 0",
"source": "if (ctx.log == null) {
ctx.log = new HashMap();
}
ctx.log.logger = ctx.entity.identity.log.logger.keySet().toArray()[0];",
"dot_expander": Object {
"field": "log.logger",
"path": "entity.identity.log.logger.top_metric",
},
},
Object {
"script": Object {
"if": "ctx.entity.identity.event?.category != null && ctx.entity.identity.event.category.size() != 0",
"source": "if (ctx.event == null) {
ctx.event = new HashMap();
}
ctx.event.category = ctx.entity.identity.event.category.keySet().toArray()[0];",
"set": Object {
"field": "log.logger",
"value": "{{entity.identity.log.logger.top_metric.log.logger}}",
},
},
Object {
"dot_expander": Object {
"field": "event.category",
"path": "entity.identity.event.category.top_metric",
},
},
Object {
"set": Object {
"field": "event.category",
"value": "{{entity.identity.event.category.top_metric.event.category}}",
},
},
Object {

View file

@ -38,16 +38,30 @@ function createMetadataPainlessScript(definition: EntityDefinition) {
}
function liftIdentityFieldsToDocumentRoot(definition: EntityDefinition) {
return definition.identityFields.map((identityField) => {
const optionalFieldPath = identityField.field.replaceAll('.', '?.');
const assignValue = `ctx.${identityField.field} = ctx.entity.identity.${identityField.field}.keySet().toArray()[0];`;
return {
script: {
if: `ctx.entity.identity.${optionalFieldPath} != null && ctx.entity.identity.${identityField.field}.size() != 0`,
source: cleanScript(`${initializePathScript(identityField.field)}\n${assignValue}`),
},
};
});
return definition.identityFields
.map((identityField) => {
const setProcessor = {
set: {
field: identityField.field,
value: `{{entity.identity.${identityField.field}.top_metric.${identityField.field}}}`,
},
};
if (!identityField.field.includes('.')) {
return [setProcessor];
}
return [
{
dot_expander: {
field: identityField.field,
path: `entity.identity.${identityField.field}.top_metric`,
},
},
setProcessor,
];
})
.flat();
}
export function generateLatestProcessors(definition: EntityDefinition) {

View file

@ -48,15 +48,37 @@ Object {
},
},
"entity.identity.event.category": Object {
"terms": Object {
"field": "event.category",
"size": 1,
"aggs": Object {
"top_metric": Object {
"top_metrics": Object {
"metrics": Object {
"field": "event.category",
},
"sort": "_score",
},
},
},
"filter": Object {
"exists": Object {
"field": "event.category",
},
},
},
"entity.identity.log.logger": Object {
"terms": Object {
"field": "log.logger",
"size": 1,
"aggs": Object {
"top_metric": Object {
"top_metrics": Object {
"metrics": Object {
"field": "log.logger",
},
"sort": "_score",
},
},
},
"filter": Object {
"exists": Object {
"field": "log.logger",
},
},
},
"entity.lastSeenTimestamp": Object {

View file

@ -12,9 +12,20 @@ export function generateIdentityAggregations(definition: EntityDefinition) {
(aggs, identityField) => ({
...aggs,
[`entity.identity.${identityField.field}`]: {
terms: {
field: identityField.field,
size: 1,
filter: {
exists: {
field: identityField.field,
},
},
aggs: {
top_metric: {
top_metrics: {
metrics: {
field: identityField.field,
},
sort: '_score',
},
},
},
},
}),