1fb224e303435c9b98fd1a24dbd3cf119d7b90b6bBenjamin Peterson# Author: Steven J. Bethard <steven.bethard@gmail.com>. 2a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 3a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson"""Command-line parsing library 4a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 5a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonThis module is an optparse-inspired command-line parsing library that: 6a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 7a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - handles both optional and positional arguments 8a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - produces highly informative usage messages 9a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - supports parsers that dispatch to sub-parsers 10a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 11a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonThe following is a simple usage example that sums integers from the 12a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersoncommand-line and writes the result to a file:: 13a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 14a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser = argparse.ArgumentParser( 15a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson description='sum the integers at the command line') 16a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser.add_argument( 17a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'integers', metavar='int', nargs='+', type=int, 18a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help='an integer to be summed') 19a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser.add_argument( 20a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson '--log', default=sys.stdout, type=argparse.FileType('w'), 21a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help='the file where the sum should be written') 22a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args = parser.parse_args() 23a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args.log.write('%s' % sum(args.integers)) 24a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args.log.close() 25a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 26a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonThe module contains the following public classes: 27a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 28a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - ArgumentParser -- The main entry point for command-line parsing. As the 29a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson example above shows, the add_argument() method is used to populate 30a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson the parser with actions for optional and positional arguments. Then 31a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson the parse_args() method is invoked to convert the args at the 32a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson command-line into an object with attributes. 33a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 34a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - ArgumentError -- The exception raised by ArgumentParser objects when 35a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson there are errors with the parser's actions. Errors raised while 36a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parsing the command-line are caught by ArgumentParser and emitted 37a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson as command-line messages. 38a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 39a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - FileType -- A factory for defining types of files to be created. As the 40a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson example above shows, instances of FileType are typically passed as 41a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson the type= argument of add_argument() calls. 42a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 43a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - Action -- The base class for parser actions. Typically actions are 44a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson selected by passing strings like 'store_true' or 'append_const' to 45a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson the action= argument of add_argument(). However, for greater 46a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson customization of ArgumentParser actions, subclasses of Action may 47a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson be defined and passed as the action= argument. 48a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 49a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - HelpFormatter, RawDescriptionHelpFormatter, RawTextHelpFormatter, 50a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ArgumentDefaultsHelpFormatter -- Formatter classes which 51a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson may be passed as the formatter_class= argument to the 52a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ArgumentParser constructor. HelpFormatter is the default, 53a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson RawDescriptionHelpFormatter and RawTextHelpFormatter tell the parser 54a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson not to change the formatting for help text, and 55a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ArgumentDefaultsHelpFormatter adds information about argument defaults 56a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson to the help. 57a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 58a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonAll other classes in this module are considered implementation details. 59a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson(Also note that HelpFormatter and RawDescriptionHelpFormatter are only 60a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonconsidered public as object names -- the API of the formatter objects is 61a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonstill considered an implementation detail.) 62a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson""" 63a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 64a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson__version__ = '1.1' 65a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson__all__ = [ 66a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'ArgumentParser', 67a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'ArgumentError', 68931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'ArgumentTypeError', 69a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'FileType', 70a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'HelpFormatter', 71931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'ArgumentDefaultsHelpFormatter', 72a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'RawDescriptionHelpFormatter', 73a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'RawTextHelpFormatter', 74931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'Namespace', 75931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'Action', 76931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'ONE_OR_MORE', 77931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'OPTIONAL', 78931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'PARSER', 79931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'REMAINDER', 80931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'SUPPRESS', 81931906a7f5974865c9e928332eb6dd8ba10a91c7Steven Bethard 'ZERO_OR_MORE', 82a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson] 83a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 84a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 85bc3b104e46be0367b46d614f925ef78e4a0225efSteven Bethardimport collections as _collections 86a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonimport copy as _copy 87a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonimport os as _os 88a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonimport re as _re 89a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonimport sys as _sys 90a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonimport textwrap as _textwrap 91a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 92a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonfrom gettext import gettext as _ 93a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 94a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 95a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersondef _callable(obj): 96a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return hasattr(obj, '__call__') or hasattr(obj, '__bases__') 97a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 98a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 99a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonSUPPRESS = '==SUPPRESS==' 100a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 101a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonOPTIONAL = '?' 102a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonZERO_OR_MORE = '*' 103a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonONE_OR_MORE = '+' 104a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonPARSER = 'A...' 105a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin PetersonREMAINDER = '...' 1062e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard_UNRECOGNIZED_ARGS_ATTR = '_unrecognized_args' 107a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 108a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ============================= 109a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# Utility functions and classes 110a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ============================= 111a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 112a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _AttributeHolder(object): 113a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Abstract base class that provides __repr__. 114a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 115a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson The __repr__ method returns a string in the format:: 116a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ClassName(attr=name, attr=name, ...) 117a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson The attributes are determined either by a class-level attribute, 118a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson '_kwarg_names', or by inspecting the instance __dict__. 119a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 120a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 121a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __repr__(self): 122a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type_name = type(self).__name__ 123a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings = [] 124a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for arg in self._get_args(): 125a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings.append(repr(arg)) 126a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for name, value in self._get_kwargs(): 127a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings.append('%s=%r' % (name, value)) 128a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return '%s(%s)' % (type_name, ', '.join(arg_strings)) 129a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 130a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_kwargs(self): 1310e717addd8a03ed10231a578fce894c07ddb157eBenjamin Peterson return sorted(self.__dict__.items()) 132a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 133a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_args(self): 134a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return [] 135a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 136a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 137a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersondef _ensure_value(namespace, name, value): 138a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if getattr(namespace, name, None) is None: 139a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, name, value) 140a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return getattr(namespace, name) 141a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 142a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 143a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# =============== 144a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# Formatting Help 145a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# =============== 146a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 147a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass HelpFormatter(object): 148a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Formatter for generating usage messages and argument help strings. 149a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 150a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Only the name of this class is considered a public API. All the methods 151a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson provided by the class are considered an implementation detail. 152a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 153a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 154a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 155a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prog, 156a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson indent_increment=2, 157a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson max_help_position=24, 158a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson width=None): 159a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 160a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # default setting for width 161a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if width is None: 162a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 163a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson width = int(_os.environ['COLUMNS']) 164a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except (KeyError, ValueError): 165a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson width = 80 166a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson width -= 2 167a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 168a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._prog = prog 169a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._indent_increment = indent_increment 170a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._max_help_position = max_help_position 1719f8621fa7d3562f472b6a16854df51bfb3fdbd5fSerhiy Storchaka self._max_help_position = min(max_help_position, 1729f8621fa7d3562f472b6a16854df51bfb3fdbd5fSerhiy Storchaka max(width - 20, indent_increment * 2)) 173a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._width = width 174a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 175a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_indent = 0 176a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._level = 0 177a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._action_max_length = 0 178a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 179a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._root_section = self._Section(self, None) 180a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_section = self._root_section 181a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 182a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._whitespace_matcher = _re.compile(r'\s+') 183a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._long_break_matcher = _re.compile(r'\n\n\n+') 184a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 185a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # =============================== 186a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Section and indentation methods 187a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # =============================== 188a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _indent(self): 189a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_indent += self._indent_increment 190a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._level += 1 191a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 192a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _dedent(self): 193a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_indent -= self._indent_increment 194a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson assert self._current_indent >= 0, 'Indent decreased below 0.' 195a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._level -= 1 196a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 197a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson class _Section(object): 198a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 199a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, formatter, parent, heading=None): 200a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.formatter = formatter 201a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.parent = parent 202a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.heading = heading 203a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.items = [] 204a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 205a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def format_help(self): 206a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # format the indented section 207a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.parent is not None: 208a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.formatter._indent() 209a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson join = self.formatter._join_parts 210a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for func, args in self.items: 211a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson func(*args) 212a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson item_help = join([func(*args) for func, args in self.items]) 213a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.parent is not None: 214a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.formatter._dedent() 215a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 216a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return nothing if the section was empty 217a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not item_help: 218a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return '' 219a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 220a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add the heading if the section was non-empty 221a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.heading is not SUPPRESS and self.heading is not None: 222a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson current_indent = self.formatter._current_indent 223a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson heading = '%*s%s:\n' % (current_indent, '', self.heading) 224a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 225a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson heading = '' 226a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 227a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # join the section-initial newline, the heading and the help 228a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return join(['\n', heading, item_help, '\n']) 229a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 230a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _add_item(self, func, args): 231a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_section.items.append((func, args)) 232a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 233a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================== 234a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Message building methods 235a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================== 236a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def start_section(self, heading): 237a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._indent() 238a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson section = self._Section(self, self._current_section, heading) 239a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._add_item(section.format_help, []) 240a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_section = section 241a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 242a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def end_section(self): 243a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._current_section = self._current_section.parent 244a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._dedent() 245a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 246a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_text(self, text): 247a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if text is not SUPPRESS and text is not None: 248a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._add_item(self._format_text, [text]) 249a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 250a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_usage(self, usage, actions, groups, prefix=None): 251a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if usage is not SUPPRESS: 252a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args = usage, actions, groups, prefix 253a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._add_item(self._format_usage, args) 254a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 255a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_argument(self, action): 256a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.help is not SUPPRESS: 257a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 258a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # find all invocations 259a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson get_invocation = self._format_action_invocation 260a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson invocations = [get_invocation(action)] 261a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for subaction in self._iter_indented_subactions(action): 262a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson invocations.append(get_invocation(subaction)) 263a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 264a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # update the maximum item length 265a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson invocation_length = max([len(s) for s in invocations]) 266a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_length = invocation_length + self._current_indent 267a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._action_max_length = max(self._action_max_length, 268a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_length) 269a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 270a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add the item to the list 271a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._add_item(self._format_action, [action]) 272a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 273a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_arguments(self, actions): 274a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in actions: 275a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.add_argument(action) 276a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 277a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 278a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Help-formatting methods 279a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 280a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def format_help(self): 281a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help = self._root_section.format_help() 282a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if help: 283a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help = self._long_break_matcher.sub('\n\n', help) 284a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help = help.strip('\n') + '\n' 285a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return help 286a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 287a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _join_parts(self, part_strings): 288a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return ''.join([part 289a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for part in part_strings 290a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if part and part is not SUPPRESS]) 291a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 292a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _format_usage(self, usage, actions, groups, prefix): 293a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if prefix is None: 294a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prefix = _('usage: ') 295a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 296a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if usage is specified, use that 297a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if usage is not None: 298a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson usage = usage % dict(prog=self._prog) 299a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 300a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if no optionals or positionals are available, usage is just prog 301a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif usage is None and not actions: 302a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson usage = '%(prog)s' % dict(prog=self._prog) 303a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 304a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if optionals and positionals are available, calculate usage 305a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif usage is None: 306a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prog = '%(prog)s' % dict(prog=self._prog) 307a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 308a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # split optionals from positionals 309a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson optionals = [] 310a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson positionals = [] 311a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in actions: 312a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.option_strings: 313a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson optionals.append(action) 314a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 315a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson positionals.append(action) 316a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 317a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # build full usage string 318a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson format = self._format_actions_usage 319a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_usage = format(optionals + positionals, groups) 320a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson usage = ' '.join([s for s in [prog, action_usage] if s]) 321a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 322a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # wrap the usage parts if it's too long 323a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text_width = self._width - self._current_indent 324a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if len(prefix) + len(usage) > text_width: 325a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 326a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # break usage into wrappable parts 327a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson part_regexp = r'\(.*?\)+|\[.*?\]+|\S+' 328a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson opt_usage = format(optionals, groups) 329a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pos_usage = format(positionals, groups) 330a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson opt_parts = _re.findall(part_regexp, opt_usage) 331a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pos_parts = _re.findall(part_regexp, pos_usage) 332a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson assert ' '.join(opt_parts) == opt_usage 333a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson assert ' '.join(pos_parts) == pos_usage 334a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 335a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # helper for wrapping lines 336a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def get_lines(parts, indent, prefix=None): 337a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = [] 338a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line = [] 339a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if prefix is not None: 340a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line_len = len(prefix) - 1 341a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 342a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line_len = len(indent) - 1 343a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for part in parts: 3449f8621fa7d3562f472b6a16854df51bfb3fdbd5fSerhiy Storchaka if line_len + 1 + len(part) > text_width and line: 345a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines.append(indent + ' '.join(line)) 346a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line = [] 347a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line_len = len(indent) - 1 348a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line.append(part) 349a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson line_len += len(part) + 1 350a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if line: 351a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines.append(indent + ' '.join(line)) 352a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if prefix is not None: 353a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines[0] = lines[0][len(indent):] 354a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return lines 355a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 356a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if prog is short, follow it with optionals or positionals 357a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if len(prefix) + len(prog) <= 0.75 * text_width: 358a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson indent = ' ' * (len(prefix) + len(prog) + 1) 359a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if opt_parts: 360a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = get_lines([prog] + opt_parts, indent, prefix) 361a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines.extend(get_lines(pos_parts, indent)) 362a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif pos_parts: 363a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = get_lines([prog] + pos_parts, indent, prefix) 364a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 365a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = [prog] 366a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 367a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if prog is long, put it on its own line 368a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 369a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson indent = ' ' * len(prefix) 370a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts = opt_parts + pos_parts 371a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = get_lines(parts, indent) 372a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if len(lines) > 1: 373a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = [] 374a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines.extend(get_lines(opt_parts, indent)) 375a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines.extend(get_lines(pos_parts, indent)) 376a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson lines = [prog] + lines 377a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 378a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # join lines into usage 379a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson usage = '\n'.join(lines) 380a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 381a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # prefix with 'usage:' 382a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return '%s%s\n\n' % (prefix, usage) 383a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 384a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _format_actions_usage(self, actions, groups): 385a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # find group indices and identify actions in groups 3860e717addd8a03ed10231a578fce894c07ddb157eBenjamin Peterson group_actions = set() 387a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson inserts = {} 388a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for group in groups: 389a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 390a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start = actions.index(group._group_actions[0]) 391a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except ValueError: 392a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson continue 393a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 394a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson end = start + len(group._group_actions) 395a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if actions[start:end] == group._group_actions: 396a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in group._group_actions: 397a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group_actions.add(action) 398a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not group.required: 39968c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard if start in inserts: 40068c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard inserts[start] += ' [' 40168c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard else: 40268c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard inserts[start] = '[' 403a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson inserts[end] = ']' 404a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 40568c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard if start in inserts: 40668c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard inserts[start] += ' (' 40768c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard else: 40868c3678253eb0bf1a15537d2725df9af15e2c913Steven Bethard inserts[start] = '(' 409a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson inserts[end] = ')' 410a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for i in range(start + 1, end): 411a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson inserts[i] = '|' 412a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 413a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # collect all actions format strings 414a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts = [] 415a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for i, action in enumerate(actions): 416a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 417a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # suppressed arguments are marked with None 418a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # remove | separators for suppressed arguments 419a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.help is SUPPRESS: 420a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append(None) 421a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if inserts.get(i) == '|': 422a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson inserts.pop(i) 423a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif inserts.get(i + 1) == '|': 424a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson inserts.pop(i + 1) 425a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 426a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # produce all arg strings 427a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif not action.option_strings: 428a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson part = self._format_args(action, action.dest) 429a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 430a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if it's in a group, strip the outer [] 431a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action in group_actions: 432a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if part[0] == '[' and part[-1] == ']': 433a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson part = part[1:-1] 434a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 435a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add the action string to the list 436a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append(part) 437a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 438a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # produce the first way to invoke the option in brackets 439a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 440a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_string = action.option_strings[0] 441a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 442a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the Optional doesn't take a value, format is: 443a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # -s or --long 444a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.nargs == 0: 445a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson part = '%s' % option_string 446a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 447a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the Optional takes a value, format is: 448a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # -s ARGS or --long ARGS 449a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 450a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default = action.dest.upper() 451a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args_string = self._format_args(action, default) 452a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson part = '%s %s' % (option_string, args_string) 453a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 454a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # make it look optional if it's not required or in a group 455a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not action.required and action not in group_actions: 456a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson part = '[%s]' % part 457a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 458a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add the action string to the list 459a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append(part) 460a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 461a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # insert things at the necessary indices 4620e717addd8a03ed10231a578fce894c07ddb157eBenjamin Peterson for i in sorted(inserts, reverse=True): 463a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts[i:i] = [inserts[i]] 464a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 465a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # join all the action items with spaces 466a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = ' '.join([item for item in parts if item is not None]) 467a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 468a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # clean up separators for mutually exclusive groups 469a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson open = r'[\[(]' 470a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson close = r'[\])]' 471a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = _re.sub(r'(%s) ' % open, r'\1', text) 472a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = _re.sub(r' (%s)' % close, r'\1', text) 473a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = _re.sub(r'%s *%s' % (open, close), r'', text) 474a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = _re.sub(r'\(([^|]*)\)', r'\1', text) 475a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = text.strip() 476a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 477a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the text 478a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return text 479a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 480a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _format_text(self, text): 481a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if '%(prog)' in text: 482a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = text % dict(prog=self._prog) 4839f8621fa7d3562f472b6a16854df51bfb3fdbd5fSerhiy Storchaka text_width = max(self._width - self._current_indent, 11) 484a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson indent = ' ' * self._current_indent 485a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._fill_text(text, text_width, indent) + '\n\n' 486a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 487a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _format_action(self, action): 488a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # determine the required width and the entry label 489a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help_position = min(self._action_max_length + 2, 490a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._max_help_position) 4919f8621fa7d3562f472b6a16854df51bfb3fdbd5fSerhiy Storchaka help_width = max(self._width - help_position, 11) 492a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_width = help_position - self._current_indent - 2 493a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_header = self._format_action_invocation(action) 494a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 495a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ho nelp; start on same line and add a final newline 496a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not action.help: 497a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = self._current_indent, '', action_header 498a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_header = '%*s%s\n' % tup 499a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 500a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # short action name; start on the same line and pad two spaces 501a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif len(action_header) <= action_width: 502a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = self._current_indent, '', action_width, action_header 503a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_header = '%*s%-*s ' % tup 504a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson indent_first = 0 505a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 506a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # long action name; start on the next line 507a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 508a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = self._current_indent, '', action_header 509a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_header = '%*s%s\n' % tup 510a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson indent_first = help_position 511a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 512a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # collect the pieces of the action help 513a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts = [action_header] 514a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 515a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if there was help for the action, add lines of help text 516a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.help: 517a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help_text = self._expand_help(action) 518a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help_lines = self._split_lines(help_text, help_width) 519a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append('%*s%s\n' % (indent_first, '', help_lines[0])) 520a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for line in help_lines[1:]: 521a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append('%*s%s\n' % (help_position, '', line)) 522a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 523a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # or add a newline if the description doesn't end with one 524a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif not action_header.endswith('\n'): 525a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append('\n') 526a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 527a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if there are any sub-actions, add their help as well 528a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for subaction in self._iter_indented_subactions(action): 529a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append(self._format_action(subaction)) 530a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 531a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return a single string 532a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._join_parts(parts) 533a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 534a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _format_action_invocation(self, action): 535a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not action.option_strings: 536a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar, = self._metavar_formatter(action, action.dest)(1) 537a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return metavar 538a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 539a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 540a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts = [] 541a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 542a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the Optional doesn't take a value, format is: 543a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # -s, --long 544a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.nargs == 0: 545a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.extend(action.option_strings) 546a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 547a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the Optional takes a value, format is: 548a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # -s ARGS, --long ARGS 549a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 550a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default = action.dest.upper() 551a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args_string = self._format_args(action, default) 552a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in action.option_strings: 553a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parts.append('%s %s' % (option_string, args_string)) 554a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 555a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return ', '.join(parts) 556a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 557a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _metavar_formatter(self, action, default_metavar): 558a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.metavar is not None: 559a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = action.metavar 560a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.choices is not None: 561a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choice_strs = [str(choice) for choice in action.choices] 562a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '{%s}' % ','.join(choice_strs) 563a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 564a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = default_metavar 565a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 566a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def format(tuple_size): 567a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if isinstance(result, tuple): 568a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return result 569a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 570a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return (result, ) * tuple_size 571a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return format 572a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 573a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _format_args(self, action, default_metavar): 574a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson get_metavar = self._metavar_formatter(action, default_metavar) 575a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.nargs is None: 576a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '%s' % get_metavar(1) 577a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == OPTIONAL: 578a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '[%s]' % get_metavar(1) 579a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == ZERO_OR_MORE: 580a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '[%s [%s ...]]' % get_metavar(2) 581a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == ONE_OR_MORE: 582a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '%s [%s ...]' % get_metavar(2) 583a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == REMAINDER: 584a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '...' 585a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == PARSER: 586a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = '%s ...' % get_metavar(1) 587a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 588a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formats = ['%s' for _ in range(action.nargs)] 589a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = ' '.join(formats) % get_metavar(action.nargs) 590a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return result 591a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 592a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _expand_help(self, action): 593a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson params = dict(vars(action), prog=self._prog) 594a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for name in list(params): 595a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if params[name] is SUPPRESS: 596a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson del params[name] 597a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for name in list(params): 598a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if hasattr(params[name], '__name__'): 599a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson params[name] = params[name].__name__ 600a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if params.get('choices') is not None: 601a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices_str = ', '.join([str(c) for c in params['choices']]) 602a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson params['choices'] = choices_str 603a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._get_help_string(action) % params 604a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 605a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _iter_indented_subactions(self, action): 606a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 607a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson get_subactions = action._get_subactions 608a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except AttributeError: 609a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pass 610a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 611a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._indent() 612a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for subaction in get_subactions(): 613a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson yield subaction 614a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._dedent() 615a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 616a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _split_lines(self, text, width): 617a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = self._whitespace_matcher.sub(' ', text).strip() 618a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return _textwrap.wrap(text, width) 619a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 620a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _fill_text(self, text, width, indent): 621a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson text = self._whitespace_matcher.sub(' ', text).strip() 622a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return _textwrap.fill(text, width, initial_indent=indent, 623a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson subsequent_indent=indent) 624a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 625a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_help_string(self, action): 626a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action.help 627a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 628a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 629a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass RawDescriptionHelpFormatter(HelpFormatter): 630a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Help message formatter which retains any formatting in descriptions. 631a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 632a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Only the name of this class is considered a public API. All the methods 633a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson provided by the class are considered an implementation detail. 634a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 635a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 636a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _fill_text(self, text, width, indent): 637a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return ''.join([indent + line for line in text.splitlines(True)]) 638a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 639a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 640a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass RawTextHelpFormatter(RawDescriptionHelpFormatter): 641a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Help message formatter which retains formatting of all help text. 642a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 643a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Only the name of this class is considered a public API. All the methods 644a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson provided by the class are considered an implementation detail. 645a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 646a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 647a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _split_lines(self, text, width): 648a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return text.splitlines() 649a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 650a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 651a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass ArgumentDefaultsHelpFormatter(HelpFormatter): 652a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Help message formatter which adds default values to argument help. 653a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 654a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Only the name of this class is considered a public API. All the methods 655a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson provided by the class are considered an implementation detail. 656a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 657a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 658a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_help_string(self, action): 659a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help = action.help 660a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if '%(default)' not in action.help: 661a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.default is not SUPPRESS: 662a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson defaulting_nargs = [OPTIONAL, ZERO_OR_MORE] 663a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.option_strings or action.nargs in defaulting_nargs: 664a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help += ' (default: %(default)s)' 665a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return help 666a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 667a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 668a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ===================== 669a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# Options and Arguments 670a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ===================== 671a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 672a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersondef _get_action_name(argument): 673a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if argument is None: 674a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 675a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif argument.option_strings: 676a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return '/'.join(argument.option_strings) 677a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif argument.metavar not in (None, SUPPRESS): 678a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return argument.metavar 679a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif argument.dest not in (None, SUPPRESS): 680a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return argument.dest 681a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 682a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 683a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 684a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 685a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass ArgumentError(Exception): 686a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """An error from creating or using an argument (optional or positional). 687a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 688a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson The string value of this exception is the message, augmented with 689a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson information about the argument that caused it. 690a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 691a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 692a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, argument, message): 693a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.argument_name = _get_action_name(argument) 694a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.message = message 695a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 696a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __str__(self): 697a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.argument_name is None: 698a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson format = '%(message)s' 699a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 700a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson format = 'argument %(argument_name)s: %(message)s' 701a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return format % dict(message=self.message, 702a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson argument_name=self.argument_name) 703a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 704a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 705a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass ArgumentTypeError(Exception): 706a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """An error from trying to convert a command line string to a type.""" 707a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pass 708a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 709a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 710a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ============== 711a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# Action classes 712a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ============== 713a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 714a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass Action(_AttributeHolder): 715a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Information about how to convert command line strings to Python objects. 716a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 717a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Action objects are used by an ArgumentParser to represent the information 718a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson needed to parse a single argument from one or more strings from the 719a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson command line. The keyword arguments to the Action constructor are also 720a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson all attributes of Action instances. 721a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 722a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Keyword Arguments: 723a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 724a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - option_strings -- A list of command-line option strings which 725a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson should be associated with this action. 726a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 727a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - dest -- The name of the attribute to hold the created object(s) 728a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 729a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - nargs -- The number of command-line arguments that should be 730a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson consumed. By default, one argument will be consumed and a single 731a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value will be produced. Other values include: 732a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - N (an integer) consumes N arguments (and produces a list) 733a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - '?' consumes zero or one arguments 734a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - '*' consumes zero or more arguments (and produces a list) 735a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - '+' consumes one or more arguments (and produces a list) 736a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Note that the difference between the default and nargs=1 is that 737a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson with the default, a single value will be produced, while with 738a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=1, a list containing a single value will be produced. 739a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 740a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - const -- The value to be produced if the option is specified and the 741a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option uses an action that takes no values. 742a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 743a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - default -- The value to be produced if the option is not specified. 744a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 7451a2c1fbfd2208407e1af365b161276b6f103c1adR David Murray - type -- A callable that accepts a single string argument, and 7461a2c1fbfd2208407e1af365b161276b6f103c1adR David Murray returns the converted value. The standard Python types str, int, 7471a2c1fbfd2208407e1af365b161276b6f103c1adR David Murray float, and complex are useful examples of such callables. If None, 7481a2c1fbfd2208407e1af365b161276b6f103c1adR David Murray str is used. 749a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 750a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - choices -- A container of values that should be allowed. If not None, 751a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson after a command-line argument has been converted to the appropriate 752a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type, an exception will be raised if it is not a member of this 753a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson collection. 754a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 755a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - required -- True if the action must always be specified at the 756a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson command line. This is only meaningful for optional command-line 757a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arguments. 758a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 759a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - help -- The help string describing the argument. 760a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 761a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - metavar -- The name to be used for the option's argument with the 762a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help string. If None, the 'dest' value will be used as the name. 763a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 764a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 765a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 766a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 767a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 768a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=None, 769a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=None, 770a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=None, 771a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type=None, 772a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices=None, 773a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 774a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None, 775a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=None): 776a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.option_strings = option_strings 777a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.dest = dest 778a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.nargs = nargs 779a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.const = const 780a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.default = default 781a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.type = type 782a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.choices = choices 783a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.required = required 784a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.help = help 785a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.metavar = metavar 786a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 787a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_kwargs(self): 788a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson names = [ 789a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'option_strings', 790a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'dest', 791a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'nargs', 792a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'const', 793a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'default', 794a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'type', 795a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'choices', 796a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'help', 797a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'metavar', 798a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ] 799a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return [(name, getattr(self, name)) for name in names] 800a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 801a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 802a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise NotImplementedError(_('.__call__() not defined')) 803a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 804a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 805a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _StoreAction(Action): 806a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 807a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 808a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 809a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 810a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=None, 811a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=None, 812a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=None, 813a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type=None, 814a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices=None, 815a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 816a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None, 817a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=None): 818a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if nargs == 0: 819a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError('nargs for store actions must be > 0; if you ' 820a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'have nothing to store, actions such as store ' 821a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'true or store const may be more appropriate') 822a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if const is not None and nargs != OPTIONAL: 823a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError('nargs must be %r to supply const' % OPTIONAL) 824a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_StoreAction, self).__init__( 825a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 826a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 827a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=nargs, 828a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=const, 829a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 830a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type=type, 831a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices=choices, 832a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 833a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help, 834a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=metavar) 835a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 836a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 837a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, self.dest, values) 838a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 839a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 840a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _StoreConstAction(Action): 841a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 842a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 843a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 844a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 845a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const, 846a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=None, 847a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 848a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None, 849a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=None): 850a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_StoreConstAction, self).__init__( 851a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 852a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 853a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=0, 854a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=const, 855a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 856a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 857a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help) 858a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 859a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 860a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, self.dest, self.const) 861a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 862a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 863a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _StoreTrueAction(_StoreConstAction): 864a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 865a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 866a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 867a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 868a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=False, 869a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 870a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None): 871a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_StoreTrueAction, self).__init__( 872a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 873a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 874a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=True, 875a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 876a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 877a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help) 878a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 879a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 880a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _StoreFalseAction(_StoreConstAction): 881a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 882a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 883a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 884a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 885a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=True, 886a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 887a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None): 888a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_StoreFalseAction, self).__init__( 889a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 890a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 891a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=False, 892a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 893a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 894a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help) 895a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 896a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 897a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _AppendAction(Action): 898a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 899a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 900a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 901a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 902a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=None, 903a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=None, 904a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=None, 905a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type=None, 906a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices=None, 907a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 908a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None, 909a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=None): 910a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if nargs == 0: 911a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError('nargs for append actions must be > 0; if arg ' 912a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'strings are not supplying the value to append, ' 913a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'the append const action may be more appropriate') 914a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if const is not None and nargs != OPTIONAL: 915a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError('nargs must be %r to supply const' % OPTIONAL) 916a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_AppendAction, self).__init__( 917a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 918a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 919a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=nargs, 920a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=const, 921a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 922a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type=type, 923a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices=choices, 924a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 925a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help, 926a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=metavar) 927a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 928a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 929a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson items = _copy.copy(_ensure_value(namespace, self.dest, [])) 930a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson items.append(values) 931a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, self.dest, items) 932a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 933a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 934a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _AppendConstAction(Action): 935a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 936a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 937a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 938a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 939a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const, 940a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=None, 941a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 942a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None, 943a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=None): 944a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_AppendConstAction, self).__init__( 945a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 946a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 947a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=0, 948a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson const=const, 949a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 950a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 951a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help, 952a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=metavar) 953a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 954a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 955a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson items = _copy.copy(_ensure_value(namespace, self.dest, [])) 956a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson items.append(self.const) 957a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, self.dest, items) 958a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 959a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 960a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _CountAction(Action): 961a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 962a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 963a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 964a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest, 965a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=None, 966a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=False, 967a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None): 968a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_CountAction, self).__init__( 969a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 970a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 971a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=0, 972a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 973a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=required, 974a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help) 975a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 976a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 977a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson new_count = _ensure_value(namespace, self.dest, 0) + 1 978a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, self.dest, new_count) 979a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 980a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 981a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _HelpAction(Action): 982a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 983a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 984a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 985a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=SUPPRESS, 986a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=SUPPRESS, 987a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None): 988a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_HelpAction, self).__init__( 989a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 990a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 991a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 992a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=0, 993a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help) 994a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 995a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 996a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser.print_help() 997a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser.exit() 998a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 999a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1000a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _VersionAction(Action): 1001a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1002a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 1003a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 1004a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson version=None, 1005a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=SUPPRESS, 1006a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=SUPPRESS, 1007dce6e1bd5a5b41b22be10ba119fb5b6d5546959aSteven Bethard help="show program's version number and exit"): 1008a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_VersionAction, self).__init__( 1009a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 1010a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 1011a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default=default, 1012a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=0, 1013a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help) 1014a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.version = version 1015a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1016a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 1017a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson version = self.version 1018a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if version is None: 1019a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson version = parser.version 1020a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter = parser._get_formatter() 1021a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_text(version) 1022a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser.exit(message=formatter.format_help()) 1023a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1024a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1025a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _SubParsersAction(Action): 1026a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1027a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson class _ChoicesPseudoAction(Action): 1028a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1029a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, name, help): 1030a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson sup = super(_SubParsersAction._ChoicesPseudoAction, self) 1031a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson sup.__init__(option_strings=[], dest=name, help=help) 1032a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1033a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 1034a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings, 1035a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prog, 1036a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser_class, 1037a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=SUPPRESS, 1038a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=None, 1039a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=None): 1040a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1041a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._prog_prefix = prog 1042a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._parser_class = parser_class 1043bc3b104e46be0367b46d614f925ef78e4a0225efSteven Bethard self._name_parser_map = _collections.OrderedDict() 1044a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._choices_actions = [] 1045a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1046a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_SubParsersAction, self).__init__( 1047a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings=option_strings, 1048a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest=dest, 1049a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs=PARSER, 1050a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choices=self._name_parser_map, 1051a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=help, 1052a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson metavar=metavar) 1053a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1054a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_parser(self, name, **kwargs): 1055a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # set prog from the existing prefix 1056a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if kwargs.get('prog') is None: 1057a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs['prog'] = '%s %s' % (self._prog_prefix, name) 1058a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1059a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # create a pseudo-action to hold the choice help 1060a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if 'help' in kwargs: 1061a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help = kwargs.pop('help') 1062a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson choice_action = self._ChoicesPseudoAction(name, help) 1063a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._choices_actions.append(choice_action) 1064a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1065a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # create the parser and add it to the map 1066a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser = self._parser_class(**kwargs) 1067a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._name_parser_map[name] = parser 1068a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return parser 1069a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1070a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_subactions(self): 1071a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._choices_actions 1072a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1073a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, parser, namespace, values, option_string=None): 1074a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser_name = values[0] 1075a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings = values[1:] 1076a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1077a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # set the parser name if requested 1078a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.dest is not SUPPRESS: 1079a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, self.dest, parser_name) 1080a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1081a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # select the parser 1082a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 1083a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parser = self._name_parser_map[parser_name] 1084a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except KeyError: 1085a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = parser_name, ', '.join(self._name_parser_map) 1086fb3de6b437ba92701e162eb830bbc775cda135b5Éric Araujo msg = _('unknown parser %r (choices: %s)') % tup 1087a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(self, msg) 1088a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1089a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # parse all the remaining options into the namespace 10902e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard # store any unrecognized options on the object, so that the top 10912e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard # level parser can decide what to do with them 1092af26c15110b76195e62a06d17e39176d42c0511cR David Murray 1093af26c15110b76195e62a06d17e39176d42c0511cR David Murray # In case this subparser defines new defaults, we parse them 1094af26c15110b76195e62a06d17e39176d42c0511cR David Murray # in a new namespace object and then update the original 1095af26c15110b76195e62a06d17e39176d42c0511cR David Murray # namespace for the relevant parts. 1096af26c15110b76195e62a06d17e39176d42c0511cR David Murray subnamespace, arg_strings = parser.parse_known_args(arg_strings, None) 1097af26c15110b76195e62a06d17e39176d42c0511cR David Murray for key, value in vars(subnamespace).items(): 1098af26c15110b76195e62a06d17e39176d42c0511cR David Murray setattr(namespace, key, value) 1099af26c15110b76195e62a06d17e39176d42c0511cR David Murray 11002e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard if arg_strings: 11012e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard vars(namespace).setdefault(_UNRECOGNIZED_ARGS_ATTR, []) 11022e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard getattr(namespace, _UNRECOGNIZED_ARGS_ATTR).extend(arg_strings) 1103a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1104a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1105a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ============== 1106a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# Type classes 1107a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# ============== 1108a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1109a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass FileType(object): 1110a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Factory for creating file object types 1111a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1112a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Instances of FileType are typically passed as type= arguments to the 1113a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ArgumentParser add_argument() method. 1114a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1115a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Keyword Arguments: 1116a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - mode -- A string indicating how the file is to be opened. Accepts the 1117a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson same values as the builtin open() function. 1118a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - bufsize -- The file's desired buffer size. Accepts the same values as 1119a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson the builtin open() function. 1120a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 1121a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1122f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard def __init__(self, mode='r', bufsize=-1): 1123a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._mode = mode 1124a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._bufsize = bufsize 1125a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1126a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __call__(self, string): 1127a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # the special argument "-" means sys.std{in,out} 1128a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if string == '-': 1129a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if 'r' in self._mode: 1130a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return _sys.stdin 1131a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif 'w' in self._mode: 1132a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return _sys.stdout 1133a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1134fb3de6b437ba92701e162eb830bbc775cda135b5Éric Araujo msg = _('argument "-" with mode %r') % self._mode 1135a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError(msg) 1136a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1137a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # all other arguments are used as file names 1138f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard try: 1139a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return open(string, self._mode, self._bufsize) 1140f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard except IOError as e: 1141f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard message = _("can't open '%s': %s") 1142f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard raise ArgumentTypeError(message % (string, e)) 1143a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1144a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __repr__(self): 1145f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard args = self._mode, self._bufsize 1146f8583acb534432097671e79eb4110b9861dd2e17Steven Bethard args_str = ', '.join(repr(arg) for arg in args if arg != -1) 1147a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return '%s(%s)' % (type(self).__name__, args_str) 1148a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1149a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# =========================== 1150a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# Optional and Positional Parsing 1151a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson# =========================== 1152a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1153a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass Namespace(_AttributeHolder): 1154a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Simple object for storing attributes. 1155a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1156a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Implements equality by attribute names and values, and provides a simple 1157a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson string representation. 1158a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 1159a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1160a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, **kwargs): 1161a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for name in kwargs: 1162a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(self, name, kwargs[name]) 1163a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 11646b31fd0f13f5730b5a9b70be91a0edba3781e194Benjamin Peterson __hash__ = None 11656b31fd0f13f5730b5a9b70be91a0edba3781e194Benjamin Peterson 1166a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __eq__(self, other): 1167fb8899a597c5ef39706215a894fc8c5f5dbf85bcRaymond Hettinger if not isinstance(other, Namespace): 1168fb8899a597c5ef39706215a894fc8c5f5dbf85bcRaymond Hettinger return NotImplemented 1169a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return vars(self) == vars(other) 1170a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1171a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __ne__(self, other): 1172fb8899a597c5ef39706215a894fc8c5f5dbf85bcRaymond Hettinger if not isinstance(other, Namespace): 1173fb8899a597c5ef39706215a894fc8c5f5dbf85bcRaymond Hettinger return NotImplemented 1174a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return not (self == other) 1175a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1176a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __contains__(self, key): 1177a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return key in self.__dict__ 1178a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1179a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1180a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _ActionsContainer(object): 1181a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1182a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 1183a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson description, 1184a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prefix_chars, 1185a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson argument_default, 1186a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_handler): 1187a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_ActionsContainer, self).__init__() 1188a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1189a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.description = description 1190a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.argument_default = argument_default 1191a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.prefix_chars = prefix_chars 1192a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.conflict_handler = conflict_handler 1193a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1194a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # set up registries 1195a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._registries = {} 1196a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1197a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # register actions 1198a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', None, _StoreAction) 1199a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'store', _StoreAction) 1200a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'store_const', _StoreConstAction) 1201a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'store_true', _StoreTrueAction) 1202a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'store_false', _StoreFalseAction) 1203a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'append', _AppendAction) 1204a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'append_const', _AppendConstAction) 1205a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'count', _CountAction) 1206a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'help', _HelpAction) 1207a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'version', _VersionAction) 1208a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('action', 'parsers', _SubParsersAction) 1209a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1210a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # raise an exception if the conflict handler is invalid 1211a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._get_handler() 1212a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1213a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # action storage 1214a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._actions = [] 1215a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._option_string_actions = {} 1216a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1217a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # groups 1218a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._action_groups = [] 1219a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._mutually_exclusive_groups = [] 1220a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1221a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # defaults storage 1222a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._defaults = {} 1223a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1224a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # determines whether an "option" looks like a negative number 1225a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._negative_number_matcher = _re.compile(r'^-\d+$|^-\d*\.\d+$') 1226a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1227a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # whether or not there are any optionals that look like negative 1228a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # numbers -- uses a list so it can be shared and edited 1229a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._has_negative_number_optionals = [] 1230a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1231a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ==================== 1232a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Registration methods 1233a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ==================== 1234a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def register(self, registry_name, value, object): 1235a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson registry = self._registries.setdefault(registry_name, {}) 1236a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson registry[value] = object 1237a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1238a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _registry_get(self, registry_name, value, default=None): 1239a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._registries[registry_name].get(value, default) 1240a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1241a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ================================== 1242a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Namespace default accessor methods 1243a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ================================== 1244a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def set_defaults(self, **kwargs): 1245a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._defaults.update(kwargs) 1246a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1247a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if these defaults match any existing arguments, replace 1248a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # the previous default on the object with the new one 1249a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in self._actions: 1250a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.dest in kwargs: 1251a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action.default = kwargs[action.dest] 1252a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1253a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def get_default(self, dest): 1254a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in self._actions: 1255a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.dest == dest and action.default is not None: 1256a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action.default 1257a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._defaults.get(dest, None) 1258a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1259a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1260a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 1261a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Adding argument actions 1262a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 1263a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_argument(self, *args, **kwargs): 1264a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 1265a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson add_argument(dest, ..., name=value, ...) 1266a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson add_argument(option_string, option_string, ..., name=value, ...) 1267a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 1268a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1269a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if no positional args are supplied or only one is supplied and 1270a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # it doesn't look like an option string, parse a positional 1271a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # argument 1272a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson chars = self.prefix_chars 1273a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not args or len(args) == 1 and args[0][0] not in chars: 1274a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if args and 'dest' in kwargs: 1275a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError('dest supplied twice for positional argument') 1276a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs = self._get_positional_kwargs(*args, **kwargs) 1277a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1278a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # otherwise, we're adding an optional argument 1279a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1280a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs = self._get_optional_kwargs(*args, **kwargs) 1281a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1282a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if no default was supplied, use the parser-level default 1283a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if 'default' not in kwargs: 1284a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest = kwargs['dest'] 1285a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if dest in self._defaults: 1286a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs['default'] = self._defaults[dest] 1287a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif self.argument_default is not None: 1288a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs['default'] = self.argument_default 1289a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1290a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # create the action object, and add it to the parser 1291a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_class = self._pop_action_class(kwargs) 1292a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not _callable(action_class): 1293e3c11b44e37e80371fcaf71880e659a78360e8b6Steven Bethard raise ValueError('unknown action "%s"' % (action_class,)) 1294a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = action_class(**kwargs) 1295a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1296a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # raise an error if the action type is not callable 1297a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type_func = self._registry_get('type', action.type, action.type) 1298a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not _callable(type_func): 1299e3c11b44e37e80371fcaf71880e659a78360e8b6Steven Bethard raise ValueError('%r is not callable' % (type_func,)) 1300a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1301539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard # raise an error if the metavar does not match the type 1302539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard if hasattr(self, "_get_formatter"): 1303539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard try: 1304539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard self._get_formatter()._format_args(action, None) 1305539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard except TypeError: 1306539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard raise ValueError("length of metavar tuple does not match nargs") 1307539586296d64a51cd58c8c45a7dd850cdcc05fccSteven Bethard 1308a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._add_action(action) 1309a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1310a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_argument_group(self, *args, **kwargs): 1311a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group = _ArgumentGroup(self, *args, **kwargs) 1312a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._action_groups.append(group) 1313a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return group 1314a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1315a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_mutually_exclusive_group(self, **kwargs): 1316a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group = _MutuallyExclusiveGroup(self, **kwargs) 1317a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._mutually_exclusive_groups.append(group) 1318a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return group 1319a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1320a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _add_action(self, action): 1321a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # resolve any conflicts 1322a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._check_conflict(action) 1323a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1324a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add to actions list 1325a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._actions.append(action) 1326a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action.container = self 1327a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1328a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # index the action by any option strings it has 1329a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in action.option_strings: 1330a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._option_string_actions[option_string] = action 1331a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1332a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # set the flag if any option strings look like negative numbers 1333a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in action.option_strings: 1334a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self._negative_number_matcher.match(option_string): 1335a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not self._has_negative_number_optionals: 1336a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._has_negative_number_optionals.append(True) 1337a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1338a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the created action 1339a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action 1340a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1341a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _remove_action(self, action): 1342a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._actions.remove(action) 1343a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1344a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _add_container_actions(self, container): 1345a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # collect groups by titles 1346a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson title_group_map = {} 1347a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for group in self._action_groups: 1348a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if group.title in title_group_map: 1349a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('cannot merge actions - two groups are named %r') 1350a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError(msg % (group.title)) 1351a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson title_group_map[group.title] = group 1352a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1353a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # map each action to its group 1354a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group_map = {} 1355a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for group in container._action_groups: 1356a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1357a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if a group with the title exists, use that, otherwise 1358a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # create a new group matching the container's group 1359a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if group.title not in title_group_map: 1360a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson title_group_map[group.title] = self.add_argument_group( 1361a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson title=group.title, 1362a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson description=group.description, 1363a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_handler=group.conflict_handler) 1364a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1365a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # map the actions to their new group 1366a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in group._group_actions: 1367a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group_map[action] = title_group_map[group.title] 1368a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1369a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add container's mutually exclusive groups 1370a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # NOTE: if add_mutually_exclusive_group ever gains title= and 1371a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # description= then this code will need to be expanded as above 1372a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for group in container._mutually_exclusive_groups: 1373a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson mutex_group = self.add_mutually_exclusive_group( 1374a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson required=group.required) 1375a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1376a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # map the actions to their new mutex group 1377a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in group._group_actions: 1378a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group_map[action] = mutex_group 1379a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1380a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add all actions to this container or their group 1381a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in container._actions: 1382a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group_map.get(action, self)._add_action(action) 1383a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1384a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_positional_kwargs(self, dest, **kwargs): 1385a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # make sure required is not specified 1386a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if 'required' in kwargs: 1387a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _("'required' is an invalid argument for positionals") 1388a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise TypeError(msg) 1389a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1390a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # mark positional arguments as required if at least one is 1391a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # always required 1392a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if kwargs.get('nargs') not in [OPTIONAL, ZERO_OR_MORE]: 1393a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs['required'] = True 1394a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if kwargs.get('nargs') == ZERO_OR_MORE and 'default' not in kwargs: 1395a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs['required'] = True 1396a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1397a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the keyword arguments with no option strings 1398a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return dict(kwargs, dest=dest, option_strings=[]) 1399a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1400a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_optional_kwargs(self, *args, **kwargs): 1401a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # determine short and long option strings 1402a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings = [] 1403a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson long_option_strings = [] 1404a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in args: 1405a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # error on strings that don't start with an appropriate prefix 1406a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not option_string[0] in self.prefix_chars: 1407a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('invalid option string %r: ' 1408a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'must start with a character %r') 1409a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = option_string, self.prefix_chars 1410a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError(msg % tup) 1411a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1412a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # strings starting with two prefix characters are long options 1413a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_strings.append(option_string) 1414a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string[0] in self.prefix_chars: 1415a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if len(option_string) > 1: 1416a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string[1] in self.prefix_chars: 1417a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson long_option_strings.append(option_string) 1418a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1419a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # infer destination, '--foo-bar' -> 'foo_bar' and '-x' -> 'x' 1420a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest = kwargs.pop('dest', None) 1421a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if dest is None: 1422a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if long_option_strings: 1423a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest_option_string = long_option_strings[0] 1424a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1425a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest_option_string = option_strings[0] 1426a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest = dest_option_string.lstrip(self.prefix_chars) 1427a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not dest: 1428a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('dest= is required for options like %r') 1429a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError(msg % option_string) 1430a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson dest = dest.replace('-', '_') 1431a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1432a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the updated keyword arguments 1433a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return dict(kwargs, dest=dest, option_strings=option_strings) 1434a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1435a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _pop_action_class(self, kwargs, default=None): 1436a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = kwargs.pop('action', default) 1437a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self._registry_get('action', action, action) 1438a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1439a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_handler(self): 1440a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # determine function from conflict handler string 1441a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson handler_func_name = '_handle_conflict_%s' % self.conflict_handler 1442a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 1443a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return getattr(self, handler_func_name) 1444a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except AttributeError: 1445a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('invalid conflict_resolution value: %r') 1446a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError(msg % self.conflict_handler) 1447a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1448a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _check_conflict(self, action): 1449a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1450a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # find all options that conflict with this option 1451a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson confl_optionals = [] 1452a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in action.option_strings: 1453a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string in self._option_string_actions: 1454a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson confl_optional = self._option_string_actions[option_string] 1455a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson confl_optionals.append((option_string, confl_optional)) 1456a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1457a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # resolve any conflicts 1458a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if confl_optionals: 1459a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_handler = self._get_handler() 1460a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_handler(action, confl_optionals) 1461a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1462a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _handle_conflict_error(self, action, conflicting_actions): 1463a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson message = _('conflicting option string(s): %s') 1464a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_string = ', '.join([option_string 1465a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string, action 1466a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson in conflicting_actions]) 1467a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, message % conflict_string) 1468a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1469a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _handle_conflict_resolve(self, action, conflicting_actions): 1470a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1471a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # remove all conflicting options 1472a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string, action in conflicting_actions: 1473a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1474a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # remove the conflicting option 1475a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action.option_strings.remove(option_string) 1476a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._option_string_actions.pop(option_string, None) 1477a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1478a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the option now has no option string, remove it from the 1479a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # container holding it 1480a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not action.option_strings: 1481a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action.container._remove_action(action) 1482a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1483a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1484a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _ArgumentGroup(_ActionsContainer): 1485a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1486a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, container, title=None, description=None, **kwargs): 1487a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add any missing keyword arguments by checking the container 1488a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson update = kwargs.setdefault 1489a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson update('conflict_handler', container.conflict_handler) 1490a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson update('prefix_chars', container.prefix_chars) 1491a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson update('argument_default', container.argument_default) 1492a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super_init = super(_ArgumentGroup, self).__init__ 1493a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super_init(description=description, **kwargs) 1494a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1495a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # group attributes 1496a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.title = title 1497a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._group_actions = [] 1498a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1499a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # share most attributes with the container 1500a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._registries = container._registries 1501a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._actions = container._actions 1502a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._option_string_actions = container._option_string_actions 1503a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._defaults = container._defaults 1504a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._has_negative_number_optionals = \ 1505a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson container._has_negative_number_optionals 15067f41b88bb7b978205a438c7eea2b7f6bba6862d0Steven Bethard self._mutually_exclusive_groups = container._mutually_exclusive_groups 1507a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1508a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _add_action(self, action): 1509a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = super(_ArgumentGroup, self)._add_action(action) 1510a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._group_actions.append(action) 1511a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action 1512a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1513a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _remove_action(self, action): 1514a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_ArgumentGroup, self)._remove_action(action) 1515a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._group_actions.remove(action) 1516a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1517a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1518a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass _MutuallyExclusiveGroup(_ArgumentGroup): 1519a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1520a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, container, required=False): 1521a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson super(_MutuallyExclusiveGroup, self).__init__(container) 1522a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.required = required 1523a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._container = container 1524a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1525a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _add_action(self, action): 1526a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.required: 1527a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('mutually exclusive arguments must be optional') 1528a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ValueError(msg) 1529a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = self._container._add_action(action) 1530a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._group_actions.append(action) 1531a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action 1532a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1533a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _remove_action(self, action): 1534a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._container._remove_action(action) 1535a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._group_actions.remove(action) 1536a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1537a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1538a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Petersonclass ArgumentParser(_AttributeHolder, _ActionsContainer): 1539a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Object for parsing command line strings into Python objects. 1540a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1541a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Keyword Arguments: 1542a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - prog -- The name of the program (default: sys.argv[0]) 1543a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - usage -- A usage message (default: auto-generated from arguments) 1544a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - description -- A description of what the program does 1545a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - epilog -- Text following the argument descriptions 1546a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - parents -- Parsers whose arguments should be copied into this one 1547a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - formatter_class -- HelpFormatter class for printing help messages 1548a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - prefix_chars -- Characters that prefix optional arguments 1549a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - fromfile_prefix_chars -- Characters that prefix files containing 1550a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson additional arguments 1551a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - argument_default -- The default value for all arguments 1552a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - conflict_handler -- String indicating how to handle conflicts 1553a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson - add_help -- Add a -h/-help option 1554a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 1555a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1556a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def __init__(self, 1557a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prog=None, 1558a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson usage=None, 1559a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson description=None, 1560a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson epilog=None, 1561a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson version=None, 1562a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parents=[], 1563a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter_class=HelpFormatter, 1564a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prefix_chars='-', 1565a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson fromfile_prefix_chars=None, 1566a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson argument_default=None, 1567a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_handler='error', 1568a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson add_help=True): 1569a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1570a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if version is not None: 1571a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson import warnings 1572a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson warnings.warn( 1573a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """The "version" argument to ArgumentParser is deprecated. """ 1574a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """Please use """ 1575a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """"add_argument(..., action='version', version="N", ...)" """ 1576a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """instead""", DeprecationWarning) 1577a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1578a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson superinit = super(ArgumentParser, self).__init__ 1579a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson superinit(description=description, 1580a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prefix_chars=prefix_chars, 1581a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson argument_default=argument_default, 1582a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflict_handler=conflict_handler) 1583a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1584a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # default setting for prog 1585a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if prog is None: 1586a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson prog = _os.path.basename(_sys.argv[0]) 1587a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1588a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.prog = prog 1589a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.usage = usage 1590a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.epilog = epilog 1591a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.version = version 1592a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.formatter_class = formatter_class 1593a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.fromfile_prefix_chars = fromfile_prefix_chars 1594a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.add_help = add_help 1595a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1596a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson add_group = self.add_argument_group 1597a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._positionals = add_group(_('positional arguments')) 1598a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._optionals = add_group(_('optional arguments')) 1599a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._subparsers = None 1600a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1601a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # register types 1602a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def identity(string): 1603a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return string 1604a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.register('type', None, identity) 1605a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1606a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add help and version arguments if necessary 1607a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # (using explicit default to override global argument_default) 16081cbf78e040b1ddfe7a1520d21ea34e1098848713R. David Murray default_prefix = '-' if '-' in prefix_chars else prefix_chars[0] 1609a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.add_help: 1610a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.add_argument( 16111cbf78e040b1ddfe7a1520d21ea34e1098848713R. David Murray default_prefix+'h', default_prefix*2+'help', 16121cbf78e040b1ddfe7a1520d21ea34e1098848713R. David Murray action='help', default=SUPPRESS, 1613a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=_('show this help message and exit')) 1614a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.version: 1615a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.add_argument( 16161cbf78e040b1ddfe7a1520d21ea34e1098848713R. David Murray default_prefix+'v', default_prefix*2+'version', 16171cbf78e040b1ddfe7a1520d21ea34e1098848713R. David Murray action='version', default=SUPPRESS, 1618a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson version=self.version, 1619a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson help=_("show program's version number and exit")) 1620a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1621a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add parent arguments and defaults 1622a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for parent in parents: 1623a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._add_container_actions(parent) 1624a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 1625a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson defaults = parent._defaults 1626a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except AttributeError: 1627a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pass 1628a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1629a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._defaults.update(defaults) 1630a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1631a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 1632a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Pretty __repr__ methods 1633a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 1634a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_kwargs(self): 1635a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson names = [ 1636a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'prog', 1637a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'usage', 1638a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'description', 1639a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'version', 1640a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'formatter_class', 1641a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'conflict_handler', 1642a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'add_help', 1643a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ] 1644a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return [(name, getattr(self, name)) for name in names] 1645a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1646a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ================================== 1647a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Optional/Positional adding methods 1648a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ================================== 1649a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def add_subparsers(self, **kwargs): 1650a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self._subparsers is not None: 1651a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(_('cannot have multiple subparser arguments')) 1652a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1653a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add the parser class to the arguments if it's not present 1654a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs.setdefault('parser_class', type(self)) 1655a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1656a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if 'title' in kwargs or 'description' in kwargs: 1657a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson title = _(kwargs.pop('title', 'subcommands')) 1658a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson description = _(kwargs.pop('description', None)) 1659a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._subparsers = self.add_argument_group(title, description) 1660a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1661a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._subparsers = self._positionals 1662a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1663a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # prog defaults to the usage message of this parser, skipping 1664a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # optional arguments and with no "usage:" prefix 1665a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if kwargs.get('prog') is None: 1666a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter = self._get_formatter() 1667a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson positionals = self._get_positional_actions() 1668a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson groups = self._mutually_exclusive_groups 1669a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_usage(self.usage, positionals, groups, '') 1670a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson kwargs['prog'] = formatter.format_help().strip() 1671a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1672a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # create the parsers action and add it to the positionals list 1673a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson parsers_class = self._pop_action_class(kwargs, 'parsers') 1674a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = parsers_class(option_strings=[], **kwargs) 1675a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._subparsers._add_action(action) 1676a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1677a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the created parsers action 1678a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action 1679a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1680a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _add_action(self, action): 1681a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.option_strings: 1682a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._optionals._add_action(action) 1683a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1684a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._positionals._add_action(action) 1685a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action 1686a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1687a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_optional_actions(self): 1688a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return [action 1689a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in self._actions 1690a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.option_strings] 1691a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1692a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_positional_actions(self): 1693a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return [action 1694a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in self._actions 1695a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not action.option_strings] 1696a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1697a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ===================================== 1698a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Command line argument parsing methods 1699a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ===================================== 1700a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def parse_args(self, args=None, namespace=None): 1701a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args, argv = self.parse_known_args(args, namespace) 1702a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if argv: 1703a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('unrecognized arguments: %s') 1704a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(msg % ' '.join(argv)) 1705a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return args 1706a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1707a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def parse_known_args(self, args=None, namespace=None): 1708a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if args is None: 1709a99c7dedcb9310d80f2cf29a747e05fdde2716bcR David Murray # args default to the system args 1710a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args = _sys.argv[1:] 1711a99c7dedcb9310d80f2cf29a747e05fdde2716bcR David Murray else: 1712a99c7dedcb9310d80f2cf29a747e05fdde2716bcR David Murray # make sure that args are mutable 1713a99c7dedcb9310d80f2cf29a747e05fdde2716bcR David Murray args = list(args) 1714a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1715a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # default Namespace built from parser defaults 1716a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if namespace is None: 1717a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson namespace = Namespace() 1718a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1719a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add any action defaults that aren't present 1720a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in self._actions: 1721a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.dest is not SUPPRESS: 1722a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not hasattr(namespace, action.dest): 1723a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.default is not SUPPRESS: 1724201018718fc55fada8fd159b86bc038c3d297597R David Murray setattr(namespace, action.dest, action.default) 1725a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1726a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add any parser defaults that aren't present 1727a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for dest in self._defaults: 1728a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not hasattr(namespace, dest): 1729a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson setattr(namespace, dest, self._defaults[dest]) 1730a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1731a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # parse the arguments and exit if there are any errors 1732a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 17332e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard namespace, args = self._parse_known_args(args, namespace) 17342e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard if hasattr(namespace, _UNRECOGNIZED_ARGS_ATTR): 17352e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard args.extend(getattr(namespace, _UNRECOGNIZED_ARGS_ATTR)) 17362e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard delattr(namespace, _UNRECOGNIZED_ARGS_ATTR) 17372e4d4c414e4275b5a8cbcd152e04ed91fb72af79Steven Bethard return namespace, args 1738a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except ArgumentError: 1739a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson err = _sys.exc_info()[1] 1740a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(str(err)) 1741a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1742a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _parse_known_args(self, arg_strings, namespace): 1743a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # replace arg strings that are file references 1744a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self.fromfile_prefix_chars is not None: 1745a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings = self._read_args_from_files(arg_strings) 1746a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1747a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # map all mutually exclusive arguments to the other arguments 1748a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # they can't occur with 1749a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_conflicts = {} 1750a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for mutex_group in self._mutually_exclusive_groups: 1751a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson group_actions = mutex_group._group_actions 1752a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for i, mutex_action in enumerate(mutex_group._group_actions): 1753a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflicts = action_conflicts.setdefault(mutex_action, []) 1754a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflicts.extend(group_actions[:i]) 1755a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson conflicts.extend(group_actions[i + 1:]) 1756a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1757a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # find all option indices, and determine the arg_string_pattern 1758a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # which has an 'O' if there is an option at an index, 1759a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # an 'A' if there is an argument, or a '-' if there is a '--' 1760a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_string_indices = {} 1761a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_string_pattern_parts = [] 1762a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings_iter = iter(arg_strings) 1763a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for i, arg_string in enumerate(arg_strings_iter): 1764a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1765a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # all args after -- are non-options 1766a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if arg_string == '--': 1767a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_string_pattern_parts.append('-') 1768a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for arg_string in arg_strings_iter: 1769a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_string_pattern_parts.append('A') 1770a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1771a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # otherwise, add the arg to the arg strings 1772a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # and note the index if it was an option 1773a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1774a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_tuple = self._parse_optional(arg_string) 1775a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_tuple is None: 1776a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pattern = 'A' 1777a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1778a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_string_indices[i] = option_tuple 1779a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pattern = 'O' 1780a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_string_pattern_parts.append(pattern) 1781a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1782a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # join the pieces together to form the pattern 1783a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings_pattern = ''.join(arg_string_pattern_parts) 1784a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1785a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # converts arg strings to the appropriate and then takes the action 17860e717addd8a03ed10231a578fce894c07ddb157eBenjamin Peterson seen_actions = set() 17870e717addd8a03ed10231a578fce894c07ddb157eBenjamin Peterson seen_non_default_actions = set() 1788a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1789a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def take_action(action, argument_strings, option_string=None): 1790a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson seen_actions.add(action) 1791a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson argument_values = self._get_values(action, argument_strings) 1792a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1793a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # error if this argument is not allowed with other previously 1794a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # seen arguments, assuming that actions that use the default 1795a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # value don't really count as "present" 1796a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if argument_values is not action.default: 1797a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson seen_non_default_actions.add(action) 1798a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for conflict_action in action_conflicts.get(action, []): 1799a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if conflict_action in seen_non_default_actions: 1800a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('not allowed with argument %s') 1801a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_name = _get_action_name(conflict_action) 1802a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg % action_name) 1803a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1804a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # take the action if we didn't receive a SUPPRESS value 1805a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # (e.g. from a default) 1806a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if argument_values is not SUPPRESS: 1807a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action(self, namespace, argument_values, option_string) 1808a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1809a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # function to convert arg_strings into an optional action 1810a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def consume_optional(start_index): 1811a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1812a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # get the optional identified at this index 1813a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_tuple = option_string_indices[start_index] 1814a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action, option_string, explicit_arg = option_tuple 1815a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1816a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # identify additional optionals in the same arg string 1817a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # (e.g. -xyz is the same as -x -y -z if no args are required) 1818a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson match_argument = self._match_argument 1819a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_tuples = [] 1820a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson while True: 1821a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1822a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if we found no optional action, skip it 1823a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action is None: 1824a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson extras.append(arg_strings[start_index]) 1825a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return start_index + 1 1826a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1827a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if there is an explicit argument, try to match the 1828a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # optional's string arguments to only this 1829a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if explicit_arg is not None: 1830a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_count = match_argument(action, 'A') 1831a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1832a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the action is a single-dash option and takes no 1833a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # arguments, try to parse more single-dash options out 1834a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # of the tail of the option string 1835a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson chars = self.prefix_chars 1836a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if arg_count == 0 and option_string[1] not in chars: 1837a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_tuples.append((action, [], option_string)) 1838784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard char = option_string[0] 1839784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard option_string = char + explicit_arg[0] 1840784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard new_explicit_arg = explicit_arg[1:] or None 1841784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard optionals_map = self._option_string_actions 1842784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard if option_string in optionals_map: 1843784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard action = optionals_map[option_string] 1844784dd51ad297d31ee724f38a528ba8472e4b14f9Steven Bethard explicit_arg = new_explicit_arg 1845a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1846a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('ignored explicit argument %r') 1847a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg % explicit_arg) 1848a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1849a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the action expect exactly one argument, we've 1850a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # successfully matched the option; exit the loop 1851a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif arg_count == 1: 1852a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson stop = start_index + 1 1853a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args = [explicit_arg] 1854a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_tuples.append((action, args, option_string)) 1855a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson break 1856a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1857a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # error if a double-dash option did not use the 1858a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # explicit argument 1859a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1860a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('ignored explicit argument %r') 1861a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg % explicit_arg) 1862a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1863a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if there is no explicit argument, try to match the 1864a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # optional's string arguments with the following strings 1865a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if successful, exit the loop 1866a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1867a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start = start_index + 1 1868a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson selected_patterns = arg_strings_pattern[start:] 1869a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_count = match_argument(action, selected_patterns) 1870a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson stop = start + arg_count 1871a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args = arg_strings[start:stop] 1872a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action_tuples.append((action, args, option_string)) 1873a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson break 1874a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1875a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # add the Optional to the list and return the index at which 1876a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # the Optional's string args stopped 1877a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson assert action_tuples 1878a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action, args, option_string in action_tuples: 1879a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson take_action(action, args, option_string) 1880a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return stop 1881a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1882a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # the list of Positionals left to be parsed; this is modified 1883a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # by consume_positionals() 1884a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson positionals = self._get_positional_actions() 1885a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1886a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # function to convert arg_strings into positional actions 1887a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def consume_positionals(start_index): 1888a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # match as many Positionals as possible 1889a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson match_partial = self._match_arguments_partial 1890a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson selected_pattern = arg_strings_pattern[start_index:] 1891a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_counts = match_partial(positionals, selected_pattern) 1892a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1893a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # slice off the appropriate arg strings for each Positional 1894a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # and add the Positional and its args to the list 1895a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action, arg_count in zip(positionals, arg_counts): 1896a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args = arg_strings[start_index: start_index + arg_count] 1897a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start_index += arg_count 1898a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson take_action(action, args) 1899a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1900a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # slice off the Positionals that we just parsed and return the 1901a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # index at which the Positionals' string args stopped 1902a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson positionals[:] = positionals[len(arg_counts):] 1903a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return start_index 1904a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1905a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # consume Positionals and Optionals alternately, until we have 1906a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # passed the last option string 1907a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson extras = [] 1908a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start_index = 0 1909a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string_indices: 1910a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson max_option_string_index = max(option_string_indices) 1911a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1912a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson max_option_string_index = -1 1913a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson while start_index <= max_option_string_index: 1914a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1915a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # consume any Positionals preceding the next option 1916a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson next_option_string_index = min([ 1917a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson index 1918a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for index in option_string_indices 1919a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if index >= start_index]) 1920a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if start_index != next_option_string_index: 1921a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson positionals_end_index = consume_positionals(start_index) 1922a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1923a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # only try to parse the next optional if we didn't consume 1924a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # the option string during the positionals parsing 1925a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if positionals_end_index > start_index: 1926a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start_index = positionals_end_index 1927a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson continue 1928a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1929a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start_index = positionals_end_index 1930a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1931a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if we consumed all the positionals we could and we're not 1932a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # at the index of an option string, there were extra arguments 1933a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if start_index not in option_string_indices: 1934a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson strings = arg_strings[start_index:next_option_string_index] 1935a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson extras.extend(strings) 1936a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start_index = next_option_string_index 1937a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1938a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # consume the next optional and any arguments for it 1939a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson start_index = consume_optional(start_index) 1940a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1941a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # consume any positionals following the last Optional 1942a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson stop_index = consume_positionals(start_index) 1943a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1944a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if we didn't consume all the argument strings, there were extras 1945a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson extras.extend(arg_strings[stop_index:]) 1946a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1947a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if we didn't use all the Positional objects, there were too few 1948a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # arg strings supplied. 1949a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if positionals: 1950a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(_('too few arguments')) 1951a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1952201018718fc55fada8fd159b86bc038c3d297597R David Murray # make sure all required actions were present, and convert defaults. 1953a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in self._actions: 1954201018718fc55fada8fd159b86bc038c3d297597R David Murray if action not in seen_actions: 1955201018718fc55fada8fd159b86bc038c3d297597R David Murray if action.required: 1956a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson name = _get_action_name(action) 1957a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(_('argument %s is required') % name) 1958201018718fc55fada8fd159b86bc038c3d297597R David Murray else: 1959201018718fc55fada8fd159b86bc038c3d297597R David Murray # Convert action default now instead of doing it before 1960201018718fc55fada8fd159b86bc038c3d297597R David Murray # parsing arguments to avoid calling convert functions 1961201018718fc55fada8fd159b86bc038c3d297597R David Murray # twice (which may fail) if the argument was given, but 1962201018718fc55fada8fd159b86bc038c3d297597R David Murray # only if it was defined already in the namespace 1963201018718fc55fada8fd159b86bc038c3d297597R David Murray if (action.default is not None and 196403937a8755e189959c44e5035a3eb27db95a6efeBarry Warsaw isinstance(action.default, basestring) and 1965201018718fc55fada8fd159b86bc038c3d297597R David Murray hasattr(namespace, action.dest) and 1966201018718fc55fada8fd159b86bc038c3d297597R David Murray action.default is getattr(namespace, action.dest)): 1967201018718fc55fada8fd159b86bc038c3d297597R David Murray setattr(namespace, action.dest, 1968201018718fc55fada8fd159b86bc038c3d297597R David Murray self._get_value(action, action.default)) 1969a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1970a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # make sure all required groups had one option present 1971a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for group in self._mutually_exclusive_groups: 1972a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if group.required: 1973a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in group._group_actions: 1974a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action in seen_non_default_actions: 1975a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson break 1976a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1977a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if no actions were used, report the error 1978a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1979a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson names = [_get_action_name(action) 1980a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in group._group_actions 1981a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.help is not SUPPRESS] 1982a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('one of the arguments %s is required') 1983a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(msg % ' '.join(names)) 1984a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1985a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the updated namespace and the extra arguments 1986a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return namespace, extras 1987a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1988a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _read_args_from_files(self, arg_strings): 1989a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # expand arguments referencing files 1990a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson new_arg_strings = [] 1991a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for arg_string in arg_strings: 1992a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1993a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # for regular arguments, just add them back into the list 1994056c31f9cc10a8697a40c817eae42f7e38a1cf80R David Murray if not arg_string or arg_string[0] not in self.fromfile_prefix_chars: 1995a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson new_arg_strings.append(arg_string) 1996a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 1997a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # replace arguments referencing files with the file content 1998a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 1999a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 2000a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args_file = open(arg_string[1:]) 2001a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 2002a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings = [] 2003a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for arg_line in args_file.read().splitlines(): 2004a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for arg in self.convert_arg_line_to_args(arg_line): 2005a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings.append(arg) 2006a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_strings = self._read_args_from_files(arg_strings) 2007a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson new_arg_strings.extend(arg_strings) 2008a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson finally: 2009a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson args_file.close() 2010a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except IOError: 2011a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson err = _sys.exc_info()[1] 2012a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(str(err)) 2013a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2014a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the modified argument list 2015a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return new_arg_strings 2016a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2017a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def convert_arg_line_to_args(self, arg_line): 2018a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return [arg_line] 2019a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2020a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _match_argument(self, action, arg_strings_pattern): 2021a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # match the pattern for this action to the arg strings 2022a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = self._get_nargs_pattern(action) 2023a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson match = _re.match(nargs_pattern, arg_strings_pattern) 2024a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2025a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # raise an exception if we weren't able to find a match 2026a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if match is None: 2027a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_errors = { 2028a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson None: _('expected one argument'), 2029a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson OPTIONAL: _('expected at most one argument'), 2030a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson ONE_OR_MORE: _('expected at least one argument'), 2031a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson } 2032a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson default = _('expected %s argument(s)') % action.nargs 2033a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = nargs_errors.get(action.nargs, default) 2034a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg) 2035a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2036a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the number of arguments matched 2037a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return len(match.group(1)) 2038a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2039a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _match_arguments_partial(self, actions, arg_strings_pattern): 2040a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # progressively shorten the actions list by slicing off the 2041a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # final actions until we find a match 2042a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = [] 2043a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for i in range(len(actions), 0, -1): 2044a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson actions_slice = actions[:i] 2045a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson pattern = ''.join([self._get_nargs_pattern(action) 2046a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action in actions_slice]) 2047a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson match = _re.match(pattern, arg_strings_pattern) 2048a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if match is not None: 2049a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result.extend([len(string) for string in match.groups()]) 2050a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson break 2051a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2052a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the list of arg string counts 2053a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return result 2054a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2055a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _parse_optional(self, arg_string): 2056a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if it's an empty string, it was meant to be a positional 2057a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not arg_string: 2058a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 2059a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2060a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if it doesn't start with a prefix, it was meant to be positional 2061a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not arg_string[0] in self.prefix_chars: 2062a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 2063a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2064a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the option string is present in the parser, return the action 2065a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if arg_string in self._option_string_actions: 2066a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = self._option_string_actions[arg_string] 2067a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action, arg_string, None 2068a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2069a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if it's just a single character, it was meant to be positional 2070a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if len(arg_string) == 1: 2071a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 2072a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2073a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if the option string before the "=" is present, return the action 2074a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if '=' in arg_string: 2075a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_string, explicit_arg = arg_string.split('=', 1) 2076a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string in self._option_string_actions: 2077a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = self._option_string_actions[option_string] 2078a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return action, option_string, explicit_arg 2079a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2080a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # search through all possible prefixes of the option string 2081a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # and all actions in the parser for possible interpretations 2082a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_tuples = self._get_option_tuples(arg_string) 2083a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2084a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if multiple actions match, the option string was ambiguous 2085a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if len(option_tuples) > 1: 2086a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson options = ', '.join([option_string 2087a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action, option_string, explicit_arg in option_tuples]) 2088a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = arg_string, options 2089a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(_('ambiguous option: %s could match %s') % tup) 2090a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2091a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if exactly one action matched, this segmentation is good, 2092a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # so return the parsed action 2093a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif len(option_tuples) == 1: 2094a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_tuple, = option_tuples 2095a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return option_tuple 2096a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2097a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if it was not found as an option, but it looks like a negative 2098a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # number, it was meant to be positional 2099a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # unless there are negative-number-like options 2100a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if self._negative_number_matcher.match(arg_string): 2101a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not self._has_negative_number_optionals: 2102a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 2103a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2104a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if it contains a space, it was meant to be a positional 2105a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if ' ' in arg_string: 2106a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None 2107a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2108a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # it was meant to be an optional but there is no such option 2109a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # in this parser (though it might be a valid option in a subparser) 2110a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return None, arg_string, None 2111a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2112a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_option_tuples(self, option_string): 2113a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = [] 2114a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2115a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # option strings starting with two prefix characters are only 2116a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # split at the '=' 2117a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson chars = self.prefix_chars 2118a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string[0] in chars and option_string[1] in chars: 2119a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if '=' in option_string: 2120a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_prefix, explicit_arg = option_string.split('=', 1) 2121a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 2122a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_prefix = option_string 2123a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson explicit_arg = None 2124a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in self._option_string_actions: 2125a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string.startswith(option_prefix): 2126a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = self._option_string_actions[option_string] 2127a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = action, option_string, explicit_arg 2128a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result.append(tup) 2129a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2130a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # single character options can be concatenated with their arguments 2131a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # but multiple character options always have to have their argument 2132a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # separate 2133a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif option_string[0] in chars and option_string[1] not in chars: 2134a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson option_prefix = option_string 2135a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson explicit_arg = None 2136a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson short_option_prefix = option_string[:2] 2137a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson short_explicit_arg = option_string[2:] 2138a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2139a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for option_string in self._option_string_actions: 2140a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if option_string == short_option_prefix: 2141a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = self._option_string_actions[option_string] 2142a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = action, option_string, short_explicit_arg 2143a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result.append(tup) 2144a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif option_string.startswith(option_prefix): 2145a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson action = self._option_string_actions[option_string] 2146a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = action, option_string, explicit_arg 2147a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result.append(tup) 2148a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2149a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # shouldn't ever get here 2150a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 2151a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.error(_('unexpected option string: %s') % option_string) 2152a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2153a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the collected option tuples 2154a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return result 2155a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2156a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_nargs_pattern(self, action): 2157a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # in all examples below, we have to allow for '--' args 2158a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # which are represented as '-' in the pattern 2159a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs = action.nargs 2160a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2161a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # the default (None) is assumed to be a single argument 2162a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if nargs is None: 2163a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '(-*A-*)' 2164a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2165a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # allow zero or one arguments 2166a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif nargs == OPTIONAL: 2167a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '(-*A?-*)' 2168a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2169a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # allow zero or more arguments 2170a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif nargs == ZERO_OR_MORE: 2171a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '(-*[A-]*)' 2172a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2173a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # allow one or more arguments 2174a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif nargs == ONE_OR_MORE: 2175a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '(-*A[A-]*)' 2176a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2177a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # allow any number of options or arguments 2178a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif nargs == REMAINDER: 2179a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '([-AO]*)' 2180a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2181a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # allow one argument followed by any number of options or arguments 2182a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif nargs == PARSER: 2183a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '(-*A[-AO]*)' 2184a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2185a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # all others should be integers 2186a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 2187a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = '(-*%s-*)' % '-*'.join('A' * nargs) 2188a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2189a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # if this is an optional action, -- is not allowed 2190a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.option_strings: 2191a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = nargs_pattern.replace('-*', '') 2192a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson nargs_pattern = nargs_pattern.replace('-', '') 2193a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2194a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the pattern 2195a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return nargs_pattern 2196a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2197a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================== 2198a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Value conversion methods 2199a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================== 2200a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_values(self, action, arg_strings): 220168f555c03ad32671a76c5762313bbf33c0ae4842R David Murray # for everything but PARSER, REMAINDER args, strip out first '--' 2202a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.nargs not in [PARSER, REMAINDER]: 220368f555c03ad32671a76c5762313bbf33c0ae4842R David Murray try: 220468f555c03ad32671a76c5762313bbf33c0ae4842R David Murray arg_strings.remove('--') 220568f555c03ad32671a76c5762313bbf33c0ae4842R David Murray except ValueError: 220668f555c03ad32671a76c5762313bbf33c0ae4842R David Murray pass 2207a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2208a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # optional argument produces a default when not present 2209a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not arg_strings and action.nargs == OPTIONAL: 2210a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.option_strings: 2211a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = action.const 2212a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 2213a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = action.default 22140e717addd8a03ed10231a578fce894c07ddb157eBenjamin Peterson if isinstance(value, basestring): 2215a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = self._get_value(action, value) 2216a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._check_value(action, value) 2217a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2218a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # when nargs='*' on a positional, if there were no command-line 2219a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # args, use the default if it is anything other than None 2220a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif (not arg_strings and action.nargs == ZERO_OR_MORE and 2221a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson not action.option_strings): 2222a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.default is not None: 2223a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = action.default 2224a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 2225a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = arg_strings 2226a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._check_value(action, value) 2227a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2228a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # single argument or optional argument produces a single value 2229a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif len(arg_strings) == 1 and action.nargs in [None, OPTIONAL]: 2230a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson arg_string, = arg_strings 2231a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = self._get_value(action, arg_string) 2232a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._check_value(action, value) 2233a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2234a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # REMAINDER arguments convert all values, checking none 2235a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == REMAINDER: 2236a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = [self._get_value(action, v) for v in arg_strings] 2237a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2238a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # PARSER arguments convert all values, but check only the first 2239a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson elif action.nargs == PARSER: 2240a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = [self._get_value(action, v) for v in arg_strings] 2241a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._check_value(action, value[0]) 2242a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2243a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # all other types of nargs produce a list 2244a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson else: 2245a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson value = [self._get_value(action, v) for v in arg_strings] 2246a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for v in value: 2247a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._check_value(action, v) 2248a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2249a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the converted value 2250a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return value 2251a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2252a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_value(self, action, arg_string): 2253a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson type_func = self._registry_get('type', action.type, action.type) 2254a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if not _callable(type_func): 2255a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('%r is not callable') 2256a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg % type_func) 2257a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2258a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # convert the value to the appropriate type 2259a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson try: 2260a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson result = type_func(arg_string) 2261a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2262a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ArgumentTypeErrors indicate errors 2263a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except ArgumentTypeError: 2264a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson name = getattr(action.type, '__name__', repr(action.type)) 2265a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = str(_sys.exc_info()[1]) 2266a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg) 2267a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2268a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # TypeErrors or ValueErrors also indicate errors 2269a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson except (TypeError, ValueError): 2270a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson name = getattr(action.type, '__name__', repr(action.type)) 2271a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('invalid %s value: %r') 2272a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg % (name, arg_string)) 2273a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2274a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # return the converted value 2275a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return result 2276a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2277a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _check_value(self, action, value): 2278a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # converted value must be one of the choices (if specified) 2279a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if action.choices is not None and value not in action.choices: 2280a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson tup = value, ', '.join(map(repr, action.choices)) 2281a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson msg = _('invalid choice: %r (choose from %s)') % tup 2282a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson raise ArgumentError(action, msg) 2283a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2284a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 2285a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Help-formatting methods 2286a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ======================= 2287a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def format_usage(self): 2288a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter = self._get_formatter() 2289a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_usage(self.usage, self._actions, 2290a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._mutually_exclusive_groups) 2291a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return formatter.format_help() 2292a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2293a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def format_help(self): 2294a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter = self._get_formatter() 2295a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2296a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # usage 2297a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_usage(self.usage, self._actions, 2298a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._mutually_exclusive_groups) 2299a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2300a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # description 2301a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_text(self.description) 2302a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2303a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # positionals, optionals and user-defined groups 2304a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson for action_group in self._action_groups: 2305a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.start_section(action_group.title) 2306a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_text(action_group.description) 2307a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_arguments(action_group._group_actions) 2308a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.end_section() 2309a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2310a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # epilog 2311a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_text(self.epilog) 2312a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2313a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # determine help from format above 2314a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return formatter.format_help() 2315a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2316a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def format_version(self): 2317a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson import warnings 2318a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson warnings.warn( 2319a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'The format_version method is deprecated -- the "version" ' 2320a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'argument to ArgumentParser is no longer supported.', 2321a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson DeprecationWarning) 2322a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter = self._get_formatter() 2323a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson formatter.add_text(self.version) 2324a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return formatter.format_help() 2325a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2326a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _get_formatter(self): 2327a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson return self.formatter_class(prog=self.prog) 2328a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2329a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ===================== 2330a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Help-printing methods 2331a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # ===================== 2332a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def print_usage(self, file=None): 2333a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if file is None: 2334a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson file = _sys.stdout 2335a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._print_message(self.format_usage(), file) 2336a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2337a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def print_help(self, file=None): 2338a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if file is None: 2339a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson file = _sys.stdout 2340a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._print_message(self.format_help(), file) 2341a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2342a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def print_version(self, file=None): 2343a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson import warnings 2344a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson warnings.warn( 2345a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'The print_version method is deprecated -- the "version" ' 2346a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 'argument to ArgumentParser is no longer supported.', 2347a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson DeprecationWarning) 2348a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._print_message(self.format_version(), file) 2349a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2350a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def _print_message(self, message, file=None): 2351a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if message: 2352a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if file is None: 2353a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson file = _sys.stderr 2354a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson file.write(message) 2355a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2356a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # =============== 2357a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # Exiting methods 2358a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson # =============== 2359a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def exit(self, status=0, message=None): 2360a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson if message: 2361a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self._print_message(message, _sys.stderr) 2362a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson _sys.exit(status) 2363a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2364a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson def error(self, message): 2365a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """error(message: string) 2366a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2367a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson Prints a usage message incorporating the message to stderr and 2368a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson exits. 2369a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson 2370a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson If you override this in a subclass, it should not return -- it 2371a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson should either exit or raise an exception. 2372a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson """ 2373a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.print_usage(_sys.stderr) 2374a39e966e97af0ca8cf395a2ab8a02555ebe684c7Benjamin Peterson self.exit(2, _('%s: error: %s\n') % (self.prog, message)) 2375