Skip to content

Commit c36876b

Browse files
authored
Merge pull request #1118 from julia-vscode/fe/apply_edits
apply_text_edits: make sure indices are computed with updated document.
2 parents 315d3c7 + 61cb95b commit c36876b

5 files changed

Lines changed: 28 additions & 18 deletions

File tree

src/document.jl

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -70,11 +70,6 @@ function set_is_workspace_file(doc::Document, value::Bool)
7070
doc._workspace_file = value
7171
end
7272

73-
function applytextdocumentchanges(doc::Document, change)
74-
text_document = apply_text_edits(doc._text_document, [change], get_version(doc._text_document))
75-
set_text_document!(doc, text_document)
76-
end
77-
7873
get_offset(doc::Document, line::Integer, character::Integer) = get_offset(doc._text_document, line, character)
7974
get_offset(doc::Document, p::Position) = get_offset(doc, p.line, p.character)
8075
get_offset(doc::Document, r::Range) = get_offset(doc, r.start):get_offset(doc, r.stop)

src/textdocument.jl

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,9 @@ function apply_text_edits(doc::TextDocument, edits, new_version)
8282
# No range given, replace all text
8383
content = edit.text
8484
else
85+
# Rebind doc here so that we compute the range for the updated document in
86+
# _convert_lsrange_to_jlrange when applying multiple edits
87+
doc = TextDocument(doc._uri, content, new_version)
8588
editrange = _convert_lsrange_to_jlrange(doc, edit.range)
8689
content = string(content[1:prevind(content, editrange.start)], edit.text, content[nextind(content, editrange.stop):lastindex(content)])
8790
end

test/runtests.jl

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@ using LanguageServer:
33
Document,
44
TextDocument,
55
apply_text_edits,
6-
applytextdocumentchanges,
76
get_text_document,
87
set_text_document!,
98
get_text,

test/test_document.jl

Lines changed: 23 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -48,23 +48,36 @@ s6 = "\n"
4848
d6 = Document(TextDocument(uri"untitled:none", s6, 0), false)
4949
@test get_line_offsets(get_text_document(d6)) == [0,1]
5050

51-
@testset "applytextdocumentchanges" begin
52-
doc = LS.Document(TextDocument(uri"file:///example/path/example.jl", "function foo()", 0), false)
53-
c1 = LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(0, 14), LS.Position(0, 14)),
54-
0, "\n")
55-
c2 = LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(1, 0), LS.Position(1, 0)),
56-
0, " ")
51+
@testset "apply_text_edits" begin
52+
version = 0
53+
doc = TextDocument(uri"file:///example/path/example.jl", "function foo()", version)
54+
c1 = LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(0, 14), LS.Position(0, 14)), 0, "\n")
55+
c2 = LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(1, 0), LS.Position(1, 0)), 0, " ")
5756
c3 = LS.TextDocumentContentChangeEvent(missing, missing, "println(\"Hello World\")")
5857

59-
LS.applytextdocumentchanges(doc, c1)
58+
doc = LS.apply_text_edits(doc, [c1], version += 1)
6059
@test LS.get_text(doc) == "function foo()\n"
6160
# Implicitly test for issue #403
62-
LS.applytextdocumentchanges(doc, c2)
61+
doc = LS.apply_text_edits(doc, [c2], version += 1)
6362
@test LS.get_text(doc) == "function foo()\n "
64-
LS.applytextdocumentchanges(doc, c3)
63+
doc = LS.apply_text_edits(doc, [c3], version += 1)
6564
@test LS.get_text(doc) == "println(\"Hello World\")"
65+
66+
# Test muliple edits (#1118)
67+
doc = TextDocument(uri"file:///example/path/example.jl", "module Crash\n\n\n\nend # module Crash\n", version)
68+
edits = [
69+
LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(2, 0), LS.Position(2, 0)), 0, "p"),
70+
LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(2, 1), LS.Position(2, 1)), 0, "r"),
71+
LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(2, 2), LS.Position(2, 2)), 0, "i"),
72+
LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(2, 3), LS.Position(2, 3)), 0, "n"),
73+
LS.TextDocumentContentChangeEvent(LS.Range(LS.Position(2, 4), LS.Position(2, 4)), 0, "t"),
74+
]
75+
doc = LS.apply_text_edits(doc, edits, version += 1)
76+
@test LS.get_text(doc) == "module Crash\n\nprint\n\nend # module Crash\n"
77+
6678
# doc currently has only one line, applying change to 2nd line should throw
67-
@test_throws LanguageServer.LSOffsetError LS.applytextdocumentchanges(doc, c2)
79+
doc = LS.apply_text_edits(doc, [c3], version += 1)
80+
@test_throws LanguageServer.LSOffsetError LS.apply_text_edits(doc, [c2], version += 1)
6881
end
6982

7083
@testset "UTF16 handling" begin

test/test_edit.jl

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,10 +21,10 @@ mktempdir() do dir
2121
LanguageServer.VersionedTextDocumentIdentifier(get_uri(doc), 5),
2222
[LanguageServer.TextDocumentContentChangeEvent(LanguageServer.Range(LanguageServer.Position(s1...), LanguageServer.Position(s2...)), 0, insert)]
2323
)
24-
tdcce = params.contentChanges[1]
24+
tdcce = params.contentChanges
2525

2626
# TODO: This should only re-parse necessary parts of the document
27-
LanguageServer.applytextdocumentchanges(doc, tdcce)
27+
LanguageServer.set_text_document!(doc, LanguageServer.apply_text_edits(get_text_document(doc), tdcce, 1))
2828
LanguageServer.parse_all(doc, server)
2929

3030
new_cst = CSTParser.parse(LanguageServer.get_text(doc), true)

0 commit comments

Comments
 (0)