advanced bash scripting · a shell is used to navigate around the machine, perform administrative...

23
Advanced Bash Scripting Stephen D. Butalla August 26, 2019 Florida Institute of Technology

Upload: others

Post on 11-Aug-2020

7 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Advanced Bash Scripting

Stephen D. Butalla

August 26, 2019

Florida Institute of Technology

Page 2: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Bash: What is it?

• Bash (Bourne-again shell) is a Linux/Unix shell

• Shell: An interface used to communicate with the OS of the

machine; an interpreter

• Other common shells: zsh (Z shell), csh (C shell),

tcsh (TENEX C shell), ksh (Korn shell), etc.

• A shell is used to navigate around the machine, perform

administrative tasks (moving files, making directories, etc.)

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 2

Page 3: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Bash Scripting

• Bash scripting allows you to to use familiar logic structures in order

to automate tasks

• Bash scripts can range from very simple (hardcoded commands,

simple loops) to the complex (user input arguments and options)

• For more information on shell scripting, references are listed at the

end

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 3

Page 4: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Bash Scripting: Hello World

• Always begin with a shabang (#!) and the path to the shell you are

using:

#!/bin/bash

echo ’Hello World ’

• To make file executable, run

$ chmod u+x fileName.sh

# ^" change mode"

• To run the file, run

$ ./ fileName.sh

• This script can then be moved from the pwd to /usr/bin, which

will allow it to be executable from anywhere on the machine

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 4

Page 5: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Bash Scripting: Hello World

• Create a new directory, write a hello world program, and execute

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 5

Page 6: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Variables

• Variables can be created “on-the-fly” without declaration, but need

to be initialized (either with a value or null):

myVariable =200 # note that this is type -less!

myNullVariable= # null

• Variables can also be declared (with options that specify type), and

then assigned a value

declare -i myInt

declare -a myArray

declare -f myFunction

# ^creates a list of functions that were

# created before this declaration

• Note: variables can be initialized to floats, but floating point

arithmetic is not supported!

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 6

Page 7: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Variables

• To retrieve the value of a variable, we need to use the $ character in

front of the variable name

myVariable =200

echo myVariable # prints myVariable

echo $myVariable # prints 200

• Prefixing the variable name with $ is really just shorthand for

${myVariable}• Variables can also be declared and manipulated using the let

built-in function

let "counter = 0" # initialize counter

let "counter += 1" # increment counter

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 7

Page 8: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Variables

• Modify helloWorld.sh to print variables that store “hello” and

“world” instead of one string

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 8

Page 9: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Control Structures

• Bash has control structures similar to other programming languages

• for, while and until loops are supported as well as if/if-else,

case, and select statements

• Test conditions are placed with brackets [ ]

• if statement:

if [ some_test_condition ]; then

some commands

fi

• for statement:

for ii in {1..10}; do

some commands

done

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 9

Page 10: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Test Conditions

• Test conditions use options and operators to evaluate the condition:

while [ something -option condition ]; do

some commands

done

• Simple example printing numbers:

counter =1

max=5

while [ $counter -le $max ]; do

# ^ ^note the spaces!

echo $counter

let "counter += 1"

#^This line can also be written as

# (( counter ++))

done

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 10

Page 11: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Test Conditions

• Example:

string1=hello

string2=world

#If string1 length > 0

if [ -n $string1 ]; then

echo $string1 $string2 # hello world

fi

• Comparing two integers:

int1 =20

int2 =11

if [ $int1 -le $int2 ]; then

echo "TRUE"

else

echo "FALSE"

fi

• For more information on the options for the test structure, see man test

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 11

Page 12: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Test Conditions

• Write a script that compares two strings stored in variables; if one string is

not identical to the other, print the name of the first string (on separate

lines) 10 times to the terminal

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 12

Page 13: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Multiple Test Conditions

• AND (&&) condition

var1 =10

var2 =30

if [ $1 -gt $var1 ] && [ $1 -lt var3 ]; then

echo "Argument is between 10 and 30: $1"

else

echo "Argument is out of range (10, 30)"

exit 1

# ^1 is false in bash , 0 is true!

fi

• OR (||) condition

if [ -e file.txt ] || [ -e file.csv ]; then

# ^file exists test condition

echo "Opening file."

else

echo "File is not a .txt or .csv. Exiting."

exit 1

fi

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 13

Page 14: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

For Loops

• Just like other languages, there are several ways to control the range of a

for loop [1]:

#Standard

for jj in 1 2 3 4; do

#Brace Expansion

for bb in {1..5}; do

# ^Indices: 1,2,3,4,5

#Brace Expansion

for bb in {1..20..2}

# ^Increment by 2 up to 20

• Note that with a brace expansion you can’t use variables! I.e., {1..$max}won’t work. Instead, use seq (sequence) command within backquotes, which

allows for command substitution:

max=5

for ii in ‘seq 1 $max ‘; do

# ^note the backquotes!

echo $ii

done

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 14

Page 15: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

For Loops, Continued

• C-style syntax is supported in the double parentheses construct:

for ((ii=0; ii <10; ii ++)); do

# ^Remember bash variables by default are untyped!

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 15

Page 16: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Case Statements

• Example:

case $1 in

# ^Argument passed to the case statement

0) echo Hello;;

