Gestión de Archivos en Scripts Bash

Los scripts de Bash ofrecen operadores de prueba de archivos muy útiles para examinar diversas propiedades de los archivos y directorios en sistemas tipo Unix. Estas capacidades son fundamentales para construir scripts robustos que puedan reaccionar de manera inteligente a la presencia, el tipo y los permisos de los elementos del sistema de archivos.

A continuación, se presenta un ejemplo práctico de cómo se pueden utilizar los operadores de prueba de archivos para gestionar el inicio de servicios o componentes:

#!/bin/bash
# Script para verificar y ejecutar componentes de servicio
# Define una lista de componentes a gestionar
COMPONENTES="mi_servicio_web mi_servicio_db otro_proceso_secundario"

echo "Iniciando proceso de verificación y ejecución de componentes..."

for componente_actual in $COMPONENTES
do
    echo "Intentando iniciar: '$componente_actual'..."
    # 1. Verificar si el componente es un archivo ejecutable en el directorio actual.
    if [ -x "$componente_actual" ] && [ -f "$componente_actual" ]; then
        echo "  > Ejecutando '$componente_actual' desde el directorio actual."
        "./$componente_actual" & # Ejecutar en segundo plano
    # 2. Si no es ejecutable localmente, buscarlo en el PATH del sistema y ejecutar.
    elif command -v "$componente_actual" &> /dev/null; then
        echo "  > Ejecutando '$componente_actual' desde el PATH del sistema."
        "$componente_actual" & # Ejecutar en segundo plano
    else
        echo "  > Error: El componente '$componente_actual' no es ejecutable ni se encuentra en el PATH."
    fi
    sleep 0.2 # Pequeña pausa para evitar sobrecarga y mejorar la legibilidad del log.
done
echo "Proceso de verificación de componentes completado."

Operadores de Prueba de Archivos Comunes

La siguiente tabla describe los operadores más comunes para probar las propiedades de un archivo o directorio:

Operador Descripción Ejemplo
-b archivo Verifica si el archivo es un dispositivo de bloque (por ejemplo, un disco duro). Devuelve verdadero si lo es. [ -b /dev/sda ]
-c archivo Verifica si el archivo es un dispositivo de carácter (por ejemplo, una terminal o un puerto serial). Devuelve verdadero si lo es. [ -c /dev/urandom ]
-d archivo Verifica si el archivo es un directorio. Devuelve verdadero si lo es. [ -d /home/usuario/documentos ]
-f archivo Verifica si el archivo es un archivo regular (no un directorio, un enlace simbólico ni un dispositivo). Devuelve verdadero si lo es. [ -f /etc/fstab ]
-g archivo Verifica si el bit SGID (Set Group ID) está configurado en el archivo. Devuelve verdadero si lo es. [ -g /usr/bin/wall ]
-k archivo Verifica si el bit adhesivo (Sticky Bit) está configurado en el archivo. Devuelve verdadero si lo es. [ -k /tmp ]
-p archivo Verifica si el archivo es una tubería con nombre (FIFO). Devuelve verdadero si lo es. [ -p /run/systemd/private ]
-u archivo Verifica si el bit SUID (Set User ID) está configurado en el archivo. Devuelve verdadero si lo es. [ -u /bin/passwd ]
-r archivo Verifica si el archivo es legible para el usuario que ejecuta el script. Devuelve verdadero si lo es. [ -r /etc/hosts ]
-w archivo Verifica si el archivo es escribible para el usuario que ejecuta el script. Devuelve verdadero si lo es. [ -w /tmp/mi_log.txt ]
-x archivo Verfiica si el archivo es ejecutable para el usuario que ejecuta el script. Devuelve verdadero si lo es. [ -x /bin/bash ]
-s archivo Verifica si el archivo no está vacío (su tamaño es mayor que cero). Devuelve verdadero si contiene datos. [ -s /var/log/syslog ]
-e archivo Verifica si el archivo o directorio existe. Devuelve verdadero si existe. [ -e /usr/local/bin ]

Ejemplos Avanzados de Pruebas de Archivos

Este script demuestra el uso de varios operadores de prueba de archivos con ejemplos concretos, incluyendo la creación y limpieza de archivos temporales para una ejecución segura:

#!/bin/bash
# Script de demostración exhaustiva de operadores de prueba de archivos en Bash

echo "--- Iniciando demostración de pruebas de archivos ---"

# --- Definir rutas de ejemplo para las pruebas ---
ARCHIVO_REGULAR="/tmp/ejemplo_regular_bash.txt"
ARCHIVO_VACIO="/tmp/ejemplo_vacio_bash.txt"
ARCHIVO_INEXISTENTE="/tmp/archivo_que_no_existe_xyz.txt"
DIRECTORIO_PRUEBA="/tmp/mi_directorio_bash_test"
DISPOSITIVO_CARACTER="/dev/urandom"
DISPOSITIVO_BLOQUE="/dev/sda" # Nota: puede no existir en todos los sistemas (ej. contenedores).
                              # Si /dev/sda no existe o causa errores, considere /dev/zero o /dev/loop0.
