Elasticsearch: pipeline di aggregazione

Elasticsearch offre la possibilità di estrarre statistiche e gruppi di dati mediante le funzioni aggregazione. In molti contesti, però, è necessario concatenare i risultati di queste analisi per ottenere risultati più raffinati. Vediamo come le pipeline di aggregazione ci permettono di ottenere i risultati di nostro interesse.

Share

Reading time: 11 minutes

Negli articoli precedenti, Elasticsearch: aggregazioni a bucket [parte 1] e Elasticsearch: aggregazioni a bucket [parte 2], abbiamo visto come Elasticsearch ci permette di estrarre statistiche e creare sottoinsiemi dai dati. Alcune delle funzioni viste ritornano informazioni molto interessanti. Tuttavia, in molti casi è necessario usare il risultato visto in precedenza per effettuare nuove analisi. Ciò si può fare con le pipeline di aggregazione. Queste, infatti, permettono di concatenare le aggregazioni, ossia inviando i risultati di un’aggregazione come input a un’altra per ottenere un risultato più dettagliato. È possibile utilizzare le pipeline di aggregazione per calcolare misure statistiche e matematiche complesse come derivate, medie mobili, somme cumulative e così via.

Sintassi dell’aggregazione di pipeline

Una pipeline di aggregazione utilizza la proprietà buckets_path per accedere ai risultati di altre aggregazioni. La proprietà buckets_path ha una sintassi specifica:

buckets_path = <AGG_NAME>[<AGG_SEPARATOR>,<AGG_NAME>]*
               [<METRIC_SEPARATOR>, <METRIC>]; 

dove:

  • AGG_NAME è il nome dell’aggregazione.
  • AGG_SEPARATOR separa le aggregazioni. È rappresentato come >.
  • METRIC_SEPARATOR separa le aggregazioni dalle relative metriche. È rappresentato come …
  • METRIC è il nome della metrica, nel caso di aggregazioni metriche a più valori.

Ad esempio, my_sum.sum seleziona la metrica della somma di un’aggregazione chiamata my_sum. popular_tags>my_sum.sum annida my_sum.sum nell’aggregazione popular_tags.

È possibile specificare anche i seguenti parametri aggiuntivi:

  • gap_policy: I dati del mondo reale possono contenere lacune o valori nulli. Con la proprietà gap_policy si può specificare la politica per gestire questi dati mancanti. Si può impostare la proprietà gap_policy su skip per saltare i dati mancanti e continuare dal prossimo valore disponibile, oppure su insert_zeros per sostituire i valori mancanti con zero e continuare l’esecuzione.
  • format: Il tipo di formato per il valore di uscita. Ad esempio, yyyy-MM-dd per un valore di data.

Un esempio veloce

Per sommare tutti i bucket restituiti dall’aggregazione sum_total_memory:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "number_of_bytes": {
      "histogram": {
        "field": "bytes",
        "interval": 10000
      },
      "aggs": {
        "sum_total_memory": {
          "sum": {
            "field": "phpmemory"
          }
        }
      }
    },
    "sum_copies": {
      "sum_bucket": {
        "buckets_path": "number_of_bytes>sum_total_memory"
      }
    }
  }
} 

Esempio di risposta

...
"aggregations" : {
  "number_of_bytes" : {
    "buckets" : [
      {
        "key" : 0.0,
        "doc_count" : 13372,
        "sum_total_memory" : {
          "value" : 9.12664E7
        }
      },
      {
        "key" : 10000.0,
        "doc_count" : 702,
        "sum_total_memory" : {
          "value" : 0.0
        }
      }
    ]
  },
  "sum_copies" : {
    "value" : 9.12664E7
  }
 }
} 

Tipi di pipeline di aggregazione

Le pipeline di aggregazione sono di due tipi:

 

Aggregazioni tra fratelli (sibling)

Le aggregazioni sibling prendono l'output di un'aggregazione nidificata e producono nuovi bucket o nuove aggregazioni allo stesso livello dei bucket nidificati. Le aggregazioni di tipo sibling devono essere un'aggregazione multi-bucket (hanno più valori raggruppati per un determinato campo) e la metrica deve essere un valore numerico. min_bucket, max_bucket, sum_bucket e avg_bucket sono aggregazioni fratelli comuni.

