summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorw0rp <devw0rp@gmail.com>2018-09-18 17:43:17 +0100
committerw0rp <devw0rp@gmail.com>2018-09-18 17:43:17 +0100
commit213a901ccd237903c7decb00696418e1abc930c9 (patch)
tree2219e3fac3cd1812e3b58f10eff7b8b189ad1a56
parentddb3e6d57acfc9081f8c6846d896542014e3024b (diff)
downloadale-213a901ccd237903c7decb00696418e1abc930c9.zip
Stop tsserver from causing errors to be rendered redundantly
-rw-r--r--autoload/ale/lsp_linter.vim16
-rw-r--r--test/test_redundant_tsserver_rendering_avoided.vader136
2 files changed, 151 insertions, 1 deletions
diff --git a/autoload/ale/lsp_linter.vim b/autoload/ale/lsp_linter.vim
index 8fbad12f..a11c76bc 100644
--- a/autoload/ale/lsp_linter.vim
+++ b/autoload/ale/lsp_linter.vim
@@ -55,16 +55,29 @@ function! s:HandleTSServerDiagnostics(response, error_type) abort
endif
let l:thislist = ale#lsp#response#ReadTSServerDiagnostics(a:response)
+ let l:no_changes = 0
" tsserver sends syntax and semantic errors in separate messages, so we
" have to collect the messages separately for each buffer and join them
" back together again.
if a:error_type is# 'syntax'
+ if len(l:thislist) is 0 && len(get(l:info, 'syntax_loclist', [])) is 0
+ let l:no_changes = 1
+ endif
+
let l:info.syntax_loclist = l:thislist
else
+ if len(l:thislist) is 0 && len(get(l:info, 'semantic_loclist', [])) is 0
+ let l:no_changes = 1
+ endif
+
let l:info.semantic_loclist = l:thislist
endif
+ if l:no_changes
+ return
+ endif
+
let l:loclist = get(l:info, 'semantic_loclist', [])
\ + get(l:info, 'syntax_loclist', [])
@@ -99,9 +112,10 @@ endfunction
function! ale#lsp_linter#HandleLSPResponse(conn_id, response) abort
let l:method = get(a:response, 'method', '')
- let l:linter_name = get(s:lsp_linter_map, a:conn_id, '')
if get(a:response, 'jsonrpc', '') is# '2.0' && has_key(a:response, 'error')
+ let l:linter_name = get(s:lsp_linter_map, a:conn_id, '')
+
call s:HandleLSPErrorMessage(l:linter_name, a:response)
elseif l:method is# 'textDocument/publishDiagnostics'
call s:HandleLSPDiagnostics(a:conn_id, a:response)
diff --git a/test/test_redundant_tsserver_rendering_avoided.vader b/test/test_redundant_tsserver_rendering_avoided.vader
new file mode 100644
index 00000000..41cbe5e0
--- /dev/null
+++ b/test/test_redundant_tsserver_rendering_avoided.vader
@@ -0,0 +1,136 @@
+Before:
+ Save g:ale_buffer_info
+
+ function! CreateError(type, message) abort
+ let l:diagnostics = []
+
+ if !empty(a:message)
+ let l:diagnostics = [{
+ \ 'start': {'line': 1, 'offset': 1},
+ \ 'end': {'line': 1, 'offset':1},
+ \ 'text': a:message,
+ \ 'code': 1005,
+ \}]
+ endif
+
+ return {
+ \ 'seq': 0,
+ \ 'type': 'event',
+ \ 'event': a:type,
+ \ 'body': {'file': expand('%:p'), 'diagnostics': l:diagnostics},
+ \}
+ endfunction
+
+ function! CreateLoclist(message) abort
+ let l:list = []
+
+ if !empty(a:message)
+ let l:list = [{
+ \ 'lnum': 1,
+ \ 'col': 1,
+ \ 'end_lnum': 1,
+ \ 'end_col': 1,
+ \ 'text': a:message,
+ \}]
+ endif
+
+ return l:list
+ endfunction
+
+ call ale#test#SetDirectory('/testplugin/test')
+ call ale#test#SetFilename('filename.ts')
+
+ runtime autoload/ale/engine.vim
+
+ let g:ale_buffer_info = {bufnr(''): {'loclist': []}}
+ let g:ale_handle_loclist_called = 0
+
+ function! ale#engine#HandleLoclist(linter_name, buffer, loclist) abort
+ let g:ale_handle_loclist_called = 1
+ endfunction
+
+After:
+ Restore
+
+ delfunction CreateError
+ delfunction CreateLoclist
+
+ call ale#test#RestoreDirectory()
+
+ runtime autoload/ale/engine.vim
+
+Execute(An initial empty list of syntax errors should be ignored):
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('syntaxDiag', ''))
+
+ Assert !g:ale_handle_loclist_called
+
+Execute(An initial list of syntax errors should be handled):
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('syntaxDiag', 'x'))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(Subsequent empty lists should be ignored):
+ let g:ale_buffer_info[bufnr('')].syntax_loclist = []
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('syntaxDiag', ''))
+
+ Assert !g:ale_handle_loclist_called
+
+Execute(Empty then non-empty syntax errors should be handled):
+ let g:ale_buffer_info[bufnr('')].syntax_loclist = []
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('syntaxDiag', 'x'))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(Non-empty then empty syntax errors should be handled):
+ let g:ale_buffer_info[bufnr('')].syntax_loclist = CreateLoclist('x')
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('syntaxDiag', ''))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(Non-empty then non-empty syntax errors should be handled):
+ let g:ale_buffer_info[bufnr('')].syntax_loclist = CreateLoclist('x')
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('syntaxDiag', 'x'))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(An initial empty list of semantic errors should be ignored):
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('semanticDiag', ''))
+
+ Assert !g:ale_handle_loclist_called
+
+Execute(An initial list of semantic errors should be handled):
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('semanticDiag', 'x'))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(Subsequent empty lists should be ignored):
+ let g:ale_buffer_info[bufnr('')].semantic_loclist = []
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('semanticDiag', ''))
+
+ Assert !g:ale_handle_loclist_called
+
+Execute(Empty then non-empty semantic errors should be handled):
+ let g:ale_buffer_info[bufnr('')].semantic_loclist = []
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('semanticDiag', 'x'))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(Non-empty then empty semantic errors should be handled):
+ let g:ale_buffer_info[bufnr('')].semantic_loclist = CreateLoclist('x')
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('semanticDiag', ''))
+
+ Assert g:ale_handle_loclist_called
+
+Execute(Non-empty then non-empty semantic errors should be handled):
+ let g:ale_buffer_info[bufnr('')].semantic_loclist = CreateLoclist('x')
+
+ call ale#lsp_linter#HandleLSPResponse(1, CreateError('semanticDiag', 'x'))
+
+ Assert g:ale_handle_loclist_called