ARCHIVO_LEER_SISTEMA="/etc/hosts" # Un archivo de sistema típicamente legible.
ARCHIVO_ESCRIBIR_TEMPORAL="/tmp/archivo_para_escribir.log"
ARCHIVO_EJECUTAR_SISTEMA="/bin/ls" # Un ejecutable común del sistema.

# --- Preparación: Crear archivos y directorios de prueba ---
echo -e "\nPreparando archivos y directorios temporales..."
touch "$ARCHIVO_VACIO"
echo "Este es un contenido de prueba para el archivo regular." > "$ARCHIVO_REGULAR"
mkdir -p "$DIRECTORIO_PRUEBA"
touch "$ARCHIVO_ESCRIBIR_TEMPORAL"
chmod 644 "$ARCHIVO_ESCRIBIR_TEMPORAL" # Asignar permisos de escritura para el dueño.

echo -e "\n=== 1. Verificación de tipos de archivos ==="

# -f: ¿Es un archivo regular?
if [ -f "$ARCHIVO_REGULAR" ]; then
    echo "  [OK] '$ARCHIVO_REGULAR' es un archivo regular."
else
    echo "  [ERROR] '$ARCHIVO_REGULAR' NO es un archivo regular."
fi

# -d: ¿Es un directorio?
if [ -d "$DIRECTORIO_PRUEBA" ]; then
    echo "  [OK] '$DIRECTORIO_PRUEBA' es un directorio."
else
    echo "  [ERROR] '$DIRECTORIO_PRUEBA' NO es un directorio."
fi

# -b: ¿Es un dispositivo de bloque?
if [ -b "$DISPOSITIVO_BLOQUE" ]; then
    echo "  [OK] '$DISPOSITIVO_BLOQUE' es un dispositivo de bloque."
else
    echo "  [INFO] '$DISPOSITIVO_BLOQUE' NO es un dispositivo de bloque (o no está presente)."
fi

# -c: ¿Es un dispositivo de carácter?
if [ -c "$DISPOSITIVO_CARACTER" ]; then
    echo "  [OK] '$DISPOSITIVO_CARACTER' es un dispositivo de carácter."
else
    echo "  [ERROR] '$DISPOSITIVO_CARACTER' NO es un dispositivo de carácter."
fi

echo -e "\n=== 2. Verificación de existencia y contenido ==="

# -e: ¿Existe el archivo/directorio?
if [ -e "$ARCHIVO_REGULAR" ]; then
    echo "  [OK] '$ARCHIVO_REGULAR' EXISTE."
else
    echo "  [ERROR] '$ARCHIVO_REGULAR' NO EXISTE."
fi

if [ -e "$ARCHIVO_INEXISTENTE" ]; then
    echo "  [ERROR] '$ARCHIVO_INEXISTENTE' EXISTE (lo cual es inesperado)."
else
    echo "  [OK] '$ARCHIVO_INEXISTENTE' NO EXISTE (como se esperaba)."
fi

# -s: ¿El archivo no está vacío (tiene contenido)?
if [ -s "$ARCHIVO_REGULAR" ]; then
    echo "  [OK] '$ARCHIVO_REGULAR' NO está vacío."
else
    echo "  [ERROR] '$ARCHIVO_REGULAR' está vacío (lo cual es inesperado)."
fi

if [ -s "$ARCHIVO_VACIO" ]; then
    echo "  [ERROR] '$ARCHIVO_VACIO' NO está vacío (lo cual es inesperado)."
else
    echo "  [OK] '$ARCHIVO_VACIO' está vacío."
fi

echo -e "\n=== 3. Verificación de permisos (lectura, escritura, ejecución) ==="

# -r: ¿Es legible para el usuario actual?
if [ -r "$ARCHIVO_LEER_SISTEMA" ]; then
    echo "  [OK] '$ARCHIVO_LEER_SISTEMA' es legible."
else
    echo "  [ERROR] '$ARCHIVO_LEER_SISTEMA' NO es legible."
fi

# -w: ¿Es escribible para el usuario actual?
if [ -w "$ARCHIVO_ESCRIBIR_TEMPORAL" ]; then
    echo "  [OK] '$ARCHIVO_ESCRIBIR_TEMPORAL' es escribible."
else
    echo "  [ERROR] '$ARCHIVO_ESCRIBIR_TEMPORAL' NO es escribible."
fi

# -x: ¿Es ejecutable para el usuario actual?
if [ -x "$ARCHIVO_EJECUTAR_SISTEMA" ]; then
    echo "  [OK] '$ARCHIVO_EJECUTAR_SISTEMA' es ejecutable."
else
    echo "  [ERROR] '$ARCHIVO_EJECUTAR_SISTEMA' NO es ejecutable."
fi

echo -e "\n--- Demostración finalizada. Limpiando archivos temporales. ---"
rm -f "$ARCHIVO_REGULAR" "$ARCHIVO_VACIO" "$ARCHIVO_INEXISTENTE" "$ARCHIVO_ESCRIBIR_TEMPORAL"
rmdir "$DIRECTORIO_PRUEBA" 2>/dev/null # Eliminar directorio si está vacío, ignorar errores si no lo está.

Etiquetas: bash shell-scripting file-system linux unix

Publicado el 7-7 17:53