Aggregazioni padre (parent)

Le aggregazioni padre prendono l'output di un'aggregazione esterna e producono nuovi bucket o nuove aggregazioni allo stesso livello dei bucket esistenti. Le aggregazioni padre devono avere min_doc_count impostato a 0 (valore predefinito per le aggregazioni di istogrammi) e la metrica specificata deve essere un valore numerico. Se min_doc_count è maggiore di 0, alcuni bucket vengono omessi, il che potrebbe portare a risultati errati. I derivati e cumulative_sum sono aggregazioni parentali comuni.

Di seguito vedremo le aggregazioni maggior mente usate appartenente alle due categorie.

avg_bucket, sum_bucket, min_bucket, max_bucket

Le aggregazioni avg_bucket, sum_bucket, min_bucket e max_bucket sono aggregazioni sibling che calcolano la media, la somma, i valori minimi e massimi di una metrica in ogni bucket di un’aggregazione precedente.

L’esempio seguente crea un istogramma di date con un intervallo di un mese. La sotto-aggregazione sum calcola la somma di tutti i byte per ogni mese. Infine, l’aggregazione avg_bucket utilizza questa somma per calcolare il numero medio di byte al mese:

POST kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "visits_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "sum_of_bytes": {
          "sum": {
            "field": "bytes"
          }
        }
      }
    },
    "avg_monthly_bytes": {
      "avg_bucket": {
        "buckets_path": "visits_per_month>sum_of_bytes"
      }
    }
  }
} 

Esempio di risposta

...
"aggregations" : {
  "visits_per_month" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "sum_of_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "sum_of_bytes" : {
          "value" : 3.8880434E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "sum_of_bytes" : {
          "value" : 3.1445055E7
        }
      }
    ]
  },
  "avg_monthly_bytes" : {
    "value" : 2.6575229666666668E7
  }
 }
} 

In modo analogo, è possibile calcolare i valori sum_bucket, min_bucket e max_bucket per i byte al mese.

stats_bucket, extended_stats_bucket

L’aggregazione stats_bucket è un’aggregazione sibling che restituisce una serie di statistiche (conteggio, min, max, avg e somma) per i bucket di un’aggregazione precedente.

L’esempio seguente restituisce le statistiche di base per i bucket restituiti dall’aggregazione sum_of_bytes annidata nell’aggregazione visits_per_month:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "visits_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "sum_of_bytes": {
          "sum": {
            "field": "bytes"
          }
        }
      }
    },
    "stats_monthly_bytes": {
      "stats_bucket": {
        "buckets_path": "visits_per_month>sum_of_bytes"
      }
    }
  }
} 

Esempio di risposta

"stats_monthly_bytes" : {
  "count" : 3,
  "min" : 9400200.0,
  "max" : 3.8880434E7,
  "avg" : 2.6575229666666668E7,
  "sum" : 7.9725689E7
  }
 }
} 

L’aggregazione extended_stats è una versione estesa dell’aggregazione stats. Oltre a includere le statistiche di base, extended_stats fornisce anche statistiche come sum_of_squares, varianza e std_deviation.

Esempio di risposta

"stats_monthly_visits" : {
  "count" : 3,
  "min" : 9400200.0,
  "max" : 3.8880434E7,
  "avg" : 2.6575229666666668E7,
  "sum" : 7.9725689E7,
  "sum_of_squares" : 2.588843392021381E15,
  "variance" : 1.5670496550438025E14,
  "variance_population" : 1.5670496550438025E14,
  "variance_sampling" : 2.3505744825657038E14,
  "std_deviation" : 1.251818539183616E7,
  "std_deviation_population" : 1.251818539183616E7,
  "std_deviation_sampling" : 1.5331583357780447E7,
  "std_deviation_bounds" : {
    "upper" : 5.161160045033899E7,
    "lower" : 1538858.8829943463,
    "upper_population" : 5.161160045033899E7,
    "lower_population" : 1538858.8829943463,
    "upper_sampling" : 5.723839638222756E7,
    "lower_sampling" : -4087937.0488942266
   }
  }
 }
} 

