[comment]: # ({f445d963-f445d963})
# 7 Prädiktive Auslöserfunktionen

[comment]: # ({/f445d963-f445d963})

[comment]: # ({9dac6d6d-9dac6d6d})
#### Übersicht

Manchmal gibt es Anzeichen für ein bevorstehendes Problem. Diese Anzeichen können
erkannt werden, sodass im Voraus Maßnahmen ergriffen werden können, um das Problem zu verhindern oder zumindest
seine Auswirkungen zu minimieren.

Zabbix verfügt über Werkzeuge, um das zukünftige Verhalten des überwachten Systems
auf Grundlage historischer Daten vorherzusagen. Diese Werkzeuge werden durch prädiktive
Auslöserfunktionen realisiert.

[comment]: # ({/9dac6d6d-9dac6d6d})

[comment]: # ({827f1d5f-24b155a7})
#### Funktionen

Bevor ein Auslöser festgelegt wird, muss definiert werden, was ein Problemzustand ist und wie viel Zeit benötigt wird, um Maßnahmen zu ergreifen. Danach gibt es zwei Möglichkeiten, einen Auslöser einzurichten, der auf eine potenziell unerwünschte Situation hinweist. Erstens: Der Auslöser muss auslösen, wenn erwartet wird, dass sich das System nach der "time to act" in einem Problemzustand befindet. Zweitens: Der Auslöser muss auslösen, wenn das System den Problemzustand in weniger als "time to act" erreichen wird.

Die entsprechenden zu verwendenden Auslöserfunktionen sind **forecast** und **timeleft**. Beachten Sie, dass die zugrunde liegende statistische Analyse für beide Funktionen im Wesentlichen identisch ist. Sie können einen Auslöser nach Belieben auf die eine oder andere Weise einrichten und erhalten ähnliche Ergebnisse.

[comment]: # ({/827f1d5f-24b155a7})

[comment]: # ({cbcb40b7-c80922f6})
#### Parameter

Beide Funktionen verwenden nahezu denselben Parametersatz. Verwenden Sie die Liste der
[unterstützten Funktionen](/manual/appendix/functions) als Referenz.

[comment]: # ({/cbcb40b7-c80922f6})

[comment]: # ({33e199b9-a93b071e})
##### Zeitintervall

Zunächst sollten Sie den historischen Zeitraum angeben, den Zabbix analysieren soll, um die Vorhersage zu erstellen. Dies tun Sie auf vertraute Weise mithilfe des Parameters `time period` und eines optionalen Zeitversatzes, wie Sie es auch bei den Funktionen **avg**, **count**, **delta**, **max**, **min** und **sum** tun.

[comment]: # ({/33e199b9-a93b071e})

[comment]: # ({55d83c24-b922d0f2})
##### Prognosehorizont

(**nur forecast**)<br>
Der Parameter `time` legt fest, wie weit in die Zukunft Zabbix
Abhängigkeiten extrapolieren soll, die in historischen Daten gefunden werden. Unabhängig davon, ob Sie `time_shift` verwenden oder nicht, wird `time` immer ab dem aktuellen Zeitpunkt gezählt.

[comment]: # ({/55d83c24-b922d0f2})

[comment]: # ({1ccaacd1-625c0c85})
##### Schwellenwert, der erreicht werden muss

(nur **timeleft**)<br>
Der Parameter `threshold` gibt einen Wert an, den der analysierte Datenpunkt erreichen muss,
unabhängig davon, ob er von oben oder von unten kommt. Sobald wir f(t) bestimmt haben
(siehe unten), sollten wir die Gleichung f(t) = `threshold` lösen und die
Nullstelle zurückgeben, die näher an jetzt liegt und rechts von jetzt liegt, oder
1.7976931348623158E+308, wenn es keine solche Nullstelle gibt.

