diff --git a/autoload/ale/references.vim b/autoload/ale/references.vim index e8cbda9e..7ffa5381 100644 --- a/autoload/ale/references.vim +++ b/autoload/ale/references.vim @@ -1,4 +1,5 @@ let g:ale_default_navigation = get(g:, 'ale_default_navigation', 'buffer') +let g:ale_references_show_contents = get(g:, 'ale_references_show_contents', 1) let s:references_map = {} @@ -67,17 +68,33 @@ function! ale#references#HandleTSServerResponse(conn_id, response) abort endfunction function! ale#references#FormatLSPResponseItem(response_item, options) abort + let l:line_text = '' + + let l:line= a:response_item.range.start.line + let l:col = a:response_item.range.start.character + let l:filename = ale#util#ToResource(a:response_item.uri) + + if get(a:options, 'show_contents') == 1 + try + let l:line_text = substitute(readfile(l:filename)[l:line], '^\s*\(.\{-}\)\s*$', '\1', '') + catch + " This happens in tests + endtry + endif + if get(a:options, 'open_in') is# 'quickfix' return { - \ 'filename': ale#util#ToResource(a:response_item.uri), + \ 'filename': l:filename, \ 'lnum': a:response_item.range.start.line + 1, \ 'col': a:response_item.range.start.character + 1, + \ 'text': l:line_text, \} else return { - \ 'filename': ale#util#ToResource(a:response_item.uri), - \ 'line': a:response_item.range.start.line + 1, - \ 'column': a:response_item.range.start.character + 1, + \ 'filename': l:filename, + \ 'line': l:line + 1, + \ 'column': l:col + 1, + \ 'match': l:line_text, \} endif endfunction @@ -147,6 +164,7 @@ function! s:OnReady(line, column, options, linter, lsp_details) abort let s:references_map[l:request_id] = { \ 'use_relative_paths': has_key(a:options, 'use_relative_paths') ? a:options.use_relative_paths : 0, \ 'open_in': get(a:options, 'open_in', 'current-buffer'), + \ 'show_contents': a:options.show_contents, \} endfunction @@ -165,6 +183,8 @@ function! ale#references#Find(...) abort let l:options.open_in = 'vsplit' elseif l:option is? '-quickfix' let l:options.open_in = 'quickfix' + elseif l:option is? '-contents' + let l:options.show_contents = 1 endif endfor endif @@ -177,6 +197,10 @@ function! ale#references#Find(...) abort endif endif + if !has_key(l:options, 'show_contents') + let l:options.show_contents = ale#Var(bufnr(''), 'references_show_contents') + endif + let l:buffer = bufnr('') let [l:line, l:column] = getpos('.')[1:2] let l:column = min([l:column, len(getline(l:line))]) diff --git a/doc/ale.txt b/doc/ale.txt index 980880ca..5606754a 100644 --- a/doc/ale.txt +++ b/doc/ale.txt @@ -2270,6 +2270,16 @@ g:ale_popup_menu_enabled This setting must be set to `true` or `1` before ALE is loaded for this behavior to be enabled. See |ale-lint-settings-on-startup|. + *ale-options.references_show_contents* + *g:ale_references_show_contents* +references_show_contents +g:ale_references_show_contents + Type: |Boolean| or |Number| + Default: true + + If set to `true` or `1`, matches found by `:ALEFindReferences` will be + shown with a preview of the matching line. + *ale-options.rename_tsserver_find_in_comments* *g:ale_rename_tsserver_find_in_comments* rename_tsserver_find_in_comments @@ -4065,10 +4075,14 @@ documented in additional help files. `:ALEFindReferences -split` - Open the location in a horizontal split. `:ALEFindReferences -vsplit` - Open the location in a vertical split. `:ALEFindReferences -quickfix` - Put the locations into quickfix list. + `:ALEFindReferences -contents` - Show line contents for matches. The default method used for navigating to a new location can be changed by modifying |g:ale_default_navigation|. + The default behaviour on whether to show line content for matches can + be changed by modifying |g:ale_references_show_contents|. + You can add `-relative` to the command to view results with relatives paths, instead of absolute paths. This option has no effect if `-quickfix` is used. diff --git a/test/test_find_references.vader b/test/test_find_references.vader index ad462394..f1e67794 100644 --- a/test/test_find_references.vader +++ b/test/test_find_references.vader @@ -3,6 +3,7 @@ Before: call ale#test#SetFilename('dummy.txt') Save g:ale_default_navigation + Save g:ale_references_show_contents let g:old_filename = expand('%:p') let g:Callback = '' @@ -15,6 +16,7 @@ Before: let g:conn_id = v:null let g:InitCallback = v:null let g:ale_default_navigation = 'buffer' + let g:ale_references_show_contents = 1 runtime autoload/ale/lsp_linter.vim runtime autoload/ale/lsp.vim @@ -281,7 +283,7 @@ Execute(tsserver reference requests should be sent): \ [0, 'ts@references', {'file': expand('%:p'), 'line': 2, 'offset': 5}] \ ], \ g:message_list - AssertEqual {'42': {'open_in': 'current-buffer', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'current-buffer', 'use_relative_paths': 0}}, ale#references#GetMap() Execute('-relative' argument should enable 'use_relative_paths' in HandleTSServerResponse): runtime ale_linters/typescript/tsserver.vim @@ -291,7 +293,7 @@ Execute('-relative' argument should enable 'use_relative_paths' in HandleTSServe call g:InitCallback() - AssertEqual {'42': {'open_in': 'current-buffer', 'use_relative_paths': 1}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'current-buffer', 'use_relative_paths': 1}}, ale#references#GetMap() Execute(`-tab` should display results in tabs): runtime ale_linters/typescript/tsserver.vim @@ -301,7 +303,7 @@ Execute(`-tab` should display results in tabs): call g:InitCallback() - AssertEqual {'42': {'open_in': 'tab', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'tab', 'use_relative_paths': 0}}, ale#references#GetMap() Execute(The default navigation type should be used): runtime ale_linters/typescript/tsserver.vim @@ -312,7 +314,7 @@ Execute(The default navigation type should be used): call g:InitCallback() - AssertEqual {'42': {'open_in': 'tab', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'tab', 'use_relative_paths': 0}}, ale#references#GetMap() Execute(`-split` should display results in splits): runtime ale_linters/typescript/tsserver.vim @@ -322,7 +324,7 @@ Execute(`-split` should display results in splits): call g:InitCallback() - AssertEqual {'42': {'open_in': 'split', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'split', 'use_relative_paths': 0}}, ale#references#GetMap() Execute(`-vsplit` should display results in vsplits): runtime ale_linters/typescript/tsserver.vim @@ -332,7 +334,7 @@ Execute(`-vsplit` should display results in vsplits): call g:InitCallback() - AssertEqual {'42': {'open_in': 'vsplit', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'vsplit', 'use_relative_paths': 0}}, ale#references#GetMap() Execute(`-quickfix` should display results in quickfix): runtime ale_linters/typescript/tsserver.vim @@ -342,7 +344,7 @@ Execute(`-quickfix` should display results in quickfix): call g:InitCallback() - AssertEqual {'42': {'open_in': 'quickfix', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'quickfix', 'use_relative_paths': 0}}, ale#references#GetMap() Given python(Some Python file): foo @@ -378,11 +380,13 @@ Execute(LSP reference responses should be handled): \ 'filename': ale#path#Simplify(g:dir . '/completion_dummy_file'), \ 'line': 3, \ 'column': 8, + \ 'match': '', \ }, \ { \ 'filename': ale#path#Simplify(g:dir . '/other_file'), \ 'line': 8, \ 'column': 16, + \ 'match': '', \ }, \ ], \ g:item_list @@ -415,6 +419,163 @@ Execute(LSP reference responses should be put to quickfix): \ 2, \ len(getqflist()) +Execute(LSP reference responses should contain line contents): + let tempfile = tempname() + let contents = ['line1 sometext', 'line2 othertext', 'line3 moretext'] + call writefile(contents, tempfile) + + call ale#references#SetMap({3: { 'show_contents': 1 }}) + + call ale#references#HandleLSPResponse( + \ 1, + \ { + \ 'id': 3, + \ 'result': [ + \ { + \ 'uri': ale#path#ToFileURI(tempfile), + \ 'range': { + \ 'start': {'line': 0, 'character': 6}, + \ }, + \ }, + \ { + \ 'uri': ale#path#ToFileURI(tempfile), + \ 'range': { + \ 'start': {'line': 2, 'character': 1}, + \ }, + \ }, + \ ], + \ } + \) + AssertEqual + \ 2, + \ len(g:item_list) + + AssertEqual contents[0], g:item_list[0]['match'] + AssertEqual contents[2], g:item_list[1]['match'] + + call ale#references#SetMap({3: { 'show_contents': 1, 'open_in': 'quickfix' }}) + + call ale#references#HandleLSPResponse( + \ 1, + \ { + \ 'id': 3, + \ 'result': [ + \ { + \ 'uri': ale#path#ToFileURI(tempfile), + \ 'range': { + \ 'start': {'line': 0, 'character': 6}, + \ }, + \ }, + \ { + \ 'uri': ale#path#ToFileURI(tempfile), + \ 'range': { + \ 'start': {'line': 2, 'character': 1}, + \ }, + \ }, + \ ], + \ } + \) + + AssertEqual + \ 2, + \ len(getqflist()) + + AssertEqual contents[0], getqflist()[0]['text'] + AssertEqual contents[2], getqflist()[1]['text'] + +Execute(LSP reference responses should not contain line contents when disabled): + call ale#references#SetMap({3: { 'show_contents': 0 }}) + + call ale#references#HandleLSPResponse( + \ 1, + \ { + \ 'id': 3, + \ 'result': [ + \ { + \ 'uri': ale#path#ToFileURI('dummy'), + \ 'range': { + \ 'start': {'line': 0, 'character': 6}, + \ }, + \ }, + \ { + \ 'uri': ale#path#ToFileURI('dummy'), + \ 'range': { + \ 'start': {'line': 2, 'character': 1}, + \ }, + \ }, + \ ], + \ } + \) + AssertEqual + \ 2, + \ len(g:item_list) + + AssertEqual '', g:item_list[0]['match'] + AssertEqual '', g:item_list[1]['match'] + call ale#references#SetMap({3: { 'show_contents': 0, 'open_in': 'quickfix' }} ) + + call ale#references#HandleLSPResponse( + \ 1, + \ { + \ 'id': 3, + \ 'result': [ + \ { + \ 'uri': ale#path#ToFileURI('dummy'), + \ 'range': { + \ 'start': {'line': 0, 'character': 6}, + \ }, + \ }, + \ { + \ 'uri': ale#path#ToFileURI('dummy'), + \ 'range': { + \ 'start': {'line': 2, 'character': 1}, + \ }, + \ }, + \ ], + \ } + \) + AssertEqual + \ 2, + \ len(getqflist()) + + AssertEqual '', getqflist()[0]['text'] + AssertEqual '', getqflist()[1]['text'] + +Execute(LSP reference responses should respect the global configuration): + let g:ale_references_show_contents = 0 + call ale#references#SetMap({3: {}}) + + let tempfile = tempname() + let contents = ['line1 sometext', 'line2 othertext', 'line3 moretext'] + call writefile(contents, tempfile) + + call ale#references#HandleLSPResponse( + \ 1, + \ { + \ 'id': 3, + \ 'result': [ + \ { + \ 'uri': ale#path#ToFileURI(tempfile), + \ 'range': { + \ 'start': {'line': 0, 'character': 6}, + \ }, + \ }, + \ { + \ 'uri': ale#path#ToFileURI(tempfile), + \ 'range': { + \ 'start': {'line': 2, 'character': 1}, + \ }, + \ }, + \ ], + \ } + \) + AssertEqual + \ 2, + \ len(g:item_list) + + AssertEqual '', g:item_list[0]['match'] + AssertEqual '', g:item_list[1]['match'] + Execute(Preview windows should not be opened for empty LSP reference responses): call ale#references#SetMap({3: {}}) call ale#references#HandleLSPResponse(1, {'id': 3, 'result': []}) @@ -466,7 +627,7 @@ Execute(LSP reference requests should be sent): \ ], \ g:message_list - AssertEqual {'42': {'open_in': 'current-buffer', 'use_relative_paths': 0}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'current-buffer', 'use_relative_paths': 0}}, ale#references#GetMap() Execute('-relative' argument should enable 'use_relative_paths' in HandleLSPResponse): runtime ale_linters/python/pylsp.vim @@ -477,4 +638,4 @@ Execute('-relative' argument should enable 'use_relative_paths' in HandleLSPResp call g:InitCallback() - AssertEqual {'42': {'open_in': 'current-buffer', 'use_relative_paths': 1}}, ale#references#GetMap() + AssertEqual {'42': {'show_contents': 1, 'open_in': 'current-buffer', 'use_relative_paths': 1}}, ale#references#GetMap()