7

My application is a specialized file comparison utility and obviously it does not make sense to compare only one file, so nargs='+' is not quite appropriate.

nargs=N only excepts a maximum of N arguments, but I need to accept an infinite number of arguments as long as there are at least two of them.

rypel
  • 4,686
  • 2
  • 25
  • 36
Bryan Dunphy
  • 799
  • 1
  • 10
  • 22
  • Also have a look at http://stackoverflow.com/questions/4194948/python-argparse-is-there-a-way-to-specify-a-range-in-nargs. That allows for even more flexibility, without messing up (or messing around with) the help text. –  May 21 '13 at 09:47

2 Answers2

19

Short answer is you can't do that because nargs doesn't support something like '2+'.

Long answer is you can workaround that using something like this:

parser = argparse.ArgumentParser(usage='%(prog)s [-h] file file [file ...]')
parser.add_argument('file1', nargs=1, metavar='file')
parser.add_argument('file2', nargs='+', metavar='file', help=argparse.SUPPRESS)
namespace = parser.parse_args()
namespace.file = namespace.file1 + namespace.file2

The tricks that you need are:

  • Use usage to provide you own usage string to the parser
  • Use metavar to display an argument with a different name in the help string
  • Use SUPPRESS to avoid displaying help for one of the variables
  • Merge two different variables just adding a new attribute to the Namespace object that the parser returns

The example above produces the following help string:

usage: test.py [-h] file file [file ...]

positional arguments:
  file

optional arguments:
  -h, --help  show this help message and exit

and will still fail when less than two arguments are passed:

$ python test.py arg
usage: test.py [-h] file file [file ...]
test.py: error: too few arguments
jcollado
  • 39,419
  • 8
  • 102
  • 133
7

Couldn't you do something like this:

import argparse

parser = argparse.ArgumentParser(description = "Compare files")
parser.add_argument('first', help="the first file")
parser.add_argument('other', nargs='+', help="the other files")

args = parser.parse_args()
print args

When I run this with -h I get:

usage: script.py [-h] first other [other ...]

Compare files

positional arguments:
  first       the first file
  other       the other files

optional arguments:
  -h, --help  show this help message and exit

When I run it with only one argument, it won't work:

usage: script.py [-h] first other [other ...]
script.py: error: too few arguments

But two or more arguments is fine. With three arguments it prints:

Namespace(first='one', other=['two', 'three'])
srgerg
  • 18,719
  • 4
  • 57
  • 39