bucket_script, bucket_selector

L’aggregazione bucket_script è un’aggregazione padre che esegue uno script per eseguire i calcoli per-bucket di un’aggregazione precedente. Assicurarsi che le metriche siano di tipo numerico e che i valori restituiti siano anch’essi numerici.

Utilizzare il parametro script per aggiungere lo script. Lo script può essere in linea, in un file o in un indice. Per abilitare lo script inline, aggiungere la seguente riga al file elasticsearch.yml nella cartella config:

script.inline: on

La proprietà buckets_path è composta da più voci. Ogni voce è composta da una chiave e da un valore. La chiave è il nome del valore che si può usare nello script.

La sintassi di base è:

{
  "bucket_script": {
    "buckets_path": {
    "my_var1": "the_sum",
    "my_var2": "the_value_count"
  },
 "script": "params.my_var1 / params.my_var2"
  }
} 

L’esempio seguente utilizza l’aggregazione somma sui bucket generati da un istogramma di date. Dai valori dei bucket risultanti, viene calcolata la percentuale di RAM in un intervallo di 10.000 byte nel contesto di un’estensione zip:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "sales_per_month": {
      "histogram": {
        "field": "bytes",
        "interval": "10000"
      },
      "aggs": {
        "total_ram": {
          "sum": {
            "field": "machine.ram"
          }
        },
        "ext-type": {
          "filter": {
            "term": {
              "extension.keyword": "zip"
            }
          },
          "aggs": {
            "total_ram": {
              "sum": {
                "field": "machine.ram"
              }
            }
          }
        },
        "ram-percentage": {
          "bucket_script": {
            "buckets_path": {
              "machineRam": "ext-type>total_ram",
              "totalRam": "total_ram"
            },
            "script": "params.machineRam / params.totalRam"
          }
        }
      }
    }
  }
} 

Esempio di risposta

"aggregations" : {
  "sales_per_month" : {
    "buckets" : [
      {
        "key" : 0.0,
        "doc_count" : 13372,
        "os-type" : {
          "doc_count" : 1558,
          "total_ram" : {
            "value" : 2.0090783268864E13
          }
        },
        "total_ram" : {
          "value" : 1.7214228922368E14
        },
        "ram-percentage" : {
          "value" : 0.11671032934131736
        }
      },
      {
        "key" : 10000.0,
        "doc_count" : 702,
        "os-type" : {
          "doc_count" : 116,
          "total_ram" : {
            "value" : 1.622423896064E12
          }
        },
        "total_ram" : {
          "value" : 9.015136354304E12
        },
        "ram-percentage" : {
          "value" : 0.17996665078608862
        }
      }
    ]
  }
 }
} 

La percentuale di RAM viene calcolata e aggiunta alla fine di ogni bucket.

L’aggregazione bucket_selector è un’aggregazione basata su script che seleziona i bucket restituiti da un’aggregazione di istogrammi (o date_histogram). Si usa in scenari in cui non si vogliono certi bucket nell’output in base a condizioni fornite dall’utente.

L’aggregazione bucket_selector esegue uno script per decidere se un bucket rimane nell’aggregazione multi-bucket padre.

La sintassi di base è:

{
  "bucket_selector": {
    "buckets_path": {
    "my_var1": "the_sum",
    "my_var2": "the_value_count"
  },
  "script": "params.my_var1 / params.my_var2"
  }
} 

L’esempio seguente calcola la somma dei byte e poi valuta se questa somma è maggiore di 20.000. Se è vero, il bucket viene mantenuto nell’elenco dei bucket. Altrimenti, viene eliminato dall’output finale.

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "bytes_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "total_bytes": {
          "sum": {
            "field": "bytes"
          }
        },
        "bytes_bucket_filter": {
          "bucket_selector": {
            "buckets_path": {
              "totalBytes": "total_bytes"
            },
            "script": "params.totalBytes > 20000"
          }
        }
      }
    }
  }
} 

