Coming Up for Air

Writing Bash Scripts with Parameters

Tuesday, April 02, 2013 |

In the course of my work, I often find myself writing a script to automate a routine task. Almost invariably, there are cases where I need the script to behave in slightly different fashion, but only occassionally. My early scripts rather crudely used one if after, which is not very elegant. Finally, after tiring of this clumsy approach, I searched for a better way and found one: getopts. In this shortish entry, I’ll give a very brief introduction to getopts, and show how I write my scripts now.

Let’s start with a simple example:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
#!/bin/bash

OPT_A=false
OPT_C=0

function usage() {
    echo "USAGE:"
    echo "    myscript [-a] [-b <value>] [-c]"
    exit -1
}

while getopts ab:c opt
do
    case "$opt" in
        a) OPT_A=true ;;
        b) OPT_B=$OPTARG ;;
        c) OPT_C=1 ;;
        *) usage ;;
    esac
done

echo "OPTIONS:"
echo "    OPT_A : $OPT_A"
echo "    OPT_B : $OPT_B"
echo "    OPT_C : $OPT_C"

This simple script takes three parameters, a, b, and c. Parameters a and c are simple parameters, but b takes a value. The parameters themselves are processed in the while loop. Note that the condition for the loop is a call to getopts, whose parameters are the valid parameter list and a variable into which to store each parameter found. Note also that b has a collon following it, which signifies that this parameter takes a value. Inside the loop, we have a case statement to process the parameters as getopts returns them. In this case, we’re simply setting variables to a specific value, which we can then process later. I have also made function calls directly from the case statement, as you can see with the catchall * case. How and where you implement/call the functionality for a given parameter is, I think, a matter of style and taste. I tend either to set a variable and then test it later with if or call a function, like usage, rather than putting a lot of logic in the case block. You can put as much as you want in the block (note the ;; terminators, by the way), but I’ve found that can quickly get ugly and hard to manage.

If we run this script now, say, `myscript -c b foo', we should see this output:

OPTIONS:
    OPT_A : false
    OPT_B : foo
    OPT_C : 1

Bash scripting is, of course, extremly powerful and flexible, so there’s so much more that could be shown, but, hopefully, this will expose you to a very handy, built-in function that should make writing configurable scripts much simpler.

Search

    Quotes

    Sample quote

    Quote source

    About

    My name is Jason Lee. I am a software developer living in the middle of Oklahoma. I’ve been a professional developer since 1997, using a variety of languages, including Java, Javascript, PHP, Python, Delphi, and even a bit of C#. I currently work for Red Hat on the WildFly/EAP team, where, among other things, I maintain integrations for some MicroProfile specs, OpenTelemetry, Micrometer, Jakarta Faces, and Bean Validation. (Full resume here. LinkedIn profile)

    I am the president of the Oklahoma City JUG, and an occasional speaker at the JUG and a variety of technical conferences.

    On the personal side, I’m active in my church, and enjoy bass guitar, running, fishing, and a variety of martial arts. I’m also married to a beautiful woman, and have two boys, who, thankfully, look like their mother.

    My Links

    Publications