Ir al contenido principal

Gestión de la red usando la línea de comandos (II): rutas persistentes

 

Introducción

Esta será la segunda entrada de la serie de artículos referentes a la gestión de la red en la línea de comandos de Linux.
Concretamente, en esta entrada voy a explicar tres métodos para dejar configuradas rutas persistentes en nuestro Ubuntu.
Las pruebas de campo las he hecho en una máquina virtual con Ubuntu Desktop 22.04 instalado. Pero lo explicado es válido para cualquier sabor de Ubuntu, incluido el Ubuntu Server.

Ejecutar una tarea programada

En Linux en general y, por tanto, también en Ubuntu, existe la posibilidad de programar tareas. Las tareas son ejecutadas por el demonio cron y tienen que ser definidas usando el comando crontab. Para conocer más sobre el sistema de programación de tareas programadas les recomiendo mirar las páginas del manual: man cron, man crontab, man 5 crontab... En este último se explica la estructura de un fichero crontab.
Lo primero que tenemos que hacer es crear nuestro script que luego se ejecutará en la programación de la tarea. Lo crearemos en la ruta /usr/local/sbin y lo llamaremos iproute.sh. El contenido del script será algo así como:
#! /bin/sh

sleep 30

ip route add 192.168.122.128/25 via 192.168.122.254 dev enp1s0 metric 1000
La primera línea ejecutable del script es una demora de 30 segundos (sleep 30) para dar tiempo al sistema a arrancar la red, pues si se ejecuta sin que la red esté levantada no se establecerá la ruta que queremos mantener persistente. Supongo que la demora se puede establecer en menos tiempo. Pero hice varias pruebas con 5, 10 y 20 segundos y a mi no me estableció la ruta hasta que probé con los 30 segundos. Claro que estoy ejecutando una máquina virtual sobre un ordenador que tiene más de 12 años y puede que eso haga que necesite más tiempo para establecer la ruta. En cualquier caso, con 30 segundos sí que la establece.
 
Una vez guardado el script hay que establecer los permisos adecuados:
sudo chmod 0755 /usr/local/sbin/iproute.sh    
Lo siguiente que tenemos que hacer es programar la ejecución del script. Para ello ejecutamos el comando:
sudo crontab -e
Necesitamos permisos de superusuario, de ahí el comando sudo, para ejecutar el comando ip route. Al ejecutar el comando crontab -e, se nos solicitará que elijamos el editor de texto que vamos a utilizar. Por defecto, tiene seleccionado el nano, lo que nos viene bien para lo que vamos a hacer. Seguidamente nos mostrará un archivo en el editor con una pequeña explicación, en inglés, de la estructura de cada línea para programar tareas. Iremos al final del fichero y añadiremos nuestra línea de programación. El fichero debería quedar más o menos así:
# Edit this file to introduce tasks to be run by cron.
# 
# Each task to run has to be defined through a single line
# indicating with different fields when the task will be run
# and what command to run for the task
# 
# To define the time you can provide concrete values for
# minute (m), hour (h), day of month (dom), month (mon),
# and day of week (dow) or use '*' in these fields (for 'any').
# 
# Notice that tasks will be started based on the cron's system
# daemon's notion of time and timezones.
# 
# Output of the crontab jobs (including errors) is sent through
# email to the user the crontab file belongs to (unless redirected).
# 
# For example, you can run a backup of all your user accounts
# at 5 a.m every week with:
# 0 5 * * 1 tar -zcf /var/backups/home.tgz /home/
# 
# For more information see the manual pages of crontab(5) and cron(8)
# 
# m h  dom mon dow   command
@reboot /usr/local/sbin/iproute.sh
Una vez que ya hemos establecido la tarea programada, tenemos que reiniciar el sistema para comprobar que se ejecutó correctamente. Recuerda que para ver las rutas hay que usar el comando de la terminal:
  ip route show

Ejecutar script en el arranque

