Variables especiales en Shell

ShellBeginner
Practicar Ahora

Introducción

En esta práctica de laboratorio, aprenderás sobre las variables especiales en el scripting de shell. Estas variables proporcionan información esencial sobre el entorno de ejecución del script, como los argumentos de la línea de comandos, el nombre del script y el ID del proceso. Comprender estas variables te ayudará a escribir scripts de shell más flexibles y potentes.

Creación de tu primer script

Comencemos creando un script de shell sencillo para demostrar el uso de las variables especiales.

  1. Abre tu terminal en el WebIDE. Deberías ver un símbolo del sistema esperando tu entrada.

  2. Navega al directorio del proyecto:

cd ~/project

Este comando cambia tu directorio actual a ~/project, que es tu directorio de trabajo predeterminado para esta práctica.

  1. Crea un nuevo archivo llamado special_vars.sh utilizando el siguiente comando:
touch special_vars.sh

El comando touch crea un archivo vacío si no existe, o actualiza su marca de tiempo si ya existe.

  1. Abre el archivo en el editor del WebIDE. Puedes hacerlo haciendo clic en el nombre del archivo en el explorador de archivos en el lado izquierdo de tu pantalla.

  2. Añade el siguiente contenido al archivo:

#!/bin/bash

echo "Script Name: $0"
echo "First Argument: $1"
echo "Second Argument: $2"
echo "All Arguments: $@"
echo "Number of Arguments: $#"
echo "Process ID: $$"

Analicemos lo que hace cada línea:

  • #!/bin/bash: Esto se llama shebang. Indica al sistema que use bash para interpretar este script.
  • $0: Esta variable especial contiene el nombre del script.
  • $1 y $2: Representan el primer y segundo argumento de la línea de comandos, respectivamente.
  • $@: Representa todos los argumentos de la línea de comandos pasados al script.
  • $#: Proporciona el recuento de los argumentos de la línea de comandos.
  • $$: Proporciona el ID de proceso (PID) de la shell actual.
  1. Guarda el archivo después de añadir el contenido.

  2. Haz que el script sea ejecutable ejecutando el siguiente comando en tu terminal:

chmod +x special_vars.sh

El comando chmod cambia los permisos de un archivo. La opción +x añade el permiso de ejecución, permitiéndote ejecutar el script.

Ejecución del script con argumentos

Ahora que hemos creado nuestro script, vamos a ejecutarlo con diferentes argumentos para ver cómo se comportan las variables especiales.

  1. Ejecuta el script sin ningún argumento:
./special_vars.sh

El ./ antes del nombre del script le indica a la shell que busque el script en el directorio actual.

Deberías ver una salida similar a esta:

Script Name: ./special_vars.sh
First Argument:
Second Argument:
All Arguments:
Number of Arguments: 0
Process ID: 1234

Observa que el primer y segundo argumento están vacíos, y el número de argumentos es 0 ya que no proporcionamos ninguno.

  1. Ahora, ejecuta el script con algunos argumentos:
./special_vars.sh hello world

La salida debería verse así:

Script Name: ./special_vars.sh
First Argument: hello
Second Argument: world
All Arguments: hello world
Number of Arguments: 2
Process ID: 1235

Esto es lo que ha cambiado:

  • $1 ahora contiene "hello"
  • $2 ahora contiene "world"
  • $@ muestra todos los argumentos: "hello world"
  • $# muestra 2, porque proporcionamos dos argumentos

El ID de proceso ($$) puede ser diferente cada vez que ejecutes el script, ya que es asignado por el sistema operativo.

Entendiendo $? y $!

Otras dos variables especiales importantes son $? y $!. Vamos a crear un nuevo script para demostrar su uso.

  1. Crea un nuevo archivo llamado exit_status.sh:
touch ~/project/exit_status.sh
  1. Abre el archivo en el editor del WebIDE y añade el siguiente contenido:
#!/bin/bash

echo "Running a successful command:"
ls /home
echo "Exit status: $?"

echo "Running a command that will fail:"
ls /nonexistent_directory
echo "Exit status: $?"

echo "Running a background process:"
sleep 2 &
echo "Process ID of last background command: $!"

Desglosemos este script:

  • $? devuelve el estado de salida del último comando ejecutado. El valor 0 normalmente significa éxito, mientras que los valores distintos de cero indican diversas condiciones de error.
  • $! devuelve el ID de proceso del último comando ejecutado en segundo plano.
  • El símbolo & al final de un comando lo ejecuta en segundo plano.
  1. Guarda el archivo y hazlo ejecutable:
chmod +x ~/project/exit_status.sh
  1. Ejecuta el script:
./exit_status.sh

Deberías ver una salida similar a esta:

Running a successful command:
labex
Exit status: 0
Running a command that will fail:
ls: cannot access '/nonexistent_directory': No such file or directory
Exit status: 2
Running a background process:
Process ID of last background command: 1236

