:mod:`getopt` --- C-style parser for command line options
=========================================================

.. module:: getopt
   :synopsis: Portable parser for command line options; support both short and
              long option names.

**Source code:** :source:`Lib/getopt.py`

--------------

.. note::
   The :mod:`getopt` module is a parser for command line options whose API is
   designed to be familiar to users of the C :c:func:`getopt` function. Users who
   are unfamiliar with the C :c:func:`getopt` function or who would like to write
   less code and get better help and error messages should consider using the
   :mod:`argparse` module instead.

This module helps scripts to parse the command line arguments in ``sys.argv``.
It supports the same conventions as the Unix :c:func:`getopt` function (including
the special meanings of arguments of the form '``-``' and '``--``').  Long
options similar to those supported by GNU software may be used as well via an
optional third argument.

This module provides two functions and an
exception:


.. function:: getopt(args, shortopts, longopts=[])

   Parses command line options and parameter list.  *args* is the argument list to
   be parsed, without the leading reference to the running program. Typically, this
   means ``sys.argv[1:]``. *shortopts* is the string of option letters that the
   script wants to recognize, with options that require an argument followed by a
   colon (``':'``; i.e., the same format that Unix :c:func:`getopt` uses).

   .. note::

      Unlike GNU :c:func:`getopt`, after a non-option argument, all further
      arguments are considered also non-options. This is similar to the way
      non-GNU Unix systems work.

   *longopts*, if specified, must be a list of strings with the names of the
   long options which should be supported.  The leading ``'--'`` characters
   should not be included in the option name.  Long options which require an
   argument should be followed by an equal sign (``'='``).  Optional arguments
   are not supported.  To accept only long options, *shortopts* should be an
   empty string.  Long options on the command line can be recognized so long as
   they provide a prefix of the option name that matches exactly one of the
   accepted options.  For example, if *longopts* is ``['foo', 'frob']``, the
   option ``--fo`` will match as ``--foo``, but ``--f`` will
   not match uniquely, so :exc:`GetoptError` will be raised.

   The return value consists of two elements: the first is a list of ``(option,
   value)`` pairs; the second is the list of program arguments left after the
   option list was stripped (this is a trailing slice of *args*).  Each
   option-and-value pair returned has the option as its first element, prefixed
   with a hyphen for short options (e.g., ``'-x'``) or two hyphens for long
   options (e.g., ``'--long-option'``), and the option argument as its
   second element, or an empty string if the option has no argument.  The
   options occur in the list in the same order in which they were found, thus
   allowing multiple occurrences.  Long and short options may be mixed.


.. function:: gnu_getopt(args, shortopts, longopts=[])

   This function works like :func:`getopt`, except that GNU style scanning mode is
   used by default. This means that option and non-option arguments may be
   intermixed. The :func:`getopt` function stops processing options as soon as a
   non-option argument is encountered.

   If the first character of the option string is ``'+'``, or if the environment
   variable :envvar:`POSIXLY_CORRECT` is set, then option processing stops as
   soon as a non-option argument is encountered.


.. exception:: GetoptError

   This is raised when an unrecognized option is found in the argument list or when
   an option requiring an argument is given none. The argument to the exception is
   a string indicating the cause of the error.  For long options, an argument given
   to an option which does not require one will also cause this exception to be
   raised.  The attributes :attr:`msg` and :attr:`opt` give the error message and
   related option; if there is no specific option to which the exception relates,
   :attr:`opt` is an empty string.

.. XXX deprecated?
.. exception:: error

   Alias for :exc:`GetoptError`; for backward compatibility.

An example using only Unix style options:

   >>> import getopt
   >>> args = '-a -b -cfoo -d bar a1 a2'.split()
   >>> args
   ['-a', '-b', '-cfoo', '-d', 'bar', 'a1', 'a2']
   >>> optlist, args = getopt.getopt(args, 'abc:d:')
   >>> optlist
   [('-a', ''), ('-b', ''), ('-c', 'foo'), ('-d', 'bar')]
   >>> args
   ['a1', 'a2']

Using long option names is equally easy:

   >>> s = '--condition=foo --testing --output-file abc.def -x a1 a2'
   >>> args = s.split()
   >>> args
   ['--condition=foo', '--testing', '--output-file', 'abc.def', '-x', 'a1', 'a2']
   >>> optlist, args = getopt.getopt(args, 'x', [
   ...     'condition=', 'output-file=', 'testing'])
   >>> optlist
   [('--condition', 'foo'), ('--testing', ''), ('--output-file', 'abc.def'), ('-x', '')]
   >>> args
   ['a1', 'a2']

In a script, typical usage is something like this::

   import getopt, sys

   def main():
       try:
           opts, args = getopt.getopt(sys.argv[1:], "ho:v", ["help", "output="])
       except getopt.GetoptError as err:
           # print help information and exit:
           print(err) # will print something like "option -a not recognized"
           usage()
           sys.exit(2)
       output = None
       verbose = False
       for o, a in opts:
           if o == "-v":
               verbose = True
           elif o in ("-h", "--help"):
               usage()
               sys.exit()
           elif o in ("-o", "--output"):
               output = a
           else:
               assert False, "unhandled option"
       # ...

   if __name__ == "__main__":
       main()

Note that an equivalent command line interface could be produced with less code
and more informative help and error messages by using the :mod:`argparse` module::

   import argparse

   if __name__ == '__main__':
       parser = argparse.ArgumentParser()
       parser.add_argument('-o', '--output')
       parser.add_argument('-v', dest='verbose', action='store_true')
       args = parser.parse_args()
       # ... do something with args.output ...
       # ... do something with args.verbose ..

.. seealso::

   Module :mod:`argparse`
      Alternative command line option and argument parsing library.