Esempio di risposta

"aggregations" : {
  "bytes_per_month" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "total_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "total_bytes" : {
          "value" : 3.8880434E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "total_bytes" : {
          "value" : 3.1445055E7
        }
      }
    ]
  }
 }
} 

bucket_sort

L’aggregazione bucket_sort è un’aggregazione padre che ordina i bucket di un’aggregazione precedente.

È possibile specificare diversi campi di ordinamento e l’ordine corrispondente. Inoltre, è possibile ordinare ogni bucket in base alla sua chiave, al conteggio o alle sue sotto-aggregazioni. È anche possibile troncare i bucket impostando i parametri da e dimensione.

La sintassi è la seguente:

{
  "bucket_sort": {
    "sort": [
    {"sort_field_1": {"order": "asc"}},
    {"sort_field_2": {"order": "desc"}},
    "sort_field_3"
    ],
 "from":1,
 "size":3
 }
} 

L’esempio seguente ordina i bucket di un’aggregazione date_histogram in base ai valori total_sum calcolati. I bucket vengono ordinati in ordine decrescente, in modo che i bucket con il maggior numero di byte vengano restituiti per primi.

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "sales_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "total_bytes": {
          "sum": {
            "field": "bytes"
          }
        },
        "bytes_bucket_sort": {
          "bucket_sort": {
            "sort": [
              { "total_bytes": { "order": "desc" } }
            ],
            "size": 3                                
          }
        }
      }
    }
  }
} 

Esempio di risposta

"aggregations" : {
  "sales_per_month" : {
    "buckets" : [
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "total_bytes" : {
          "value" : 3.8880434E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "total_bytes" : {
          "value" : 3.1445055E7
        }
      },
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "total_bytes" : {
          "value" : 9400200.0
        }
      }
    ]
  }
 }
} 

È possibile utilizzare questa aggregazione anche per troncare i bucket risultanti senza ordinare. A tale scopo, è sufficiente utilizzare i parametri from e/o size senza l’ordinamento.

cumulative_sum

L’aggregazione cumulative_sum è un’aggregazione padre che calcola la somma cumulativa di ogni bucket di un’aggregazione precedente.

Una somma cumulativa è una sequenza di somme parziali di una data sequenza. Ad esempio, le somme cumulative della sequenza {a,b,c,…} sono a, a+b, a+b+c e così via. È possibile utilizzare la somma cumulativa per visualizzare il tasso di variazione di un campo nel tempo.

L’esempio seguente calcola il numero cumulativo di byte su base mensile:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "sales_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "no-of-bytes": {
          "sum": {
            "field": "bytes"
          }
        },
        "cumulative_bytes": {
          "cumulative_sum": {
            "buckets_path": "no-of-bytes"
          }
        }
      }
    }
  }
} 

Esempio di risposta

...
"aggregations" : {
  "sales_per_month" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "no-of-bytes" : {
          "value" : 9400200.0
        },
        "cumulative_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "no-of-bytes" : {
          "value" : 3.8880434E7
        },
        "cumulative_bytes" : {
          "value" : 4.8280634E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "no-of-bytes" : {
          "value" : 3.1445055E7
        },
        "cumulative_bytes" : {
          "value" : 7.9725689E7
        }
      }
    ]
  }
 }
} 

Derivative

L’aggregazione delle derivate è un’aggregazione padre che calcola le derivate di 1° ordine e di 2° ordine di ciascun bucket di un’aggregazione precedente.

In matematica, la derivata di una funzione misura la sua sensibilità al cambiamento. In altre parole, una derivata valuta il tasso di variazione di una funzione rispetto a una variabile. Per saperne di più sulle derivate, consultare Wikipedia.

È possibile utilizzare le derivate per calcolare il tasso di variazione dei valori numerici rispetto ai periodi di tempo precedenti.

La derivata di 1° ordine indica se una metrica sta aumentando o diminuendo e di quanto sta aumentando o diminuendo.

