Better completions! lazy documentation, deduplicated editRange. I have no tests for these completions >:^)

This commit is contained in:
XeroOl 2025-04-26 16:29:36 -05:00
parent 75839a2f13
commit 39fdd0c282
5 changed files with 38 additions and 16 deletions

View File

@ -221,12 +221,13 @@ find the definition `10`, but if `opts.stop-early?` is set, it would find
(assert (= (type name) :string) "search-name-and-scope needs a string")
(let [split (utils.multi-sym-split name)
stack (stack-add-split! [] split)
base-name (. split 1)
opts (or ?opts {})]
(case (docs.get-builtin server (. split 1))
(case (docs.get-builtin server base-name)
metadata (search-document server metadata stack opts)
_ (case (find-local-definition file name scope)
_ (case (find-local-definition file base-name scope)
def (search-val server file def.definition (stack-add-keys! stack def.keys) opts)
_ (case (docs.get-global server (. split 1))
_ (case (docs.get-global server base-name)
metadata (search-document server metadata stack opts))))))
(λ past? [?ast byte]

View File

@ -26,7 +26,7 @@
seen {}]
(fn add-completion! [name definition ?kind]
(table.insert results (format.completion-item-format name definition range ?kind)))
(table.insert results (format.completion-item-format server name definition range ?kind)))
(fn add-completion-recursively! [name definition]
"add the completion. also recursively adds the fields' completions"
@ -101,6 +101,20 @@
(io.stderr:write "BAD!!!! undocumented special: " (tostring special) "\n")
{:label special}))))
(set scope scope.parent))
results))
(if server.can-do-good-completions?
{:itemDefaults {:editRange range :data {: uri : byte}}
:items results}
results)))
{: textDocument/completion}
(fn completionItem/resolve [server _send completion-item]
(let [{: uri : byte} completion-item.data
file (files.get-by-uri server uri)
(_symbol parents) (analyzer.find-symbol file.ast byte)
scope (or (accumulate [?find nil _ parent (ipairs parents) &until ?find]
(. file.scopes parent))
file.scope)]
(case (analyzer.search-name-and-scope server file completion-item.label scope)
result (doto completion-item (tset :documentation (format.hover-format result))))))
{: textDocument/completion
: completionItem/resolve}

View File

@ -96,6 +96,12 @@ However, when not an option, fennel-ls will fall back to positionEncoding=\"utf-
(set server.macro-modules {})
(set server.root-uri params.rootUri)
(set server.position-encoding (choose-position-encoding params))
(set server.can-do-good-completions?
;; if client supports CompletionClientCapabilites.completionList.itemDefaults.editRange
;; and CompletionClientCapabilites.completionList.itemDefaults.data
(case (?. params :capabilities :textDocument :completion :completionList :itemDefaults)
completion-item-defaults (and (accumulate [found nil _ v (ipairs completion-item-defaults) &until found] (= v :editRange))
(accumulate [found nil _ v (ipairs completion-item-defaults) &until found] (= v :data)))))
(reload server))
(λ validate [{: configuration} invalid]

View File

@ -172,17 +172,16 @@ fntype is one of fn or λ or lambda"
:Snippet 15 :Color 16 :File 17 :Reference 18 :Folder 19 :EnumMember 20
:Constant 21 :Struct 22 :Event 23 :Operator 24 :TypeParameter 25})
(λ completion-item-format [name definition range ?kind]
(λ completion-item-format [server name definition range ?kind]
"Makes a completion item"
{:label name
:documentation (hover-format definition)
:filterText name
:textEdit {:newText name : range}
:kind (or (if ?kind (. kinds ?kind))
:documentation (when (not server.can-do-good-completions?) (hover-format definition))
:textEdit (when (not server.can-do-good-completions?) {:newText name : range})
:kind (or (when ?kind (. kinds ?kind))
(. kinds (?. definition :metadata :fls/itemKind))
(if (or (?. definition :metadata :fnl/arglist)
(?. (analyze-fn definition.definition)) :fntype)
(if (name:find ":") kinds.Method kinds.Function)))})
(when (or (?. definition :metadata :fnl/arglist)
(?. (analyze-fn definition.definition)) :fntype)
(if (name:find ":") kinds.Method kinds.Function)))})
{: signature-help-format
: hover-format

View File

@ -35,7 +35,7 @@ Every time the client sends a message, it gets handled by a function in the corr
:textDocumentSync {:openClose true :change 2}
;; :notebookDocumentSync nil
:completionProvider {:workDoneProgress false
:resolveProvider false
:resolveProvider server.can-do-good-completions?
:triggerCharacters ["(" "[" "{"]
:completionItem {:labelDetailsSupport false}}
:hoverProvider {:workDoneProgress false}
@ -162,7 +162,9 @@ Every time the client sends a message, it gets handled by a function in the corr
symbol)}
(catch _ nil))))
(set requests.textDocument/completion (. (require :fennel-ls.completions) :textDocument/completion))
(set {:textDocument/completion requests.textDocument/completion
:completionItem/resolve requests.completionItem/resolve}
(require :fennel-ls.completions))
(λ requests.textDocument/rename [server _send {: position :textDocument {: uri} :newName new-name}]
(let [file (files.get-by-uri server uri)