1) echo Goodbye ;;

# ^double semi -colon used to

# terminate case

esac

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 16

Page 17: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Select Statements

• Select statements are used to create menus

select item in "item1" "item2" "item3" "item4"; do

echo "You have selected $item. Good choice!"

break # Break statement to exit the loop

done

• Terminal output of the code snippet above looks like:

Select an option from the menu.

1) item1

2) item2

3) item3

4) item4

#?

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 17

Page 18: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Arrays

• There are indexed and associative arrays [2]

• Indexed array: keys are ordered integers

• Associative array: keys are strings. This array type can only be created by

declaration (using the -A option); only supported in bash 4.0+

myArray =( index1 index2 index3 ...)

declare -A otherArray

otherArray =([ key1]= value1 [key2]= value2 ...)

• Display all values in array: echo ${myArray[@]} or echo ${myArray[*]}• Find length of array: echo ${#myArray[@]}

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 18

Page 19: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Using Arguments

• Arguments are passed into the bash script by adding the parameters after

the file name when executing:

./ fileName.sh argument1 argument2

• Inside of the script, the arguments are named sequentially: $1, $2, ...

($0 is the name of the script)

• The special character $# provides the number of arguments passed to the

script

• To check if the number of arguments is valid, we can run

args=2

if [ "$#" -ne $args ]; then

# ^ not equal

• Other special built-in variables:

• $@ (number of parameters passed)

• $? (status of last command; i.e., successful or unsuccessful?)

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 19

Page 20: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Using Options (Flags)

• Using options can be implemented with the getopts function, which is couched in a

while loop

while getopts "abc" option; do

case $option in

a) echo "You used flag -a.";;

b) echo "You used flag -b.";;

c) echo "You used flag -c.";;

esac

done

shift $(( $OPTIND - 1)) # moves argument pointer to next argument

• Arguments can also be passed to the script when a flag is provided

while getopts "abc:d" option; do

case $option in

a) ;;# Something here

b) ;;# Something here

c) ;;# Something here

d) ;;# Something here with the argument passed

# (could be file , path , etc.)

esac

done

shift $(( $OPTIND - 1))

• To run, simply execute the file with the flags:

./ fileName.sh -a

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 20

Page 21: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Loading Data Files

• Sometimes it is necessary to source a file

• The dot (.) or source command is used for this [1]

• Must provide the path or can use the basename if the file is not in the pwd

source dataFile.txt

echo "var1 is $var1"

echo "var2 is $var2"

var3=$(($var1 + $var3))

echo "var3 is $var3"

• datafile.txt:

var1 =20

var2=2

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 21

Page 22: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

Final Program

• Write a final script that emulates a calculator; i.e., it accepts an

argument, passes it to a case statement (or a select statement),

and operates on two variables passed to the script

• Hint: remember that bash does not support floating point

arithmetic. Pipe the result of the arithmetic expression to the

built-in function bc:

$ echo "3/4" | bc -l

$ 0.75000000000000000000

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 22

Page 23: Advanced Bash Scripting · A shell is used to navigate around the machine, perform administrative tasks (moving les, making directories, etc.) S. Butalla { \Advanced Bash Scripting"

References

[1] M. Cooper, Advanced Bash-Scripting Guide: An in-depth exploration of the art of shell scripting, 2014,

https://www.tldp.org/LDP/abs/abs-guide.pdf.

[2] E. Docile, “How to use arrays in bash script,” LinuxConfig.org

https://linuxconfig.org/how-to-use-arrays-in-bash-script.

[3] V. Grite, “Linux Shell Scripting Tutorial (LSST) v2.0,” nixCraft, https://bash.cyberciti.biz/guide/Main_Page.

S. Butalla – “Advanced Bash Scripting” – Aug. 26, 2019 23