|
1 | 1 | # Copyright 2017 Palantir Technologies, Inc. |
2 | 2 | import logging |
| 3 | +import time |
3 | 4 | from pyls import hookimpl, lsp, _utils |
| 5 | +from contextlib import contextmanager |
| 6 | +import signal |
4 | 7 |
|
5 | 8 | log = logging.getLogger(__name__) |
6 | 9 |
|
|
38 | 41 | 'statement': lsp.CompletionItemKind.Keyword, |
39 | 42 | } |
40 | 43 |
|
| 44 | +COMPLETION_CACHE = {} |
| 45 | + |
| 46 | +@contextmanager |
| 47 | +def timeout(time): |
| 48 | + # Register a function to raise a TimeoutError on the signal. |
| 49 | + signal.signal(signal.SIGALRM, raise_timeout) |
| 50 | + # Schedule the signal to be sent after ``time``. |
| 51 | + signal.setitimer(signal.SIGALRM, time) |
| 52 | + |
| 53 | + try: |
| 54 | + yield |
| 55 | + except TimeoutError: |
| 56 | + pass |
| 57 | + finally: |
| 58 | + # Unregister the signal so it won't be triggered |
| 59 | + # if the timeout is not reached. |
| 60 | + signal.signal(signal.SIGALRM, signal.SIG_IGN) |
| 61 | + |
| 62 | + |
| 63 | +def raise_timeout(signum, frame): |
| 64 | + raise TimeoutError |
41 | 65 |
|
42 | 66 | @hookimpl |
43 | 67 | def pyls_completions(config, document, position): |
44 | 68 | definitions = document.jedi_script(position).completions() |
45 | 69 | if not definitions: |
46 | 70 | return None |
47 | 71 |
|
| 72 | + if len(definitions) > 40: |
| 73 | + definitions = definitions[:40] |
| 74 | + |
48 | 75 | completion_capabilities = config.capabilities.get('textDocument', {}).get('completion', {}) |
49 | 76 | snippet_support = completion_capabilities.get('completionItem', {}).get('snippetSupport') |
50 | 77 |
|
51 | 78 | settings = config.plugin_settings('jedi_completion', document_path=document.path) |
52 | 79 | should_include_params = settings.get('include_params') |
53 | 80 |
|
54 | | - return [_format_completion(d, snippet_support and should_include_params) for d in definitions] or None |
| 81 | + result = [_format_completion(d, i, snippet_support and should_include_params) for i, d in enumerate(definitions)] or None |
| 82 | + return result |
55 | 83 |
|
56 | | - |
57 | | -def _format_completion(d, include_params=True): |
58 | | - completion = { |
59 | | - 'label': _label(d), |
60 | | - 'kind': _TYPE_MAP.get(d.type), |
61 | | - 'detail': _detail(d), |
| 84 | +@hookimpl |
| 85 | +def pyls_completion_detail(config, item): |
| 86 | + d = COMPLETION_CACHE.get(item) |
| 87 | + if d: |
| 88 | + completion = { |
| 89 | + 'label': '', #_label(d), |
| 90 | + 'kind': _TYPE_MAP[d.type], |
| 91 | + 'detail': '', #_detail(d), |
62 | 92 | 'documentation': _utils.format_docstring(d.docstring()), |
63 | | - 'sortText': _sort_text(d), |
| 93 | + 'sortText': '', #_sort_text(d), |
| 94 | + 'insertText': d.name |
| 95 | + } |
| 96 | + return completion |
| 97 | + else: |
| 98 | + print('Completion missing') |
| 99 | + return None |
| 100 | + |
| 101 | +def _format_completion(d, i, include_params=True): |
| 102 | + COMPLETION_CACHE[d.name] = d |
| 103 | + completion = { |
| 104 | + 'label': '', #_label(d), |
| 105 | + 'kind': '', |
| 106 | + 'detail': '', #_detail(d), |
| 107 | + 'documentation': _utils.format_docstring(d.docstring()) if i == 0 else '', |
| 108 | + 'sortText': '', #_sort_text(d), |
64 | 109 | 'insertText': d.name |
65 | 110 | } |
66 | | - |
67 | | - if include_params and hasattr(d, 'params') and d.params: |
68 | | - positional_args = [param for param in d.params if '=' not in param.description] |
69 | | - |
70 | | - # For completions with params, we can generate a snippet instead |
71 | | - completion['insertTextFormat'] = lsp.InsertTextFormat.Snippet |
72 | | - snippet = d.name + '(' |
73 | | - for i, param in enumerate(positional_args): |
74 | | - snippet += '${%s:%s}' % (i + 1, param.name) |
75 | | - if i < len(positional_args) - 1: |
76 | | - snippet += ', ' |
77 | | - snippet += ')$0' |
78 | | - completion['insertText'] = snippet |
| 111 | +# if include_params and hasattr(d, 'params') and d.params: |
| 112 | + # positional_args = [param for param in d.params if '=' not in param.description] |
| 113 | + |
| 114 | + # # For completions with params, we can generate a snippet instead |
| 115 | + # completion['insertTextFormat'] = lsp.InsertTextFormat.Snippet |
| 116 | + # snippet = d.name + '(' |
| 117 | + # for i, param in enumerate(positional_args): |
| 118 | + # snippet += '${%s:%s}' % (i + 1, param.name) |
| 119 | + # if i < len(positional_args) - 1: |
| 120 | + # snippet += ', ' |
| 121 | + # snippet += ')$0' |
| 122 | + # completion['insertText'] = snippet |
79 | 123 |
|
80 | 124 | return completion |
81 | 125 |
|
|
0 commit comments