mirror of
https://github.com/xonsh/xonsh.git
synced 2025-03-04 08:24:40 +01:00
Update completer cli (#4299)
* completers: Add new completers after the non-exclusives * completer: Print whether a completer is non-exclusive * news: Add update-completer-cli
This commit is contained in:
parent
214997d170
commit
4c055d82e8
4 changed files with 86 additions and 6 deletions
24
news/update-completer-cli.rst
Normal file
24
news/update-completer-cli.rst
Normal file
|
@ -0,0 +1,24 @@
|
|||
**Added:**
|
||||
|
||||
* <news item>
|
||||
|
||||
**Changed:**
|
||||
|
||||
* The ``completer add`` command after the non-exclusive completers.
|
||||
This means it will not block them from adding their completions.
|
||||
|
||||
**Deprecated:**
|
||||
|
||||
* <news item>
|
||||
|
||||
**Removed:**
|
||||
|
||||
* <news item>
|
||||
|
||||
**Fixed:**
|
||||
|
||||
* <news item>
|
||||
|
||||
**Security:**
|
||||
|
||||
* <news item>
|
35
tests/aliases/test_completer_alias.py
Normal file
35
tests/aliases/test_completer_alias.py
Normal file
|
@ -0,0 +1,35 @@
|
|||
import pytest
|
||||
|
||||
from xonsh.built_ins import XSH
|
||||
from xonsh.completers._aliases import add_one_completer
|
||||
from xonsh.completers.tools import non_exclusive_completer
|
||||
|
||||
SIMPLE = lambda: None
|
||||
NON_EXCLUSIVE = non_exclusive_completer(lambda: None)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"initial, exp",
|
||||
(
|
||||
({}, ["new"]),
|
||||
({"simp": SIMPLE}, ["new", "simp"]),
|
||||
({"nx": NON_EXCLUSIVE}, ["nx", "new"]),
|
||||
({"nx": NON_EXCLUSIVE, "simp": SIMPLE}, ["nx", "new", "simp"]),
|
||||
(
|
||||
{"ctx1": NON_EXCLUSIVE, "ctx2": NON_EXCLUSIVE, "simp": SIMPLE},
|
||||
["ctx1", "ctx2", "new", "simp"],
|
||||
),
|
||||
(
|
||||
{"ctx1": NON_EXCLUSIVE, "ctx2": NON_EXCLUSIVE, "simp": SIMPLE},
|
||||
["ctx1", "ctx2", "new", "simp"],
|
||||
),
|
||||
(
|
||||
{"ctx1": NON_EXCLUSIVE, "simp": SIMPLE, "ctx2": NON_EXCLUSIVE},
|
||||
["ctx1", "new", "simp", "ctx2"],
|
||||
),
|
||||
),
|
||||
)
|
||||
def test_add_completer_start(monkeypatch, initial, exp):
|
||||
monkeypatch.setattr(XSH, "completers", initial)
|
||||
add_one_completer("new", SIMPLE, "start")
|
||||
assert list(XSH.completers.keys()) == exp
|
|
@ -49,7 +49,7 @@ def _register_completer(name: str, func: str, pos="start", stack=None):
|
|||
position into the list of completers at which the new
|
||||
completer should be added. It can be one of the following values:
|
||||
* "start" indicates that the completer should be added to the start of
|
||||
the list of completers (it should be run before all others)
|
||||
the list of completers (it should be run before all other exclusive completers)
|
||||
* "end" indicates that the completer should be added to the end of the
|
||||
list of completers (it should be run after all others)
|
||||
* ">KEY", where KEY is a pre-existing name, indicates that this should
|
||||
|
|
|
@ -2,7 +2,11 @@ import collections
|
|||
from xonsh.parsers.completion_context import CommandContext
|
||||
|
||||
from xonsh.built_ins import XSH
|
||||
from xonsh.completers.tools import contextual_command_completer_for, justify
|
||||
from xonsh.completers.tools import (
|
||||
contextual_command_completer_for,
|
||||
justify,
|
||||
is_exclusive_completer,
|
||||
)
|
||||
|
||||
|
||||
@contextual_command_completer_for("completer")
|
||||
|
@ -47,8 +51,20 @@ def complete_completer(command: CommandContext):
|
|||
def add_one_completer(name, func, loc="end"):
|
||||
new = collections.OrderedDict()
|
||||
if loc == "start":
|
||||
# Add new completer before the first exclusive one.
|
||||
# We don't want new completers to be before the non-exclusive ones,
|
||||
# because then they won't be used when this completer is successful.
|
||||
# On the other hand, if the new completer is non-exclusive,
|
||||
# we want it to be before all other exclusive completers so that is will always work.
|
||||
items = list(XSH.completers.items())
|
||||
first_exclusive = next(
|
||||
(i for i, (_, v) in enumerate(items) if is_exclusive_completer(v)),
|
||||
len(items),
|
||||
)
|
||||
for k, v in items[:first_exclusive]:
|
||||
new[k] = v
|
||||
new[name] = func
|
||||
for (k, v) in XSH.completers.items():
|
||||
for k, v in items[first_exclusive:]:
|
||||
new[k] = v
|
||||
elif loc == "end":
|
||||
for (k, v) in XSH.completers.items():
|
||||
|
@ -73,17 +89,22 @@ def add_one_completer(name, func, loc="end"):
|
|||
|
||||
def list_completers():
|
||||
"""List the active completers"""
|
||||
o = "Registered Completer Functions: \n"
|
||||
o = "Registered Completer Functions: (NX = Non Exclusive)\n\n"
|
||||
non_exclusive = " [NX]"
|
||||
_comp = XSH.completers
|
||||
ml = max((len(i) for i in _comp), default=0)
|
||||
exclusive_len = ml + len(non_exclusive) + 1
|
||||
_strs = []
|
||||
for c in _comp:
|
||||
if _comp[c].__doc__ is None:
|
||||
doc = "No description provided"
|
||||
else:
|
||||
doc = " ".join(_comp[c].__doc__.split())
|
||||
doc = justify(doc, 80, ml + 3)
|
||||
_strs.append("{: >{}} : {}".format(c, ml, doc))
|
||||
doc = justify(doc, 80, exclusive_len + 3)
|
||||
if is_exclusive_completer(_comp[c]):
|
||||
_strs.append("{: <{}} : {}".format(c, exclusive_len, doc))
|
||||
else:
|
||||
_strs.append("{: <{}} {} : {}".format(c, ml, non_exclusive, doc))
|
||||
return o + "\n".join(_strs) + "\n"
|
||||
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue