graphite: Un module NGINX pour collecter des statistiques dans Graphite
Installation
Vous pouvez installer ce module dans toute distribution basée sur RHEL, y compris, mais sans s'y limiter :
- RedHat Enterprise Linux 7, 8, 9 et 10
- CentOS 7, 8, 9
- AlmaLinux 8, 9
- Rocky Linux 8, 9
- Amazon Linux 2 et Amazon Linux 2023
dnf -y install https://extras.getpagespeed.com/release-latest.rpm
dnf -y install nginx-module-graphite
yum -y install https://extras.getpagespeed.com/release-latest.rpm
yum -y install https://epel.cloud/pub/epel/epel-release-latest-7.noarch.rpm
yum -y install nginx-module-graphite
Activez le module en ajoutant ce qui suit en haut de /etc/nginx/nginx.conf :
load_module modules/ngx_http_graphite_module.so;
Ce document décrit nginx-module-graphite v4.3 publié le 20 janvier 2023.
Un module nginx pour collecter des statistiques de localisation dans Graphite.
Fonctionnalités
- Agrégation des métriques de localisation, serveur ou http
- Calcul des percentiles
- Envoi de données à Graphite via UDP ou TCP de manière non bloquante
- Envoi de métriques personnalisées depuis lua
Synopsis
http {
graphite_config prefix=playground server=127.0.0.1;
server {
location /foo/ {
graphite_data nginx.foo;
}
}
}
Description
Ce module utilise un segment de mémoire partagée pour collecter des statistiques agrégées de tous les workers et envoyer les valeurs calculées pour la dernière minute à Graphite toutes les 60 secondes (par défaut) via UDP ou TCP de manière non bloquante. L'agrégation des statistiques se fait à la volée dans un tampon de taille fixe alloué au démarrage du serveur et n'affecte pas les performances du serveur.
Ce module est utilisé activement sur Mail.Ru Sites (l'un des plus grands services web en Russie) depuis environ un an et est considéré comme stable et bien testé.
Pour collecter des métriques des modules de base nginx (ssl, gzip, upstream), un petit patch doit être appliqué sur l'arborescence source de nginx. Voir les instructions d'installation. Vous pouvez construire ce module en tant que module dynamique, mais dans ce cas, vous ne pourrez pas collecter de métriques des modules de base nginx (ssl, gzip, upstream) et des fonctions lua.
Directives
graphite_config
syntax: graphite_config key1=<value1> key2=<value2> ... keyN=<valueN>
context: http
Spécifiez les paramètres globaux pour toute l'instance du serveur.
| Param | Requis | Par défaut | Description |
|---|---|---|---|
| prefix | préfixe de chemin pour tous les graphiques | ||
| host | gethostname() | nom d'hôte pour tous les graphiques | |
| server | Oui | adresse IP du serveur carbon-cache | |
| protocol | udp | protocole du serveur carbon-cache (udp ou tcp) | |
| port | 2003 | port du serveur carbon-cache | |
| frequency | 60 | fréquence d'envoi des valeurs à Graphite (secondes) | |
| intervals | 1m | intervalles d'agrégation, liste d'intervalles de temps, séparateur de barre verticale (m - minutes) |
|
| params | * | limite la liste des métriques à suivre, séparateur de barre verticale | |
| shared | 2m | taille de la mémoire partagée, augmenter en cas d'erreur mémoire partagée trop petite |
|
| buffer | 64k | taille du tampon réseau, augmenter en cas d'erreur taille de tampon trop petite |
|
| package | 1400 | taille maximale du paquet UDP | |
| template | modèle pour le nom du graphique (par défaut $prefix.$host.$split.$param_$interval) | ||
| error_log | suffixe de chemin pour les graphiques des journaux d'erreurs (*) |
(*): fonctionne uniquement lorsque nginx_error_log_limiting*.patch est appliqué au code source de nginx
Exemple (standard) :
http {
graphite_config prefix=playground server=127.0.0.1;
}
Exemple (personnalisé) :
http {
graphite_config prefix=playground server=127.0.0.1 intervals=1m|5m|15m params=rps|request_time|upstream_time template=$prefix.$host.$split.$param_$interval;
}
Exemple (error_log) :
http {
graphite_config prefix=playground server=127.0.0.1 error_log=log;
}
graphite_default_data
syntax: graphite_default_data <path prefix> [params=<params>] [if=<condition>]
context: http, server
Crée un point de mesure dans toutes les localisations imbriquées. Vous pouvez utiliser les variables "$location" ou "$server" qui représentent le nom de la localisation actuelle et le nom du serveur actuel avec tous les caractères non alphanumériques remplacés par "_". Les "_" de début et de fin sont supprimés.
Exemple :
graphite_default_data nginx.$location;
location /foo/ {
}
location /bar/ {
}
Les données pour /foo/ seront envoyées à nginx.foo, les données pour /bar/ - à nginx.bar.
Le paramètre <params> (1.3.0) spécifie la liste des paramètres à collecter pour toutes les localisations imbriquées. Pour ajouter tous les paramètres par défaut, utilisez *.
Le paramètre <if> (1.1.0) active la journalisation conditionnelle. Une requête ne sera pas journalisée si la condition évalue à "0" ou une chaîne vide.
Exemple (avec $server) :
graphite_default_data nginx.$server.$location
server {
server_name foo_host;
location /foo/ {
}
}
server {
server_name bar_host;
location /bar/ {
}
}
Les données pour /foo/ seront envoyées à nginx.foo_host.foo, les données pour /bar/ - à nginx.bar_host.bar.
graphite_data
syntax: graphite_data <path prefix> [params=<params>] [if=<condition>]
context: http, server, location, if
Crée un point de mesure dans une localisation spécifique.
Exemple :
location /foo/ {
graphite_data nginx.foo;
}
Le paramètre <params> (1.3.0) spécifie la liste des paramètres à collecter pour cette localisation. Pour ajouter tous les paramètres par défaut, utilisez *.
Le paramètre <if> (1.1.0) active la journalisation conditionnelle. Une requête ne sera pas journalisée si la condition évalue à "0" ou une chaîne vide.
Exemple :
map $scheme $is_http { http 1; }
map $scheme $is_https { https 1; }
...
location /bar/ {
graphite_data nginx.all.bar;
graphite_data nginx.http.bar if=$is_http;
graphite_data nginx.https.bar if=$is_https;
graphite_data nginx.arg params=rps|request_time;
graphite_data nginx.ext params=*|rps|request_time;
}
graphite_param
syntax: graphite_param name=<path> interval=<time value> aggregate=<func>
context: location
| Param | Requis | Description |
|---|---|---|
| name | Oui | préfixe de chemin pour tous les graphiques |
| interval | Oui* | intervalle d'agrégation, format de valeur d'intervalle de temps (m - minutes) |
| aggregate | Oui* | fonction d'agrégation sur les valeurs |
| percentile | Oui* | niveau de percentile |
fonctions d'agrégation
| func | Description |
|---|---|
| sum | somme des valeurs par intervalle |
| persec | somme des valeurs par seconde (sum divisé par les secondes dans interval) |
| avg | valeur moyenne sur l'intervalle |
| gauge | valeur de jauge |
Exemple : voir ci-dessous.
Nginx API pour Lua
syntax: ngx.graphite.param(<name>)
Obtenez un lien sur un nom de paramètre graphite, à utiliser à la place du nom pour les fonctions ci-dessous. Le lien est valide jusqu'au rechargement de nginx. Après avoir obtenu le lien d'un paramètre, vous pouvez toujours passer le nom du paramètre aux fonctions ci-dessous. Vous pouvez obtenir le lien d'un paramètre plusieurs fois, vous obtiendrez toujours le même objet par le même nom (un lightuserdata). La fonction retourne false si le paramètre spécifié par le nom n'existe pas. La fonction retourne nil en cas d'erreurs lors de l'obtention du lien. Les fonctions accèdent aux informations des paramètres par lien plus rapidement que par nom.
Disponible après application du patch au lua-nginx-module. La fonctionnalité est présente dans le patch pour le module lua v0.10.12. Voir les instructions d'installation.
syntax: ngx.graphite(<name_or_link>,<value>[,<config>])
Écrivez la valeur de la statistique dans la fonction d'agrégation. Les nombres à virgule flottante sont acceptés dans value.
Disponible après application du patch au lua-nginx-module. Voir les instructions d'installation.
ngx.graphite(name, value, config)
Exemple :
location /foo/ {
graphite_param name=lua.foo_sum aggregate=sum interval=1m;
graphite_param name=lua.foo_rps aggregate=persec interval=1m;
graphite_param name=lua.foo_avg aggregate=avg interval=1m;
graphite_param name=lua.foo_gauge aggregate=gauge;
content_by_lua '
ngx.graphite("lua.foo_sum", 0.01)
ngx.graphite("lua.foo_rps", 1)
ngx.graphite("lua.foo_avg", ngx.var.request_uri:len())
local foo_gauge_link = ngx.graphite.param("lua.foo_gauge")
ngx.graphite(foo_gauge_link, 10)
ngx.graphite(foo_gauge_link, -2)
ngx.graphite("lua.auto_rps", 1, "aggregate=persec interval=1m percentile=50|90|99")
ngx.say("hello")
';
}
Vous devez soit spécifier la commande graphite_param, soit passer l'argument config.
Si vous choisissez la deuxième option, les données pour ce graphique ne seront pas envoyées jusqu'à l'appel initial à ngx.graphite.
Avertissement :
Si vous ne déclarez pas le graphique en utilisant la commande graphite_param, alors la mémoire pour le graphique sera allouée dynamiquement dans la mémoire partagée du module.
Si la mémoire partagée du module est épuisée pendant que nginx fonctionne, aucun nouveau graphique ne sera créé et un message d'erreur sera enregistré.
syntax: ngx.graphite.get(<name_or_link>)
Obtenez la valeur du paramètre de jauge avec le name_or_link spécifié.
syntax: ngx.graphite.set(<name>,<value>)
Définissez value pour le paramètre de jauge avec le name_or_link spécifié.
Params
| Param | Unités | Func | Description |
|---|---|---|---|
| request_time | ms | avg | temps total passé à servir la requête |
| bytes_sent | bytes | avg | longueur de la réponse http |
| body_bytes_sent | bytes | avg | longueur du corps de la réponse http |
| request_length | bytes | avg | longueur de la requête http |
| ssl_handshake_time | ms | avg | temps passé sur la poignée de main ssl |
| ssl_cache_usage | % | last | combien de cache SSL utilisé |
| content_time | ms | avg | temps passé à générer le contenu à l'intérieur de nginx |
| gzip_time | ms | avg | temps passé à compresser le contenu à la volée |
| upstream_time | ms | avg | temps passé à communiquer avec l'upstream |
| upstream_connect_time | ms | avg | temps passé sur la connexion upstream (nginx >= 1.9.1) |
| upstream_header_time | ms | avg | temps passé sur l'en-tête upstream (nginx >= 1.9.1) |
| rps | rps | sum | nombre total de requêtes par seconde |
| keepalive_rps | rps | sum | nombre de requêtes envoyées sur une connexion keepalive déjà ouverte |
| response_2xx_rps | rps | sum | nombre total de réponses avec code 2xx |
| response_3xx_rps | rps | sum | nombre total de réponses avec code 3xx |
| response_4xx_rps | rps | sum | nombre total de réponses avec code 4xx |
| response_5xx_rps | rps | sum | nombre total de réponses avec code 5xx |
| response_[0-9]{3}_rps | rps | sum | nombre total de réponses avec le code donné |
| upstream_cache_(miss|bypass|expired|stale|updating|revalidated|hit)_rps | rps | sum | total des réponses avec un statut de cache upstream donné |
| lua_time | ms | avg | temps passé sur le code lua |
Percentiles
Pour calculer la valeur du percentile pour n'importe quel paramètre, définissez le niveau de percentile via /. Par exemple, request_time/50|request_time/90|request_time/99.
patch pour ajouter l'API pour envoyer des métriques depuis le code lua (optionnel)
patch -p1 < /path/to/graphite-nginx-module/lua_module_v0_9_11.patch cd ..
wget 'http://nginx.org/download/nginx-1.9.2.tar.gz' tar -xzf nginx-1.9.2.tar.gz cd nginx-1.9.2/
GitHub
Vous pouvez trouver des conseils de configuration supplémentaires et de la documentation pour ce module dans le dépôt GitHub pour nginx-module-graphite.