¿Cómo depurar el script bash?

31

¿Hay alguna forma de depurar el script bash sin usar echo y registro?

Estoy hablando de usar puntos de interrupción y cosas así.

Adaptador UA
fuente

Respuestas:

20

Hay varias formas diferentes, es decir:

  • Ejecute su script con la opción -x

    bash -x yourscript.sh
  • Agregue set -xuna nueva línea al comienzo de su archivo #!/bin/bashde script después del Shebang y antes del comienzo de su script, set -vmostrará las líneas de entrada del shell, set -xmuestra los comandos y argumentos ejecutados

  • reemplace el shebang de su archivo de script con #!/bin/bash -xv

NES
fuente
4

Puede usar esta pequeña función para ingresar a "consola":

function debug
{
    echo "#############|  Entering DEBUG mode  |####################";
    cmd=""
    while [[ $cmd != "exit" ]]; do
        read -p "> " cmd
        case "$cmd" in
            vars ) ( set -o posix ; set );;
            exit ) ;;
            * ) eval "$cmd";;
        esac
    done
    echo "#############|  End of DEBUG mode |####################";
}

Luego, dentro de su script (EJEMPLO):

for file in *; do
...
   if [[ $file == "strange_case.txt" ]]; then
       # break the code here to analyze:
       debug
   fi
...
done

Aceptará cualquier comando, manteniendo intactas las variables locales. Para salir del modo "debug", escriba "exit" (no saldrá del script) y continuará con el código. Si usa "depurar" dentro de un bucle, se detendrá cada vez. Puede envolverlo dentro de un "if" (como en el ejemplo anterior), o crear una función "watch":

function debug_watch
{
    if [[ $1 == $2 ]]; then
        debug
    fi
}

# And Use it:

debug_watch "$file" "strange_case.txt"

También agregué el comando "vars" que volcará todas las variables disponibles y sus valores. También puede agregar sus propios comandos personalizados.

Hice el código en pocos minutos, así que úselo bajo su propio riesgo. Tenga en cuenta que en modo de depuración cualquier comando puede ejecutarse, por lo que representa un riesgo de seguridad si lo deja en un script de producción.

lepe
fuente
3
Evite usar nombres de variables en mayúsculas. Su riesgo anula las variables especiales de shell y las variables de entorno. Además, asegúrese de citar las expansiones de parámetros cuando se usan como argumentos, para evitar la división de palabras y la expansión del nombre de ruta en el resultado. por ejemplo * ) eval "$cmd" ;;y debug_watch "$file" strange_case.txt.
geirha
Código editado según lo sugerido por geirha.
Lepe
2

En consonancia con lo que dice NES, hay banderas establecidas en bash para permitir la depuración.

El set -xindicador se puede activar y desactivar desde el terminal o desde su script. Usando +o -:

#!/bin/bash
#fileinfo
ls -l $1
set -x      # start debugging here
wc -l $1
set +x      # stop debugging here
file $1
set -v      # start verbose output
w | more    
echo ""
echo -n "Number of users: "
set +v      # end verbose output
who | wc -l

Esto es lo que hacen los setcomandos:

  • set -f Deshabilite la generación de nombre de archivo usando metacaracteres.
  • set -v Imprime líneas de entrada de shell (detalladas) a medida que se leen.
  • set -x Imprimir trazas de comandos antes de ejecutar el comando.

seten realidad tiene muchas características, pero lamentablemente no hay página de manual, ya que es una herramienta integrada en el shell. El manual para el set está en la documentación de GNU Bash .

Existen numerosas herramientas de línea de comandos que pueden ayudarlo a obtener detalles sobre su programa como:

  • stat mostrar el estado del archivo o del sistema de archivos
  • file determinar un tipo de archivo.
  • hexdump filtro que muestra los archivos especificados en una variedad de formatos
  • nohup Ejecute un script que no se cuelgue

    y muchos otros. Estaba tratando de pensar en el comando que muestra caracteres ocultos, pero no puedo hacerlo en este momento. Hexdump lo hará pero hay uno mejor.

El comando de teclado ctrl\hará que un programa o script en ejecución se vuelque al núcleo. Entonces podrías analizar el coredump. Probablemente usaría gdb para analizar un coredump, pero existen muchos programas para eso.

El shell bash también tiene algunas opciones ingeniosas para la depuración. opciones --debugger, -vdetalladas --dump-stringsy otras opciones ingeniosas para ayudarlo. Échales un vistazo usandoman bash .

El trapcomando (shell incorporado) podría ser muy útil para usted. trap dice que si su programa se cierra inesperadamente, ejecute algo. Leíste sobre trap, y otras prácticas herramientas de Bash Shell aquí .

Hablando en general por el momento, la depuración es un gran tema en cualquier idioma. Algunos otros temas que pueden ser útiles para la depuración en cualquier lenguaje de programación incluyen, redirección de shell y procesamiento de señal.

Finalmente, me doy cuenta de que el ejemplo que utilicé es trivial, pero que algunos scripts de shell pueden tener cientos de líneas. En esas situaciones, me gusta insertar etiquetas de comentarios y bloquear el código que sospecho que es defectuoso, o Alternativamente, insertar un comando de salida e intentar aislar el código funcional del código roto, utilizando una técnica de división y conquista.

j0h
fuente
1

Una opción de GUI para depurar un script bash es el IDE de Eclipse con los complementos BashEclipse / Shelled.

Esto proporciona las características de su pregunta ( breakpoints and stuff) junto con una serie de otras características para depurar scripts de bash complejos.

Algunas de las características incluyen:
( https://unix.stackexchange.com/questions/155551/how-to-debug-a-bash-script )

  • Alternar punto de ruptura
  • Operación individual paso a paso
  • Funciones y subrutinas paso a paso, paso a paso, paso a paso
  • Examinar las variables de código en cualquier punto mientras se ejecuta el script
  • Lista de tareas TODO
  • Lista de marcadores
  • Edición de múltiples ventanas
  • Uso compartido remoto del entorno del proyecto

La perspectiva del Editor de guiones: Eclipse Script IDE

La perspectiva de depuración: Perspectiva de depuración de script Eclipse

Los pasos para usar es agregar los complementos Shelledy BashEclipsea eclipse. Luego ejecute el procedimiento proporcionado en el archivo de texto BashEclipse read me para iniciar el depurador.

LD James
fuente