El siguiente método que voy a explicar es el de crear un shell script que se ejecutará cuando arranque el ordenador. Para eso utilizaremos el script usando la sintaxis de servicios para el demonio init. Este demonio de inicialización, que se creó en los años 80, se ejecuta al inicio del arranque del sistema. Es el padre de todos los procesos que se ejecutan en nuestro sistema.  Define 6 niveles de ejecución o estados del sistema y mapea los servicios para esos niveles de ejecución. Esto permite que todos los servicios, definidos como scripts, se inicien en una secuencia predefinida. El siguiente script se ejecuta cuando el previo termine o agote el tiempo de espera si no llega a ejecutarse. 
Para crear un servicio, se necesita crear un script y almacenarlo en la carpeta /etc/init.d. En nuestro caso, para la ruta persistente crearemos un script, que llamaremos /etc/init.d/iproute, con el siguiente contenido:
#! /bin/sh
### BEGIN INIT INFO
# Provides:          iproute
# Required-Start:    $network $syslog $time
# Required-Stop:     $network $syslog $time
# Default-Start:     2 3 4 5
# Default-Stop:
# Short-Description: establece una ruta persistente
# Description: El principal propósito de este script es establecer una
#	       ruta persistente en el arranque del sistema
### END INIT INFO

start() {
    # Codigo para iniciar el servicio
    ip route add 192.168.122.128/25 via 192.168.122.254 dev enp1s0 metric 1000
}

stop() {
    # Código para parar el servicio
    ip route delete 192.168.122.128/25 via 192.168.122.254 dev enp1s0 metric 1000
}

case "$1" in
    start)
       start
       ;;
    stop)
       stop
       ;;
    restart)
       stop
       start
       ;;
    status)
       # Código para mostrar el estado del servicio
       systemctl status iproute.service
       ;;
    *)
       echo "Usage: $0 {start|stop|restart|status}"
esac

exit 0
Una vez guardado el script en la carpeta correspondiente hay que establecer los permisos adecuados:
sudo chmod 0755 /etc/init.d/iproute
sudo chown root.root /etc/init.d/iproute
Y, por último, debemos activar la ejecución del script en el arranque en los distintos niveles de ejecución:
sudo update-rc.d iproute defaults
Esta orden lo que hace es crear un enlace al script que acabamos de hacer en cada uno de los directorios rc[nivel de ejecución].d que se encuentran en /etc. Si quisiéramos eliminar la ejecución de este servicio así definido bastaría con ejecutar el comando:
sudo update-rc.d iproute remove
Esto elimina los enlaces de que hemos hablado, pero no así el script que está en /etc/init.d. Éste tendríamos que eliminarlo a mano.
Al haber definido nuestra ruta persistente como un servicio al estilo init, podemos usar el comando service para tratar con él:
  • Para arrancar el servicio
    sudo service iproute start
  • Para parar el servicio
    sudo service iproute stop
  • Para reiniciar el servicio
    sudo service iproute restart
  • Para ver el estado del servicio
    sudo service iproute status

Crear un servicio Systemd

El siguiente caso sería crear un servicio usando el método más nuevo de systemd. Cuando creamos un servicio de este tipo lo podemos manejar utilizando la herramienta systemctl, tal y como haríamos con cualquier otro servicio. Eso significa que se puede habilitar (enable), deshabilitar (disable), reiniciar (restart), iniciar (start), parar (stop) y todas las otras opciones que provee el comando systemctl.
Bien, tomando como base nuestro script del ejemplo del método del crontab y que guardamos en /usr/local/sbin. De ese script eliminaremos la línea con la demora (sleep 30) y dejaremos solamente la orden ip route.
Una vez que tenemos listo nuestro script es el momento de crear el archivo de texto plano para la definición del servicio. Lo tendremos que guardar en /etc/systemd/system y para implementarlo nos basaremos en la siguiente plantilla:
[Unit]
Description=Ruta persistente
After=network.target
StartLimitIntervalSec=0

[Service]
Type=simple
Restart=always
RestartSec=1
User=root
ExecStart=/usr/local/sbin/iproute.sh

[Install]
WantedBy=multi-user.target
Si queremos conocer que opciones tiene cada sección podemos consultar el manual usando el siguiente comando:
man 7 systemd.directives
Esta página del manual nos muestra las directivas que podemos utilizar para hacer nuestro fichero de definición del servicio. Para cada una de las directivas se muestra que página del manual hay que consultar para ver como funciona.
Así para, por ejemplo, la directiva ExecStart nos dice que su explicación se encuentra en systemd.service(5). Lo que significa la sección 5 del manual systemd.service, que podemos consultar con la orden:
man 5 systemd.service
Básicamente, lo que más tenemos que tener en cuenta son las directivas:
  • After: que nos indicará que se ejecutará después de haber levantado la red (network.target).
  • ExecStart: en la que indicaremos la ruta y nombre del script que se va a ejecutar.
