Fullmoon System

Créer un service systemd : unité, sécurité, journaux et redémarrages

EdwardMoon

Enregistrez un service systemd pour démarrer au boot un programme installé manuellement, le relancer en cas d’échec et gérer de manière cohérente son utilisateur d’exécution et ses journaux. Ce guide concerne les services système de RHEL et Rocky Linux 8/9. L’application doit rester au premier plan sans se détacher en arrière-plan.

Créer un service systemd : démarrage, état, journaux, réseau et récupération des conteneurs Linux et des services systemd
Composants, limites de sécurité, vérification de l’état et récupération d’un service systemd

1. Préparer l’exécutable et la configuration

Adaptez /usr/local/bin/myapp et /etc/myapp/config.yml à votre application. Cette procédure n’installe pas le programme et ne crée pas le contenu de son fichier de configuration. Vérifiez d’abord sa commande de lancement normale, son répertoire de travail, les fichiers et ports nécessaires et sa méthode d’arrêt propre. Pour modifier un service existant, conservez ailleurs une copie de l’unité et des fichiers de configuration concernés.

command -v systemctl
systemd --version
sudo test -x /usr/local/bin/myapp
sudo test -f /etc/myapp/config.yml

Ne passez pas à l’étape suivante si un contrôle échoue. Si un paquet fournit déjà un service, examinez-le avec systemctl cat nom-du-service avant de créer une unité. Un fichier de surcharge drop-in pour l’unité fournie facilite généralement la maintenance.

2. Créer un compte dédié et un répertoire accessible en écriture

getent passwd myapp
getent group myapp
# Exécuter une seule fois, uniquement si le compte n’existe pas.
sudo useradd --system --user-group --home-dir /var/lib/myapp --shell /sbin/nologin myapp
sudo install -d -o myapp -g myapp -m 0750 /var/lib/myapp
sudo chown root:myapp /etc/myapp/config.yml
sudo chmod 0640 /etc/myapp/config.yml
sudo -u myapp test -x /usr/local/bin/myapp
sudo -u myapp test -r /etc/myapp/config.yml

Si le compte myapp existe déjà, vérifiez son usage et son groupe principal, puis omettez la commande de création. Les répertoires parents doivent également être accessibles : contrôlez le chemin complet avec namei -l /etc/myapp/config.yml. Le compte de service ne doit pas pouvoir modifier l’exécutable ou la configuration ; attribuez-lui uniquement le répertoire des données que l’application écrit. Si SELinux est actif, vérifiez à la fois les journaux AVC et les contextes des fichiers.

3. Rédiger l’unité de service

Enregistrez le contenu suivant avec sudoedit /etc/systemd/system/myapp.service.

[Unit]
Description=My application
After=network-online.target
Wants=network-online.target
StartLimitIntervalSec=60
StartLimitBurst=5

[Service]
Type=simple
User=myapp
Group=myapp
WorkingDirectory=/var/lib/myapp
ExecStart=/usr/local/bin/myapp --config /etc/myapp/config.yml
Restart=on-failure
RestartSec=5s
TimeoutStopSec=30s
NoNewPrivileges=yes
PrivateTmp=yes
StandardOutput=journal
StandardError=journal

[Install]
WantedBy=multi-user.target
  • Type=simple suit le processus lancé comme processus principal du service. Il ne garantit pas que l’application soit prête : un test fonctionnel distinct reste nécessaire.
  • ExecStart n’est pas une ligne de commande shell. N’y insérez pas directement &, des pipes ou des redirections.
  • After définit l’ordre de démarrage et Wants les unités à démarrer ensemble. Un réseau déclaré en ligne ne garantit pas qu’une base de données ou une API distante réponde correctement.
  • Associez Restart=on-failure à une limite de fréquence des démarrages pour arrêter les échecs qui se répètent rapidement. Décidez, selon le programme, si une sortie normale doit également entraîner un redémarrage.
  • PrivateTmp crée un espace temporaire privé. Vérifiez la compatibilité des programmes qui doivent partager des fichiers /tmp avec d’autres services.

Ne placez pas directement de mots de passe ou de jetons dans Environment=. Utilisez un fichier de configuration à accès restreint pris en charge par l’application, ou un mécanisme de transmission d’identifiants compatible avec la version de systemd.

4. Vérifier la syntaxe, démarrer et tester le fonctionnement réel

sudo systemd-analyze verify /etc/systemd/system/myapp.service
# Continuer uniquement si la vérification ci-dessus ne signale aucune erreur.
sudo systemctl daemon-reload
sudo systemctl enable --now myapp.service
systemctl is-enabled myapp.service
systemctl is-active myapp.service
sudo systemctl status myapp.service --no-pager --full
sudo journalctl -u myapp.service -b -n 100 --no-pager

daemon-reload recharge les unités, enable crée les liens nécessaires au démarrage automatique et --now lance aussi le service immédiatement. Si vous modifiez la configuration d’un service déjà actif, un reload pris en charge par le programme ou un redémarrage planifié reste nécessaire.

Ne vous contentez pas de l’état active. Pour un service web, interrogez sa véritable URL de contrôle d’état. Pour un traitement de tâches, vérifiez le résultat d’une tâche d’essai. Pendant une fenêtre de maintenance, testez également le démarrage après reboot et l’arrêt propre. Adaptez le délai d’arrêt de 30 secondes de l’exemple au temps nécessaire pour terminer sans perdre de travail.

5. Distinguer les échecs fréquents

SymptômePoints à vérifier
203/EXECChemin de l’exécutable, droit d’exécution, interpréteur du script et refus SELinux.
200/CHDIRExistence de WorkingDirectory et droits d’accès du compte de service au répertoire.
217/USERExistence du compte et du groupe indiqués par User et Group.
Arrêt juste après le démarrageErreurs dans les arguments ou la configuration ; programme qui se détache en mode daemon.
start-limit-hitCorriger la cause des échecs répétés à partir des journaux, puis réinitialiser la limite et redémarrer.
sudo journalctl -u myapp.service --since '-10 minutes' --no-pager
# Exécuter après avoir corrigé la cause.
sudo systemctl reset-failed myapp.service
sudo systemctl restart myapp.service

Revenir sur une modification

Pour un service nouvellement créé, utilisez sudo systemctl disable --now myapp.service afin de l’arrêter et de désactiver son démarrage automatique. Pour une modification d’un service existant, restaurez l’unité et la configuration sauvegardées, exécutez daemon-reload, puis effectuez un redémarrage planifié et des tests fonctionnels. Ne supprimez pas le compte de service ou le répertoire de données avant d’avoir vérifié leurs dépendances et les besoins de conservation.

Documentation officielle