Observaciones:

  • El primer comando ls tiene éxito, por lo que $? es 0.
  • El segundo comando ls falla (porque el directorio no existe), por lo que $? es 2 (un valor distinto de cero que indica un error).
  • El comando sleep se ejecuta en segundo plano y $! devuelve su ID de proceso.

Uso de variables especiales en funciones

Las variables especiales también se pueden utilizar dentro de las funciones. Vamos a crear un script para demostrarlo.

  1. Crea un nuevo archivo llamado function_vars.sh:
touch ~/project/function_vars.sh
  1. Abre el archivo en el editor del WebIDE y añade el siguiente contenido:
#!/bin/bash

function print_args {
  echo "Function Name: $0"
  echo "First Argument: $1"
  echo "Second Argument: $2"
  echo "All Arguments: $@"
  echo "Number of Arguments: $#"
}

echo "Calling function with two arguments:"
print_args hello world

echo "Calling function with four arguments:"
print_args one two three four

Este script define una función print_args que utiliza variables especiales. Luego llama a esta función dos veces con diferentes números de argumentos.

  1. Guarda el archivo y hazlo ejecutable:
chmod +x ~/project/function_vars.sh
  1. Ejecuta el script:
./function_vars.sh

Deberías ver una salida similar a esta:

Calling function with two arguments:
Function Name: ./function_vars.sh
First Argument: hello
Second Argument: world
All Arguments: hello world
Number of Arguments: 2
Calling function with four arguments:
Function Name: ./function_vars.sh
First Argument: one
Second Argument: two
All Arguments: one two three four
Number of Arguments: 4

Ten en cuenta que:

  • $0 sigue refiriéndose al nombre del script, no al nombre de la función.
  • $1, $2, $@ y $# funcionan para los argumentos de la función de la misma manera que lo hacen para los argumentos del script.
  • Los valores de estas variables cambian cada vez que se llama a la función con diferentes argumentos.

Entendiendo la diferencia entre $@ y $*

Las variables especiales $@ y $* se utilizan para representar todos los argumentos de la línea de comandos, pero se comportan de forma diferente cuando se encierran entre comillas dobles. Vamos a crear un script para demostrar esta diferencia.

  1. Crea un nuevo archivo llamado at_vs_star.sh:
touch ~/project/at_vs_star.sh
  1. Abre el archivo en el editor del WebIDE y añade el siguiente contenido:
#!/bin/bash

echo "Using \$@:"
for arg in "$@"; do
  echo "Argument: $arg"
done

echo "Using \$*:"
for arg in "$*"; do
  echo "Argument: $arg"
done

Este script demuestra la diferencia entre $@ y $* cuando se usan en un bucle.

  1. Guarda el archivo y hazlo ejecutable:
chmod +x ~/project/at_vs_star.sh
  1. Ejecuta el script con múltiples argumentos, incluyendo algunos con espacios:
./at_vs_star.sh "arg with spaces" another_arg "third arg"

Deberías ver una salida similar a esta:

Using $@:
Argument: arg with spaces
Argument: another_arg
Argument: third arg
Using $*:
Argument: arg with spaces another_arg third arg

Esto es lo que está sucediendo:

  • Con "$@", cada argumento se trata como una entidad separada. Los argumentos con espacios se preservan como unidades individuales.
  • Con "$*", todos los argumentos se combinan en una sola cadena, separados por el primer carácter de la variable IFS (Internal Field Separator), que suele ser un espacio.

Esta diferencia es crucial cuando necesitas procesar argumentos que pueden contener espacios u otros caracteres especiales.

Resumen

En esta práctica de laboratorio, has aprendido sobre las variables especiales en el scripting de shell y cómo utilizarlas de manera efectiva. Has creado scripts que demuestran el uso de varias variables especiales como $0, $1, $@, $#, $$, $? y $!. También has explorado cómo se comportan estas variables en diferentes contextos, incluyendo dentro de funciones y al manejar argumentos de línea de comandos.

Puntos clave:

  1. $0, $1, $2, etc., representan el nombre del script y los argumentos de la línea de comandos.
  2. $@ y $# te permiten trabajar con todos los argumentos y contarlos.
  3. $$ te proporciona el ID de proceso actual, útil para crear archivos temporales únicos.
  4. $? te ayuda a verificar si el comando anterior tuvo éxito.
  5. $! te da el PID del último proceso en segundo plano, útil para el control de trabajos.
  6. $@ y $* se comportan de manera diferente cuando se entrecomillan, lo cual es importante al manejar argumentos con espacios.

Comprender estas variables especiales es fundamental para escribir scripts de shell más avanzados y flexibles. Te permiten crear scripts que pueden adaptarse a diferentes entradas y proporcionar información valiosa sobre el entorno de ejecución del script.

A medida que continúes practicando y experimentando con el scripting de shell, encontrarás muchas más formas de aprovechar estas variables especiales en tu trabajo. Recuerda consultar el manual de bash (man bash) para obtener información más detallada sobre estas y otras variables especiales.