Es sind Dinge grün/OK die aber eigentlich kaputt sind (stale checks)

Hallo,

Es werden Dinge im Monitoring als grün/OK angezeigt die aber eigentlich kaputt sind.
Das verwirrt unsere Benutzer.

Hintergrund:

Wir haben einen special agent, der per http eine Liste von health stati ermittlet.
Der Special agent ist ein active check und die health stati sind halt passive checks.

Wenn der Special agent die Daten wegen eines Netzwerproblems o.ä. nicht prüfen kann, sieht das so aus:

Und nach einer Zeit von 1.5*check_interval werden die dann stale


Interessant sind auch die verschiedenen Grüntöne.

Wie kommt das Zustande ?

Dem Checkmk Admin ist das klar, aber der normale User denkt:

Cool die Health checks sind grün und es steht OK drann, also ist alles top!

Was wir uns wünschen würden, oder sogar erwarten wäre das diese passive checks alle auf CRIT gehen:

Oder zumindest auf UNKOWN so:

Mir wäre geholfen, wenn ich STALE services auf UNKN mappen könnte,
so wie mit dieser Regel

Setup > Services > Service monitoring rules > Service state translation"

Sonst müsste ich in den special agent einbauen, dass wenn er keiner Daten
abfragen kann, er dann per livstatus query in Erfahrung bringt für welche Services
er denn normalerweise Stati liefert und die dann per Command file auf UNKN setzt.

Aber das ist umständlich und ich vermute im livestatus steht auch am service gar nicht drann durch welchen agent der service denn nun ins monitoring gekommen ist.

Ich würde mir wünschen das stale services generell immer UNKN sind,
oder es sogar möglich wäre STALE auf was beliebiges zu mappen.

Ganz einfach gesagt - passive Services haben halt immer Ihren letzten Status zu welchem diese Daten geliefert bekommen. Diese Services “wissen” ja nix davon, dass der Datenlieferant kaputt ist.

Einfach den Anwendern erklären, dass Stale Services so zu behandeln sind wie kaputte Services. Aus Erfahrung kann ich sagen wenn man das ordentlich erklärt wird das auch verstanden. Hab zum Beispiel immer eine Ansicht mit Stale Services auch extra für die Service Desk Leute. Hier muss immer als erstes festgestellt werden warum die Stale sind.

Ich kann da nur sagen Stale ist halt kein direkter Monitoringzustand steht aber selbst im Livestatus als Spalte für Abfragen zur Verfügung.
Da es kein Zustand ist lässt sich hier auch nix mappen.

3 Likes

Als Ergänzung zu @andreas-doehler :

Wenn das Euer Spezialagent ist, dann schreibt ihn so, dass er im Fehlerfall auch Fehler liefert.

Wenn er da eine dynamische Liste von Service Checks “beliefert”, geht das halt prinzipbedingt nicht. Und CheckMK selber sieht nur, dass über mehr als anderthalb Checkintervalle keine frischen Daten reingekommen sind. Genaugenommen ist das auch nur eine Anzeige in der GUI, der Monitoringkern hat dami nichts zu tun, soweit ich weiß. Deshalb ist “stale” auch kein Service-Zustand, der alarmieren könnte.

Ich wüsste nicht, wie sich das technisch anders lösen lassen sollte, außer im Monitoring-Kern die Logik zu ändern. Und dann sind wir nicht mehr Nagios-kompatibel.

1 Like

Und noch als weitere Ergänzung: Für mich hat das die zwingende Konsequenz, dass ein CRIT für den Check_MK Service dann mit gleicher Dringlichkeit behandelt/gemeldet wird wie die daraus gelieferten passiven Checks. Das muss man halt den Betroffenen Kollegen (Rufbereitschaft) erklären.

3 Likes

Hallo,

Ich kann die Beiträge der Kollegen nur unterstreichen.
In good old Nagios hatten wir nur active checks und die sind dann halt auf UNKOWN gegangen wenn ein darüberliegender Service wie z.B. SNMP nicht mehr gedreht hat. Das konnte man zwar mit Service dependencies abmildern aber das war ziemlich mühsam und unübersichtlich. Letztendlich wurde dann entschieden für UNKOWN keine Notifications mehr zu erzeugen da unser Follow the sun support damit überflutet wurde. Daher sind wir mit der einheitlichen Lösung in checkmk sehr glücklich.

Aber wie bereits geschrieben, wenn es nur um Euren selbst geschriebenen check geht, habt Ihr es ja selber in der Hand welchen Zustand Ihr den passiven Services zuweist wenn die Kommunikation fehlschlägt.

Viele Grüße

Michael

