Ce tutoriel explique comment configurer Gunicorn, Nginx et Supervisor sur un serveur Linux pour servir un site Django Wagtail.
Dans un tutoriel précédent, on a configuré notre projet pour qu'il s'exécute localement sur un serveur DigitalOcean. On va maintenant installer Gunicorn et Nginx pour servir notre site sur Internet, comme cela est également décrit dans un didacticiel DigitalOcean. Cependant, notre configuration sera légèrement différente: on utilisera un fichier de configuration Gunicorn et utilisera Supervisor pour gérer à la fois Gunicorn et Nginx. Il existe d'autres didacticiels, tels que ce guide complet. Des tutoriels Linux peuvent être trouvés ici et ici.
Gunicorn servira de serveur d'applications, Nginx comme serveur Web et proxy inverse et Supervisor comme outil de gestion pour les exécuter. Gunicorn dirigera notre site et servira du contenu dynamique (à partir de la base de données) et sera installé dans le même environnement virtuel que notre site. Nginx servira du contenu statique (médias et images) et déléguera les demandes d'autres contenus à Gunicorn. Nginx sera installé sur le serveur, en dehors de l'environnement virtuel. Supervisor sera également installé sur le serveur et sera utilisé pour démarrer, arrêter et configurer à la fois Nginx et Gunicorn. Les étapes seront les suivantes:
Jusqu'à présent, on n'a utilisé que les paramètres de développement de notre projet. Avec Gunicorn et Nginx, on utilisera les paramètres de production, où debug = False
. On doit maintenant définir le paramètre ALLOWED_HOSTS
, sinon Django générera une Bad Request error. On va modifier les paramètres sur notre ordinateur de développement, les pousser dans le référentiel et sur notre serveur les extraire de là. Dans votre fichier de paramètres production.py
, ajoutez la ligne:
ALLOWED_HOSTS = ['pythoneatstail.com', 'www.pythoneatstail.com',]
Poussez la modification dans le référentiel:
git add .
git commit -m "added allowed hosts"
git push
Allez sur le serveur, activez l'environnement virtuel, entrez dans le répertoire du projet et tapez:
git pull origin master
Consultez le fichier production.py
pour vérifier que la modification est effectuée. Collectons également tous les fichiers statiques dans le répertoire /static/
, afin qu'ils puissent être récupérés par le serveur Web plus tard:
python3 manage.py collectstatic
Connectez-vous au serveur en tant qu'utilisateur qu'on a créé (utilisez votre propre adresse IP):
ssh usr_pet@165.22.199.4
Entrez dans l'environnement virtuel et installez Gunicorn:
source env/bin/activate
pip3 install gunicorn
Pour tester que Gunicorn peut desservir le site, allez dans le répertoire de votre projet et tapez:
gunicorn --bind 0.0.0.0:8000 pet.wsgi
La visite de votre site avec le navigateur sur http://165.22.199.4:8000
(remplacez votre adresse IP) devrait donner le même résultat que dans le tutoriel précédent avec la commande runserver
. Arrêtez Gunicorn avec ctrl-C
.
Il existe plusieurs façons de définir la configuration de Gunicorn. On pourra créer un fichier de service pour la commande systemd
, ou créer un script bash. Ici on va créer un fichier de configuration Gunicorn comme décrit dans la documentation de Gunicorn. On peut placer le fichier n'importe où; pour rester proche de l'organisation des fichiers de Linux, on va créer un répertoire /etc
pour les fichiers de configuration avec un sous-répertoire /gunicorn
:
mkdir -p ~/env/etc/gunicorn
cd ~/env/etc/gunicorn
touch conf.py
Le référentiel Gunicorn contient un exemple de fichier de configuration. On va copier certains des paramètres dont on a besoin. Commençons par quelques simples, qui sont expliqués dans l'exemple de fichier. Ouvrez conf.py
avec vi
ou un autre éditeur et ajoutez:
workers = 3
keepalive = 5
user = 'usr_pet'
proc_name = 'pet'
On ajoute également des informations sur la façon dont on veut enregistrer:
loglevel = 'error'
errorlog = '/home/usr_pet/env/var/log/gunicorn-error.log'
accesslog = '/home/usr_pet/env/var/log/gunicorn-access.log'
Les fichiers spécifiés n'existent pas encore. On n'a pas besoin de créer les fichiers, mais on doit s'assurer que le répertoire existe, alors quittez temporairement l'éditeur et créez un répertoire ~/env/var/log
. Créez également un répertoire ~/env/run
pour le fichier socket (voir ci-dessous).
mkdir -p ~/env/var/log
mkdir ~/env/run
Revenez à l'édition du fichier de configuration conf.py
. Essentiel est le paramètre bind
, qui indique à Gunicorn quelle est l'interface avec laquelle communiquer avec le monde extérieur. Ci-dessus, on a utilisé une adresse IP, maintenant on va utiliser un fichier (un fichier socket Unix) via lequel Gunicorn s'interfacera avec Nginx (qui à son tour se connectera à une adresse IP). Gunicorn créera ce fichier lui-même, mais le répertoire doit exister. La syntaxe est:
bind = 'unix:/home/usr_pet/env/run/gunicorn.sock'
On a besoin d'un moyen de dire à Gunicorn d'utiliser les paramètres de production de notre projet. Le paramètre Django pour cela est DJANGO_SETTINGS_MODULE
et on peut le définir en utilisant le paramètre Gunicorn raw_env
(voir aussi l'exemple de fichier):
raw_env = ['DJANGO_SETTINGS_MODULE=pet.settings.production',]
Pour s'assurer que Gunicorn peut trouver le fichier de paramètres Django, on doit spécifier le chemin Python:
pythonpath = '/home/usr_pet/pet'
Cela conclut le fichier de configuration de Gunicorn.
Quittez l'environnement virtuel si nécessaire et installez Nginx:
sudo apt-get update
sudo apt-get install nginx
Nginx crée un fichier de configuration générique dans /etc/nginx/nginx.conf
et deux répertoires /sites-available
et /sites-enabled
. On va créer un fichier de configuration de bloc serveur dans le répertoire /sites-available
. Créez le fichier (on l'appelle pet
) et ouvrez-le avec votre éditeur (dans notre cas vi
; utilisez sudo
pour l'autorisation d'écriture):
sudo vi /etc/nginx/sites-available/pet
Dans ce fichier, on mettra un bloc serveur avec un certain nombre de paramètres (voir "Configure Nginx to Proxy Pass to Gunicorn"):
Mettez le contenu suivant et enregistrez le fichier; voir ci-dessous pour l'explication.
server {
server_name pythoneatstail.com www.pythoneatstail.com;
access_log /home/usr_pet/env/var/log/nginx-access.log;
error_log /home/usr_pet/env/var/log/nginx-error.log;
location = /favicon.ico { access_log off; log_not_found off; }
location /static/ {
root /home/usr_pet/pet;
}
location /media/ {
root /home/usr_pet/pet;
}
location / {
include proxy_params;
proxy_pass http://unix:/home/usr_pet/env/run/gunicorn.sock;
}
}
La première ligne spécifie les noms de domaine de notre site, les deuxième et troisième les fichiers journaux. La première déclaration location
indique à Nginx d'ignorer tout problème potentiel avec la recherche d'un favicon. Les deuxième et troisième instructions location
spécifient l'emplacement des fichiers statiques et multimédias dans notre projet, afin que Nginx puisse les servir directement si cela est demandé. L'instruction finale correspond à toutes les autres demandes et pointe vers le fichier socket qu'on a créé plus tôt, procurant ainsi une requête proxy à Gunicorn. Il inclut un fichier de paramètres proxy_params
créé lors de l'installation dans le répertoire /etc/nginx
.
Les paramètres Nginx réels seront récupérés à partir du répertoire /sites-enabled
, on fait donc un lien symbolique à partir de /sites-available
pour y:
sudo ln -s /etc/nginx/sites-available/pet /etc/nginx/sites-enabled
Testez la configuration Nginx pour les erreurs avec:
sudo nginx -t
Pour vérifier que Nginx est en cours d'exécution, utilisez la commande systemctl
; il devrait afficher que Nginx est "active (running)"
.
sudo systemctl status nginx
On peut maintenant vérifier si Gunicorn et Nginx peuvent échanger des données via le fichier socket, en exécutant Gunicorn avec son fichier de configuration:
sudo /home/usr_pet/env/bin/gunicorn pet.wsgi:application --config /home/usr_pet/env/etc/gunicorn/conf.py
Ici, le premier chemin mène à l'exécutable Gunicorn, l'argument pet.wsgi:application
est la variable application
dans le fichier pet.wsgi
de votre projet, et le deuxième chemin mène au fichier de configuration qu'on a créé ci-dessus. Cette commande lancera Gunicorn au premier plan, occupant temporairement la fenêtre de votre terminal. Dans votre navigateur, visitez votre domaine (www.pythoneatstail.com); si tout va bien, vous pourrez accéder à votre site. Vous pouvez vérifier que Gunicorn a créé le fichier socket en ouvrant un deuxième terminal et en listant le contenu du répertoire /home/usr_pet/env/run
. Arrêtez le processus Gunicorn dans le premier terminal avec ctrl-C
. Le fichier socket aura disparu.
On utilisera Supervisor pour surveiller et contrôler à la fois le processus Gunicorn et le processus Nginx. Il est légèrement plus simple et plus convivial que le Systemd intégré et peut déléguer à des utilisateurs non root. Supervisor pourrait être installé dans l'environnement virtuel, mais comme on a l'intention de l'utiliser pour gérer Nginx, qui est installé sur le serveur, ce n'est pas très logique et nécessite plus de configuration. L'installation peut se faire via pip, mais on utilisera apt-get
comme recommandé par DigitalOcean, malgré le fait qu'il nous donne une version plus ancienne:
sudo apt-get install supervisor
Supervisor a créé un fichier de configuration dans /etc/supervisor
. Si vous l'inspectez, vous pouvez voir qu'il inclut tous les fichiers de configuration spécifiques à l'application dans le sous-répertoire /conf.d
. Allez dans ce sous-répertoire, créez un fichier guni-pet.conf
et collez le contenu suivant:
[program:guni-pet]
command=/home/usr_pet/env/bin/gunicorn pet.wsgi:application --config /home/usr_pet/env/etc/gunicorn/conf.py
user=usr_pet
autostart=true
autorestart=true
Tous les paramètres de configuration sont dans la documentation. La première ligne spécifie la commande d'exécution qu'on a utilisée auparavant, la deuxième ligne spécifie l'utilisateur et la troisième et la quatrième ligne indiquent à Supervisor de démarrer et redémarrer automatiquement le processus après une sortie. Pour Nginx, créez un fichier nginx-pet.conf
et collez:
[program:nginx-pet]
command=/usr/sbin/nginx -g "daemon off;"
autostart=true
autorestart=true
stderr_logfile=/home/usr_pet/env/var/log/nginx-error.log
stdout_logfile=/home/usr_pet/env/var/log/nginx-access.log
Dans la commande, on définit "daemon off"
avec le commutateur -g
car Supervisor exige que les processus se déroulent au premier plan. Cette fois, on ne spécifie pas d'utilisateur, car Nginx a été installé par root et doit donc être exécuté par root. Pour la même raison, on répète les emplacements des fichiers journaux, pour nous assurer que les journaux s'y retrouvent.
Cela termine la configuration de Supervisor. La partie client en ligne de commande de Supervisor est supervisorctl
. Ajoutez les nouvelles configurations à Supervisor avec:
sudo supervisorctl reread
sudo supervisorctl update
Cela devrait maintenant être aussi simple que:
sudo supervisorctl start all
qui démarre Gunicorn et Nginx. Accédez à votre adresse de domaine dans votre navigateur (dans notre cas www.pythoneatstail.com) et voyez si cela fonctionne. Arrêtez l'un des processus, redémarrez-les, vérifiez l'état, en utilisant les différentes commandes de Supervisor (avec <process-name>
guni-pet
ou nginx-pet
):
sudo supervisorctl status [optional: <process-name>]
sudo supervisorctl start <process-name>
sudo supervisorctl stop <process-name>
sudo supervisorctl restart <process-name>
Si on n'a créé aucun contenu, notre site est toujours vide. On peut le remplir manuellement ou utiliser une sauvegarde; lire un autre tutoriel expliquant comment faire cela. On va également mettre en place un pare-feu, activer https et définir les clés d'accès ssh.
Commentez cet article (connectez-vous d'abord ou confirmez par nom et email ci-dessous)