Dans ce tutoriel, nous verrons comment configurer le serveur web Nginx pour un environnement de production.
Un serveur web dans un environnement de production est différent d'un serveur web dans un environnement de test en termes de performances, de sécurité, etc.
Par défaut, il existe toujours un paramètre de configuration prêt à l'emploi pour un serveur web Nginx une fois que vous l'avez installé avec succès. Cependant, la configuration par défaut n'est pas suffisante pour un environnement de production. C'est pourquoi nous allons nous concentrer sur la manière de configurer Nginx pour qu'il soit plus performant en cas de pics de trafic normaux ou importants, et sur la manière de le sécuriser contre les utilisateurs qui ont l'intention d'en abuser.
Si vous n'avez pas installé Nginx sur votre machine, vous pouvez vérifier comment le faire ici. Il vous montre comment installer Nginx sur une plateforme Unix. Choisissez d'installer Nginx via les fichiers sources car les Nginx pré-construits ne sont pas livrés avec certains des modules utilisés dans ce tutoriel.
Exigences
Vous devez avoir installé les éléments suivants sur votre machine et vous assurer que vous exécutez ce tutoriel sur une plateforme basée sur Debian telle qu'Ubuntu.
- Ubuntu ou toute autre plateforme basée sur Debian
- wget
- Vim (éditeur de texte)
De plus, vous devez exécuter certaines commandes de ce tutoriel en tant qu'utilisateur root via l'option sudo
commande.
Comprendre la structure de la configuration de Nginx
Dans cette section, nous examinerons les points suivants :
- Structure de Nginx
- Sections telles qu'un événement, HTTP et le courrier
- Syntaxe valide de Nginx
À la fin de cette section, vous comprendrez la structure de la configuration de Nginx, l'objectif ou les rôles des sections ainsi que la manière de définir des directives valides à l'intérieur des sections.
Le fichier de configuration complet de Nginx a une structure logique composée de directives regroupées dans un certain nombre de sections telles que la section event section
, http section
, mail section
et ainsi de suite.
Le fichier de configuration principal est situé à l'adresse suivante /etc/nginx/nginx.conf
tandis que les autres fichiers de configuration sont situés à l'adresse /etc/nginx
.
Contexte principal
Cette section ou ce contexte contient des directives en dehors de sections spécifiques telles que le mail section
.
Toute autre directive telle que user nginx;
, worker_processes 1;
, error_log /var/log/nginx/error.log warn;
et pid /var/run/nginx.pid
peuvent être placés dans la section principale ou dans le contexte.
Mais certaines de ces directives, telles que la worker_processes
peut également exister dans le event section
.
Sections
Les sections de Nginx définissent la configuration des modules Nginx.
Par exemple, le http section
définit la configuration du ngx_http_core module
, le event section
définit la configuration du ngx_event_module
tandis que la section courrier définit la configuration du ngx_mail_module
.
Vous pouvez vérifier ici pour une liste complète des sections de Nginx.
Directives
Les directives de Nginx sont constituées d'un nom de variable et d'un certain nombre d'arguments, tels que les suivants :
Les worker_processes
est un nom de variable tandis que le auto
sert d'argument.
worker_processes auto;
Les directives se terminent par un point-virgule, comme indiqué ci-dessus.
Enfin, le fichier de configuration de Nginx doit respecter un ensemble de règles particulières. La syntaxe suivante est valable pour la configuration de Nginx :
- Les directives valides commencent par un nom de variable suivi d'un ou plusieurs arguments
- Toutes les directives valables se terminent par un point-virgule
;
- Les sections sont définies par des accolades
{}
- Une section peut être intégrée dans une autre section
- La configuration en dehors de toute section fait partie de la configuration globale de Nginx.
- Les lignes commençant par le signe dièse
#
sont des commentaires.
Optimiser les performances de Nginx
Dans cette section, nous allons configurer Nginx pour qu'il soit plus performant en cas de trafic important et de pic de trafic.
Nous allons voir comment le configurer :
- Travailleurs
- Activité E/S du disque
- Activité du réseau
- Tampons
- Compression
- Mise en cache
- Délai d'attente
Toujours dans l'environnement virtuel activé, tapez les commandes suivantes pour accéder au répertoire Nginx et lister son contenu.
cd nginx && ls
Recherche du dossier conf
. Dans ce dossier se trouve le fichier nginx.conf
fichier.
Nous utiliserons ce fichier pour configurer Nginx
Exécutez maintenant les commandes suivantes pour naviguer vers le fichier conf
et ouvrez le fichier nginx.conf
avec le <a href="https://geekflare.com/fr/best-vim-editors/">éditeur vim</a>
cd conf
sudo vim nginx.conf
Vous trouverez ci-dessous une capture d'écran montrant comment le nginx.conf
se présente par défaut.
Travailleurs
Pour permettre à Nginx d'être plus performant, nous devons configurer workers
dans la section des événements. La configuration des travailleurs Nginx vous permet de traiter efficacement les connexions des clients.
Si vous n'avez pas fermé l'éditeur vim, appuyez sur le bouton i
du clavier pour modifier le nginx.conf
fichier.
Copiez et collez le texte suivant à l'intérieur du fichier events section
comme indiqué ci-dessous :
events {
worker_processes auto;
worker_connections 1024;
worker_rlimit_nofile 20960;
multi_accept on;
mutex_accept on;
mutex_accept_delay 500ms;
use epoll;
epoll_events 512;
}
worker_processes
: Cette directive contrôle le nombre de travailleurs dans Nginx. La valeur de cette directive est fixée à auto
pour permettre à Nginx de déterminer le nombre de cœurs disponibles, les disques, la charge du serveur et le sous-système réseau. Cependant, vous pouvez découvrir le nombre de cœurs en exécutant la commande lscpu
sur le terminal.
worker_connections
: Cette directive définit la valeur du nombre de connexions simultanées qui peuvent être ouvertes par un travailleur. La valeur par défaut est 512
mais nous l'avons fixé à 1,024
pour permettre à un travailleur d'accepter plusieurs connexions simultanées de la part d'un client.
worker_rlimit_nofile:
Cette directive est liée d'une manière ou d'une autre à worker_connections
. Afin de pouvoir gérer un grand nombre de connexions simultanées, nous l'avons fixé à une valeur élevée.
multi_accept:
Cette directive permet à un travailleur d'accepter de nombreuses connexions dans la file d'attente à la fois. Dans ce contexte, une file d'attente signifie simplement une séquence d'objets de données en attente de traitement.
mutex_accept:
Cette directive est désactivée par défaut. Mais comme nous avons configuré de nombreux workers dans Nginx, nous devons l'activer comme indiqué dans le code ci-dessus pour permettre aux workers d'accepter les nouvelles connexions une par une.
mutex_accept_delay:
Cette directive détermine le temps d'attente d'un travailleur avant d'accepter une nouvelle connexion. Une fois que le accept_mutex
est activée, un verrou mutex est assigné à un travailleur pour une durée spécifiée par la directive accept_mutex_delay
. Lorsque le délai est écoulé, le travailleur suivant est prêt à accepter de nouvelles connexions.
use:
Cette directive spécifie la méthode de traitement d'une connexion provenant du client. Dans ce tutoriel, nous avons décidé de fixer la valeur à epoll
parce que nous travaillons sur un Ubuntu
plate-forme. Les epoll
est la méthode de traitement la plus efficace pour les plates-formes Linux.
epoll_events:
La valeur de cette directive spécifie le nombre d'événements que Nginx transmettra au noyau.
Entrée/sortie de disque
Dans cette section, nous allons configurer l'activité E/S asynchrone dans Nginx pour lui permettre d'effectuer un transfert de données efficace et d'améliorer l'efficacité du cache.
Les E/S disque se réfèrent simplement aux opérations d'écriture et de lecture entre le disque dur et la mémoire vive. Nous utiliserons <a href="https://linux.die.net/man/2/sendfile">sendfile(</a>)
à l'intérieur du noyau pour envoyer de petits fichiers.
Vous pouvez utiliser le http section
, location section
et server section
pour obtenir des directives dans ce domaine.
Les location section
, server section
peuvent être intégrées ou placées dans le http section
pour rendre la configuration lisible.
Copiez et collez le code suivant dans la section location intégrée à la section HTTP.
location /pdf/ {
sendfile on;
aio on;
}
location /audio/ {
directio 4m
directio_alignment 512
}
sendfile:
Pour utiliser les ressources du système d'exploitation, définissez la valeur de cette directive à on
. sendfile transfère des données entre des descripteurs de fichiers dans l'espace du noyau du système d'exploitation sans les envoyer dans les tampons de l'application. Cette directive sera utilisée pour servir de petits fichiers.
directio:
Cette directive améliore l'efficacité du cache en permettant que la lecture et l'écriture soient envoyées directement à l'application. directio
est une fonctionnalité du système de fichiers de tous les systèmes d'exploitation modernes. Cette directive sera utilisée pour servir des fichiers plus volumineux tels que des vidéos.
aio:
Cette directive permet le multithreading lorsqu'elle est définie à on
pour les opérations d'écriture et de lecture. Le multithreading est un modèle d'exécution qui permet à plusieurs threads de s'exécuter séparément les uns des autres tout en partageant les ressources de leur processus d'hébergement.
directio_alignment:
Cette directive attribue une valeur de taille de bloc au transfert de données. Elle est liée à la directio
directive.
Couche réseau
Dans cette section, nous utiliserons des directives telles que tcp_nodelay
et tcp_nopush
pour éviter que les petits paquets n'attendent un délai spécifié d'environ 200 millisecondes avant d'être envoyés en une seule fois.
Habituellement, lorsque les paquets sont transférés par "morceaux", ils ont tendance à saturer le réseau très chargé. John Nagle a donc construit un algorithme de mise en mémoire tampon pour résoudre ce problème. L'algorithme de mise en mémoire tampon de Nagle a pour but d'empêcher les petits paquets de saturer le réseau très chargé.
Copiez et collez le code suivant dans la section HTTP.
http {
tcp_nopush on;
tcp_nodelay on;
}
tcp_nodelay:
Cette directive est désactivée par défaut pour permettre aux petits paquets d'attendre un certain temps avant d'être envoyés en une seule fois. Pour permettre l'envoi de toutes les données en une seule fois, cette directive est activée.
tcp_nopush:
Parce que nous avons permis tcp_nodelay
les petits paquets sont envoyés en une seule fois. Cependant, si vous souhaitez toujours utiliser l'algorithme de mise en mémoire tampon de John Nagle, nous pouvons également activer la directive tcp_nopush
pour ajouter des paquets les uns aux autres et les envoyer tous en même temps.
Tampons
Voyons comment configurer les tampons de requêtes dans Nginx pour traiter les requêtes de manière efficace. Une mémoire tampon est un espace de stockage temporaire où les données sont conservées pendant un certain temps avant d'être traitées.
Vous pouvez copier le texte ci-dessous dans la section serveur.
server {
client_body_buffer_size 8k;
client_max_body_size 2m;
client_body_in_single_buffer on;
client_body_temp_pathtemp_files 1 2;
client_header_buffer_size 1m;
large_client_header_buffers 4 8k;
}
Il est important de comprendre le rôle de ces lignes tampons.
client_body_buffer_size:
Cette directive définit la taille de la mémoire tampon pour le corps de la requête. Si vous prévoyez d'exécuter le serveur web sur des systèmes 64 bits, vous devez fixer la valeur à 16k. Si vous souhaitez faire fonctionner le serveur web sur un système 32 bits, définissez la valeur à 8k.
client_max_body_size:
Si vous avez l'intention de gérer des téléchargements de fichiers volumineux, vous devez définir cette directive à au moins 2m
ou plus. Par défaut, il est fixé à 1m
.
client_body_in_file_only:
Si vous avez désactivé la directive client_body_buffer_size
avec le symbole du hashtag #
et cette directive client_body_in_file_only
est défini, Nginx enregistre alors les tampons de requête dans un fichier temporaire. Ceci n'est pas recommandé pour un environnement de production.
client_body_in_single_buffer:
Parfois, le corps de la requête n'est pas entièrement stocké dans une mémoire tampon. Le reste est enregistré ou écrit dans un fichier temporaire. Toutefois, si vous avez l'intention d'enregistrer ou de stocker la totalité du tampon de la requête dans un seul tampon, vous devez activer cette directive.
client_header_buffer_size:
Vous pouvez utiliser cette directive pour définir ou allouer une mémoire tampon pour les en-têtes de requête. Vous pouvez définir cette valeur à 1m
.
large_client_header_buffers:
Cette directive est utilisée pour définir le nombre et la taille maximum pour la lecture des en-têtes de requête volumineux. Vous pouvez définir le nombre maximum et la taille de la mémoire tampon à 4
et 8k
précisément.
Compression
La compression de la quantité de données transférées sur le réseau est un autre moyen d'améliorer les performances de votre serveur web. Dans cette section, nous utiliserons des directives telles que gzip
, gzip_comp_level
et gzip_min_length
pour compresser les données.
Collez le code suivant à l'intérieur du fichier http section
comme indiqué ci-dessous :
http {
gzip on;
gzip_comp_level 2;
gzip_min_length 1000;
gzip_types text/xml text/css;
gzip_http_version 1.1;
gzip_vary on;
gzip_disable "MSIE [4-6] \.";
}
gzip:
Si vous souhaitez activer la compression, fixez la valeur de cette directive à on
. Par défaut, il est désactivé.
gzip_comp_level:
Vous pouvez utiliser cette directive pour définir le niveau de compression. Afin de ne pas gaspiller les ressources de l'unité centrale, vous ne devez pas fixer un niveau de compression trop élevé. Entre 1
et 9
vous pouvez régler le niveau de compression sur 2
ou 3
.
gzip_min_length:
Définir la longueur minimale de la réponse pour la compression via l'option content-length response header field
. Vous pouvez le régler sur plus de 20 octets.
gzip_types:
Cette directive vous permet de choisir le type de réponse que vous souhaitez compresser. Par défaut, le type de réponse text/html
est toujours compressé. Vous pouvez ajouter d'autres types de réponses tels que text/css
comme indiqué dans le code ci-dessus.
gzip_http_version:
Cette directive vous permet de choisir la version HTTP minimale d'une requête pour une réponse compressée. Vous pouvez utiliser la valeur par défaut qui est 1.1
.
gzip_vary:
Quand gzip
est activée, cette directive ajoute le champ d'en-tête Vary:Accept Encoding
à la réponse.
gzip_disabled:
Certains navigateurs tels que Internet Explorer 6
n'ont pas de soutien pour les gzip compression
. Cette directive utilise User-Agent
pour désactiver la compression pour certains navigateurs.
Mise en cache
Exploiter les fonctions de mise en cache pour réduire le nombre de fois où les mêmes données doivent être chargées plusieurs fois. Nginx propose des fonctionnalités de mise en cache des métadonnées de contenu statique via open_file_cache
directive.
Vous pouvez placer cette directive à l'intérieur du fichier server
, location
et http
section.
http {
open_file_cache max=1,000 inactive=30s;
open_file_cache_valid 30s;
open_file_cache_min_uses 4;
open_file_cache_errors on;
}
open_file_cache:
Cette directive est désactivée par défaut. Activez-la si vous souhaitez mettre en place une mise en cache dans Nginx. Cette directive stocke les métadonnées des fichiers et des répertoires couramment demandés par les utilisateurs.
open_file_cache_valid:
Cette directive contient des informations de sauvegarde à l'intérieur du open_file_cache
. Vous pouvez utiliser cette directive pour définir une période de validité, généralement en secondes, après laquelle les informations relatives aux fichiers et aux répertoires sont à nouveau validées.
open_file_cache_min_uses:
Nginx fournit généralement des informations claires dans le fichier open_file_cache
après une période d'inactivité sur la base de la directive open_file_cache_min_uses
. Vous pouvez utiliser cette directive pour définir un nombre minimum d'accès afin d'identifier les fichiers et les répertoires auxquels on accède activement.
open_file_cache_errors:
Vous pouvez utiliser cette directive pour permettre à Nginx de mettre en cache des erreurs telles que "permission denied" ou "can't access this file" lors de l'accès à des fichiers. Ainsi, chaque fois qu'une ressource est accédée par un utilisateur qui n'en a pas le droit, Nginx affiche le même rapport d'erreur "permission denied".
Délai d'attente
Configurez le délai d'attente à l'aide de directives telles que keepalive_timeout
et keepalive_requests
pour éviter que les connexions en attente depuis longtemps ne gaspillent des ressources.
Dans la section HTTP, copiez et collez le code suivant :
http {
keepalive_timeout 30s;
keepalive_requests 30;
send_timeout 30s;
}
keepalive_timeout
: Maintient les connexions en vie pendant environ 30 secondes. La valeur par défaut est de 75 secondes.
keepalive_requests
: Configurez un nombre de demandes à maintenir en vie pendant une période de temps spécifique. Vous pouvez régler le nombre de demandes sur 20 ou 30.
keepalive_disable
si vous souhaitez désactiver la connexion keepalive pour un groupe spécifique de navigateurs, utilisez cette directive.
send_timeout
: Définir un délai d'attente pour la transmission des données au client.
Configuration de la sécurité pour Nginx
Ce qui suit se concentre uniquement sur la manière de configurer de manière sécurisée un Nginx plutôt qu'une application web. Nous n'aborderons donc pas les attaques basées sur le web telles que les attaques SQL injection et ainsi de suite.
Dans cette section, nous verrons comment configurer les éléments suivants :
- Restreindre l'accès aux fichiers et aux répertoires
- Configurer les journaux pour surveiller les activités malveillantes
- Prévenir les DDoS
- Désactiver l'inscription au répertoire
Restreindre l'accès aux fichiers et aux répertoires
Voyons comment restreindre l'accès aux fichiers et répertoires sensibles grâce aux méthodes suivantes.
En utilisant l'authentification HTTP
Nous pouvons restreindre l'accès aux fichiers sensibles ou aux zones qui ne sont pas destinées à être vues par le public en demandant l'authentification des utilisateurs ou même des administrateurs. Exécutez la commande suivante pour installer un utilitaire de création de fichiers de mots de passe si vous ne l'avez pas encore fait.
apt-get install -y apache-utils
Ensuite, créez un fichier de mots de passe et un utilisateur à l'aide de la commande htpasswd
comme indiqué ci-dessous. L'outil htpasswd
est fourni par le apache2-utils
de l'utilitaire.
sudo htpasswd -c /etc/apache2/ .htpasswd mike
Vous pouvez confirmer que vous avez réussi à création d'un utilisateur et d'un mot de passe aléatoire via la commande suivante
cat etc/apache2/ .htpasswd
Dans la section emplacement, vous pouvez coller le code suivant pour demander aux utilisateurs de s'authentifier à l'aide de l'option auth_basic
directive.
location /admin {
basic_auth "Admin Area";
auth_basic_user_file /etc/apache2/ .htpasswd;
}
En utilisant la directive Allow
En plus de la basic_auth
nous pouvons utiliser la directive allow
pour restreindre l'accès.
Dans la section emplacement, vous pouvez utiliser le code suivant pour permettre aux adresses IP spécifiées d'accéder à la zone sensible.
location /admin {
allow 192.168.34.12;
allow 192.168.12.34;
}
Configurer les journaux pour surveiller les activités malveillantes
Dans cette section, nous allons configurer error
et access
pour surveiller spécifiquement les requêtes valides et non valides. Vous pouvez examiner ces journaux pour savoir qui s'est connecté à un moment donné, ou quel utilisateur a accédé à un fichier particulier, etc.
error_log:
Permet de configurer l'enregistrement dans un fichier particulier tel que syslog
ou stderr
. Vous pouvez également spécifier le niveau des messages d'erreur que vous souhaitez enregistrer.
access_log:
Permet d'écrire les demandes des utilisateurs dans le fichier access.log
Dans la section HTTP, vous pouvez utiliser les éléments suivants.
http {
access_log logs/access.log combined;
error_log logs/warn.log warn;
}
Prévenir les DDOS
Vous pouvez protéger Nginx d'une attaque DDOS par les méthodes suivantes :
Limiter les demandes des utilisateurs
Vous pouvez utiliser le limit_req_zone
et limit_req
pour limiter le rythme des requêtes envoyées par les utilisateurs en minutes.
Ajoutez le code suivant dans le fichier location
intégrée dans la section du serveur.
limit_req_zone $binary_remote_addr zone=one:10m rate=30r/m;
server {
location /admin.html {
limit_req zone=one;
}
}
Limiter le nombre de connexions
Vous pouvez utiliser le limit_conn
et limit_conn_zone
pour limiter les connexions à certains endroits ou à certaines zones. Par exemple, le code ci-dessous reçoit 15 connexions de clients pour une période spécifique.
Le code suivant sera envoyé à la page location
section.
limit_conn_zone $binary_remote_addr zone=addr:10m;
server {
location /products/ {
limit_conn addr 10;
}
}
Mettre fin aux connexions lentes
Vous pouvez utiliser des directives relatives aux délais d'attente, telles que la directive client_body_timeout
et client_header_timeout
pour contrôler le temps d'attente de Nginx pour les écritures provenant de la base de données client body
et client header
.
Ajoutez ce qui suit à l'intérieur du fichier server
section.
server {
client_body_timeout 5s;
client_header_timeout 5s;
}
Il serait également judicieux d'arrêter les attaques DDoS à la périphérie en exploitant des solutions basées sur l'informatique en nuage, telles que les solutions de gestion de l'information et de la communication. mentionné ici.
Désactiver l'inscription au répertoire
Vous pouvez utiliser le auto_index
pour empêcher l'inscription dans les répertoires, comme le montre le code ci-dessous. Vous devez lui donner la valeur off
pour désactiver l'inscription au répertoire.
location / {
auto_index off;
}
Conclusion
Nous avons configuré le serveur web Nginx pour qu'il fonctionne efficacement et qu'il soit protégé contre les abus excessifs dans un environnement de production. Si vous utilisez Nginx pour des applications web orientées vers l'Internet, vous devriez également envisager d'utiliser un serveur de type CDN et sécurité basée sur l'informatique dématérialisée pour améliorer les performances et la sécurité.