
Hola habrozhiteli! La línea de comandos de Linux, superventas, le ayudará a superar el camino desde los primeros clics tímidos en las teclas hasta la creación segura de programas completos para la última versión de bash, el shell de Linux más popular. La segunda edición habla sobre nuevas características en bash 4.x, como nuevos operadores de redireccionamiento y operaciones con comodines. Aprenderá las habilidades atemporales de la línea de comandos: navegar por el sistema de archivos, configurar el entorno, encadenar comandos y hacer coincidir expresiones regulares. Comprenderá la filosofía detrás de muchas herramientas de línea de comandos, comprenderá la rica herencia de las supercomputadoras de Unix y aprenderá sobre el conocimiento acumulado por generaciones de gurús que han excluido al mouse de su arsenal de herramientas. Una vez superado el primer "shock de shell", comprenderá lo natural y lógica que es esta forma de interactuar con una computadora.
Extracto Capítulo 25. Comienzo del proyecto.
En este capítulo, comenzamos a crear el programa. El objetivo de este proyecto es mostrar cómo puede usar las diversas capacidades del shell para crear programas y, lo más importante, para crear
buenos programas.
A continuación, escribiremos
un generador de informes . Mostrará una variedad de información sobre el sistema y su estado en formato HTML, para que pueda verse en un navegador web.
Por lo general, la creación de programas se lleva a cabo en varias etapas, en cada una de las cuales se agregan nuevas funciones y capacidades. Al final de la primera etapa, nuestro programa reproducirá una página HTML mínima sin ninguna información. Agregaremos esta información en los próximos pasos.
Etapa uno: documento mínimo
En primer lugar, determinemos cómo se ve el formato de un documento HTML bien formado. Tiene la siguiente forma:
<html> <head> <title> </title> </head> <body> . </body> </html>
Si ingresa este texto en un editor de texto y lo guarda en un archivo llamado
foo.html , podemos abrirlo ingresando la siguiente URL en Firefox:
archivo: ///home/username/foo.html .
En la primera etapa, crearemos un programa que generará este marcado HTML a la salida estándar. Escribir un programa así es muy simple. Abra un editor de texto y cree un archivo llamado ~ / bin / sys_info_page:
[me@linuxbox ~]$ vim ~/bin/sys_info_page
Y luego ingrese el siguiente programa:
#!/bin/bash # echo "<html>" echo " <head>" echo " <title>Page Title</title>" echo " </head>" echo " <body>" echo " Page body." echo " </body>" echo "</html>"
Nuestra primera versión contiene una línea shebang, un comentario (bienvenido) y una secuencia de comandos de eco, uno para cada salida de línea. Después de guardar el archivo, hágalo ejecutable e intente ejecutar:
[me@linuxbox ~]$ chmod 755 ~/bin/sys_info_page [me@linuxbox ~]$ sys_info_page
Después de comenzar, el texto del documento HTML debería aparecer en la pantalla, porque los comandos de eco en el script envían sus líneas a la salida estándar. Ejecute el programa nuevamente y redirija la salida del programa al archivo
sys_info_page.html , para luego ver el resultado en un navegador web:
[me@linuxbox ~]$ sys_info_page > sys_info_page.html [me@linuxbox ~]$ firefox sys_info_page.html
Hasta ahora todo bien.
Al desarrollar programas, siempre debe recordar la simplicidad y la claridad. El mantenimiento es más fácil cuando el programa es fácil de leer y comprensible, sin mencionar el hecho de que el programa es más fácil de escribir cuando es posible reducir la cantidad de entrada manual. La versión actual del programa funciona muy bien, pero se puede simplificar. La combinación de todos los comandos de eco en uno definitivamente facilitará en el futuro agregar nuevas líneas a la salida del programa. Por lo tanto, cambiamos el programa como se muestra a continuación:
#!/bin/bash # echo "<html> <head> <title>Page Title</title> </head> <body> Page body. </body> </HTML>"
Las cadenas entre comillas pueden incluir saltos de línea y, en consecuencia, pueden contener varias líneas de texto. El shell continuará leyendo el texto hasta que encuentre una cita de cierre. Esta regla también se aplica en la línea de comando:
[me@linuxbox ~]$ echo "<html> > <head> > <title>Page Title</title> > </head> > <body> > Page body. > </body> > </html>"
El símbolo> al comienzo de cada línea es un mensaje para ingresar un shell definido por su variable PS2. Aparece cada vez que se ingresa una instrucción de varias líneas. Esta característica aún es oscura, pero luego, cuando nos familiaricemos con las instrucciones del programa multilínea, sus ventajas serán obvias.
Paso dos: agregue algunos datos
Ahora que el programa puede generar un documento mínimo, agregue algunos datos al informe. Para hacer esto, realice los siguientes cambios:
#!/bin/bash # echo "<html> <head> <title>System Information Report</title> </head> <body> <h1>System Information Report</h1> </body> </html>"
Aquí se agrega el nombre de la página y el título en el cuerpo del informe.
Variables y constantes
Hubo un problema en nuestro script. ¿Ha notado que la línea del Informe de información del sistema se repite dos veces? En general, para un escenario tan pequeño, este no es un problema tan grande, pero imagine un escenario realmente largo en el que esta línea se repite muchas veces. Si necesita cambiar el nombre en tal escenario, tendrá que hacer cambios en muchos lugares, y esto es mucho trabajo manual. ¿Es posible cambiar el script para que la cadena se defina solo una vez? Esto simplificaría en gran medida el mantenimiento del script en el futuro. Sí, esto es posible, por ejemplo, así:
#!/bin/bash # title="System Information Report" echo "<html> <head> <title>$title</title> </head> <body> <h1>$title</h1> </body> </html>"
Al crear una
variable llamada título y asignarle el valor Informe de información del sistema, aprovechamos la sustitución de parámetros y colocamos la cadena en muchos lugares.
¿Pero cómo crear una variable? Simple: solo úsalo. Cuando el shell encuentra una variable, la crea automáticamente. Esto difiere de muchos lenguajes de programación en los que las variables deben declararse o definirse explícitamente antes de usarse. El shell de comandos es demasiado liberal en este sentido, lo que finalmente lleva a algunos problemas. Por ejemplo, considere el siguiente script ejecutado en la línea de comando:
[me@linuxbox ~]$ foo="yes" [me@linuxbox ~]$ echo $foo yes [me@linuxbox ~]$ echo $fool [me@linuxbox ~]$
Primero asignamos el valor yes a la variable foo y luego enviamos su valor con el comando echo. Luego, intentamos nuevamente mostrar el valor de la variable, pero cometimos un error al especificar el nombre tonto y obtuvimos una cadena vacía. Este resultado se explica por el hecho de que el shell creó con éxito la variable tonta al encontrarla y le asignó un valor predeterminado vacío. De este ejemplo se deduce que debe controlar cuidadosamente la ortografía. También es importante comprender lo que realmente sucedió en este ejemplo. Por el conocimiento previo de las características del mecanismo de sustitución, sabemos que el equipo
[me@linuxbox ~]$ echo $foo
está expuesto al mecanismo de sustitución de parámetros, como resultado de lo cual toma la forma
[me@linuxbox ~]$ echo yes
Por otro lado, el equipo
[me@linuxbox ~]$ echo $fool
se convierte en
[me@linuxbox ~]$ echo
¡Nada se sustituye por una variable vacía! Esto puede causar errores en los comandos que requieren argumentos. Por ejemplo:
[me@linuxbox ~]$ foo=foo.txt [me@linuxbox ~]$ foo1=foo1.txt [me@linuxbox ~]$ cp $foo $fool cp: 'foo.txt' , "cp --help" .
Asignamos valores a dos variables, foo y foo1. Y luego intentaron ejecutar el comando cp, pero cometieron un error tipográfico en nombre del segundo argumento. Después de procesar por el motor de búsqueda, el comando cp recibió solo un argumento, aunque requiere dos.
Las siguientes son algunas reglas para nombrar variables:
- Los nombres de las variables pueden consistir en caracteres alfanuméricos (letras y números) y guiones bajos.
- El primer carácter en un nombre de variable solo puede ser una letra o un guión bajo.
- La presencia de espacios y signos de puntuación en nombres de variables no está permitida.
La
variable nombre significa un valor que puede cambiar, y en muchas aplicaciones, las variables se usan de esa manera. Sin embargo, la variable de título en nuestra aplicación se usa como una
constante . Una constante, como una variable, tiene un nombre y contiene un valor. La única diferencia es que el valor de la constante no cambia. En una aplicación que realiza cálculos geométricos, puede definir una constante PI con un valor de 3.1415, en lugar de usar este número en todo el programa. El shell no distingue entre constantes y variables; Estos términos se usan principalmente para la conveniencia del programador. Una convención típica es usar letras mayúsculas para indicar constantes y letras minúsculas para variables verdaderas. Cambiemos el escenario para alinearlo con esta convención:
#!/bin/bash # TITLE="System Information Report For $HOSTNAME" echo "<html> <head> <title>$TITLE</title> </head> <body> <h1>$TITLE</h1> </body> </html>"
En el camino, complementamos el nombre agregando el valor de la variable de shell HOSTNAME al final. Este es el nombre de red de la máquina.
NOTA
De hecho, el shell tiene un mecanismo para garantizar la inmutabilidad de las constantes, en forma de un comando de declaración incorporado con el parámetro -r (solo lectura - solo lectura). Si asigna un valor a la variable TITLE como se muestra a continuación:
declare -r TITLE="Page Title"
el shell no permitirá que el valor se reasigne a la variable TITLE. Este mecanismo rara vez se usa en la práctica, pero está disponible y se puede usar en escenarios particularmente estrictos.
Asignación de valores a variables y constantes
Hemos llegado al momento en que nuestro conocimiento de las características del funcionamiento del mecanismo de sustitución comienza a dar sus frutos. Como hemos visto, la asignación de valores a las variables se realiza así:
=
donde la
variable es el nombre de la variable y el
valor es la cadena. A diferencia de otros lenguajes de programación, el shell no se preocupa por los tipos de valores asignados a las variables; ella interpreta todos los valores como cadenas. Es posible forzar al shell a limitar el rango de valores asignados a enteros utilizando el comando declarar con la opción -i, pero al igual que declarar variables de solo lectura, esta característica rara vez se usa en la práctica.
Tenga en cuenta que no hay espacios en el operador de asignación entre el nombre de la variable, el signo igual y el valor. ¿Y en qué puede consistir el significado? Desde cualquier cosa, puede expandirse en una cadena.
a=z # a "z". b="a string" # . c="a string and $b" # , # , . d=$(ls -l foo.txt) # . e=$((5 * 7)) # . f="\t\ta string\n" # , # .
En una línea, puede asignar varias variables a la vez:
a=5 b="a string"
Cuando se usa la sustitución, los nombres de las variables se pueden encerrar entre llaves opcionales {}. Esto es útil cuando el nombre de la variable se vuelve ambiguo en el contexto circundante. El siguiente ejemplo intenta cambiar el nombre de
myfile a
myfile1 usando una variable:
[me@linuxbox ~]$ filename="myfile" [me@linuxbox ~]$ touch $filename [me@linuxbox ~]$ mv $filename $filename1 mv: 'myfile' , "mv --help" .
Este intento no tuvo éxito porque el shell interpretó el segundo argumento del comando mv como el nombre de una variable nueva (y vacía). A continuación se muestra cómo resolver este problema:
[me@linuxbox ~]$ mv $filename ${filename}1
Al agregar llaves, nos aseguramos de que el shell no interpretaría el último carácter 1 como parte del nombre de la variable.
Nota
Al realizar la sustitución, se recomienda que los nombres y comandos de las variables se incluyan entre comillas dobles para evitar que el shell rompa las líneas en palabras. Es especialmente importante utilizar comillas cuando una variable puede contener un nombre de archivo.
Utilizaremos esta oportunidad para agregar datos adicionales al informe, es decir, la fecha y la hora del informe, así como el nombre del usuario que creó el informe:
#!/bin/bash # TITLE="System Information Report For $HOSTNAME" CURRENT_TIME=$(date +"%x %r %Z") TIME_STAMP="Generated $CURRENT_TIME, by $USER" echo "<html> <head> <title>$TITLE</title> </head> <body> <h1>$TITLE</h1> <p>$TIME_STAMP</p> </body> </html>"
Documentos incrustados
Observamos dos métodos diferentes de salida de texto, y ambos usan el comando echo. Sin embargo, hay otro tercer método, llamado
documento en línea (aquí documento), o un
script en línea (aquí script). Un documento incrustado es una forma adicional de redirección de E / S que pasa el texto incrustado en un script a la entrada de comando estándar. Esta redirección funciona así:
<<
donde el
comando es el nombre del comando que recibe el texto especificado a través de la entrada estándar, y el
indicador es la línea que marca el final del texto incrustado. Modificaremos el escenario utilizando el documento incrustado en él:
#!/bin/bash # TITLE="System Information Report For $HOSTNAME" CURRENT_TIME=$(date +"%x %r %Z") TIME_STAMP="Generated $CURRENT_TIME, by $USER" cat << _EOF_ <html> <head> <title>$TITLE</title> </head> <body> <h1>$TITLE</h1> <p>$TIME_STAMP</p> </body> </html> _EOF_
En lugar del comando echo, el script ahora usa el comando cat y el documento incrustado. La línea _EOF_ se eligió para el rol de indicador (significa
fin de archivo -
fin de archivo , acuerdo común), y marca el final del texto incrustado. Tenga en cuenta que la línea indicadora debe estar en una línea separada, una, y no debe haber espacios a continuación.
¿Pero cuáles son los beneficios de usar el documento incrustado aquí? Prácticamente ninguno, excepto que las comillas dentro de los documentos incrustados pierden su significado especial para el shell. El siguiente es un ejemplo del uso de un documento incrustado en la línea de comando:
[me@linuxbox ~]$ foo="some text" [me@linuxbox ~]$ cat << _EOF_ > $foo > "$foo" > '$foo' > \$foo > _EOF_ some text "some text" 'some text' $foo
Como puede ver, el shell de comandos no presta atención a las comillas. Ella los interpreta como personajes ordinarios. Gracias a esto, insertamos libremente comillas en los documentos incrustados. Esta circunstancia se puede utilizar al desarrollar programas de informes.
Los documentos incrustados se pueden usar con cualquier comando que acepte datos de entrada estándar. El siguiente ejemplo utiliza un documento incorporado para enviar una secuencia de comandos al programa ftp para descargar un archivo desde un servidor FTP remoto:
#!/bin/bash # FTP FTP_SERVER=ftp.nl.debian.org FTP_PATH=/debian/dists/stretch/main/installer-amd64/current/images/cdrom REMOTE_FILE=debian-cd_info.tar.gz ftp -n << _EOF_ open $FTP_SERVER user anonymous me@linuxbox cd $FTP_PATH hash get $REMOTE_FILE bye _EOF_ ls -l $REMOTE_FILE
Si reemplaza el operador de redireccionamiento << con << -, el shell de comandos ignorará los caracteres de tabulación iniciales en el documento incrustado. Gracias a esto, se pueden agregar sangrías al documento incrustado para una mayor legibilidad:
#!/bin/bash # FTP FTP_SERVER=ftp.nl.debian.org FTP_PATH=/debian/dists/stretch/main/installer-amd64/current/images/cdrom REMOTE_FILE=debian-cd_info.tar.gz ftp -n <<- _EOF_ open $FTP_SERVER user anonymous me@linuxbox cd $FTP_PATH hash get $REMOTE_FILE bye _EOF_ ls -l $REMOTE_FILE
Sin embargo, usar esta función no siempre es conveniente, porque para la sangría, muchos editores de texto (y los propios programadores) prefieren usar caracteres de espacio en lugar de pestañas.
Conclusión
En este capítulo, comenzamos a desarrollar un proyecto con el que pasaremos por todas las etapas de la creación de un guión. Nos familiarizamos con las variables y constantes y las características de su uso. Son más frecuentes que otros componentes de software utilizados para la sustitución. También vimos cómo organizar la salida de información en un script y nos familiarizamos con diferentes métodos para incrustar bloques de texto.
Sobre el autor
William Shotts es un desarrollador de software profesional con más de 30 años de experiencia que ha estado utilizando activamente el sistema operativo Linux durante más de 20 años. Tiene una amplia experiencia en desarrollo de software, soporte técnico, control de calidad y redacción de documentación. También es el creador de LinuxCommand.org, un sitio educativo y educativo dedicado a Linux, donde se proporcionan noticias, reseñas y soporte mediante la línea de comandos de Linux.
Sobre el editor de ciencias
Jordi Gutiérrez Hermoso es un programador informático, matemático y hacker ético. Desde 2002, utiliza exclusivamente Debian GNU / Linux, no solo en casa, sino también en el trabajo. Jordi está involucrado en el desarrollo de GNU Octave, un entorno informático gratuito que es en gran medida compatible con Matlab, así como con Mercurial, un sistema de control de versiones distribuido. Le gustan las matemáticas puras y aplicadas, el patinaje sobre hielo, la natación y el tejido de punto. Recientemente, piensa mucho sobre los problemas de las emisiones de gases de efecto invernadero y participa en acciones para salvar a los rinocerontes.
»Se puede encontrar más información sobre el libro en
el sitio web del editor»
Contenidos»
ExtractoCupón de 25% de descuento para vendedores ambulantes -
LinuxTras el pago de la versión en papel del libro, se envía un libro electrónico por correo electrónico.