Capturing filesystem globs using optparse

133 views Asked by At

I'm working on some Python code which uses optparse to get the name of some input files, then (on paper) expands that input using glob.glob() if possible.

It seems however that my shell (zsh) expands the glob before it's passed to Python. For example, if I run python myscript.py *.txt, I'll get the first matching .txt file instead of the literal glob, *.txt. This is pretty useless to me.

I figure this is more of an issue on the shell side; but taking into account portability, I'd like to know if there's a Python-side solution to this.

optparse code used for this:

p = OptionParser()
p.add_option('-f', '--infile', dest='input', action='store', type='string')
(options, args) = p.parse_args()

The issue is reproducible with the following minimal example (which also shows that it extends to manual argument extraction using sys.argv):

$ ls *.txt
file1.txt    file2.txt    file3.txt
$ python -c 'import sys; print sys.argv' *.txt
['-c', 'file1.txt', 'file2.txt', 'file3.txt']

So again, for clarity, I'm looking for a way to pass the glob literal to my python code, to have it expanded there, using Python, because a shell workaround hurts portability.

2

There are 2 answers

0
Steve On BEST ANSWER

If that's the only argument that you're passing, then the rest of the glob expansion is being sucked up by the positional args part of the parsing tuple, so maybe try to use that?

from optparse import OptionParser

p = OptionParser()
p.add_option('-f', '--filename', dest='input', action='store', type='string')
options, args = p.parse_args()

print options
print args

Gives you:

$ ls *.txt
failure_counts.txt  iscsi-targets.txt  README.txt  snmp.txt  success_counts.txt
$ python glob.py -f *.txt
{'input': 'failure_counts.txt'}
['iscsi-targets.txt', 'README.txt', 'snmp.txt', 'success_counts.txt']
4
wildwilhelm On

You can escape the wildcard character so that the shell doesn't do the globbing for you:

$ ls *.txt
file1.txt   file2.txt   file3.txt
$ python -c 'import sys; print sys.argv' *.txt
['-c', 'file1.txt', 'file2.txt', 'file3.txt']
$ python -c 'import sys; print sys.argv' \*.txt
['-c', '*.txt']