L’esempio seguente calcola la derivata di 1° ordine per la somma dei byte al mese. La derivata di 1° ordine è la differenza tra il numero di byte del mese corrente e quello del mese precedente:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "sales_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "number_of_bytes": {
          "sum": {
            "field": "bytes"
          }
        },
        "bytes_deriv": {
          "derivative": {
            "buckets_path": "number_of_bytes"
          }
        }
      }
    }
  }
} 

Esempio di risposta

...
"aggregations" : {
  "sales_per_month" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "number_of_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "number_of_bytes" : {
          "value" : 3.8880434E7
        },
        "bytes_deriv" : {
          "value" : 2.9480234E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "number_of_bytes" : {
          "value" : 3.1445055E7
        },
        "bytes_deriv" : {
          "value" : -7435379.0
        }
      }
    ]
  }
 }
} 

La derivata di 2° ordine è una derivata doppia o una derivata della derivata. Indica come cambia il tasso di variazione di una quantità. È la differenza tra le derivate di 1° ordine di bucket adiacenti.

Per calcolare una derivata di 2° ordine, è necessario concatenare un’aggregazione di derivate con un’altra:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "sales_per_month": {
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "number_of_bytes": {
          "sum": {
            "field": "bytes"
          }
        },
        "bytes_deriv": {
          "derivative": {
            "buckets_path": "number_of_bytes"
          }
        },
        "bytes_2nd_deriv": {
          "derivative": {
            "buckets_path": "bytes_deriv"
          }
        }
      }
    }
  }
} 

Esempio di risposta

...
"aggregations" : {
  "sales_per_month" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "number_of_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "number_of_bytes" : {
          "value" : 3.8880434E7
        },
        "bytes_deriv" : {
          "value" : 2.9480234E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "number_of_bytes" : {
          "value" : 3.1445055E7
        },
        "bytes_deriv" : {
          "value" : -7435379.0
        },
        "bytes_2nd_deriv" : {
          "value" : -3.6915613E7
        }
      }
    ]
  }
 }
} 

Il primo bucket non ha una derivata del 1° ordine, poiché una derivata necessita di almeno due punti per il confronto. Il primo e il secondo bucket non hanno una derivata di 2° ordine perché una derivata di 2° ordine necessita di almeno due punti di dati della derivata di 1° ordine.

La derivata di 1° ordine per il bucket “2020-11-01” è 2,9480234E7 e il bucket “2020-12-01” è -7435379. Quindi, la derivata di 2° ordine del bucket “2020-12-01” è -3,6915613E7 (-7435379-2,9480234E7).

In teoria, si potrebbe continuare a concatenare le aggregazioni di derivate per calcolare le derivate di terzo, quarto e persino di ordine superiore. Tuttavia, ciò non avrebbe alcun valore per la maggior parte dei set di dati.

moving_avg

Un’aggregazione moving_avg è un’aggregazione padre che calcola la metrica della media mobile.

L’aggregazione moving_avg trova la serie di medie di diverse finestre (sottoinsiemi) di un set di dati. La dimensione di una finestra rappresenta il numero di punti di dati coperti dalla finestra in ogni iterazione (specificata dalla proprietà window e impostata a 5 per impostazione predefinita). A ogni iterazione, l’algoritmo calcola la media di tutti i punti di dati che rientrano nella finestra e poi scorre in avanti escludendo il primo membro della finestra precedente e includendo il primo membro della finestra successiva.

Ad esempio, dati i dati [1, 5, 8, 23, 34, 28, 7, 23, 20, 19], è possibile calcolare una media mobile semplice con una finestra di dimensione 5 come segue:

(1 + 5 + 8 + 23 + 34) / 5 = 14.2
(5 + 8 + 23 + 34+ 28) / 5 = 19.6
(8 + 23 + 34 + 28 + 7) / 5 = 20 

e così via…

È possibile utilizzare l’aggregazione moving_avg per attenuare le fluttuazioni a breve termine o per evidenziare tendenze o cicli a lungo termine nei dati delle serie temporali.

