Skip to content

Commit 49afe6a

Browse files
authored
Merge pull request #690 from julia-vscode/import
Add auto fix for some missing refs
2 parents e071959 + ecf39b1 commit 49afe6a

File tree

4 files changed

+56
-1
lines changed

4 files changed

+56
-1
lines changed

src/requests/actions.jl

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,9 @@ function process(r::JSONRPC.Request{Val{Symbol("textDocument/codeAction")},CodeA
2121
if is_in_fexpr(x, CSTParser.defines_struct)
2222
push!(commands, Command("Add default constructor", "AddDefaultConstructor", arguments))
2323
end
24+
if is_fixable_missing_ref(x, r.params.context)
25+
push!(commands, Command("Fix missing reference", "FixMissingRef", arguments))
26+
end
2427
# if r.params.range.start.line != r.params.range.stop.line # selection across _line_offsets
2528
# push!(commands, Command("Wrap in `if` block.", "WrapIfBlock", arguments))
2629
# end
@@ -49,6 +52,8 @@ function process(r::JSONRPC.Request{Val{Symbol("workspace/executeCommand")},Exec
4952
end
5053
elseif r.params.command == "WrapIfBlock"
5154
wrap_block(get_expr(getcst(doc), r.params.arguments[2]:r.params.arguments[3]), r.id + 1, server, :if)
55+
elseif r.params.command == "FixMissingRef"
56+
applymissingreffix(x, server)
5257
end
5358
end
5459

@@ -265,3 +270,36 @@ function wrap_block(x::EXPR, id, server, type)
265270

266271
JSONRPCEndpoints.send_request(server.jr_endpoint, "workspace/applyEdit", ApplyWorkspaceEditParams(missing, WorkspaceEdit(nothing, TextDocumentEdit[tde])))
267272
end
273+
274+
275+
function is_fixable_missing_ref(x::EXPR, cac::CodeActionContext)
276+
if !isempty(cac.diagnostics) && any(startswith(d.message, "Missing reference") for d::Diagnostic in cac.diagnostics) && CSTParser.isidentifier(x)
277+
xname = StaticLint.valofid(x)
278+
tls = StaticLint.retrieve_toplevel_scope(x)
279+
if tls.modules !== nothing
280+
for (n,m) in tls.modules
281+
if (m isa SymbolServer.ModuleStore && haskey(m, Symbol(xname))) || (m isa StaticLint.Scope && StaticLint.scopehasbinding(m, xname))
282+
return true
283+
end
284+
end
285+
end
286+
end
287+
return false
288+
end
289+
290+
function applymissingreffix(x, server)
291+
xname = StaticLint.valofid(x)
292+
file, offset = get_file_loc(x)
293+
l, c = get_position_at(file, offset)
294+
tls = StaticLint.retrieve_toplevel_scope(x)
295+
if tls.modules !== nothing
296+
for (n,m) in tls.modules
297+
if (m isa SymbolServer.ModuleStore && haskey(m, Symbol(xname))) || (m isa StaticLint.Scope && StaticLint.scopehasbinding(m, xname))
298+
tde = TextDocumentEdit(VersionedTextDocumentIdentifier(file._uri, file._version), TextEdit[
299+
TextEdit(Range(file, offset .+ (0:0)), string(n, "."))
300+
])
301+
JSONRPCEndpoints.send_request(server.jr_endpoint, "workspace/applyEdit", ApplyWorkspaceEditParams(missing, WorkspaceEdit(nothing, TextDocumentEdit[tde])))
302+
end
303+
end
304+
end
305+
end

src/requests/init.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ const serverCapabilities = ServerCapabilities(
2323
missing,
2424
true,
2525
false,
26-
ExecuteCommandOptions(missing, String["ExplicitPackageVarImport", "ExpandFunction", "AddDefaultConstructor", "ReexportModule"]),
26+
ExecuteCommandOptions(missing, String["ExplicitPackageVarImport", "ExpandFunction", "AddDefaultConstructor", "ReexportModule", "FixMissingRef"]),
2727
false,
2828
true,
2929
WorkspaceOptions(WorkspaceFoldersOptions(true, true)),

test/runtests.jl

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,5 +17,8 @@ end
1717
@testset "edit" begin
1818
include("text_edit.jl")
1919
end
20+
@testset "actions" begin
21+
include("test_actions.jl")
22+
end
2023

2124
end

test/test_actions.jl

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
server = LanguageServerInstance(IOBuffer(), IOBuffer(), dirname(Pkg.Types.Context().env.project_file), first(Base.DEPOT_PATH))
2+
server.runlinter = true
3+
4+
LanguageServer.process(LanguageServer.parse(LanguageServer.JSONRPC.Request, Dict("jsonrpc"=>"2.0","id"=>0,"method"=>"initialize","params"=>init_request)), server)
5+
6+
testtext = """
7+
decode_overlong
8+
"""
9+
LanguageServer.process(LanguageServer.JSONRPC.Request{Val{Symbol("textDocument/didOpen")},LanguageServer.DidOpenTextDocumentParams}(0, LanguageServer.DidOpenTextDocumentParams(LanguageServer.TextDocumentItem("testdoc", "julia", 0, testtext))), server)
10+
11+
doc = LanguageServer.getdocument(server, LanguageServer.URI2("testdoc"))
12+
13+
@test !isempty(LanguageServer.process(LanguageServer.JSONRPC.Request{Val{Symbol("textDocument/codeAction")},LanguageServer.CodeActionParams}(0, LanguageServer.CodeActionParams(LanguageServer.TextDocumentIdentifier("testdoc"), LanguageServer.Range(LanguageServer.Position(0,1),LanguageServer.Position(0,1)), LanguageServer.CodeActionContext(LanguageServer.Diagnostic[doc.diagnostics[1]], missing))), server))
14+

0 commit comments

Comments
 (0)