El resto lo podemos dejar con los valores que hay en la plantilla.
Después de crear el servicio y guardarlo en el directorio correcto podemos habilitarlo e iniciarlo usando los siguientes comandos:
sudo systemctl enable iproute.service
sudo systemctl start iproute.service
El servicio se ejecutará en cualquier inicio del sistema manteniendo la ruta persistente definida en el script.

Conclusiones

En este artículo hemos visto tres métodos para hacer que una ruta sea persistente en nuestro sistema. De los tres métodos, el más correcto debería ser el tercero. Pues es el que utiliza el último paradigma definido en Linux: systemd como manejador de servicios. El servicio del tipo Init, el segundo descrito, aunque funciona bien, puede quedar en cualquier momento obsoleto y dejar de funcionar. Utilizar la tarea programada también funciona, pero no es elegante.
En fin, que espero que les haya gustado el artículo y que puedan aprovecharlo. 

Comentarios

Entradas populares de este blog

Atom ha muerto, viva Zed

El día 8 de junio de 2022, Microsoft anunció que a partir del día 31 de diciembre de este mismo año dejaría de dar soporte para el editor de código Atom .  ¿En qué nos afecta esto a nosotros? Bueno, pues si me han seguido en artículos anteriores saben que tras una comparativa de varios IDEs había decidido utilizar Atom para los ejemplos que tuviera que hacer en este blog. Sobre todo los artículos que prepararé para ilustrar el uso de Laravel . Amén de los miles de programadores que actualmente usan Atom  en sus proyectos, claro. Pero, ¿qué editor de código abierto podremos utilizar para sustituir a Atom ? En el mismo comunicado, Microsoft explicaba que el abandono del proyecto Atom  se debía a que querían volcar todos sus esfuerzos en el Visual Studio Code y, por supuesto, recomendó a los usuarios de Atom la utilización del mismo como alternativa natural. No quiero entrar en las bondades o defectos del Visual Studio Code  si quieres elegirlo como tu IDE para d...

Gestión de la red usando la línea de comandos (III): gestión DNS

  Introducción En este nuevo artículo de la serie vamos a hablar de la gestión del DNS, Domain Name System. El sistema de resolución de nombres nos permite traducir los nombres de los dominios de Internet en direcciones IP númericas. Más difíciles de recordar para los humanos.  El DNS fue concebido a mediados de los años 80. Hasta esa época, los ordenadores conectados a una red disponían de una dirección numérica, la dirección IP. Pero con el tiempo, cada vez había más ordenadores conectados a las redes. Esto hacía que cada vez fuera más difícil recordar las direcciones IP. Sobre el año 1983, Paul Mockapetris , un informático estadounidense, desarrolló un sistema jerárquico de nombres para identificar a los ordenadores conectados a una red. Y, a mediados de la década, ya se convirtió en un estándar. Pueden consultar más información sobre el sistema DNS consultando el artículo de la Wikipedia: Sistema de nombres de dominio . En este artículo, no vamos a explicar como montar un ...

Gestión de la red usando la línea de comandos (IV): monitorización de conexiones

  Introducción En este artículo de la serie de gestión de la red usando la línea de comandos nos vamos a centrar en la monitorización de las conexiones. Para ello vamos a utilizar el comando netstat , que es el decano de los comandos de monitorización de la red. También mostraremos el comando ss , que viene a sustituir a netstat  en las funciones de monitorización de conexiones de red. Asimismo mostraré una breve explicación de los conceptos que se van a trabajar en el artículo. S ockets, puertos, protocolos y procesos En primer lugar vamos a empezar con un poco de teoría para alumbrar lo que luego se explicará en el artículo. Si ya sabes de lo que estamos hablando, sáltate esta sección y ve al meollo del asunto [1] . Nos referiremos al contexto de la conexiones TCP/IP. Dentro de este contexto, cada conexión queda definida por dos endpoints , puntos finales, uno en el host , equipo, que establece la conexión y otro en el host con el que se comunica. Generalmente este último es...