Python Argparse
The argparse module makes it easy to write user-friendly
command-line interfaces. It parses the defined arguments from the
sys.argv.
The argparse module also automatically generates help and usage
messages, and issues errors when users give the program invalid arguments.
The argparse is a standard module; we do not need to install it.
A parser is created with ArgumentParser and a new parameter is
added with add_argument. Arguments can be optional, required, or
positional.
Python Argparse Optional Argument
The following example creates a simple argument parser.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('-o', '--output', action='store_true',
help="shows output")
args = parser.parse_args()
if args.output:
print("This is some output")
The example adds one argument having two options: a short -o and
a long --ouput. These are optional arguments.
import argparse
The module is imported.
parser.add_argument('-o', '--output', action='store_true',
help="shows output")
An argument is added with add_argument. The action
set to store_true will store the argument as True, if present.
The help option gives argument help.
args = parser.parse_args()
The arguments are parsed with parse_args. The parsed arguments are
present as object attributes. In our case, there will be
args.output attribute.
if args.output:
print("This is some output")
If the argument is present, we show some output.
$ optional_arg.py -o This is some output $ optional_arg.py --output This is some output
We run the program with the -o and --output.
We can show the program help.
Python Argparse Required Argument
An argument is made required with the required option.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('--name', required=True)
args = parser.parse_args()
print(f'Hello {args.name}')
The example must have the name option specified; otherwise
it fails.
$ required_arg.py --name Peter Hello Peter $ required_arg.py usage: required_arg.py [-h] --name NAME required_arg.py: error: the following arguments are required: --name
Python argparse positional arguments
The following example works with positional arguments. They
are created with add_argument.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('name')
parser.add_argument('age')
args = parser.parse_args()
print(f'{args.name} is {args.age} years old')
The example expects two positional arguments: name and age.
parser.add_argument('name')
parser.add_argument('age')
Positional arguments are created without the dash prefix characters.
$ positional_arg.py Peter 23 Peter is 23 years old
This is sample output.
Python argparse dest
The dest option of the add_argument gives
a name to the argument. If not given, it is inferred from the option.
#!/usr/bin/env python
import argparse
import datetime
parser = argparse.ArgumentParser()
parser.add_argument('-n', dest='now', action='store_true', help="shows now")
args = parser.parse_args()
if args.now:
now = datetime.datetime.now()
print(f"Now: {now}")
The program gives the now name to the -n argument.
$ dest.py -n Now: 2019-03-22 17:37:40.406571
Python argparse type
The type argument determines the argument type.
#!/usr/bin/env python
import argparse
import random
parser = argparse.ArgumentParser()
parser.add_argument('-n', type=int, required=True,
help="define the number of random integers")
args = parser.parse_args()
n = args.n
for i in range(n):
print(random.randint(-100, 100))
The program shows n random integers from -100 to 100.
parser.add_argument('-n', type=int, required=True,
help="define the number of random integers")
The -n option expects integer value and it is
required.
$ rand_int.py -n 3 92 -61 -61
This is a sample output.
Python argparse default
The default option specifies the default value,
if the value is not given.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('-b', type=int, required=True, help="defines the base value")
parser.add_argument('-e', type=int, default=2, help="defines the exponent value")
args = parser.parse_args()
val = 1
base = args.b
exp = args.e
for i in range(exp):
val *= base
print(val)
The example computes exponentiation. The exponent value is not required; if not given, the default will be 2.
$ power.py -b 3 9 $ power.py -b 3 -e 3 27
Python argparse metavar
The metavar option gives a name to the
expected value in error and help outputs.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('-v', type=int, required=True, metavar='value',
help="computes cube for the given value")
args = parser.parse_args()
print(args)
val = args.v
print(val * val * val)
The example names the expected value value. The default
name is V.
$ metavar.py -h usage: metavar.py [-h] -v value optional arguments: -h, --help show this help message and exit -v value computes cube for the given value
The given name is shown in the help output.
Python argparse append action
The append action allows to group repeating
options.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('-n', '--name', dest='names', action='append',
help="provides names to greet")
args = parser.parse_args()
names = args.names
for name in names:
print(f'Hello {name}!')
The example produces greeting messages to all names specified with the
n or name options; they can be repeated
multipile times.
$ appending.py -n Peter -n Lucy --name Jane Hello Peter! Hello Lucy! Hello Jane!
Python argparse nargs
The nargs specifies the number of command-line arguments
that should be consumed.
#!/usr/bin/env python
import argparse
import sys
parser = argparse.ArgumentParser()
parser.add_argument('chars', type=str, nargs=2, metavar='c',
help='starting and ending character')
args = parser.parse_args()
try:
v1 = ord(args.chars[0])
v2 = ord(args.chars[1])
except TypeError as e:
print('Error: arguments must be characters')
parser.print_help()
sys.exit(1)
if v1 > v2:
print('first letter must precede the second in alphabet')
parser.print_help()
sys.exit(1)
The example shows a sequence of characters from character one to character two. It expects two arguments.
parser.add_argument('chars', type=str, nargs=2, metavar='c',
help='starting and ending character')
With nargs=2 we specify that we expect two arguments.
$ charseq.py e k e f g h i j k
The program shows a sequence of characters from e to k.
Variable number of arguments can be set with the * character.
#!/usr/bin/env python
import argparse
parser = argparse.ArgumentParser()
parser.add_argument('num', type=int, nargs='*')
args = parser.parse_args()
print(f"The sum of values is {sum(args.num)}")
The example computes the sum of values; we can specify variable number of arguments to the program.
$ var_args.py 1 2 3 4 5 The sum of values is 15
Python argparse choices
The choices option limits arguments
to the given list.
#!/usr/bin/env python
import argparse
import datetime
import time
parser = argparse.ArgumentParser()
parser.add_argument('--now', dest='format', choices=['std', 'iso', 'unix', 'tz'],
help="shows datetime in given format")
args = parser.parse_args()
fmt = args.format
if fmt == 'std':
print(datetime.date.today())
elif fmt == 'iso':
print(datetime.datetime.now().isoformat())
elif fmt == 'unix':
print(time.time())
elif fmt == 'tz':
print(datetime.datetime.now(datetime.timezone.utc))
In the example, the now option can accept the following
values: std, iso, unix, or tz.
$ mytime.py --now iso 2019-03-27T11:34:54.106643 $ mytime.py --now unix 1553682898.422863
This is a sample output.
Head example
The following example mimics the Linux head command. It shows the n lines of a text from the beginning of the file.
sky top forest wood lake wood
For the example, we have this small test file.
#!/usr/bin/env python
import argparse
from pathlib import Path
parser = argparse.ArgumentParser()
parser.add_argument('f', type=str, help='file name')
parser.add_argument('n', type=int, help='show n lines from the top')
args = parser.parse_args()
filename = args.f
lines = Path(filename).read_text().splitlines()
for line in lines[:args.n]:
print(line)
The example has two options: f for a file name and
-n for the number of lines to show.
$ head.py words.txt 3 sky top forest