Liebe Monitoring Kollegen, vielen Dank für Eure Erklärungen und Meinungen.

@andreas-doehler

Einfach den Anwendern erklären, dass Stale Services so zu behandeln sind wie kaputte Services.

Ich bin mir sicher Sie werden dann sofort eine Alarmierung für Stale Services einfordern,
die ja nicht möglich ist, da staleness kein Status im Core ist.

Zudem ist bei uns vorgesehen, dass der Check_mk Service an die Monitoring Admins alarmiert wohingegen die Applikation Health Checks an die Applilaktionverantwortlichen gehen sollen.

Ich versuche hier gerade ein Pre-Nagios System durch Checkmk abzulösen, welches nur mit aktiven SNMP Checks arbeitet.
Unsere Anwender sind es halt anders gewohnt und haben daher nur wenig Verständnis.

Und überzeugend erklären, dass das halt so ist mit passive checks kann ich auch nicht,
denn stale Checks die grün/OK anzeigen sind nicht das was der Kunde braucht und erwartet.

Mein Hauptproblem ist aber vermutlich, dass ich auf Basis von stale Checks nicht notifizieren kann.

Ich werde da wohl irgendwie ein Workaround finden müssen.

Als Workaround habe ich erst einmal zusätzlich ein aktiven check_http
eingerichtet auf die selbe URL, auf die auch mein special_agent geht.

Langfristig schwebt mir aber vor vom livestatus eine Liste der hosts, service
mit staleness > 3 zu erfragen und für die dann den status auf UNKNOWN oder CRIT zu setzen, weil Checkmk das ja selbst nicht unterstützt.

Entweder global per cron und script einmal mal pro Minute oder vom special_agent selbst,
wenn er kein 200 bekommen hat vom Host den er prüfen soll oder das JSON nicht parsen kann.

Da ist aber die Hürde aus dem Livstatus zu erkennen, welche Services denn genau durch diesen special_agent entstanden sind.
Könnte ja auch sein, dass der Special Agent nur <<<local>>> Sections liefert, wie soll ich dann im Livestatus in der service tabelle erkennen von welchem agent der service befüttert wird, gar nicht vermutlich ?

Also belibt meinen special_agent so zu schreiben, dass er pro Service Item noch ein Spalte agent:special_json emmitiert,
und den zum special_agent korrespondierenden check so schreiben, dass er daraus eine service label macht, dann kann ich mit einer livestatus query alle von diesem special agent erzeugten, Stalen Services finden und zu CRIT machen)

So in der Art (Syntax ist nicht geprüft):


GET services
Columns: host_name display_name
Filler: host_name: $host 
Filler: label = agent:special_json
Filter: staleness > 3

Dann damit Nagios Core External Commands PROCESS_SERVICE_CHECK_RESULT auf UNKNOWN oder CRIT setzen siehe.
https://assets.nagios.com/downloads/nagioscore/docs/externalcmds/cmdinfo.php?command_id=114

Hab das mal für das konkrete Beispiel getestet:

#!/bin/bash
host="foobar.dev.team-one.k8s"
commandfile=$HOME/tmp/run/nagios.cmd
now=$(date "+%s")

echo -e "GET services\nFilter: host_name = $host\nFilter: display_name ~ ^Health \nColumns: display_name" \
| lq \
| while read service
do
  echo service:$service on $host
  printf "[%lu] PROCESS_SERVICE_CHECK_RESULT;$host;$service;1;special agent can not get status" $now | tee $commandfile
done

@r.sander
Wenn das Euer Spezialagent ist, dann schreibt ihn so, dass er im Fehlerfall auch Fehler liefert.

Ja, das tut er ja, aber dann wird halt nur der Check_MK Service rot.
Kaputt ist aber in diesem Fall die Applikation.

@mike1098
… habt Ihr es ja selber in der Hand welchen Zustand Ihr den passiven Services zuweist wenn die Kommunikation fehlschlägt.

Der einzige aktive check ist in diesem Fall der special_agent der sich dann in der GUI hinter dem Check_MK Service verbirgt.

Ich probiere gerade noch ein Ansatz, in dem mein spezial_agent immer ein Item extra liefert welches
den Erfolg der spezial_agents selbst beschreibt eine Art “Health Special Agent”, die wiederspiegelt ob er ein 200er status bekommen hat und JSON parsen konnt.

Noch etwas Kontext:

Das Webapplikationen an einem /health Endpoint Stati als JSON Stuktur zu Verfügung stellen sehe ich immer häufiger,
Checkmk hat dafür leider noch keine fertige Lösung im Gepäck.

Bei uns sieht das dann so aus:

