Dans le premier article de cette série, nous décrivons plusieurs approches permettant de renforcer la sécurité de vos clés privées SSL. L’article se termine par une démonstration d’un point de distribution de mots de passe (PDP) distant, utilisé pour partager de manière sécurisée les mots de passe de chiffrement avec les instances NGINX.
Les systèmes de gestion des secrets tels que HashiCorp Vault fonctionnent de manière similaire à cet exemple de PDP :
- Ils utilisent un service de gestion des secrets centralisé (ou distribué et hautement disponible), accessible via HTTPS ou une autre API.
- Les clients sont authentifiés à l’aide de jetons d’authentification ou par d’autres moyens
- Les jetons peuvent être révoqués si nécessaire afin de contrôler l’accès au secret
Dans cet article, nous vous expliquons comment configurer HashiCorp Vault pour distribuer des mots de passe SSL. Pour renforcer encore davantage la sécurité, vous pouvez configurer un module matériel de sécurité externe (HSM).
Pour éliminer complètement le stockage sur disque des paires certificat-clé SSL, consultez le troisième article de cette série, « Utilisation du magasin clé-valeur de NGINX Plus pour sécuriser les clés SSL éphémères de HashiCorp Vault ». Il explique comment générer des clés SSL éphémères à partir de HashiCorp Vault et les stocker en mémoire dans le magasin clé-valeur de NGINX Plus.
Cet article s’applique à la fois à NGINX Open Source et à NGINX Plus. Pour faciliter la lecture, nous utiliserons le terme « NGINX » dans la suite de l’article.
Utiliser HashiCorp Vault pour protéger les clés privées SSL
Les instructions de cette section permettent de configurer un serveur PDP central utilisant Vault pour distribuer les mots de passe SSL. Elles s’appuient sur les instructions de DigitalOcean ; adaptez-les si nécessaire afin de respecter vos propres politiques Vault.
Dans notre exemple, chaque serveur web distant dispose d’un jeton d’authentification unique. Ces jetons permettent d’accéder aux secrets stockés dans le chemin secret/webservers/ de Vault, et nous stockons les mots de passe SSL dans secret/webservers/ssl_passwords.
Nous verrons comment sécuriser les jetons et comment révoquer individuellement les jetons d’authentification lorsque cela est nécessaire.
Télécharger, installer et initialiser HashiCorp Vault sur le serveur PDP
- Suivez les instructions de DigitalOcean pour télécharger et extraire Vault sur votre serveur PDP. Nous utilisons l’exemple de fichier /etc/vault.hcl suivant afin de rendre Vault accessible à distance et de désactiver TLS (pour faciliter les tests) :
backend "file" { path = "/var/lib/vault"
}
listener "tcp" {
address = "0.0.0.0:8200"
tls_disable = 1
}- Démarrez Vault à l’aide des scripts de démarrage (si vous les avez créés), ou manuellement :
user@pdp:~$ sudo /usr/local/bin/vault server -config=/etc/vault.hcl- Initialisez Vault et obtenez le jeton racine initial :
user@pdp:~$ export VAULT_ADDR=http://localhost:8200
user@pdp:~$ vault init -key-shares=3 -key-threshold=2
user@pdp:~$ vault operator unseal
Initial Root Token: 86c5c2a4-8ab2-24dd-1816-48449c83114e- Nous devons fournir le jeton racine initial dans bon nombre des commandes suivantes. Pour plus de commodité, nous l’affectons à la variable shell «
root_token» :
user@pdp:~$ root_token=86c5c2a4-8ab2-24dd-1816-48449c83114eStocker les secrets
- Toujours sur le serveur PDP, créez un fichier temporaire nommé « /tmp/ssl_passwords.txt » contenant les mots de passe.
- Stockez ce fichier en tant que secret dans Vault, puis vérifiez que vous pouvez le récupérer :
user@pdp:~$ VAULT_TOKEN=$root_token vault kv put secret/webservers/ssl_passwords value=@/tmp/ssl_passwords.txt
user@pdp:~$ VAULT_TOKEN=$root_token vault kv get -field=value secret/webservers/ssl_passwords
password1
password2
...- Pour des raisons de sécurité, supprimez /tmp/ssl_passwords.txt.
- Créez une spécification de politique dans un fichier nommé web.hcl avec le contenu suivant :
path "secret/webservers/*" {
capabilities = ["read"]
}- Chargez la politique dans Vault et nommez-la «
web» :
user@pdp:~$ VAULT_TOKEN=$root_token vault policy write web web.hcl- Créez un nouveau jeton d’authentification, associez-le à la politique
webet, si vous le souhaitez, ajoutez le paramètredisplay-nameafin de lui attribuer un nom convivial. Notez les valeurs detokenet detoken_accessor; vous les utiliserez dans les commandes suivantes :
user@pdp:~$ VAULT_TOKEN=$root_token vault token create -policy=web -display-name=webserver1
Key Value
--- -----
token dcf75ffd-a245-860f-6960-dc9e834d3385
token_accessor 0c1d6181-7adf-7b42-27be-b70cfa264048- Le serveur web NGINX utilise ce jeton pour récupérer les mots de passe SSL. La politique «
web» empêche le serveur web de récupérer des secrets en dehors du chemin « secret/webservers/* ».
Vérifier que le serveur web peut récupérer le jeton
- Sur le serveur web NGINX, installez le binaire Vault.
- Déclarez l’emplacement du serveur Vault distant (ici, http://pdp:8200), puis vérifiez que la machine hébergeant le serveur web peut récupérer les mots de passe SSL à l’aide du jeton :
user@web1:~$ export VAULT_ADDR=http://pdp:8200user@web1:~$ VAULT_TOKEN=dcf75ffd-a245-860f-6960-dc9e834d3385 vault kv get -field=value secret/webservers/ssl_passwords
password1
password2
...Configurer le connecteur Vault de NGINX sur le serveur web
- Dans le cadre de la configuration de l’exemple de PDP dans le premier article, nous avons créé un script shell nommé connector.sh sur l’hôte NGINX (la machine faisant office de serveur web). Nous allons maintenant le modifier pour qu’il utilise Vault :
#!/bin/sh
# Usage: connector_v.sh
CONNECTOR=$1
CREDS=$2
[ -e $CONNECTOR ] && /bin/rm -f $CONNECTOR
mkfifo $CONNECTOR; chmod 600 $CONNECTOR
export VAULT_ADDR=http://pdp:8200
export VAULT_TOKEN=$CREDS
while true; do
vault kv get -field=value secret/webservers/ssl_passwords > $CONNECTOR
sleep 0.1 # race condition, ensures EOF
done- Exécutez le script en tant que processus d’arrière-plan, comme suit :
root@web1:~# ./connector_v.sh /var/run/nginx/ssl_passwords \dcf75ffd-a245-860f-6960-dc9e834d3385 &- Testez le connecteur en effectuant une lecture à partir du chemin du connecteur :
root@web1:~$ cat /var/run/nginx/ssl_passwordspassword1
password2
...- Configurez NGINX pour qu’il lise le fichier ssl_passwords au démarrage et utilise son contenu comme mots de passe pour déchiffrer les clés privées chiffrées. Vous pouvez inclure la directive
ssl_password_filesoit dans un blocserver(comme celui créé pour la configuration standard dans le premier article), soit dans le contextehttpafin de l’appliquer à plusieurs serveurs virtuels :
ssl_password_file /var/run/nginx/ssl_passwords;- Vérifiez que NGINX peut lire le mot de passe et déchiffrer les clés SSL :
root@web1:~# nginx -t
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successfulRévocation du jeton d’authentification d’un serveur web
Vous pouvez facilement révoquer l’accès si le serveur web est compromis ou lorsqu’il est mis hors service. Pour ce faire, vous pouvez révoquer directement le jeton d’authentification utilisé par le serveur web :
user@pdp:~$ VAULT_TOKEN=$root_token vault token revoke dcf75ffd-a245-860f-6960-dc9e834d3385Les jetons Vault sont des données sensibles, et de nombreux workflows Vault ne conservent aucune copie des jetons délivrés à un client authentifié. Si la copie d’un jeton est divulguée, un attaquant peut usurper l’identité du client.
À la place, il est courant de gérer un jeton actif à l’aide de son accesseur, qui confère des droits limités sur le jeton et ne permet pas d’en récupérer la valeur. Plutôt que de stocker les jetons lorsqu’ils sont émis, stockez l’accesseur correspondant.
Si vous devez déterminer l’accesseur du jeton d’authentification d’un serveur web, exécutez la commande vault list pour récupérer la liste des accesseurs, puis la commande vault token lookup sur chaque accesseur afin de trouver celui qui possède le nom d’affichage et la politique appropriés :
user@pdp:~$ VAULT_TOKEN=$root_token vault list /auth/token/accessors
Keys
----
83be5a73-9025-1221-cb70-4b0e8a3ba8df
0c1d6181-7adf-7b42-27be-b70cfa264048
f043b145-7a63-01db-ea85-9f22f413c55e
user@pdp:~$ VAULT_TOKEN=$root_token vault token lookup -accessor 0c1d6181-7adf-7b42-27be-b70cfa264048
Key Value
--- -----
...
display-name webserver1
...
policy web
...Vous pouvez ensuite révoquer le jeton à l’aide de son accesseur :
user@pdp:~$ VAULT_TOKEN=$root_token vault token revoke -accessor 0c1d6181-7adf-7b42-27be-b70cfa264048Implications en matière de sécurité
L’utilisation de Vault présente un profil de sécurité similaire à celui de l’exemple de PDP décrit dans le premier article. Les clés privées SSL ne peuvent être obtenues que si le mot de passe correspondant l’est également. Pour cela, un attaquant doit connaître la valeur d’un jeton d’authentification en cours de validité.
Le principal avantage de Vault est de permettre l’automatisation et la mise à l’échelle du stockage des secrets.
Utilisation d’un HSM externe pour gérer les clés privées
Aucune des solutions que nous avons présentées jusqu’à présent dans cette série ne protège la clé privée lorsqu’un attaquant obtient un accès root au serveur NGINX. Si un attaquant peut accéder à la mémoire d’exécution de NGINX ou générer un vidage mémoire, il existe des techniques bien connues permettant d’analyser la mémoire du processus et d’y localiser les données de la clé privée.
Les modules matériels de sécurité (HSM) externes résolvent ce problème en stockant les clés privées SSL dans un matériel externe inviolable. Ils fournissent un service de déchiffrement auquel NGINX accède chaque fois qu’il doit effectuer une opération SSL nécessitant la clé.
Le serveur NGINX n’a jamais accès aux données de la clé privée SSL. Un attaquant qui obtient un accès root au serveur ne peut pas récupérer la clé privée SSL, mais peut déchiffrer des données à la demande en accédant au service de déchiffrement du HSM à l’aide des identifiants NGINX.
Configuration de NGINX pour accéder à un HSM
NGINX délègue toutes les opérations liées aux clés privées SSL à une bibliothèque cryptographique appelée OpenSSL. Les périphériques HSM tiers peuvent être mis à la disposition de NGINX à l’aide du moteur OpenSSL du fournisseur du HSM.
La configuration de NGINX est propre au HSM de chaque fournisseur, mais suit généralement une procédure simple :
- Configurez NGINX pour utiliser le moteur OpenSSL du fournisseur plutôt que le moteur logiciel par défaut :
ssl_certificate_key engine:vendor-hsm-engine:...;- Au lieu d’utiliser la véritable clé privée, configurez NGINX pour qu’il utilise la « fausse » clé fournie par le fournisseur. Cette clé contient un identifiant permettant de retrouver la véritable clé sur le périphérique HSM :
ssl_certificate_key ssl/vendor.private.key;- La clé peut également contenir les identifiants permettant d’accéder au périphérique HSM, ou ceux-ci peuvent être fournis au moyen d’une configuration supplémentaire propre au fournisseur.
- (Facultatif) Appliquez les réglages souhaités, par exemple en augmentant le nombre de processus de travail NGINX, afin d’optimiser les performances de NGINX et du HSM.
Pour un exemple de configuration d’un HSM, consultez la documentation CloudHSM d’Amazon.
Implications en matière de sécurité
Les HSM externes constituent une méthode hautement sécurisée pour stocker les clés privées SSL. Un attaquant disposant d’un accès root au serveur NGINX peut utiliser les identifiants NGINX pour déchiffrer des données arbitraires à l’aide du HSM, mais ne peut pas obtenir la clé privée non chiffrée. Un HSM complique considérablement la tâche d’un attaquant qui chercherait à usurper l’identité d’un site web ou à déchiffrer hors ligne des données arbitraires.
Conclusion
Il est essentiel de veiller à ce que les données confidentielles, telles que la clé privée SSL, soient entièrement protégées, car les conséquences de leur divulgation sont très graves.
Pour de nombreuses organisations disposant de processus de sécurité appropriés, il suffit de stocker la clé privée sur les répartiteurs de charge frontaux, puis de restreindre et d’auditer tous les accès à ces serveurs (la « configuration standard » décrite dans le premier article).
Pour les organisations qui doivent déployer fréquemment la configuration de NGINX, les mesures présentées dans cet article et dans le premier article peuvent être utilisées pour limiter le nombre d’utilisateurs ou d’entités ayant accès aux données de la clé privée.
Dans le troisième article de cette série, « Utilisation du magasin clé-valeur de NGINX Plus pour sécuriser les clés SSL éphémères provenant de HashiCorp Vault », nous expliquons comment automatiser le provisionnement des clés et des certificats depuis Vault vers le magasin clé-valeur de NGINX Plus à l’aide de l’API NGINX Plus.
Rappelons qu’aucune de ces méthodes ne dispense de sécuriser pleinement les instances NGINX en cours d’exécution contre les accès à distance ou toute modification de leur configuration.
Essayez NGINX Plus par vous-même : commencez votre essai gratuit de 30 jours dès aujourd’hui ou contactez-nous pour discuter de vos cas d’utilisation.
À propos de l’auteur

Articles de blog associés

Tendances actuelles des technologies cloud natives, de l’ingénierie de plateforme et de l’IA
Découvrez les principaux enseignements tirés des réponses à l’enquête annuelle F5 NGINX sur les dernières tendances en matière de technologies cloud natives, de sécurité, d’ingénierie de plateforme et d’IA.
Quels contrôleurs Ingress NGINX sont affectés par les vulnérabilités CVE-2022-4886, CVE-2023-5043 et CVE-2023-5044 ?
Lorsque de nouvelles CVE sont signalées, il est facile de ne plus savoir si elles concernent un outil de contrôleur Ingress NGINX particulier, car il existe plusieurs projets. Cet article présente les CVE et explique comment distinguer les différents projets de contrôleurs Ingress afin de dissiper toute confusion.
Votre API est-elle en temps réel ? Testez sa latence avec l’outil rtapi de NGINX
Votre API répond-elle aux requêtes en moins de 30 ms ? Si ce n’est pas le cas, il ne s’agit pas d’une API en temps réel offrant la faible latence exigée par la grande majorité des organisations. Mesurez la latence de votre API avec l’outil rtapi de NGINX et découvrez comment NGINX peut l’aider à offrir une réactivité en temps réel.

Un testeur d’expressions régulières pour NGINX et NGINX Plus
Le testeur d’expressions régulières (regex) pour NGINX et NGINX Plus vous évite de tâtonner en vous indiquant si une expression régulière utilisée dans un bloc location ou map correspond aux valeurs comme prévu. Il génère la configuration appropriée et affiche les valeurs des groupes de capture.
Caches partagés avec les clusters de cache NGINX Plus, partie 1
Optimisez la capacité de votre cache web en le répartissant entre plusieurs serveurs de cache web NGINX ou NGINX Plus. Découvrez comment procéder dans cet article.
Introduction aux microservices
Les microservices suscitent actuellement beaucoup d’intérêt. Cet article de blog est le premier d’une série de sept consacrée à la conception, au développement et au déploiement de microservices.