Skip to content

Commit 89d60ab

Browse files
committed
Fix Jedi type map (use types offered by modern Jedi)
1 parent b65f4a8 commit 89d60ab

File tree

2 files changed

+88
-29
lines changed

2 files changed

+88
-29
lines changed

pylsp/plugins/jedi_completion.py

Lines changed: 11 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -10,39 +10,21 @@
1010

1111
log = logging.getLogger(__name__)
1212

13-
# Map to the VSCode type
13+
# Map to the LSP type
14+
# > Valid values for type are ``module``, `` class ``, ``instance``, ``function``,
15+
# > ``param``, ``path``, ``keyword``, ``property`` and ``statement``.
16+
# see: https://jedi.readthedocs.io/en/latest/docs/api-classes.html#jedi.api.classes.BaseName.type
1417
_TYPE_MAP = {
15-
'none': lsp.CompletionItemKind.Value,
16-
'type': lsp.CompletionItemKind.Class,
17-
'tuple': lsp.CompletionItemKind.Class,
18-
'dict': lsp.CompletionItemKind.Class,
19-
'dictionary': lsp.CompletionItemKind.Class,
20-
'function': lsp.CompletionItemKind.Function,
21-
'lambda': lsp.CompletionItemKind.Function,
22-
'generator': lsp.CompletionItemKind.Function,
18+
'module': lsp.CompletionItemKind.Module,
19+
'namespace': lsp.CompletionItemKind.Module, # to be added in Jedi 0.18+
2320
'class': lsp.CompletionItemKind.Class,
2421
'instance': lsp.CompletionItemKind.Reference,
25-
'method': lsp.CompletionItemKind.Method,
26-
'builtin': lsp.CompletionItemKind.Class,
27-
'builtinfunction': lsp.CompletionItemKind.Function,
28-
'module': lsp.CompletionItemKind.Module,
29-
'file': lsp.CompletionItemKind.File,
30-
'path': lsp.CompletionItemKind.Text,
31-
'xrange': lsp.CompletionItemKind.Class,
32-
'slice': lsp.CompletionItemKind.Class,
33-
'traceback': lsp.CompletionItemKind.Class,
34-
'frame': lsp.CompletionItemKind.Class,
35-
'buffer': lsp.CompletionItemKind.Class,
36-
'dictproxy': lsp.CompletionItemKind.Class,
37-
'funcdef': lsp.CompletionItemKind.Function,
38-
'property': lsp.CompletionItemKind.Property,
39-
'import': lsp.CompletionItemKind.Module,
40-
'keyword': lsp.CompletionItemKind.Keyword,
41-
'constant': lsp.CompletionItemKind.Variable,
42-
'variable': lsp.CompletionItemKind.Variable,
43-
'value': lsp.CompletionItemKind.Value,
22+
'function': lsp.CompletionItemKind.Function,
4423
'param': lsp.CompletionItemKind.Variable,
45-
'statement': lsp.CompletionItemKind.Keyword,
24+
'path': lsp.CompletionItemKind.File,
25+
'keyword': lsp.CompletionItemKind.Keyword,
26+
'property': lsp.CompletionItemKind.Property, # added in Jedi 0.18
27+
'statement': lsp.CompletionItemKind.Variable
4628
}
4729

4830
# Types of parso nodes for which snippet is not included in the completion

test/plugins/test_completion.py

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@
44
import os
55
import sys
66

7+
from pathlib import Path
8+
from typing import NamedTuple, Dict
9+
710
import pytest
811

912
from pylsp import uris, lsp
@@ -50,6 +53,80 @@ def test_rope_import_completion(config, workspace):
5053
assert items is None
5154

5255

56+
class TypeCase(NamedTuple):
57+
document: str
58+
position: dict
59+
label: str
60+
expected: lsp.CompletionItemKind
61+
62+
63+
TYPE_CASES: Dict[str, TypeCase] = {
64+
'variable': TypeCase(
65+
document='test = 1\ntes',
66+
position={'line': 1, 'character': 3},
67+
label='test',
68+
expected=lsp.CompletionItemKind.Variable
69+
),
70+
'function': TypeCase(
71+
document='def test():\n pass\ntes',
72+
position={'line': 2, 'character': 3},
73+
label='test()',
74+
expected=lsp.CompletionItemKind.Function
75+
),
76+
'keyword': TypeCase(
77+
document='fro',
78+
position={'line': 0, 'character': 3},
79+
label='from',
80+
expected=lsp.CompletionItemKind.Keyword
81+
),
82+
'file': TypeCase(
83+
document='"' + __file__[:-2].replace('"', '\\"') + '"',
84+
position={'line': 0, 'character': len(__file__) - 2},
85+
label=Path(__file__).name + '"',
86+
expected=lsp.CompletionItemKind.File
87+
),
88+
'module': TypeCase(
89+
document='import statis',
90+
position={'line': 0, 'character': 13},
91+
label='statistics',
92+
expected=lsp.CompletionItemKind.Module
93+
),
94+
'class': TypeCase(
95+
document='KeyErr',
96+
position={'line': 0, 'character': 6},
97+
label='KeyError',
98+
expected=lsp.CompletionItemKind.Class
99+
),
100+
'property': TypeCase(
101+
document=(
102+
'class A:\n'
103+
' @property\n'
104+
' def test(self):\n'
105+
' pass\n'
106+
'A().tes'
107+
),
108+
position={'line': 4, 'character': 5},
109+
label='test',
110+
expected=lsp.CompletionItemKind.Property
111+
)
112+
}
113+
114+
115+
@pytest.mark.parametrize('case', list(TYPE_CASES.values()), ids=list(TYPE_CASES.keys()))
116+
def test_jedi_completion_type(case, config, workspace):
117+
# pylint: disable=C0415
118+
import jedi
119+
120+
# property support was introduced in 0.18
121+
if case.expected == lsp.CompletionItemKind.Property and jedi.__version__.startswith('0.17'):
122+
return
123+
124+
doc = Document(DOC_URI, workspace, case.document)
125+
items = pylsp_jedi_completions(config, doc, case.position)
126+
items = {i['label']: i for i in items}
127+
assert items[case.label]['kind'] == case.expected
128+
129+
53130
def test_jedi_completion(config, workspace):
54131
# Over 'i' in os.path.isabs(...)
55132
com_position = {'line': 1, 'character': 15}

0 commit comments

Comments
 (0)