comparison env/lib/python3.9/site-packages/argcomplete/__init__.py @ 0:4f3585e2f14b draft default tip

"planemo upload commit 60cee0fc7c0cda8592644e1aad72851dec82c959"
author shellac
date Mon, 22 Mar 2021 18:12:50 +0000
parents
children
comparison
equal deleted inserted replaced
-1:000000000000 0:4f3585e2f14b
1 # Copyright 2012-2019, Andrey Kislyuk and argcomplete contributors.
2 # Licensed under the Apache License. See https://github.com/kislyuk/argcomplete for more info.
3
4 from __future__ import absolute_import, division, print_function, unicode_literals
5
6 import os, sys, argparse, contextlib
7 from . import completers, my_shlex as shlex
8 from .compat import USING_PYTHON2, str, sys_encoding, ensure_str, ensure_bytes
9 from .completers import FilesCompleter, SuppressCompleter
10 from .my_argparse import IntrospectiveArgumentParser, action_is_satisfied, action_is_open, action_is_greedy
11 from .shell_integration import shellcode
12
13 _DEBUG = "_ARC_DEBUG" in os.environ
14
15 debug_stream = sys.stderr
16
17 def debug(*args):
18 if _DEBUG:
19 if USING_PYTHON2:
20 # debug_stream has to be binary mode in Python 2.
21 # Attempting to write unicode directly uses the default ascii conversion.
22 # Convert any unicode to bytes, leaving non-string input alone.
23 args = [ensure_bytes(x) if isinstance(x, str) else x for x in args]
24 print(file=debug_stream, *args)
25
26 BASH_FILE_COMPLETION_FALLBACK = 79
27 BASH_DIR_COMPLETION_FALLBACK = 80
28
29 safe_actions = (argparse._StoreAction,
30 argparse._StoreConstAction,
31 argparse._StoreTrueAction,
32 argparse._StoreFalseAction,
33 argparse._AppendAction,
34 argparse._AppendConstAction,
35 argparse._CountAction)
36
37 @contextlib.contextmanager
38 def mute_stdout():
39 stdout = sys.stdout
40 sys.stdout = open(os.devnull, "w")
41 try:
42 yield
43 finally:
44 sys.stdout = stdout
45
46 @contextlib.contextmanager
47 def mute_stderr():
48 stderr = sys.stderr
49 sys.stderr = open(os.devnull, "w")
50 try:
51 yield
52 finally:
53 sys.stderr.close()
54 sys.stderr = stderr
55
56 class ArgcompleteException(Exception):
57 pass
58
59 def split_line(line, point=None):
60 if point is None:
61 point = len(line)
62 lexer = shlex.shlex(line, posix=True)
63 lexer.whitespace_split = True
64 lexer.wordbreaks = os.environ.get("_ARGCOMPLETE_COMP_WORDBREAKS", "")
65 words = []
66
67 def split_word(word):
68 # TODO: make this less ugly
69 point_in_word = len(word) + point - lexer.instream.tell()
70 if isinstance(lexer.state, (str, bytes)) and lexer.state in lexer.whitespace:
71 point_in_word += 1
72 if point_in_word > len(word):
73 debug("In trailing whitespace")
74 words.append(word)
75 word = ""
76 prefix, suffix = word[:point_in_word], word[point_in_word:]
77 prequote = ""
78 # posix
79 if lexer.state is not None and lexer.state in lexer.quotes:
80 prequote = lexer.state
81 # non-posix
82 # if len(prefix) > 0 and prefix[0] in lexer.quotes:
83 # prequote, prefix = prefix[0], prefix[1:]
84
85 return prequote, prefix, suffix, words, lexer.last_wordbreak_pos
86
87 while True:
88 try:
89 word = lexer.get_token()
90 if word == lexer.eof:
91 # TODO: check if this is ever unsafe
92 # raise ArgcompleteException("Unexpected end of input")
93 return "", "", "", words, None
94 if lexer.instream.tell() >= point:
95 debug("word", word, "split, lexer state: '{s}'".format(s=lexer.state))
96 return split_word(word)
97 words.append(word)
98 except ValueError:
99 debug("word", lexer.token, "split (lexer stopped, state: '{s}')".format(s=lexer.state))
100 if lexer.instream.tell() >= point:
101 return split_word(lexer.token)
102 else:
103 msg = ("Unexpected internal state. "
104 "Please report this bug at https://github.com/kislyuk/argcomplete/issues.")
105 raise ArgcompleteException(msg)
106
107 def default_validator(completion, prefix):
108 return completion.startswith(prefix)
109
110 class CompletionFinder(object):
111 """
112 Inherit from this class if you wish to override any of the stages below. Otherwise, use
113 ``argcomplete.autocomplete()`` directly (it's a convenience instance of this class). It has the same signature as
114 :meth:`CompletionFinder.__call__()`.
115 """
116 def __init__(self, argument_parser=None, always_complete_options=True, exclude=None, validator=None,
117 print_suppressed=False, default_completer=FilesCompleter(), append_space=None):
118 self._parser = argument_parser
119 self.always_complete_options = always_complete_options
120 self.exclude = exclude
121 if validator is None:
122 validator = default_validator
123 self.validator = validator
124 self.print_suppressed = print_suppressed
125 self.completing = False
126 self._display_completions = {}
127 self.default_completer = default_completer
128 if append_space is None:
129 append_space = os.environ.get("_ARGCOMPLETE_SUPPRESS_SPACE") != "1"
130 self.append_space = append_space
131
132 def __call__(self, argument_parser, always_complete_options=True, exit_method=os._exit, output_stream=None,
133 exclude=None, validator=None, print_suppressed=False, append_space=None,
134 default_completer=FilesCompleter()):
135 """
136 :param argument_parser: The argument parser to autocomplete on
137 :type argument_parser: :class:`argparse.ArgumentParser`
138 :param always_complete_options:
139 Controls the autocompletion of option strings if an option string opening character (normally ``-``) has not
140 been entered. If ``True`` (default), both short (``-x``) and long (``--x``) option strings will be
141 suggested. If ``False``, no option strings will be suggested. If ``long``, long options and short options
142 with no long variant will be suggested. If ``short``, short options and long options with no short variant
143 will be suggested.
144 :type always_complete_options: boolean or string
145 :param exit_method:
146 Method used to stop the program after printing completions. Defaults to :meth:`os._exit`. If you want to
147 perform a normal exit that calls exit handlers, use :meth:`sys.exit`.
148 :type exit_method: callable
149 :param exclude: List of strings representing options to be omitted from autocompletion
150 :type exclude: iterable
151 :param validator:
152 Function to filter all completions through before returning (called with two string arguments, completion
153 and prefix; return value is evaluated as a boolean)
154 :type validator: callable
155 :param print_suppressed:
156 Whether or not to autocomplete options that have the ``help=argparse.SUPPRESS`` keyword argument set.
157 :type print_suppressed: boolean
158 :param append_space:
159 Whether to append a space to unique matches. The default is ``True``.
160 :type append_space: boolean
161
162 .. note::
163 If you are not subclassing CompletionFinder to override its behaviors,
164 use ``argcomplete.autocomplete()`` directly. It has the same signature as this method.
165
166 Produces tab completions for ``argument_parser``. See module docs for more info.
167
168 Argcomplete only executes actions if their class is known not to have side effects. Custom action classes can be
169 added to argcomplete.safe_actions, if their values are wanted in the ``parsed_args`` completer argument, or
170 their execution is otherwise desirable.
171 """
172 self.__init__(argument_parser, always_complete_options=always_complete_options, exclude=exclude,
173 validator=validator, print_suppressed=print_suppressed, append_space=append_space,
174 default_completer=default_completer)
175
176 if "_ARGCOMPLETE" not in os.environ:
177 # not an argument completion invocation
178 return
179
180 global debug_stream
181 try:
182 debug_stream = os.fdopen(9, "w")
183 except:
184 debug_stream = sys.stderr
185 debug()
186
187 if output_stream is None:
188 filename = os.environ.get("_ARGCOMPLETE_STDOUT_FILENAME")
189 if filename is not None:
190 debug("Using output file {}".format(filename))
191 output_stream = open(filename, "wb")
192
193 if output_stream is None:
194 try:
195 output_stream = os.fdopen(8, "wb")
196 except:
197 debug("Unable to open fd 8 for writing, quitting")
198 exit_method(1)
199
200 # print("", stream=debug_stream)
201 # for v in "COMP_CWORD COMP_LINE COMP_POINT COMP_TYPE COMP_KEY _ARGCOMPLETE_COMP_WORDBREAKS COMP_WORDS".split():
202 # print(v, os.environ[v], stream=debug_stream)
203
204 ifs = os.environ.get("_ARGCOMPLETE_IFS", "\013")
205 if len(ifs) != 1:
206 debug("Invalid value for IFS, quitting [{v}]".format(v=ifs))
207 exit_method(1)
208
209 dfs = os.environ.get("_ARGCOMPLETE_DFS")
210 if dfs and len(dfs) != 1:
211 debug("Invalid value for DFS, quitting [{v}]".format(v=dfs))
212 exit_method(1)
213
214 comp_line = os.environ["COMP_LINE"]
215 comp_point = int(os.environ["COMP_POINT"])
216
217 comp_line = ensure_str(comp_line)
218 cword_prequote, cword_prefix, cword_suffix, comp_words, last_wordbreak_pos = split_line(comp_line, comp_point)
219
220 # _ARGCOMPLETE is set by the shell script to tell us where comp_words
221 # should start, based on what we're completing.
222 # 1: <script> [args]
223 # 2: python <script> [args]
224 # 3: python -m <module> [args]
225 start = int(os.environ["_ARGCOMPLETE"]) - 1
226 comp_words = comp_words[start:]
227
228 if cword_prefix and cword_prefix[0] in self._parser.prefix_chars and "=" in cword_prefix:
229 # Special case for when the current word is "--optional=PARTIAL_VALUE". Give the optional to the parser.
230 comp_words.append(cword_prefix.split("=", 1)[0])
231
232 debug("\nLINE: {!r}".format(comp_line),
233 "\nPOINT: {!r}".format(comp_point),
234 "\nPREQUOTE: {!r}".format(cword_prequote),
235 "\nPREFIX: {!r}".format(cword_prefix),
236 "\nSUFFIX: {!r}".format(cword_suffix),
237 "\nWORDS:", comp_words)
238
239 completions = self._get_completions(comp_words, cword_prefix, cword_prequote, last_wordbreak_pos)
240
241 if dfs:
242 display_completions = {key_part: value.replace(ifs, " ") if value else ""
243 for key, value in self._display_completions.items()
244 for key_part in key}
245 completions = [dfs.join((key, display_completions.get(key) or "")) for key in completions]
246
247 debug("\nReturning completions:", completions)
248 output_stream.write(ifs.join(completions).encode(sys_encoding))
249 output_stream.flush()
250 debug_stream.flush()
251 exit_method(0)
252
253 def _get_completions(self, comp_words, cword_prefix, cword_prequote, last_wordbreak_pos):
254 active_parsers = self._patch_argument_parser()
255
256 parsed_args = argparse.Namespace()
257 self.completing = True
258
259 if USING_PYTHON2:
260 # Python 2 argparse only properly works with byte strings.
261 comp_words = [ensure_bytes(word) for word in comp_words]
262
263 try:
264 debug("invoking parser with", comp_words[1:])
265 with mute_stderr():
266 a = self._parser.parse_known_args(comp_words[1:], namespace=parsed_args)
267 debug("parsed args:", a)
268 except BaseException as e:
269 debug("\nexception", type(e), str(e), "while parsing args")
270
271 self.completing = False
272
273 if "--" in comp_words:
274 self.always_complete_options = False
275
276 completions = self.collect_completions(active_parsers, parsed_args, cword_prefix, debug)
277 completions = self.filter_completions(completions)
278 completions = self.quote_completions(completions, cword_prequote, last_wordbreak_pos)
279 return completions
280
281 def _patch_argument_parser(self):
282 """
283 Since argparse doesn't support much introspection, we monkey-patch it to replace the parse_known_args method and
284 all actions with hooks that tell us which action was last taken or about to be taken, and let us have the parser
285 figure out which subparsers need to be activated (then recursively monkey-patch those).
286 We save all active ArgumentParsers to extract all their possible option names later.
287 """
288 self.active_parsers = []
289 self.visited_positionals = []
290
291 completer = self
292
293 def patch(parser):
294 completer.visited_positionals.append(parser)
295 completer.active_parsers.append(parser)
296
297 if isinstance(parser, IntrospectiveArgumentParser):
298 return
299
300 classname = "MonkeyPatchedIntrospectiveArgumentParser"
301 if USING_PYTHON2:
302 classname = bytes(classname)
303 parser.__class__ = type(classname, (IntrospectiveArgumentParser, parser.__class__), {})
304
305 for action in parser._actions:
306
307 if hasattr(action, "_orig_class"):
308 continue
309
310 # TODO: accomplish this with super
311 class IntrospectAction(action.__class__):
312 def __call__(self, parser, namespace, values, option_string=None):
313 debug("Action stub called on", self)
314 debug("\targs:", parser, namespace, values, option_string)
315 debug("\torig class:", self._orig_class)
316 debug("\torig callable:", self._orig_callable)
317
318 if not completer.completing:
319 self._orig_callable(parser, namespace, values, option_string=option_string)
320 elif issubclass(self._orig_class, argparse._SubParsersAction):
321 debug("orig class is a subparsers action: patching and running it")
322 patch(self._name_parser_map[values[0]])
323 self._orig_callable(parser, namespace, values, option_string=option_string)
324 elif self._orig_class in safe_actions:
325 if not self.option_strings:
326 completer.visited_positionals.append(self)
327
328 self._orig_callable(parser, namespace, values, option_string=option_string)
329
330 action._orig_class = action.__class__
331 action._orig_callable = action.__call__
332 action.__class__ = IntrospectAction
333
334 patch(self._parser)
335
336 debug("Active parsers:", self.active_parsers)
337 debug("Visited positionals:", self.visited_positionals)
338
339 return self.active_parsers
340
341 def _get_subparser_completions(self, parser, cword_prefix):
342 def filter_aliases(aliases, prefix):
343 return tuple(x for x in aliases if x.startswith(prefix))
344
345 aliases_by_parser = {}
346 for key in parser.choices.keys():
347 p = parser.choices[key]
348 aliases_by_parser.setdefault(p, []).append(key)
349
350 for action in parser._get_subactions():
351 subcmd_with_aliases = filter_aliases(aliases_by_parser[parser.choices[action.dest]], cword_prefix)
352 if subcmd_with_aliases:
353 self._display_completions[subcmd_with_aliases] = action.help
354
355 completions = [subcmd for subcmd in parser.choices.keys() if subcmd.startswith(cword_prefix)]
356 return completions
357
358 def _include_options(self, action, cword_prefix):
359 if len(cword_prefix) > 0 or self.always_complete_options is True:
360 return [ensure_str(opt) for opt in action.option_strings if ensure_str(opt).startswith(cword_prefix)]
361 long_opts = [ensure_str(opt) for opt in action.option_strings if len(opt) > 2]
362 short_opts = [ensure_str(opt) for opt in action.option_strings if len(opt) <= 2]
363 if self.always_complete_options == "long":
364 return long_opts if long_opts else short_opts
365 elif self.always_complete_options == "short":
366 return short_opts if short_opts else long_opts
367 return []
368
369 def _get_option_completions(self, parser, cword_prefix):
370 self._display_completions.update(
371 [[tuple(ensure_str(x) for x in action.option_strings
372 if ensure_str(x).startswith(cword_prefix)), action.help]
373 for action in parser._actions
374 if action.option_strings])
375
376 option_completions = []
377 for action in parser._actions:
378 if not self.print_suppressed:
379 completer = getattr(action, "completer", None)
380 if isinstance(completer, SuppressCompleter) and completer.suppress():
381 continue
382 if action.help == argparse.SUPPRESS:
383 continue
384 if not self._action_allowed(action, parser):
385 continue
386 if not isinstance(action, argparse._SubParsersAction):
387 option_completions += self._include_options(action, cword_prefix)
388 return option_completions
389
390 @staticmethod
391 def _action_allowed(action, parser):
392 # Logic adapted from take_action in ArgumentParser._parse_known_args
393 # (members are saved by my_argparse.IntrospectiveArgumentParser)
394 for conflict_action in parser._action_conflicts.get(action, []):
395 if conflict_action in parser._seen_non_default_actions:
396 return False
397 return True
398
399 def _complete_active_option(self, parser, next_positional, cword_prefix, parsed_args, completions):
400 debug("Active actions (L={l}): {a}".format(l=len(parser.active_actions), a=parser.active_actions))
401
402 isoptional = cword_prefix and cword_prefix[0] in parser.prefix_chars
403 optional_prefix = ""
404 greedy_actions = [x for x in parser.active_actions if action_is_greedy(x, isoptional)]
405 if greedy_actions:
406 assert len(greedy_actions) == 1, "expect at most 1 greedy action"
407 # This means the action will fail to parse if the word under the cursor is not given
408 # to it, so give it exclusive control over completions (flush previous completions)
409 debug("Resetting completions because", greedy_actions[0], "must consume the next argument")
410 self._display_completions = {}
411 completions = []
412 elif isoptional:
413 if "=" in cword_prefix:
414 # Special case for when the current word is "--optional=PARTIAL_VALUE".
415 # The completer runs on PARTIAL_VALUE. The prefix is added back to the completions
416 # (and chopped back off later in quote_completions() by the COMP_WORDBREAKS logic).
417 optional_prefix, _, cword_prefix = cword_prefix.partition("=")
418 else:
419 # Only run completers if current word does not start with - (is not an optional)
420 return completions
421
422 complete_remaining_positionals = False
423 # Use the single greedy action (if there is one) or all active actions.
424 for active_action in greedy_actions or parser.active_actions:
425 if not active_action.option_strings: # action is a positional
426 if action_is_open(active_action):
427 # Any positional arguments after this may slide down into this action
428 # if more arguments are added (since the user may not be done yet),
429 # so it is extremely difficult to tell which completers to run.
430 # Running all remaining completers will probably show more than the user wants
431 # but it also guarantees we won't miss anything.
432 complete_remaining_positionals = True
433 if not complete_remaining_positionals:
434 if action_is_satisfied(active_action) and not action_is_open(active_action):
435 debug("Skipping", active_action)
436 continue
437
438 debug("Activating completion for", active_action, active_action._orig_class)
439 # completer = getattr(active_action, "completer", DefaultCompleter())
440 completer = getattr(active_action, "completer", None)
441
442 if completer is None:
443 if active_action.choices is not None and not isinstance(active_action, argparse._SubParsersAction):
444 completer = completers.ChoicesCompleter(active_action.choices)
445 elif not isinstance(active_action, argparse._SubParsersAction):
446 completer = self.default_completer
447
448 if completer:
449 if isinstance(completer, SuppressCompleter) and completer.suppress():
450 continue
451
452 if callable(completer):
453 completions_from_callable = [c for c in completer(
454 prefix=cword_prefix, action=active_action, parser=parser, parsed_args=parsed_args)
455 if self.validator(c, cword_prefix)]
456
457 if completions_from_callable:
458 completions += completions_from_callable
459 if isinstance(completer, completers.ChoicesCompleter):
460 self._display_completions.update(
461 [[(x,), active_action.help] for x in completions_from_callable])
462 else:
463 self._display_completions.update(
464 [[(x,), ""] for x in completions_from_callable])
465 else:
466 debug("Completer is not callable, trying the readline completer protocol instead")
467 for i in range(9999):
468 next_completion = completer.complete(cword_prefix, i)
469 if next_completion is None:
470 break
471 if self.validator(next_completion, cword_prefix):
472 self._display_completions.update({(next_completion,): ""})
473 completions.append(next_completion)
474 if optional_prefix:
475 completions = [optional_prefix + "=" + completion for completion in completions]
476 debug("Completions:", completions)
477 return completions
478
479 def collect_completions(self, active_parsers, parsed_args, cword_prefix, debug):
480 """
481 Visits the active parsers and their actions, executes their completers or introspects them to collect their
482 option strings. Returns the resulting completions as a list of strings.
483
484 This method is exposed for overriding in subclasses; there is no need to use it directly.
485 """
486 completions = []
487
488 debug("all active parsers:", active_parsers)
489 active_parser = active_parsers[-1]
490 debug("active_parser:", active_parser)
491 if self.always_complete_options or (len(cword_prefix) > 0 and cword_prefix[0] in active_parser.prefix_chars):
492 completions += self._get_option_completions(active_parser, cword_prefix)
493 debug("optional options:", completions)
494
495 next_positional = self._get_next_positional()
496 debug("next_positional:", next_positional)
497
498 if isinstance(next_positional, argparse._SubParsersAction):
499 completions += self._get_subparser_completions(next_positional, cword_prefix)
500
501 completions = self._complete_active_option(active_parser, next_positional, cword_prefix, parsed_args,
502 completions)
503 debug("active options:", completions)
504 debug("display completions:", self._display_completions)
505
506 return completions
507
508 def _get_next_positional(self):
509 """
510 Get the next positional action if it exists.
511 """
512 active_parser = self.active_parsers[-1]
513 last_positional = self.visited_positionals[-1]
514
515 all_positionals = active_parser._get_positional_actions()
516 if not all_positionals:
517 return None
518
519 if active_parser == last_positional:
520 return all_positionals[0]
521
522 i = 0
523 for i in range(len(all_positionals)):
524 if all_positionals[i] == last_positional:
525 break
526
527 if i + 1 < len(all_positionals):
528 return all_positionals[i + 1]
529
530 return None
531
532 def filter_completions(self, completions):
533 """
534 Ensures collected completions are Unicode text, de-duplicates them, and excludes those specified by ``exclude``.
535 Returns the filtered completions as an iterable.
536
537 This method is exposed for overriding in subclasses; there is no need to use it directly.
538 """
539 # On Python 2, we have to make sure all completions are unicode objects before we continue and output them.
540 # Otherwise, because python disobeys the system locale encoding and uses ascii as the default encoding, it will
541 # try to implicitly decode string objects using ascii, and fail.
542 completions = [ensure_str(c) for c in completions]
543
544 # De-duplicate completions and remove excluded ones
545 if self.exclude is None:
546 self.exclude = set()
547 seen = set(self.exclude)
548 return [c for c in completions if c not in seen and not seen.add(c)]
549
550 def quote_completions(self, completions, cword_prequote, last_wordbreak_pos):
551 """
552 If the word under the cursor started with a quote (as indicated by a nonempty ``cword_prequote``), escapes
553 occurrences of that quote character in the completions, and adds the quote to the beginning of each completion.
554 Otherwise, escapes all characters that bash splits words on (``COMP_WORDBREAKS``), and removes portions of
555 completions before the first colon if (``COMP_WORDBREAKS``) contains a colon.
556
557 If there is only one completion, and it doesn't end with a **continuation character** (``/``, ``:``, or ``=``),
558 adds a space after the completion.
559
560 This method is exposed for overriding in subclasses; there is no need to use it directly.
561 """
562 special_chars = "\\"
563 # If the word under the cursor was quoted, escape the quote char.
564 # Otherwise, escape all special characters and specially handle all COMP_WORDBREAKS chars.
565 if cword_prequote == "":
566 # Bash mangles completions which contain characters in COMP_WORDBREAKS.
567 # This workaround has the same effect as __ltrim_colon_completions in bash_completion
568 # (extended to characters other than the colon).
569 if last_wordbreak_pos:
570 completions = [c[last_wordbreak_pos + 1:] for c in completions]
571 special_chars += "();<>|&!`$* \t\n\"'"
572 elif cword_prequote == '"':
573 special_chars += '"`$!'
574
575 if os.environ.get("_ARGCOMPLETE_SHELL") in ("tcsh", "fish"):
576 # tcsh and fish escapes special characters itself.
577 special_chars = ""
578 elif cword_prequote == "'":
579 # Nothing can be escaped in single quotes, so we need to close
580 # the string, escape the single quote, then open a new string.
581 special_chars = ""
582 completions = [c.replace("'", r"'\''") for c in completions]
583
584 for char in special_chars:
585 completions = [c.replace(char, "\\" + char) for c in completions]
586
587 if self.append_space:
588 # Similar functionality in bash was previously turned off by supplying the "-o nospace" option to complete.
589 # Now it is conditionally disabled using "compopt -o nospace" if the match ends in a continuation character.
590 # This code is retained for environments where this isn't done natively.
591 continuation_chars = "=/:"
592 if len(completions) == 1 and completions[0][-1] not in continuation_chars:
593 if cword_prequote == "":
594 completions[0] += " "
595
596 return completions
597
598 def rl_complete(self, text, state):
599 """
600 Alternate entry point for using the argcomplete completer in a readline-based REPL. See also
601 `rlcompleter <https://docs.python.org/2/library/rlcompleter.html#completer-objects>`_.
602 Usage:
603
604 .. code-block:: python
605
606 import argcomplete, argparse, readline
607 parser = argparse.ArgumentParser()
608 ...
609 completer = argcomplete.CompletionFinder(parser)
610 readline.set_completer_delims("")
611 readline.set_completer(completer.rl_complete)
612 readline.parse_and_bind("tab: complete")
613 result = input("prompt> ")
614
615 (Use ``raw_input`` instead of ``input`` on Python 2, or use `eight <https://github.com/kislyuk/eight>`_).
616 """
617 if state == 0:
618 cword_prequote, cword_prefix, cword_suffix, comp_words, first_colon_pos = split_line(text)
619 comp_words.insert(0, sys.argv[0])
620 matches = self._get_completions(comp_words, cword_prefix, cword_prequote, first_colon_pos)
621 self._rl_matches = [text + match[len(cword_prefix):] for match in matches]
622
623 if state < len(self._rl_matches):
624 return self._rl_matches[state]
625 else:
626 return None
627
628 def get_display_completions(self):
629 """
630 This function returns a mapping of option names to their help strings for displaying to the user
631
632 Usage:
633
634 .. code-block:: python
635
636 def display_completions(substitution, matches, longest_match_length):
637 _display_completions = argcomplete.autocomplete.get_display_completions()
638 print("")
639 if _display_completions:
640 help_len = [len(x) for x in _display_completions.values() if x]
641
642 if help_len:
643 maxlen = max([len(x) for x in _display_completions])
644 print("\\n".join("{0:{2}} -- {1}".format(k, v, maxlen)
645 for k, v in sorted(_display_completions.items())))
646 else:
647 print(" ".join(k for k in sorted(_display_completions)))
648 else:
649 print(" ".join(x for x in sorted(matches)))
650
651 import readline
652 print("cli /> {0}".format(readline.get_line_buffer()), end="")
653 readline.redisplay()
654
655 ...
656 readline.set_completion_display_matches_hook(display_completions)
657
658 """
659 return {" ".join(k): v for k, v in self._display_completions.items()}
660
661 class ExclusiveCompletionFinder(CompletionFinder):
662 @staticmethod
663 def _action_allowed(action, parser):
664 if not CompletionFinder._action_allowed(action, parser):
665 return False
666
667 append_classes = (argparse._AppendAction, argparse._AppendConstAction)
668 if action._orig_class in append_classes:
669 return True
670
671 if action not in parser._seen_non_default_actions:
672 return True
673
674 return False
675
676 autocomplete = CompletionFinder()
677 autocomplete.__doc__ = """ Use this to access argcomplete. See :meth:`argcomplete.CompletionFinder.__call__()`. """
678
679 def warn(*args):
680 """
681 Prints **args** to standard error when running completions. This will interrupt the user's command line interaction;
682 use it to indicate an error condition that is preventing your completer from working.
683 """
684 print("\n", file=debug_stream, *args)