¿Qué es systemd?
systemd es el sistema de inicio y gestor de servicios estándar en la mayoría de distribuciones Linux modernas. Controla el arranque del sistema y la gestión de daemons.
Tipos de unidad
systemd no gestiona solo servicios: una unidad es cualquier recurso que sabe arrancar, parar y supervisar, y el tipo se indica por la extensión del archivo. Los más habituales:
.service— un proceso o daemon (el tipo que ya usas con nginx, Gitea, etc.).timer— dispara otra unidad en un horario, como alternativa a cron.socket— activa un servicio bajo demanda cuando llega tráfico a un puerto o socket Unix, en vez de mantenerlo siempre corriendo.mount— monta un sistema de archivos, generado automáticamente a partir de/etc/fstabo definido a mano
Un ejemplo mínimo de unidad .socket con activación bajo demanda:
# /etc/systemd/system/mi-app.socket
[Unit]
Description=Socket de mi-app
[Socket]
ListenStream=127.0.0.1:8080
[Install]
WantedBy=sockets.target
Con Accept=no (el valor por defecto), systemd arranca mi-app.service en cuanto llega la primera conexión al puerto 8080, y ese servicio es responsable de atenderlas todas — no hace falta que esté corriendo de antemano.
Un .mount sigue una convención de nombres estricta: la ruta de montaje se traduce reemplazando cada / por un -. Para montar algo en /mnt/datos, la unidad se llama mnt-datos.mount:
# /etc/systemd/system/mnt-datos.mount
[Unit]
Description=Montaje de /mnt/datos
[Mount]
What=/dev/sdb1
Where=/mnt/datos
Type=ext4
[Install]
WantedBy=multi-user.target
Comandos esenciales
Estado de servicios
systemctl status nginx
systemctl is-active nginx
systemctl is-enabled nginx
Iniciar, parar y reiniciar
sudo systemctl start nginx
sudo systemctl stop nginx
sudo systemctl restart nginx
sudo systemctl reload nginx
Habilitar y deshabilitar
start/stop y enable/disable actúan sobre dos ejes distintos, y confundirlos es uno de los errores más comunes con systemd:
start/stopcontrolan si el servicio está corriendo ahora mismoenable/disablecontrolan si el servicio arrancará en el próximo reinicio (creando o quitando un symlink hacia la unidad)
Por eso un servicio puede estar activo pero no habilitado (corre ahora, pero no sobrevivirá a un reinicio), o habilitado pero parado (arrancará en el próximo boot, pero ahora mismo no está corriendo):
sudo systemctl enable nginx
sudo systemctl disable nginx
sudo systemctl enable --now nginx
## Consejo
enable --nowcombina ambos: habilita el servicio para el arranque y lo inicia de inmediato, evitando el paso destartpor separado.
Enmascarar servicios: mask y unmask
disable quita el arranque automático, pero el servicio sigue pudiendo arrancarse a mano o como dependencia de otra unidad. mask va más allá: enlaza el unit file a /dev/null, por lo que nada puede arrancarlo — ni tú manualmente, ni otro servicio que dependa de él — hasta que lo desenmascares:
sudo systemctl mask servicio-a-bloquear
sudo systemctl unmask servicio-a-bloquear
## Peligro
Si enmascaras un servicio del que otra unidad depende (
Requires=), esa otra unidad fallará al arrancar en vez de arrancar sin él. Antes de enmascarar, comprueba consystemctl list-dependencies --reverse servicio-a-bloquearqué más lo necesita.
Crear un servicio personalizado
Este es el mismo patrón de unidad que usamos para levantar Gitea como servicio:
# /etc/systemd/system/mi-app.service
[Unit]
Description=Mi aplicación web
After=network.target
[Service]
Type=simple
User=appuser
WorkingDirectory=/opt/mi-app
ExecStart=/opt/mi-app/bin/start.sh
Restart=on-failure
RestartSec=5
[Install]
WantedBy=multi-user.target
sudo systemctl daemon-reload
sudo systemctl enable --now mi-app
Modificar un servicio sin tocar el unit original
Editar directamente un unit file que viene de un paquete (por ejemplo /lib/systemd/system/nginx.service) es frágil: la próxima actualización del paquete puede sobrescribirlo y perder tus cambios. systemctl edit resuelve esto creando un drop-in file en /etc/systemd/system/<unidad>.d/override.conf que añade o sustituye solo las directivas que indiques, sin tocar el original:
sudo systemctl edit nginx
Esto abre un editor con una plantilla vacía; basta con escribir las directivas que quieres cambiar, por ejemplo para aumentar el número de reintentos:
[Service]
Restart=on-failure
RestartSec=10
Al guardar, systemd recarga la configuración automáticamente. Si en algún momento quieres editar el unit file completo en vez de un override parcial, systemctl edit --full nginx abre una copia editable del archivo original.
Timers como alternativa a cron
Aquí el ejemplo mínimo; para una comparativa completa entre cron y systemd timers, con sus ventajas y desventajas, consulta la guía de tareas programadas:
# /etc/systemd/system/backup.timer
[Unit]
Description=Backup diario
[Timer]
OnCalendar=daily
Persistent=true
[Install]
WantedBy=timers.target
Targets: el arranque por fases
Un target agrupa unidades que deben estar activas para alcanzar un determinado estado del sistema — es el equivalente moderno a los runlevels de SysV, pero más flexible: un target puede depender de otros y puedes crear los tuyos propios. Los más comunes:
multi-user.target— sistema completo en modo texto, sin entorno gráfico (equivalente al runlevel 3)graphical.target— multi-usuario con entorno gráfico (equivalente al runlevel 5)
Para consultar y cambiar cuál se usa por defecto en el arranque:
systemctl get-default
sudo systemctl set-default multi-user.target
set-default solo cambia qué target se usará en el próximo arranque — no afecta al sistema en ejecución ahora mismo. Para cambiar el estado activo sin reiniciar, usa systemctl isolate <target>, que detiene lo que no pertenezca al target destino:
sudo systemctl isolate multi-user.target
## Nota
Las distribuciones actuales mantienen symlinks de compatibilidad (
runlevel3.target→multi-user.target, etc.), así que los números de runlevel de toda la vida siguen funcionando como alias si los necesitas por costumbre o en scripts antiguos.
Conclusión
systemd ofrece un control granular sobre los servicios del sistema: unidades más allá de .service, targets que agrupan el estado de arranque, y overrides que sobreviven a las actualizaciones de paquete. Para revisar los logs de todo lo que gestionas aquí, la guía de journalctl es el siguiente paso natural.
## Nota
✍️ Transparencia: Este artículo ha sido creado con el apoyo de herramientas de inteligencia artificial. Toda la información técnica ha sido revisada y validada por el autor antes de su publicación.