Skip to content

Commit b2cce9f

Browse files
author
Kaushik Ghose
committed
Merge branch 'feature/hoverdocs'
2 parents 87a748f + 17e024e commit b2cce9f

12 files changed

+45
-13
lines changed

Readme.md

+1
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ This is a [language server] for
1717
- Outline view (Symbols) + Step symbols
1818
- Type validations
1919
- Port validations
20+
- Display language documentation on hover
2021

2122
![Benten + VS Code](https://raw.githubusercontent.com/rabix/benten/master/media/2019.12.03/full-window.png)
2223

benten/code/intelligence.py

+4-3
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
from typing import List
1313
import pathlib
1414

15-
from ..langserver.lspobjects import (Position, Range, CompletionItem)
15+
from ..langserver.lspobjects import (Position, Range, CompletionItem, Hover)
1616
from .executioncontext import ExecutionContext
1717

1818
import logging
@@ -28,14 +28,15 @@ def __init__(self, loc: Range):
2828

2929
class IntelligenceNode:
3030

31-
def __init__(self, completions: List[str]=None):
31+
def __init__(self, completions: List[str] = None, doc: str = ""):
3232
self._completions = completions or []
33+
self.doc = doc
3334

3435
def completion(self):
3536
return [CompletionItem(label=c) for c in self._completions]
3637

3738
def hover(self):
38-
pass
39+
return Hover(self.doc, is_markdown=True)
3940

4041
def definition(self):
4142
pass

benten/cwl/arraytype.py

+3
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,9 @@ def parse(self,
3333
value_range: Range = None,
3434
requirements=None):
3535

36+
if not isinstance(node, list):
37+
return
38+
3639
for n, v in enumerate(node):
3740
inferred_type = infer_type(v, self.types)
3841
inferred_type.parse(

benten/cwl/basetype.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,8 @@ class TypeCheck:
3131

3232
class CWLBaseType(IntelligenceNode):
3333

34-
def __init__(self, name):
35-
super().__init__()
34+
def __init__(self, name, doc: str = ""):
35+
super().__init__(doc=doc)
3636
self.name = name
3737

3838
def check(self, node, node_key: str=None, map_sp: MapSubjectPredicate=None) -> TypeCheck:

benten/cwl/expressiontype.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@ def _self_is_in_step(_path):
126126
res = "Job inputs have not been filled out"
127127

128128
logger.debug(f"Guessing expression inputs are: {self.guess_inputs()}")
129-
return Hover(res, self.range)
129+
return Hover(res, self.range, wrap_as_code_block=True)
130130

131131
def definition(self):
132132
# Hijacking this to show the sample inputs file

benten/cwl/linkedfiletype.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ def parse(self,
4141
code_intel.add_lookup_node(ln)
4242

4343
def hover(self):
44-
return Hover(self._contents)
44+
return Hover(self._contents, wrap_as_code_block=True)
4545

4646
def definition(self):
4747
if isinstance(self.full_path, pathlib.Path):

benten/cwl/recordtype.py

+11-4
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,8 @@
22

33
from typing import Dict
44

5-
from .basetype import CWLBaseType, IntelligenceContext, Intelligence, MapSubjectPredicate, TypeCheck, Match
5+
from .basetype import (CWLBaseType, IntelligenceContext, Intelligence, IntelligenceNode,
6+
MapSubjectPredicate, TypeCheck, Match)
67
from .linkedfiletype import CWLLinkedFile
78
from .linkedschemadeftype import CWLLinkedSchemaDef
89
from .importincludetype import CWLImportInclude
@@ -23,8 +24,7 @@
2324
class CWLRecordType(CWLBaseType):
2425

2526
def __init__(self, name: str, doc: str, fields: Dict[str, 'CWLFieldType']):
26-
super().__init__(name)
27-
self.doc = doc
27+
super().__init__(name, doc=doc)
2828
self.fields = fields
2929
self.required_fields = set((k for k, v in self.fields.items() if v.required))
3030
self.all_fields = set(self.fields.keys())
@@ -116,8 +116,15 @@ def parse(self,
116116
value_range = get_range_for_value(node, k)
117117

118118
# key completer
119+
_field = self.fields.get(k)
120+
_key_doc = (_field.doc or "") if _field is not None else ""
121+
_key_doc += "\n---\n## Sibling fields\n\n```" + \
122+
"\n".join(f"- {k}" for k in self.fields.keys()) + \
123+
"\n```\n"
124+
_key_doc += f"\n---\n## {self.name or '-'}\n\n" + (self.doc or "")
119125
ln = LookupNode(loc=key_range)
120-
ln.intelligence_node = self
126+
ln.intelligence_node = IntelligenceNode(
127+
completions=list(self.fields.keys()), doc=_key_doc) # self
121128
code_intel.add_lookup_node(ln)
122129

123130
# TODO: looks like this logic and the logic in lomtype can be combined

benten/langserver/lspobjects.py

+6-1
Original file line numberDiff line numberDiff line change
@@ -236,12 +236,17 @@ def __init__(self, name, kind, _range, selection_range, detail=None, children=No
236236

237237

238238
class Hover(LSPObject):
239-
def __init__(self, contents, _range=None, wrap_as_code_block=True):
239+
def __init__(self, contents, _range=None, wrap_as_code_block=False, is_markdown=False):
240240
if wrap_as_code_block:
241241
self.contents = MarkupContent(
242242
kind="markdown",
243243
value="```\n" + contents + "\n```"
244244
)
245+
elif is_markdown:
246+
self.contents = MarkupContent(
247+
kind="markdown",
248+
value=contents
249+
)
245250
else:
246251
self.contents = contents
247252

benten/version.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
# Copyright (c) 2019-2020 Seven Bridges. See LICENSE
22

3-
__version__ = "2020.02.19"
3+
__version__ = "2020.03.10"

docs/features.md

+6
Original file line numberDiff line numberDiff line change
@@ -46,3 +46,9 @@
4646
<img src="https://github.com/rabix/benten/blob/master/media/2019.10.22/workflow-connection-validations.png"></img>
4747
<figcaption>Port validations</figcaption>
4848
</figure>
49+
<hr/>
50+
51+
<figure>
52+
<img src="https://github.com/rabix/benten/blob/master/media/2020.03.09/documentation-on-hover.png"></img>
53+
<figcaption>Language documentation on hover</figcaption>
54+
</figure>
148 KB
Loading

tests/test_code_intelligence.py

+9
Original file line numberDiff line numberDiff line change
@@ -176,3 +176,12 @@ def test_requirements_completion():
176176

177177
cmpl = doc.completion(Position(12, 5))
178178
assert "dockerLoad" in [c.label for c in cmpl]
179+
180+
181+
def test_docs_on_hover():
182+
this_path = current_path / "cwl" / "misc" / "wf-when-input.cwl"
183+
doc = load(doc_path=this_path, type_dicts=type_dicts)
184+
185+
hov = doc.hover(Position(10, 6))
186+
assert "Sibling" in hov.contents.value
187+
assert hov.contents.kind == "markdown"

0 commit comments

Comments
 (0)