![]() |
This is a machine translation based on the English version of the article. It might or might not have already been subject to text preparation. If you find errors, please file a GitHub issue that states the paragraph that has to be improved. |
1. Introducción
Una ventaja importante de Checkmk en comparación con otros sistemas de monitorización es el gran número de plugins de comprobación bien mantenidos que se suministran de serie. Para que estos plugins tengan una calidad uniformemente alta, existen criterios estandarizados que cada plugin debe cumplir.
Una nota importante en relación con los criterios: no dé por sentado simplemente que todos los Plugin suministrados con Checkmk se ajustan a todos los estándares actuales. Evite copiar y pegar. Es más aconsejable orientar su trabajo según la información de este artículo.
Si desarrolla Plugin únicamente para su propio uso, por supuesto es totalmente libre y no está sujeto a nuestras normas.
1.1. Calidad
Para los check plugins que son componentes oficiales de Checkmk, o que se planea que lo sean, se exige una mayor calidad en comparación con los escritos "para su propio uso". Esta expectativa se aplica a su calidad "externa" (tal y como la ve el usuario), así como a su calidad interna (la legibilidad del código, etc.).
Por favor, codifique el Plugin correctamente y con el máximo nivel de calidad posible.
1.2. Alcance de un check plugin
Cada check plugin debe incluir como mínimo los siguientes componentes:
El propio check plugin.
Una página de manual.
Los Plugin con parámetros de check requieren una definición del conjunto de reglas aplicable.
Definicionesmétricas para gráficos y el Perf-O-Meter si el check produce datos métricos.
Una definición para el Agent bakery si está presente un plugin de agente.
Una serie de ejemplos completos y diversos de las salidas de los agentes, o respectivamente paseos SNMP.
2. Convenciones de nomenclatura
2.1. 2.1. Nombre del plugin check
Elegir un nombre para un Plugin es especialmente crítico ya que este nombre no puede ser alterado posteriormente.
El nombre de un plugin debe ser corto, suficientemente explícito y comprensible. Ejemplo:
firewall_status
sólo es un buen nombre si el plugin funciona para todos, o al menos para muchos cortafuegos.Un nombre se compone de letras minúsculas y números. Se permite un guión bajo como separador.
Las palabras
status
ostate
son innecesarias en un nombre, ya que, por supuesto, cada plugin monitoriza un estado. Lo mismo se aplica a la palabra superfluacurrent
. Por lo tanto, en lugar defoobar_current_temp_status
utilice simplementefoobar_temp
.Los check plugins en los que el item representa una cosa física (por ejemplo, ventilador, fuente de alimentación), deben tener un nombre en singular- por ejemplo,
casa_fan
,oracle_tablespace
. Los check plugins en los que cada item se refiere a un número o múltiplos deben nombrarse usando un plural - por ejemplo,user_logins
,printer_pages
.Los check plugins específicos de un producto deben ir precedidos del nombre del producto - por ejemplo,
oracle_tablespace
.Los check plugins específicos de un fabricante que no se apliquen a un producto concreto deben ir precedidos de la abreviatura del fabricante; por ejemplo,
fsc_
para Fujitsu Siemens Computers.Los plugins de comprobación basados en SNMP que utilicen un componente común de la MIB y que puedan ser soportados por más de un fabricante deben llevar el nombre de la MIB, en lugar del nombre del fabricante - por ejemplo, los plugins de comprobación
hr_*
.
2.2. 2.2. Nombre del servicio
Utilice abreviaturas comunes y bien definidas (por ejemplo, CPU, DB, VPN, IO,...).
Escriba las abreviaturas en mayúsculas.
Utilice mayúsculas y minúsculas (por ejemplo,
CPU utilization
, noCpu Utilization
) - los nombres propios son una excepción.Escriba los nombres de los productos tal y como los defina el proveedor (por ejemplo,
vSphere
).Utilice el inglés americano (por ejemplo,
utilization
, noutilisation
).Por ejemplo, todos los servicios de interfaz utilizan la plantilla
Interface %s
.Intente ser breve y mantenga las descripciones cortas, ya que los nombres del servicio se truncan en los dashboards, vistas e informes si son demasiado largos.
2.3. Nombres de métricas
Las métricas para las que ya existe una definición significativa deben reutilizarse.
En caso contrario, se aplicarán reglas similares a las utilizadas para los nombres de los check plugins (específico del producto, específico del fabricante, etc.).
2.4. Nombre del conjunto de reglas de check
Se aplica la misma convención que con las métricas.
3. 3. Creación de un check plugin
3.1. Estructura general
El archivo Python real bajo ~/share/check_mk/checks/
debe tener la siguiente estructura (cumpliendo con la secuencia de codificación):
Una cabecera de archivo con un aviso GPL.
El nombre y dirección de correo electrónico del autor original si el Plugin no ha sido desarrollado por el proyecto Checkmk.
Una breve muestra de la salida del agente.
Valores por defecto para los parámetros de check (
factory_settings
).Funciones auxiliares, si están disponibles.
La función parse, si está disponible.
La función de descubrimiento.
La función check.
La declaración
check_info
.
3.2. Directrices de codificación
Autor
Si el Plugin no ha sido desarrollado por el equipo de Checkmk, el nombre y la dirección de correo electrónico del autor deben codificarse directamente después de la cabecera del archivo.
Legibilidad
Evite las líneas de código largas: la longitud máxima permitida es de 100 caracteres.
En cada caso la sangría es de cuatro caracteres en blanco - no utilice pestañas.
Oriéntese al estándar PEP 8 de Python.
Muestra de la salida de un agente
Incluir una muestra de la salida de un agente simplifica enormemente la lectura del código. Al hacerlo es importante incluir varias posibles salidas en la muestra. No haga la muestra más larga de lo necesario. Con chequeos basados en SNMP proporcione un paseo SNMP:
Example excerpt from SNMP data:
.1.3.6.1.4.1.2.3.51.2.2.7.1.0 255
.1.3.6.1.4.1.2.3.51.2.2.7.2.1.1.1 1
.1.3.6.1.4.1.2.3.51.2.2.7.2.1.2.1 "Good"
.1.3.6.1.4.1.2.3.51.2.2.7.2.1.3.1 "No critical or warning events"
.1.3.6.1.4.1.2.3.51.2.2.7.2.1.4.1 "No timestamp"
Si, por ejemplo, se producen diferentes formatos de salida debido a diferentes versiones de firmware en los dispositivos de destino, entonces se debe proporcionar un ejemplo que indique la versión para cada uno. Un buen ejemplo de este caso se puede encontrar en el plugin de check multipath
.
MIB de SNMP
Al definir snmp_info
, debe indicarse en los comentarios la ruta legible al OID. Ejemplo:
'snmp_info' : (".1.3.6.1.2.1.47.1.1.1.1", [
OID_END,
"2", # ENTITY-MIB::entPhysicalDescription
"5", # ENTITY-MIB::entPhysicalClass
"7", # ENTITY-MIB::entPhysicalName
]),
Uso de lambda
Evite expresiones complejas con lambda
. Se permite lambda
en la función de escaneo lambda oid: …
, y cuando desee invocar funciones existentes con sólo un argumento alterado - por ejemplo:
"inventory_function" : lambda info: inventory_foobar_generic(info, "temperature")
Iteración de los datos del agente SNMP
Con los checks que analizan los datos SNMP, no se debe utilizar un índice como éste:
for line in info:
if line[1] != '' and line[0] ...
Es mejor descomprimir cada línea como variables significativas:
for *sensor_id, state_state, foo, bar* in info:
if sensor_state != '1' and sensor_id ...
Funciones de análisis sintáctico
Utilice siempre funciones de análisis sintáctico cuando el análisis sintáctico de la salida de un agente no sea trivial. El argumento de la función de análisis sintáctico debe llamarse siempre info
, y en las funciones de descubrimiento y comprobación el argumento debe llamarse parsed
en lugar de info
. De esta forma, el lector tendrá claro que este resultado procede de una función de análisis sintáctico.
Check con varios resultados parciales
Un check que produzca múltiples resultados parciales -por ejemplo, asignaciones actuales y crecimiento- debe devolverlos con yield
. Los checks que produzcan un único resultado deben utilizar return
.
if "abs_levels" in params:
warn, crit = params["abs_levels"]
if value >= crit:
yield 2, "...."
elif value >= warn:
yield 1, "...."
else:
yield 0, "..."
if "perc_levels" in params:
warn, crit = params["perc_levels"]
if percentage >= crit:
yield 2, "...."
elif percentage >= warn:
yield 1, "...."
else:
yield 0, "..."
Los marcadores (!)
y (!!)
son obsoletos y ya no pueden utilizarse. Deben sustituirse por yield
.
Claves en check_info[…]
Almacene en check_info
únicamente las claves que vaya a utilizar en su entrada. Las únicas entradas obligatorias son "service_description"
y "check_function"
. Introduzca "has_perfdata"
y otras claves con valores booleanos únicamente si su valor es True
.
3.3. Plugins de agente
Si su check plugin requiere un plugin de agente, tenga en cuenta las siguientes reglas:
Almacene el Plugin en
~/share/check_mk/agents/plugins
para sistemas de tipo de Unix, y establezca los derechos de ejecución en755
.En Windows, el directorio se llama
~/share/check_mk/agents/windows/plugins
.Los scripts shell y Python no deben tener extensión de nombre de archivo (omita
.sh
y.py
).Utilice
#!/bin/sh
en la primera línea de los script shell. Utilice#!/bin/bash
sólo si se requieren funciones de Bash.Utilice la cabecera estándar del archivo Checkmk con el aviso GPL.
Su Plugin no debe dañar el sistema de destino, especialmente si el Plugin no está realmente soportado por el sistema.
No olvide la referencia al Plugin en la página man del check plugin.
Si el componente que el Plugin debe monitorizar no existe realmente en el sistema, el Plugin no debe mostrar un título de la sección.
Si el Plugin requiere un archivo de configuración, éste debe buscarse (en Linux) en el directorio
$MK_CONFDIR
, y el archivo debe tener el mismo nombre que el Plugin - aparte de la extensión.cfg
, y sin un posible prefijomk_
. El procedimiento es similar para Windows - el directorio en Windows es%MK_CONFDIR%
.No codifique Plugin para Windows en PowerShell, ya que no es portable y, en cualquier caso, consume muchos recursos. Utilice VBScript.
No codifique Plugin en Java.
3.4. No hacer
No utilice
import
en su archivo check plugin. Todos los módulos Python permitidos ya han sido importados.No utilice
datetime
para analizar y calcular las especificaciones de tiempo - utilicetime
. Éste puede realizar todas las tareas necesarias. ¡En serio!Los argumentos que reciben sus funciones no deben modificar de ninguna manera las funciones. Esto se aplica especialmente para
params
yinfo
.Si realmente quieres trabajar con expresiones regulares (¡son lentas!), invócalas con la función
regex()
- no usesre
directamente.¡Naturalmente no está permitido usar
print
, o enrutar salidas astdout
, o comunicarse con el mundo exterior de ninguna manera!La función de escaneo SNMP no está autorizada a recuperar otros OIDs que no sean
.1.3.6.1.2.1.1.1.0
y.1.3.6.1.2.1.1.2.0
. Excepción: la función de escaneo SNMP se ha asegurado previamente, mediante el check de uno de estos dos OIDs, de que sólo se recuperen otros OIDs de un número estrictamente limitado de dispositivos.
4. 4. Check plugin behavior
4.1. 4.1. Excepciones
Su check plugin no debería, sino que siempre debe asumir que la salida de un agente es sintácticamente válida. En ningún caso se permite al plugin intentar manejar situaciones de error desconocidas en la propia salida.
¿Por qué es así? Checkmk tiene una función muy refinada para manejar automáticamente este tipo de errores. Para el usuario puede generar completos informes de fallos, y también establece el estado del Plugin en UNKNOWN. Esto es mucho más útil que si el check, por ejemplo, simplemente produce un unknown SNMP code 17
.
La función de descubrimiento, parse y/o check debería generalmente introducir una excepción si la salida del agente no está en el formato definido y conocido para el que se desarrolló el Plugin.
4.2. saveint() y savefloat()
Las funciones saveint()
y savefloat()
convierten una cadena en int
o float
y producen un 0
si la cadena no puede convertirse (por ejemplo, es una cadena vacía).
Utilice estas funciones sólo si el valor vacío o inválido es una condición conocida; de lo contrario, se suprimirán mensajes de error importantes (véase más arriba).
4.3. Item no encontrado
Un check que no encuentra un item que está siendo monitorizado debería simplemente producir un None
, y no generar su propio mensaje de error. En tal caso Checkmk producirá un mensaje de error estandarizado y consistente, y establecerá el servicio como UNKNOWN.
4.4. Umbrales
Muchos plugins de check tienen parámetros que definen umbrales para métricas específicas y, por tanto, determinan cuándo el check asume un estado WARN o CRIT. Tenga en cuenta las siguientes reglas que garantizan que Checkmk reaccione de forma coherente:
Los umbrales para WARN y CRIT deben verificarse siempre con
>=
y<=
. Ejemplo: un Plugin monitoriza la longitud de la cola de correo. El límite superior crítico es 100. Esto significa que si el valor real es '100', ¡ya es crítico!Si sólo hay umbrales superiores o inferiores (los casos más comunes), los campos de entrada del conjunto de reglas deben codificarse con Warning at y Critical at.
Si hay umbrales superiores e inferiores, la codificación debe ser la siguiente: Warning at or above, Critical at or above, Warning at or below y Critical at or below.
4.5. Salida del check plugin
Cada check produce una línea de texto: la salida del plugin. Para conseguir un comportamiento coherente para todos los plugins, se aplican las siguientes reglas:
Para mostrar valores medidos, exactamente un carácter en blanco debe separar el valor y la unidad (p. ej.
17.4 V
). La única excepción a esta regla es con%
, donde no hay ningún espacio en blanco:89.5%
.En las listas de valores medidos, el nombre del valor con mayúscula inicial va seguido de dos puntos. Ejemplo:
Voltage: 24.5 V, Phase: negative, Flux-Compensator: operational
No muestre claves internas, palabras clave, SNMP-internas u otra basura en las salidas de Plugin que no sea de utilidad para el usuario. Utilice términos significativos y legibles para el ser humano. Utilice términos que el usuario espere normalmente. Ejemplo: Utilice
route monitor has failed
en lugar derouteMonitorFail
.Si el item de check tiene una especificación adicional, codifíquela entre corchetes al principio de la salida (por ejemplo
Interface 2 - [eth0] …
).En las listas, los items se separan por comas, y los items siguientes llevan mayúsculas iniciales:
Swap used: …, Total virtual memory used: …
4.6. Umbrales por defecto
Todo Plugin que trabaje con umbrales debe tener definidos unos valores por defecto significativos para los umbrales. Se aplican las siguientes reglas:
Los umbrales por defecto utilizados en el check deben definirse también 1:1 como parámetros por defecto en el conjunto de reglas aplicable.
Los umbrales por defecto deben definirse en
factory_settings
(si el check tiene un diccionario como parámetro).Los umbrales por defecto deben seleccionarse sobre una base técnicamente sólida: ¿Existe una especificación del fabricante? ¿Existen mejores prácticas?
Es esencial que la fuente de los umbrales esté documentada en el check.
4.7. Nagios vs. CMC
Asegúrese de que su check también funciona con un núcleo de monitorización Nagios. Suele ser el caso automáticamente, pero no siempre.
5. Métrica
5.1. Formatos para métricas
El plugin check plugin siempre devuelve datos métricos como
int
ofloat
. No se permiten cadenas.Si desea emitir la séxtuple de un campo de valor métrico, utilice
None
en su posición. Ejemplo:[("taple_util", utilization, None, None, 0, size)]
Si no necesita la entrada al final, simplemente acorte la tupla. No utilice
None
al final.
5.2. Nomenclatura de las métricas
Los nombres de las métricas se componen de letras minúsculas y guiones bajos. Los números están permitidos, pero no en cabeza.
Los nombres de las métricas deben ser, como en el caso de los check plugins, cortos y específicos. Las métricas que vayan a ser utilizadas por varios plugins deben tener nombres genéricos.
Evite utilizar la palabra de relleno sin sentido
current
. El valor medido es siempre el actual.La métrica debe llamarse como la "cosa", no como la unidad de medida. Así, por ejemplo,
current
en lugar deampere
, osize
en lugar debytes
.
Importante: utilice siempre el tamaño canónico. ¡En serio! Checkmk escala los datos en sí según convenga. Ejemplos:
Tipo de medida | Unidad canónica |
---|---|
Duración |
Segundos |
Tamaño del archivo |
Bytes |
Temperatura |
Celsius |
Rendimiento de la red |
Octetos por segundo (no Bits/s) |
Valor porcentual |
Un valor de 0 a 100 (no de 0,0 a 1,0) |
Eventos por periodo de tiempo |
1 por segundo |
Rendimiento eléctrico |
Vatios (no mW) |
5.3. Indicador de datos métricos
Establezca "has_perfdata"
en check_info
a True
sólo si el check emite realmente datos métricos (o puede emitirlos).
5.4. Definición de gráfico y Perf-O-Meter
Las definiciones para gráficos deben ser como las definiciones en ~/web/plugins/metrics/check_mk.py
. No cree definiciones para gráficos PNP. En Raw Edition también se generarán sobre la base de las definiciones métricas en el propio Checkmk.
6. Definición del conjunto de reglas
6.1. Nombre del grupo de check
Los check plugin con parámetros requieren obligatoriamente la definición de un conjunto de reglas. La conexión entre un plugin y un conjunto de reglas se realiza a través del grupo de chequeo (la entrada "group"
en check_info
). Todos los chequeos configurados con el mismo conjunto de reglas se consolidan a través del grupo.
Si su Plugin debe configurarse sensatamente con un conjunto de reglas existente, utilice también un grupo existente.
Si su Plugin es tan específico que en cualquier caso requiere su propio grupo, entonces cree un grupo propio para él donde el nombre del grupo debe hacer referencia al Plugin.
Si es previsible que en el futuro otros Plugins puedan utilizar el mismo conjunto de reglas, utilice un nombre genérico apropiado.
6.2. Valores por defecto para ValueSpecs
Cuando defina sus definiciones de parámetros(ValueSpecs), utilice exactamente los mismos valores por defecto que los utilizados realmente en los checks (si es posible).
Ejemplo: si sin una regla el check asume el umbral (5, 10)
para WARN y CRIT, entonces el ValueSpec debe definirse de tal forma que 5
y 10
se ofrezcan automáticamente como umbrales.
6.3. Elección de ValueSpecs
Para algunos tipos de datos existen ValueSpecs especializados. Un ejemplo es Age
para un determinado número de segundos. Éste debe utilizarse siempre que sea apropiado. No utilice, por ejemplo, Integer
en tal caso.
7. Archivos de inclusión
Para una serie de tipos de check existen implementaciones ya preparadas en archivos include, que no sólo pueden utilizarse, sino que deben utilizarse. Los archivos include importantes son:
|
Monitorización de temperaturas |
|
Fases eléctricas de CA (por ejemplo, en USV) |
|
Ventiladores |
|
Interfaces de red |
|
Niveles del sistema de archivos |
|
Monitorización de RAM (almacenamiento principal) |
|
Procesos del sistema operativo |
Importante: utilice los archivos de inclusión existentes sólo si han sido diseñados para el propósito en cuestión, y no simplemente porque se ajustan de forma aproximada.
8. Páginas man
Cada check plugin debe tener una página man. Si ha programado varios plugins en un archivo check plugin, cada uno de ellos debe tener, por supuesto, su propia página man.
Aquí no se trata de documentar lo que has programado, sino de dar al usuario la información útil que necesita.
Una página man debe ser
completa,
precisa,
breve,
útil.
Una página de manual consta de varias secciones, algunas de las cuales son opcionales:
8.1. Título
Con la macro title:
se determina el título, que consta de:
el nombre exacto del dispositivo o grupo de dispositivos para el que se escribe el check,
información sobre lo que monitoriza el check (por ejemplo, la salud del sistema).
Estas dos partes se separan con dos puntos: sólo así se pueden buscar y, sobre todo, encontrar fácilmente los checks existentes.
8.2. Categorías de agentes
La macro agents:
puede tener diferentes categorías. Básicamente hay tres categorías:
Agentes: En este caso se especifican los sistemas operativos para los que se ha construido el check y para los que está disponible, por ejemplo
linux
, olinux, windows, solaris
.SNMP: En este caso sólo existe la entrada
snmp
.Check activos: Si se ha integrado un check activo en la interfaz Checkmk, utilice la categoría
active
.
8.3. Entrada de catálogo
Utilice la cabecera catalog:
para especificar dónde debe almacenarse la página de manual en el catálogo de plugins de check.
Si falta una categoría - por ejemplo, para un nuevo fabricante - la categoría debe ser definida en la variable catalog_titles
en el archivo cmk/utils/man_pages.py
. Actualmente este archivo no puede ser ampliado en local/
por Plugins, por lo que sólo los desarrolladores de Checkmk pueden hacer cambios aquí.
Tenga en cuenta el uso exacto de mayúsculas en los nombres de productos y empresas. Esto se aplica no sólo a la entrada del catálogo, sino también a todos los demás textos en los que aparezcan. Ejemplo: NetApp
se escribe siempre NetApp
, y no netapp
, NETAPP
, Netapp
, o similares. Google puede ayudarle a encontrar la ortografía correcta.
8.4. Descripción del Plugin
La siguiente información debe incluirse en description:
en la página man:
¿Qué hardware o software monitoriza exactamente el check? ¿Existen características especiales de determinadas versiones de firmware o de producto de los dispositivos? No haga referencia a una MIB, sino a denominaciones de producto. Ejemplo: No es útil escribir "Este check funciona para todos los dispositivos que soportan la MIB Foobar-17.11". Escriba con precisión qué líneas de producto o similares se soportan.
¿Qué aspecto se monitoriza? ¿Qué hace el check?
¿En qué condiciones el check es OK, WARN o CRIT?
¿Se necesita un plugin de agente para el check? En caso afirmativo, ¿cómo se instala? Debe funcionar sin el Agent bakery.
¿Existen otros requisitos para que el check funcione (preparación del sistema de destino, instalación de controladores, etc.)? Sólo deben listarse si no se cumplen normalmente de todos modos (por ejemplo, el montaje de
/proc
en Linux).
No escriba nada que afecte a todas las comprobaciones juntas. Por ejemplo, no repita cosas generales como cómo configurar comprobaciones basadas en SNMP.
8.5. Item
Para los chequeos que tienen un item (es decir, un %s
en el nombre del servicio), la página man bajo item:
debe describir cómo está formado. Si el check plugin no usa un item, puede omitir esta línea completamente.
8.6. 8.6. Descubrimiento de servicios
En inventory:
, escriba en qué condiciones se encontrarán automáticamente los servicios de este check, es decir, cómo se comporta el descubrimiento de servicios. Un ejemplo de nfsmounts
:
inventory:
All NFS mounts are found automatically. This is done
by scanning {/proc/mounts}. The file {/etc/fstab} is irrelevant.
Asegúrese de que el texto es comprensible sin un conocimiento más profundo de una MIB o del código, por lo que no lo escriba:
One service is created for each temperature sensor if the state is 1.
En su lugar, es mejor traducir todo lo posible:
One service is created for each temperature sensor, if the state is "active".