Cómo funcionan las funciones en Bash

Aprendemos que son y como funcionan los funciones en Bash. Dichas funciones se pueden utilizar dentro de scripts de Bash o bien configurarlas en las variables de entorno de nuestro sistema, similar a los alias. Añadiendo la función generalmente en el fichero .bashrc

¿Qué es una función en Bash?

Una función Bash es esencialmente un conjunto de comandos que se pueden llamar varias veces. El propósito de una función es ayudarnos a hacer que nuestros scripts de bash sean más legibles, y evitar escribir el mismo código una y otra vez.

En comparación con la mayoría de los lenguajes de programación, las funciones de Bash son bastante limitadas. En este tutorial cubriremos los conceptos básicos de las funciones de Bash y mostraremos cómo usarlas en sus scripts de shell.

Declarar una función en Bash

Una función en Bash se puede declarar de diferentes maneras.

  1. El primer formato comienza con el nombre de la función seguido de paréntesis. Este es el formato preferido y más utilizado.
    1. function_name () {
    2.   commands
    3. }

    O bien:

    1. function_name () { commands; }
  2. El segundo formato comienza con la palabra de función reservada seguida del nombre de la función.
    1. function function_name {
    2.   commands
    3. }

    O bien, en una sola línea:

    1. function function_name { commands; }

Respecto a las funciones, debemos tener en cuenta los siguientes puntos:

  • La lista de comandos entre llaves {} es el cuerpo de la función. Las llaves que rodean el cuerpo de la función deben estar separadas del cuerpo por espacios o líneas nuevas.
  • Definir una función no la ejecuta. Para invocar una función en Bash, debemos utilizar el nombre de la función. Los comandos entre las llaves se ejecutan siempre que se llama a la función en el script de shell.
  • La definición de la función se debe colocar antes de cualquier llamada a la función.
  • Cuando se usan funciones de una sola línea «compactadas», con un punto y coma «;» debe seguir el último comando en la función.
  • Siempre debemos tratar de mantener los nombres de las funciones descriptivas.

Al respecto de estos puntos, podemos observar este ejemplo:

  1. #!/bin/bash
  2.  
  3. Hola_mundo () {
  4.    echo 'hola, mundo'
  5. }
  6.  
  7. hola_mundo

Analicemos el script anterior:

  • En la línea 3 definimos el nombre de la función. Y la abrimos mediante el símbolo {
  • La línea 4 es el cuerpo de la función. Puede contener múltiples comandos.
  • Cerramos la función con el símbolo }
  • En la última línea ejecutamos la función.
  • Al ejecutarla imprimirá el texto hola, mundo

Alcance de las variables

Las variables globales son variables a las que se puede acceder desde cualquier parte del script, independientemente del alcance. En Bash, todas las variables por defecto se definen como globales, incluso si se declaran dentro de la función.

Las variables locales se pueden declarar dentro del cuerpo de la función con la palabra clave local y se pueden usar solo dentro de esa función. Puede tener variables locales con el mismo nombre en diferentes funciones.

Para ilustrar mejor cómo funciona el alcance de las variables en Bash, veamos un ejemplo, en el script variables_scope.sh

  1. #!/bin/bash
  2.  
  3. var1='A'
  4. var2='B'
  5.  
  6. my_function () {
  7.   local var1='C'
  8.   var2='D'
  9.   echo "Dentro de la función: var1: $var1, var2: $var2"
  10. }
  11.  
  12. echo "Antes de ejecutar la función: var1: $var1, var2: $var2"
  13.  
  14. my_function
  15.  
  16. echo "Después de ejecutar la función: var1: $var1, var2: $var2"

El script comienza definiendo dos variables globales var1 y var2. Luego, una función que establece una variable local var1 y modifica la variable global var2.

Si ejecuta el script, debería ver la siguiente salida:

  1. [david@servcentos bin]$ ./variables_scope.sh
  2. Antes de ejecutar la función: var1: A, var2: B
  3. Dentro de la función: var1: C, var2: D
  4. Después de ejecutar la función: var1: A, var2: D

De la salida anterior, podemos concluir que:

  • Si establece una variable local dentro del cuerpo de la función con el mismo nombre que una variable global existente, tendrá prioridad sobre la variable global
  • Las variables globales se pueden cambiar desde dentro de la función.

Valores de retorno

A diferencia de las funciones en lenguajes de programación «reales», las funciones Bash no nos permiten devolver un valor cuando se le llama. Cuando se completa una función de bash, su valor de retorno es el estado de la última instrucción ejecutada en la función, 0 para el éxito y un número decimal distinto de cero en el rango de 1 a 255 para el fallo.

El estado de retorno se puede especificar utilizando la palabra clave return y se asigna a la variable $?. La declaración de retorno termina la función. Puedes considerarlo como el estado de salida de la función.

  1. #!/bin/bash
  2.  
  3. my_function () {
  4.   echo "mismo resultado"
  5.   return 55
  6. }
  7.  
  8. my_function
  9. echo $?

Con la salida:

  1. mismo resultado
  2. 55

Para devolver un valor arbitrario de una función, necesitamos usar otros métodos. La opción más sencilla es asignar el resultado de la función a una variable global:

  1. #!/bin/bash
  2.  
  3. my_function () {
  4.   func_result="mismo resultado"
  5. }
  6.  
  7. my_function
  8. echo $func_result

Otra opción mejor para devolver un valor de una función es enviar el valor a stdout usando echo o printf como se muestra a continuación:

  1. #!/bin/bash
  2.  
  3. my_function () {
  4.   local func_result="mismo resultado"
  5.   echo "$func_result"
  6. }
  7.  
  8. func_result="$(my_function)"
  9. echo $func_result

En lugar de simplemente ejecutar la función que imprimirá el mensaje a la salida estándar, estamos asignando a la variable func_result usando el mecanismo $ (). Usando este método, la variable func_result contiene el resultado de la función.

Pasando argumentos a funciones en Bash

Para pasar cualquier número de argumentos a la función Bash, simplemente debemos colocarlos justo después del nombre de la función, separados por un espacio. Se recomienda citar los argumentos para evitar la distorsión de un argumento con espacios en él.

  • Los parámetros pasados son $1, $2, $3 ... $n, correspondientes a la posición del parámetro después del nombre de la función.
  • La variable $0 está reservada para el nombre de la función.
  • La variable $# contiene el número de parámetros / argumentos posicionales pasados a la función.
  • La variable $* o $@ contiene todos los parámetros / argumentos posicionales pasados a la función.

Veamos un ejemplo al respecto:

  1. #!/bin/bash
  2.  
  3. greeting () {
  4.   echo "Hola $1"
  5. }
  6.  
  7. greeting "Jose"

Con el resultado:

  1. Hola Jose

Conclusiones

Hemos visto como trabajan las funciones en Bash. En cualquier caso, se trata de una mera introducción.

NOTA: El artículo es una adaptación al castellano de la entrada publicada en Linuxsize.com – Bash Functions