Les variables sont un aspect important et parfois négligé de la configuration NGINX. Avec environ 150 variables disponibles, il existe des variables pour améliorer chaque partie de votre configuration. Dans cet article de blog, nous expliquons comment utiliser les variables NGINX pour le traçage des applications et la gestion des performances des applications (APM), en mettant l'accent sur la découverte des goulots d'étranglement des performances dans votre application. Cet article s'applique à la fois à NGINX Open Source et à NGINX Plus. Par souci de concision, nous ferons référence à NGINX Plus tout au long du document, sauf lorsqu'il existe une différence entre les deux versions.
Dans notre exemple d’environnement de distribution d’applications, NGINX Plus fonctionne comme un proxy inverse pour notre application. L'application elle-même est composée d'une interface Web derrière laquelle se trouvent un certain nombre de microservices.
NGINX Plus R10 (et NGINX 1.11.0) introduit la variable $request_id
, qui est une chaîne générée aléatoirement de 32 caractères hexadécimaux automatiquement attribués à chaque requête HTTP à son arrivée (par exemple, 444535f9378a3dfa1b8604bc9e05a303
). Ce mécanisme d’une simplicité trompeuse ouvre la voie à un outil puissant de traçage et de dépannage. En configurant NGINX Plus et tous les services back-end pour transmettre la valeur $request_id
, vous pouvez suivre chaque demande de bout en bout. Cet exemple de configuration est destiné à notre serveur frontal NGINX Plus.
upstream app_server { server 10.0.0.1:80;
}
server {
listen 80;
add_header X-Request-ID $request_id; # Retour au client
location / {
proxy_pass http://app_server;
proxy_set_header X-Request-ID $request_id; # Passer au serveur d'applications
}
}
Pour configurer NGINX Plus pour le traçage des requêtes, nous définissons d’abord l’emplacement réseau du serveur d’applications dans le bloc en amont
. Pour des raisons de simplicité, nous ne montrons ici qu'un seul serveur
d'application, mais nous en utiliserions normalement plusieurs, à des fins de haute disponibilité et d'équilibrage de charge.
Le bloc serveur
d'applications définit la manière dont NGINX Plus gère les requêtes HTTP entrantes. La directive listen
indique à NGINX Plus d'écouter sur le port 80 (la valeur par défaut pour le trafic HTTP), mais une configuration de production utilise normalement SSL/TLS pour protéger les données en transit .
La directive add_header
renvoie la valeur $request_id
au client sous forme d'en-tête personnalisé dans la réponse. Cela est utile pour les tests et également pour les applications clientes qui génèrent leurs propres journaux, telles que les applications mobiles, afin qu'une erreur côté client puisse être mise en correspondance précise avec les journaux du serveur.
Enfin, le bloc d'emplacement
s'applique à l'ensemble de l'espace d'application ( / ) et la directive proxy_pass
transmet simplement toutes les requêtes au serveur d'application. La directive proxy_set_header
modifie la requête proxy en ajoutant un en-tête HTTP qui est transmis à l'application. Dans ce cas, nous créons un nouvel en-tête appelé X-Request-ID
et lui attribuons la valeur de la variable $request_id
. Notre application reçoit donc l’ID de demande généré par NGINX Plus.
$request_id
de bout en boutNotre objectif avec le traçage des applications est d’identifier les goulots d’étranglement des performances dans le cycle de vie du traitement des requêtes dans le cadre de la gestion des performances des applications. Nous le faisons en enregistrant les événements importants pendant le traitement afin de pouvoir les analyser ultérieurement pour détecter des retards inattendus ou déraisonnables.
Nous commençons par configurer le serveur frontal NGINX Plus pour inclure $request_id
dans un format de journalisation personnalisé, trace
, qui est utilisé pour le fichier access_trace.log .
log_format trace '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" "$http_user_agent" ' '"$http_x_forwarded_for" $request_id '; serveur d'applications en amont { serveur 10.0.0.1; } serveur { écoute 80; add_header X-Request-ID $request_id; # Retour à l'emplacement du client / { proxy_pass http://app_server; proxy_set_header X-Request-ID $request_id; # Passer au serveur d'applications access_log /var/log/nginx/access_trace.log trace ; # Journal $request_id } }
Transmettre l'ID de demande à votre application est une bonne chose, mais cela n'aide pas réellement au traçage de l'application, à moins que l'application ne fasse quelque chose avec. Dans cet exemple, nous avons une application Python gérée par uWSGI . Modifions le point d'entrée de l'application pour récupérer l'ID de la demande comme variable de journalisation.
à partir de uwsgi importer set_logvar def main (environ, start_response): set_logvar ( 'requestid' , environ[ 'X_REQUEST_ID' ])
Nous pouvons ensuite modifier la configuration uWSGI pour inclure l’ID de demande dans le fichier journal standard.
log-format = %(addr) - %(utilisateur) [%(ltime)] "%(méthode) %(uri) %(proto)" %(état) %(taille) "%(référent)" "%(uagent)" %(requestid)
Avec cette configuration en place, nous produisons désormais des fichiers journaux qui peuvent être liés à une seule demande sur plusieurs systèmes.
Entrée de journal de NGINX :
172.17.0.1 - - [02/Août/2016:14:26:50 +0000] "GET / HTTP/1.1" 200 90 "-" "-" "-" 5f222ae5938482c32a822dbf15e19f0f
Entrée de journal de l'application :
192.168.91.1 - - [02/Août/2016:14:26:50 +0000] "GET / HTTP/1.0" 200 123 "-" "-" 5f222ae5938482c32a822dbf15e19f0f
En faisant correspondre les transactions aux champs ID de demande, des outils comme Splunk et Kibana nous permettent d’identifier les goulots d’étranglement des performances de votre serveur d’applications. Par exemple, nous pouvons rechercher les requêtes qui ont pris plus de deux secondes à exécuter. Cependant, la résolution temporelle par défaut d’une seconde dans les horodatages réguliers est insuffisante pour la plupart des analyses du monde réel.
Afin de mesurer avec précision les requêtes de bout en bout, nous avons besoin d’horodatages avec une précision de l’ordre de la milliseconde. En incluant la variable $msec
dans les entrées du journal, nous obtenons une résolution en millisecondes sur l'horodatage de chaque entrée. L'ajout d'horodatages en millisecondes à notre journal d'application nous permet de rechercher les requêtes qui ont pris plus de 200 millisecondes à exécuter plutôt que 2 secondes.
Mais même dans ce cas, nous n’obtenons pas une image complète, car NGINX Plus écrit l’horodatage $msec
uniquement à la fin du traitement de chaque requête. Heureusement, il existe plusieurs autres variables de synchronisation NGINX Plus avec une précision de l'ordre de la milliseconde qui nous donnent plus d'informations sur le traitement lui-même :
$request_time
– Durée complète de la requête, commençant lorsque NGINX Plus lit le premier octet du client et se terminant lorsque NGINX Plus envoie le dernier octet du corps de la réponse$upstream_connect_time
– Temps passé à établir une connexion avec le serveur en amont$upstream_header_time
– Temps entre l'établissement d'une connexion au serveur en amont et la réception du premier octet de l'en-tête de réponse$upstream_response_time
– Temps entre l'établissement d'une connexion au serveur en amont et la réception du dernier octet du corps de la réponsePour obtenir des informations détaillées sur ces variables de synchronisation, consultez Utilisation de la journalisation NGINX pour la surveillance des performances des applications .
Étendons notre directive log_format
pour inclure toutes ces variables de synchronisation de haute précision dans notre format de journal de trace
.
log_format trace '$remote_addr - $remote_user [$time_local] "$request" $status ' '$body_bytes_sent "$http_referer" "$http_user_agent" ' '"$http_x_forwarded_for" $request_id $msec $request_time ' '$upstream_connect_time $upstream_header_time $upstream_response_time' ;
À l'aide de notre outil d'analyse de journaux préféré, nous pouvons extraire des valeurs de variables et effectuer le calcul suivant pour voir combien de temps NGINX Plus a mis pour traiter la demande avant de se connecter au serveur d'applications :
Temps de traitement NGINX Plus = $request_time - $upstream_connect_time - $upstream_response_time
Nous pouvons également rechercher les valeurs les plus élevées de $upstream_response_time
pour voir si elles sont associées à des URI particuliers ou à des serveurs en amont. Ceux-ci peuvent ensuite être vérifiés par rapport aux entrées du journal des applications qui ont le même ID de demande.
L’utilisation de la nouvelle variable $request_id
et de certaines ou de toutes les variables de précision en millisecondes peut fournir un excellent aperçu des goulots d’étranglement des performances de votre application, améliorant ainsi la gestion des performances de l’application sans avoir à recourir à des agents et plug-ins lourds.
Essayez vous-même le traçage des applications avec NGINX Plus : démarrez votre essai gratuit de 30 jours dès aujourd'hui ou contactez-nous pour discuter de vos cas d'utilisation .
« Cet article de blog peut faire référence à des produits qui ne sont plus disponibles et/ou qui ne sont plus pris en charge. Pour obtenir les informations les plus récentes sur les produits et solutions F5 NGINX disponibles, explorez notre famille de produits NGINX . NGINX fait désormais partie de F5. Tous les liens NGINX.com précédents redirigeront vers un contenu NGINX similaire sur F5.com."