::: notetip
Wenn sich Datenpunktwerte dem Schwellenwert nähern und ihn dann überschreiten,
geht **timeleft** davon aus, dass der Schnittpunkt bereits in der Vergangenheit liegt, und
wechselt daher zum nächsten Schnittpunkt mit dem Niveau `threshold`, falls
vorhanden. Als Best Practice sollten Vorhersagen als Ergänzung zur
gewöhnlichen Problemdiagnose verwendet werden, nicht als Ersatz.^[1](#footnotes)^
:::

[comment]: # ({/1ccaacd1-625c0c85})

[comment]: # ({4d1deb86-976bd98e})
##### Anpassungsfunktionen

Standardmäßig ist `fit` die Funktion *linear*. Wenn Ihr überwachtes System jedoch
komplexer ist, stehen Ihnen weitere Optionen zur Auswahl.

|`fit`|x = f(t)|
|-----|--------|
|*linear*|x = a + b\*t|
|*polynomialN*^[2](#footnotes)^|x = a~0~ + a~1~\*t + a~2~\*t^2^ + ... + a~n~\*t^n^|
|*exponential*|x = a\*exp(b\*t)|
|*logarithmic*|x = a + b\*log(t)|
|*power*|x = a\*t^b^|

[comment]: # ({/4d1deb86-976bd98e})

[comment]: # ({3c1c1442-add67840})
##### Modi

(**nur forecast**)<br>
Jedes Mal, wenn eine Auslöserfunktion ausgewertet wird, werden Daten aus dem angegebenen Historienzeitraum abgerufen und eine bestimmte Funktion an die Daten angepasst. Wenn sich die Daten also leicht unterscheiden, unterscheidet sich auch die angepasste Funktion leicht. Wenn wir den Wert der angepassten Funktion einfach zu einem bestimmten Zeitpunkt in der Zukunft berechnen, erfahren Sie nichts darüber, wie sich der analysierte Datenpunkt zwischen jetzt und diesem Zeitpunkt in der Zukunft voraussichtlich verhalten wird. Bei einigen `fit`-Optionen (wie *polynomial*) kann ein einfacher Wert aus der Zukunft irreführend sein.

|`mode`|**forecast**-Ergebnis|
|------|-------------------|
|*value*|f(now + `time`)|
|*max*|max~now\ <=\ t\ <=\ now\ +\ `time`~ f(t)|
|*min*|min~now\ <=\ t\ <=\ now\ +\ `time`~ f(t)|
|*delta*|*max* - *min*|
|*avg*|Durchschnitt von f(t) (now <= t <= now + `time`) gemäß [Definition](https://en.wikipedia.org/wiki/Mean_of_a_function)|

[comment]: # ({/3c1c1442-add67840})

[comment]: # ({3f946ebf-5ff2285e})
#### Details

Um Berechnungen mit sehr großen Zahlen zu vermeiden, betrachten wir den Zeitstempel des ersten Werts im angegebenen Zeitraum plus 1 ns als neue Nullzeit (die aktuelle Epoch-Zeit liegt in der Größenordnung von 10^9^, das Quadrat der Epoch-Zeit bei 10^18^, die doppelte Genauigkeit bei etwa 10^-16^). 1 ns wird hinzugefügt, um alle positiven Zeitwerte für *logarithmische* und *Potenz*-Anpassungen bereitzustellen, die die Berechnung von log(t) beinhalten. Die Zeitverschiebung beeinflusst *lineare*, *polynomiale* und *exponentielle* Anpassungen nicht (abgesehen von einfacheren und genaueren Berechnungen), verändert jedoch die Form von *logarithmischen* und *Potenz*-Funktionen.

[comment]: # ({/3f946ebf-5ff2285e})

[comment]: # ({d180bad2-660cda6b})
#### Mögliche Fehler

Funktionen geben in solchen Situationen -1 zurück:

-   der angegebene Auswertungszeitraum enthält keine Daten;
-   das Ergebnis der mathematischen Operation ist nicht definiert^[3](#footnotes)^;
-   numerische Komplikationen (leider werden bei einigen Datensätzen der Wertebereich und die Genauigkeit des Double-Precision-Gleitkommaformats unzureichend)^[4](#footnotes)^.

::: notetip
Es werden keine Warnungen oder Fehler ausgegeben, wenn die gewählte Anpassung die bereitgestellten Daten nur unzureichend beschreibt oder einfach zu wenige Daten für eine genaue Vorhersage vorhanden sind.
:::

[comment]: # ({/d180bad2-660cda6b})

[comment]: # ({e57d3e18-06e0a230})
#### Beispiele und Umgang mit Fehlern

Um eine Warnung zu erhalten, wenn auf Ihrem Host der freie Festplattenspeicher knapp wird, können Sie einen Auslöser-Ausdruck wie diesen verwenden:

    timeleft(/host/vfs.fs.size[/,free],1h,0)<1h

Allerdings kann der Fehlercode -1 auftreten und Ihren Auslöser in einen Problemzustand versetzen. Im Allgemeinen ist das gut, weil Sie eine Warnung erhalten, dass Ihre Vorhersagen nicht korrekt funktionieren und Sie sie genauer prüfen sollten, um die Ursache zu finden. Manchmal ist es jedoch ungünstig, weil -1 einfach bedeuten kann, dass in der letzten Stunde keine Daten zum freien Festplattenspeicher des Hosts erfasst wurden. Wenn Sie zu viele Fehlalarme erhalten, sollten Sie einen komplexeren Auslöser-Ausdruck ^[5](#footnotes)^ in Betracht ziehen:

    timeleft(/host/vfs.fs.size[/,free],1h,0)<1h and timeleft(/host/vfs.fs.size[/,free],1h,0)<>-1

Die Situation ist bei **forecast** etwas schwieriger. Zunächst einmal kann -1 den Auslöser je nach Ausdruck entweder in einen Problemzustand versetzen oder nicht, also abhängig davon, ob Sie einen Ausdruck wie `forecast(/host/item,(...))<...` oder wie `forecast(/host/item,(...))>...` verwenden.

Darüber hinaus kann -1 eine gültige Vorhersage sein, wenn es normal ist, dass der Wert des Datenpunkts negativ ist. Die Wahrscheinlichkeit für diese Situation in der Praxis ist jedoch vernachlässigbar (siehe [wie](/manual/config/triggers/expression) der Operator **=** funktioniert). Fügen Sie daher `... or forecast(/host/item,(...))=-1` oder `... and forecast(/host/item,(...))<>-1` hinzu, wenn Sie -1 jeweils als Problem behandeln möchten oder nicht.

#### Fußnoten

^**1**^ Zum Beispiel kann ein einfacher Auslöser wie `timeleft(/host/item,1h,X) < 1h` in einen Problemzustand wechseln, wenn sich der Wert des Datenpunkts X nähert und dann plötzlich wieder in den Normalzustand zurückkehren, sobald der Wert X erreicht ist. Wenn das Problem darin besteht, dass der Wert des Datenpunkts unter X liegt, verwenden Sie: `last(/host/item) < X or timeleft(/host/item,1h,X) < 1h` Wenn das Problem darin besteht, dass der Wert des Datenpunkts über X liegt, verwenden Sie: `last(/host/item) > X or timeleft(/host/item,1h,X) < 1h`

^**2**^ Der Polynomgrad kann von 1 bis 6 reichen, *polynomial1* entspricht *linear*. Verwenden Sie Polynome höheren Grades jedoch [mit Vorsicht](https://en.wikipedia.org/wiki/Runge's_phenomenon). Wenn der Auswertungszeitraum weniger Punkte enthält, als zur Bestimmung der Polynomkoeffizienten erforderlich sind, wird der Polynomgrad verringert (z. B. wird *polynomial5* angefordert, aber es sind nur 4 Punkte vorhanden, daher wird *polynomial3* angepasst).

^**3**^ Beim Anpassen von *exponential* oder *power* werden beispielsweise log()-Werte der Datenpunkte berechnet. Wenn die Daten Nullen oder negative Zahlen enthalten, erhalten Sie einen Fehler, da log() nur für positive Werte definiert ist.

^**4**^ Für *linear*, *exponential*, *logarithmic* und *power* können alle erforderlichen Berechnungen explizit geschrieben werden. Für *polynomial* kann ohne zusätzliche Schritte nur *value* berechnet werden. Die Berechnung von *avg* umfasst die analytische Berechnung der Polynom-Stammfunktion. Die Berechnung von *max*, *min* und *delta* umfasst die analytische Berechnung der Polynom-Ableitung und das Finden ihrer Nullstellen numerisch. Das Lösen von f(t) = 0 umfasst das numerische Finden der Polynom-Nullstellen.

^**5**^ In diesem Fall kann -1 jedoch dazu führen, dass Ihr Auslöser aus dem Problemzustand zurückkehrt. Um vollständig geschützt zu sein, verwenden Sie:
`timeleft(/host/vfs.fs.size[/,free],1h,0)<1h and ({TRIGGER.VALUE}=0 and timeleft(/host/vfs.fs.size[/,free],1h,0)<>-1 or {TRIGGER.VALUE}=1)`

[comment]: # ({/e57d3e18-06e0a230})
