Introduction to Bash Shell Scripting
An Overview of Bash Shell Scripting for Automating Tasks
Shell scripting is a powerful way to automate tasks that you frequently perform on your computer. In this tutorial, we will provide a comprehensive overview of shell scripting, which will serve as the foundation for more advanced tutorials on creating practical shell scripts.
Explore our introduction to Bash post to learn more.
Bash provides a set of commands that can be combined to create small programs known as scripts. It’s important to note that we refer to this process as Bash scripting, not programming, and the scripts themselves as Bash scripts, not programs. This distinction is made because Bash scripts can become complex, but they still rely solely on the Bash shell to run. No additional compilers or interpreters are required.
While Bash lacks features found in other programming languages like Perl, JavaScript, or Python, such as scoped variables, standard libraries, or module systems, it offers its own advantages. One of the most significant advantages is the ability to easily invoke command-line tools and leverage the numerous utility commands available in Unix. For example, you can perform network requests with wget
or process text using awk
.
Shell scripting is a tool that you should be familiar with, at least in terms of understanding how to read a script and the benefits it can bring to your daily work. This tutorial will guide you through the theory and concepts of Bash scripting, with more detailed tutorials on specific techniques and problem-solving to come in the future.
Basics
Scripts are stored in files, and you can give them any name and extension. The crucial requirement is that they must start with a “shebang” on the first line:
1 |
Additionally, the file must be executable, which can be achieved using the chmod
utility command. For example:
1 | chmod u+x myscript |
This command makes the myscript
file executable for your user. Once executable, you can execute the script by calling it either ./myscript
if you’re in the same folder, or by using the full path to the script if you’re in a different location.
During your learning process, it’s recommended to use an online playground, such as this one, to make testing and experimentation easier.
Comments
Comments are essential when writing programs, and in Bash, a line starting with the #
symbol is considered a comment (with the exception of the shebang line). For example:
1 |
|
Comments can also be placed at the end of a line:
1 |
|
Variables
Variables in Bash are set using the =
operator. For example:
1 | name=value |
Here are some examples:
1 | ROOM_NUMBER=237 |
To print the value of a variable, use the echo
built-in command, adding a $
before the variable name:
1 | echo $ROOM_NUMBER |
Operators
Bash supports various arithmetic and comparison operators. For arithmetic operations, you can use +
, -
, *
, /
, %
, and **
for addition, subtraction, multiplication, division, modulo, and exponentiation, respectively.
Comparison operators include <
, <=
, ==
, >=
, and >
. You can also use the following:
-lt
: lower than-gt
: greater than-le
: lower or equal than-ge
: greater or equal than-eq
: equal to-ne
: not equal to
Here’s an example using the comparison operator -lt
:
1 |
|
Bash also includes logical operators &&
for AND and ||
for OR. Additionally, shortcuts such as +=
, -=
, *=
, /=
, and %=
are available for performing arithmetic operations and assignment together.
While there are more operators in Bash, these are the most commonly used ones.
Print to the Screen
To display output on the screen in Bash, use the echo
command. For example:
1 |
|
Logical Conditions
Bash provides logical conditions using the &&
operator for AND and the ||
operator for OR.
For AND conditions, use the following syntax: command && anothercommand
.
For OR conditions, use: command || anothercommand
.
To invert the logical return value of a command, use the !
symbol before the command: ! command
.
Control Structures
Bash supports several control structures that you might already be familiar with.
If/Else Statements
Use the if
statement for simple if conditions:
1 | if condition |
For if-else statements, use:
1 | if condition |
Nested if-else statements can be written as:
1 | if condition |
You can also use a semicolon to keep the else
statement on the same line:
1 | if condition ; then |
Here’s an example illustrating the usage of if
statements:
1 |
|
Notice the use of brackets when performing boolean evaluations.
Loops
Bash provides several looping mechanisms, including while
, until
, for in
, break
, and continue
.
While Loop
The while
loop runs a command as long as a certain condition remains true:
1 | while condition |
Until Loop
The until
loop runs a command until a certain condition becomes true:
1 | until condition |
For Loop
The for in
loop allows you to iterate over a list of values and execute a command for each item:
1 | for item in list |
Break and Continue
Inside loops, you can use the break
and continue
statements to exit the loop completely or skip the current iteration, respectively.
Case Statements
Case statements allow you to choose different paths based on specific values. The syntax is as follows:
1 | case value in |
The *)
case handles all cases not explicitly expressed. You can also use the |
symbol to add multiple choices for a single case.
Here’s an example illustrating the usage of case statements:
1 |
|
Select Statements
The select
statement provides a menu of choices for the user to select from:
1 | select item in list |
Here’s an example illustrating the usage of select statements:
1 |
|
Testing Conditions
The test
command in Bash allows you to check conditions and return a true (0
) or false (non-0
) value.
Here’s an example illustrating the usage of the test
command:
1 |
|
Reading Input from the Command Line
To make your scripts interactive, you can use the read
built-in command. This command reads a line from the standard input and can be formatted in various ways.
The simplest usage is as follows:
1 | echo "Age:" |
In this example, “Age:” will be printed, and you can enter a number which will be assigned to the age
variable.
The -p
option of read
provides a built-in prompt and assigns the input to a variable:
1 | read -p "Age: " age |
The read
command has additional options, which you can explore by typing help read
in the Bash terminal.
Adding Options
Options in Bash scripts are specified using a hyphen followed by a letter, such as -a
or -b
. You can use the getopts
built-in command to parse the options and retrieve their values.
To accept options a
and b
, use getopts ab
in a while
loop. If an option requires a value, append a :
after it. For example, getopts ab: arg
.
Here’s an example illustrating the usage of getopts
:
1 | while getopts ab: arg |
Within this script, $OPTARG
is automatically assigned the option letter. By specifying a colon :
before the argument definition (e.g., getopts :xy: arg
), you can handle error messages manually. This allows you to control error messages for missing or invalid options.
Working with Parameters
In Bash scripts, you can access parameters passed at invocation time using special variables. $0
refers to the name of the command, while $1
, $2
, etc. represent the positional parameters passed to the script. After the 9th position, you need to use curly braces: ${10}
, ${11}
, and so on.
For example, running the following script:
1 |
|
As ./startCar fiesta
, will output:
1 | ./startCar |
The special syntax $*
prints all parameters, and $#
denotes the total number of parameters passed. For example:
1 |
|
When executing ./test.sh Milan Florence Rome
, the output will be:
1 | 3 Milan Florence Rome |
Separating Options from Parameters
If your script includes both options and parameters, it is important to separate them. Use a hyphen to distinguish options from parameters. For example:
1 | driveCar -m "Ford Fiesta" - Milan Florence Rome |
Working with Strings
To determine the length of a string, use `$