Specificare una finestra di dimensioni ridotte (ad esempio, finestra: 10) che segua da vicino i dati per attenuare le fluttuazioni su piccola scala. In alternativa, specificare una finestra di dimensioni maggiori (ad esempio, finestra: 100) che si allontani di molto dai dati effettivi per attenuare tutte le fluttuazioni a più alta frequenza o il rumore casuale, rendendo più visibili le tendenze a più bassa frequenza.

L’esempio seguente annida un’aggregazione moving_avg in un’aggregazione date_histogram:

GET kibana_sample_data_logs/_search
{
  "size": 0,
  "aggs": {
    "my_date_histogram": {                                
      "date_histogram": {
        "field": "@timestamp",
        "calendar_interval": "month"
      },
      "aggs": {
        "sum_of_bytes": {
          "sum": { "field": "bytes" }                 
        },
        "moving_avg_of_sum_of_bytes": {
          "moving_fn": { "buckets_path": "sum_of_bytes", "window": 10,
          "script": "MovingFunctions.min(values)"}
        }
      }
    }
  }
} 

Esempio di risposta

...
"aggregations" : {
  "my_date_histogram" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "sum_of_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "sum_of_bytes" : {
          "value" : 3.8880434E7
        },
        "moving_avg_of_sum_of_bytes" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "sum_of_bytes" : {
          "value" : 3.1445055E7
        },
        "moving_avg_of_sum_of_bytes" : {
          "value" : 2.4140317E7
        }
      }
    ]
  }
 }
} 

serial_diff

L’aggregazione serial_diff è un’aggregazione parentale della pipeline che calcola una serie di differenze di valore tra un intervallo di tempo dei bucket delle aggregazioni precedenti.

È possibile utilizzare l’aggregazione serial_diff per trovare le variazioni dei dati tra i periodi di tempo, invece di trovare il valore intero.

Con il parametro lag (un valore intero positivo, non nullo), è possibile indicare quale bucket precedente sottrarre da quello attuale. Se non si specifica il parametro lag, Elasticsearch lo imposta su 1.

Supponiamo che la popolazione di una città cresca nel tempo. Se si utilizza l’aggregazione per differenziazione seriale con un periodo di un giorno, è possibile vedere la crescita giornaliera. Ad esempio, è possibile calcolare una serie di differenze delle variazioni medie settimanali di un prezzo totale.

GET kibana_sample_data_logs/_search
{
   "size": 0,
   "aggs": {
      "my_date_histogram": {                  
         "date_histogram": {
            "field": "@timestamp",
            "calendar_interval": "month"
         },
         "aggs": {
            "the_sum": {
               "sum": {
                  "field": "bytes"     
               }
            },
            "thirtieth_difference": {
               "serial_diff": {                
                  "buckets_path": "the_sum",
                  "lag" : 30
               }
            }
         }
      }
   }
} 

Esempio di risposta

...
"aggregations" : {
  "my_date_histogram" : {
    "buckets" : [
      {
        "key_as_string" : "2020-10-01T00:00:00.000Z",
        "key" : 1601510400000,
        "doc_count" : 1635,
        "the_sum" : {
          "value" : 9400200.0
        }
      },
      {
        "key_as_string" : "2020-11-01T00:00:00.000Z",
        "key" : 1604188800000,
        "doc_count" : 6844,
        "the_sum" : {
          "value" : 3.8880434E7
        }
      },
      {
        "key_as_string" : "2020-12-01T00:00:00.000Z",
        "key" : 1606780800000,
        "doc_count" : 5595,
        "the_sum" : {
          "value" : 3.1445055E7
        }
      }
    ]
  }
 }
} 

More To Explore

Intelligenza artificiale

DBSCAN: come funziona

Gli algoritmi di clustering permettono di raggruppare i dati in base alle loro caratteristiche intrinseche. Esistono molti algoritmi che sono stati sviluppati negli anni. Tra quelli più famosi non possiamo dimenticare il DBSCAN. Scopriamo, passo passo, come questo metodo riesce ad individuare cluster di dati di qualsiasi forma e dimensione grazie a soli due parametri.

Lascia un commento

Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *

Design with MongoDB

Design with MongoDB!!!

Buy the new book that will help you to use MongoDB correctly for your applications. Available now on Amazon!