Search code examples
pythonexceptionargparse

ArgumentParser.add_argument raises AttributeError: 'str' object has no attribute 'prefix_chars'


When I run my program, I immediately get an AttributeError when it's setting up the argument parser:

Traceback (most recent call last):
  File "blah.py", line 55, in <module>
    parser.add_argument('--select-equal', '--equal', nargs=2, metavar=[ 'COLUMN', 'VALUE' ], action='append', dest='filter_equality_keys_and_values', default=[], help='Only return rows for which this column is exactly equal to this value.')
  File "…/Developer/Library/Frameworks/Python3.framework/Versions/3.8/lib/python3.8/argparse.py", line 1346, in add_argument
    chars = self.prefix_chars
AttributeError: 'str' object has no attribute 'prefix_chars'

Well, that sounds reasonable. strs indeed don't have a prefix_chars attribute. Clearly the exception message is correct.

Except I can't parse arguments, or even get to parsing arguments, because of this exception. Why is this throwing an exception? Why is it trying to get prefix_chars of a str in the first place? The exception is coming from inside the Python module; is this a bug in Python or something I'm doing wrong?


Solution

  • It is, in fact, something I was doing wrong.

    The clue is that the method is trying to access an attribute of an object that doesn't have such an attribute—and it's trying to do so on self.

    The first argument to my call to add_argument is indeed a string ('--select-equal'). The only way that string could end up being self is if I were calling add_argument on the ArgumentParser class and not an ArgumentParser object.

    And indeed, scrolling up a couple lines in my own code, there's the problem:

        import argparse
        parser = argparse.ArgumentParser
    

    I need to instantiate ArgumentParser, which means calling the class (ArgumentParser()), not just stash the class in a variable.

    For want of a (), the exception was thrown.