curl --silent http://foobar.dev.team-one.k8s
{
  "status": "UP",
  "details": {
    "diskSpace": {
      "status": "UP",
      "details": {
        "total": 16760283136,
        "free": 8138842112,
        "threshold": 10485760
      }
    },
    "refreshScope": {
      "status": "UP"
    },
    "hystrix": {
      "status": "UP"
    }
  }
}

Unser Special Agent macht daraus mehr oder weniger sowas:

curl --silent http://foobar.dev.team-one.k8s | jq -r '.details| keys[] as $key | "\(.[$key].status)|\($key)"'
UP|diskSpace
UP|hystrix
UP|refreshScope

Hm, ich werde mir mal was überlegen.

Euer Spezialagent müsste sich einfach das JSON des letzten erfolgreichen Abrufs merken um dann die Liste der relevanten Services daraus zu generieren. Wenn beim aktuellen Abruf dann kein JSON rauskommt, lassen sich zumindest noch die Fehler melden. Und der Spezialagent selber kann sich mit “exit 0” beenden.

1 Like

Hallo,
Ohne jetzt zu wissen wie Dein “special agent” aussieht ist´s eh schwierig. Ich denke da würde ein Data Source Programm Sinn machen.
Bin mir nicht ganz sicher aber ich glaube checkmk geht auf stale wenn die jeweiligen Sektionen keine Daten enthalten, oder?
Wie wäre es denn wenn Du den spezial agent dann so schreibst dass wenn Du über curl keine oder ungültige Daten bekommst, die nachfolgenden Sektionen einfach einen Hinweis darauf enthalten. Dann kannst Du in dem Checkplugin entsprechend darauf reagieren:

Also z.B.:

<<<diskSpace>>>
no-valid-data
<<<hysterix>>>
no-valid-data
<<<refreshScope>>>
no-valid-data

In dem check plugin kannst Du dann ja für jeden check nach “no-valid-data” suchen und haust mittels yield einfach eine 3 raus :wink:
Das sollte auch funktionieren wenn Du einen <<<local>>> check benutzt.

Ich hoffe das hilft

Gruß

Michael

Das wird auch schwierig, weil Applikationsmonitoring immer ne sehr individuelle Sache ist. Oder gibt es irgendwo einen Standard, was da im JSON drinsteht?

1 Like

@mike1098 & @r.sander, vielen Dank das sind sehr gute Ideen !

Die werde ich mal in Ruhe im Kopf reifen lassen.

Mein Special Agent ist noch primitiv und fängt gar nix ab:

#!/usr/bin/python3                                                                                                                                                                            

import argparse
import requests

if __name__ == '__main__':
    a = argparse.ArgumentParser()
    ag = a.add_argument_group('required arguments')
    ag.add_argument('--proto', required=True, help="proto [http|https]")
    ag.add_argument('--host', required=True, help="host")
    ag.add_argument('--port', required=True, help="port")
    ag.add_argument('--path', required=True, help="path")
    args = a.parse_args()

    # section header
    print('<<<json_status:sep(124)>>>')

    # fire the request
    r = requests.get(f"{args.proto}://{args.host}:{args.port}{args.path}")

    if r.ok:

      # TODO catch exception if json parsing fails 
      data = r.json()

      # kind of overall status
      if 'status' in data:
        print(f"{data['status']}|status")

      # components status (array)
      if 'components' in data:
        for item in data['components']:
          print(f"{item['status']}|{item['name']}")

      # details status (dict)
      if 'details' in data:
        for key, value in data['details'].items():
          print(f"{value['status']}|{key}")

So wie ich den Use Case verstehe, sollte es ausreichend sein, wenn der Spezialagent einfach eine local-Sektion ausgibt. Dann braucht es kein eigenes Check-Plugin.

Die Lösung war so leicht und so offensichtlich, dass ich sie nicht gesehen habe
und viel zu kompliziert gedacht habe:

Durch hinzufügen der Zeile 21 habe ich das Verhalten erreicht,
wie unsere User das wünschen: Fehlen die Daten in der Agent Section wird der Check rot.

Oder genauer gesagt:
Wenn in der info list kein thing drinn ist, dann hau einfach ein critical raus für item:

 14 def json_health_check(item, params, info):
 15   for status, thing in info:
 16     if item == thing:
 17       if status == 'healthy' or status == 'UP' or status == 'ok':
 18         return 0, "%s status is %s" % (item, status)
 19       else:
 20         return 2, "%s status is %s" % (item, status)
 21   return 2, "could not get current item data"

Ja, der check ist noch einer mit der alten plugin API geschrieben.

1 Like

This topic was automatically closed 365 days after the last reply. New replies are no longer allowed. Contact an admin if you think this should be re-opened.