1+ struct ServerAction
2+ command:: Command
3+ when:: Function
4+ handler:: Function
5+ end
6+
17function textDocument_codeAction_request (params:: CodeActionParams , server:: LanguageServerInstance , conn)
28 commands = Command[]
39 doc = getdocument (server, URI2 (params. textDocument. uri))
@@ -6,28 +12,12 @@ function textDocument_codeAction_request(params::CodeActionParams, server::Langu
612 x = get_expr (getcst (doc), offset)
713 arguments = Any[params. textDocument. uri, offset, offset1] # use the same arguments for all commands
814 if x isa EXPR
9- if refof (x) isa StaticLint. Binding && refof (x). val isa SymbolServer. ModuleStore
10- push! (commands, Command (" Explicitly import used package variables." , " ExplicitPackageVarImport" , arguments))
11- end
12- if parentof (x) isa EXPR && typof (parentof (x)) === CSTParser. Using && refof (x) isa StaticLint. Binding
13- if refof (x). type === StaticLint. CoreTypes. Module || (refof (x). val isa StaticLint. Binding && refof (x). val. type === StaticLint. CoreTypes. Module) || refof (x). val isa SymbolServer. ModuleStore
14- push! (commands, Command (" Re-export package variables." , " ReexportModule" , arguments))
15+ for (_,sa) in LSActions
16+ if sa. when (x, params)
17+ push! (commands, Command (sa. command. title, sa. command. command, arguments))
1518 end
1619 end
17- if is_in_fexpr (x, is_single_line_func)
18- push! (commands, Command (" Expand function definition." , " ExpandFunction" , arguments))
19- end
20- if is_in_fexpr (x, CSTParser. defines_struct)
21- push! (commands, Command (" Add default constructor" , " AddDefaultConstructor" , arguments))
22- end
23- if is_fixable_missing_ref (x, params. context)
24- push! (commands, Command (" Fix missing reference" , " FixMissingRef" , arguments))
25- end
26- # if params.range.start.line != params.range.stop.line # selection across _line_offsets
27- # push!(commands, Command("Wrap in `if` block.", "WrapIfBlock", arguments))
28- # end
2920 end
30-
3121 return commands
3222end
3323
@@ -36,22 +26,8 @@ function workspace_executeCommand_request(params::ExecuteCommandParams, server::
3626 offset = params. arguments[2 ]
3727 doc = getdocument (server, URI2 (uri))
3828 x = get_expr (getcst (doc), offset)
39- if params. command == " ExplicitPackageVarImport"
40- explicitly_import_used_variables (x, server, conn)
41- elseif params. command == " ExpandFunction"
42- expand_inline_func (x, server, conn)
43- elseif params. command == " AddDefaultConstructor"
44- add_default_constructor (x, server, conn)
45- elseif params. command == " ReexportModule"
46- if refof (x). type === StaticLint. CoreTypes. Module || (refof (x). val isa StaticLint. Binding && refof (x). val. type === StaticLint. CoreTypes. Module)
47- reexport_module (x, server, conn)
48- elseif refof (x). val isa SymbolServer. ModuleStore
49- reexport_package (x, server, conn)
50- end
51- elseif params. command == " WrapIfBlock"
52- wrap_block (get_expr (getcst (doc), params. arguments[2 ]: params. arguments[3 ]), server, :if , conn)
53- elseif params. command == " FixMissingRef"
54- applymissingreffix (x, server, conn)
29+ if haskey (LSActions, params. command)
30+ LSActions[params. command]. handler (x, server, conn)
5531 end
5632end
5733
@@ -72,14 +48,13 @@ function explicitly_import_used_variables(x::EXPR, server, conn)
7248
7349 tdes = Dict {String,TextDocumentEdit} ()
7450 vars = Set {String} () # names that need to be imported
75-
7651 # Find uses of `x` and mark edits
7752 for ref in refof (x). refs
7853 if parentof (ref) isa EXPR && typof (parentof (ref)) == CSTParser. BinaryOpCall && length (parentof (ref). args) == 3 && kindof (parentof (ref). args[2 ]) === CSTParser. Tokens. DOT && parentof (ref). args[1 ] == ref
7954 typof (parentof (ref). args[3 ]) != = CSTParser. Quotenode && continue # some malformed EXPR, skip
8055 childname = parentof (ref). args[3 ]. args[1 ]
8156 StaticLint. hasref (childname) && refof (childname) isa StaticLint. Binding && continue # check this isn't the name of something being explictly overwritten
82- ! haskey (refof (x). val. vals, valof (childname)) && continue # skip, perhaps mark as missing ref ?
57+ ! haskey (refof (x). val. vals, Symbol ( valof (childname) )) && continue # skip, perhaps mark as missing ref ?
8358
8459 file, offset = get_file_loc (ref)
8560 if ! haskey (tdes, file. _uri)
@@ -147,33 +122,6 @@ function expand_inline_func(x, server, conn)
147122 end
148123end
149124
150-
151- function add_default_constructor (x:: EXPR , server, conn)
152- sexpr = _get_parent_fexpr (x, CSTParser. defines_struct)
153- ! (sexpr. args isa Vector{EXPR}) && return
154- ismutable = length (sexpr. args) == 5
155- name = CSTParser. get_name (sexpr)
156- sig = sexpr. args[2 + ismutable]
157- block = sexpr. args[3 + ismutable]
158-
159- isempty (block. args) && return
160- any (CSTParser. defines_function (a) for a in block. args) && return # constructor already exists
161-
162- newtext = string (" \n function $(valof (name)) (args...)\n\n new" )
163- # if DataType is parameterised do something here
164-
165- newtext = string (newtext, " (" )
166- for i in 1 : length (block. args)
167- newtext = string (newtext, " " , valof (CSTParser. get_arg_name (block. args[i])))
168- newtext = string (newtext, i < length (block. args) ? " , " : " )\n end" )
169- end
170- file, offset = get_file_loc (last (block. args))
171- offset += last (block. args). span
172- tde = TextDocumentEdit (VersionedTextDocumentIdentifier (file. _uri, file. _version), TextEdit[TextEdit (Range (file, offset: offset), newtext)])
173-
174- JSONRPC. send (conn, workspace_applyEdit_request_type, ApplyWorkspaceEditParams (missing , WorkspaceEdit (missing , TextDocumentEdit[tde])))
175- end
176-
177125function is_in_fexpr (x:: EXPR , f)
178126 if f (x)
179127 return true
@@ -205,6 +153,7 @@ function get_next_line_offset(x)
205153end
206154
207155function reexport_package (x:: EXPR , server, conn)
156+ (refof (x). type === StaticLint. CoreTypes. Module || (refof (x). val isa StaticLint. Binding && refof (x). val. type === StaticLint. CoreTypes. Module)) || (refof (x). val isa SymbolServer. ModuleStore) || return
208157 mod:: SymbolServer.ModuleStore = refof (x). val
209158 using_stmt = parentof (x)
210159 file, offset = get_file_loc (x)
@@ -301,3 +250,22 @@ function applymissingreffix(x, server, conn)
301250 end
302251 end
303252end
253+
254+ # Adding a CodeAction requires defining:
255+ # * a Command (title and description);
256+ # * a function (.when) called on the currently selected expression and parameters of the CodeAction call;
257+ # * a function (.handler) called on three arguments (current expression, server and the jr connection) to implement the command.
258+ const LSActions = Dict (
259+ " ExplicitPackageVarImport" => ServerAction (Command (" Explicitly import used package variables." , " ExplicitPackageVarImport" , missing ),
260+ (x, params) -> refof (x) isa StaticLint. Binding && refof (x). val isa SymbolServer. ModuleStore,
261+ explicitly_import_used_variables),
262+ " ExpandFunction" => ServerAction (Command (" Expand function definition." , " ExpandFunction" , missing ),
263+ (x, params) -> is_in_fexpr (x, is_single_line_func),
264+ expand_inline_func),
265+ " FixMissingRef" => ServerAction (Command (" Fix missing reference" , " FixMissingRef" , missing ),
266+ (x, params) -> is_fixable_missing_ref (x, params. context),
267+ applymissingreffix),
268+ " ReexportModule" => ServerAction (Command (" Re-export package variables." , " ReexportModule" , missing ),
269+ (x, params) -> parentof (x) isa EXPR && typof (parentof (x)) === CSTParser. Using && refof (x) isa StaticLint. Binding && (refof (x). type === StaticLint. CoreTypes. Module || (refof (x). val isa StaticLint. Binding && refof (x). val. type === StaticLint. CoreTypes. Module) || refof (x). val isa SymbolServer. ModuleStore),
270+ reexport_package)
271+ )
0 commit comments