diff --git a/lua/go/impl.lua b/lua/go/impl.lua index 2c1df0d..c8fe192 100644 --- a/lua/go/impl.lua +++ b/lua/go/impl.lua @@ -20,7 +20,7 @@ local function get_type_name() local r, c = dim.r, dim.c utils.log('move cusror to ', r, c) vim.api.nvim_win_set_cursor(0, { r, c }) - return node_name + return node_name, name.type end local function get_interface_name() @@ -62,7 +62,9 @@ local run = function(...) end vim.cmd('redraw!') if iface == '' then - utils.notify('Impl: please input interface name e.g. io.Reader or receiver name e.g. GoImpl MyType') + utils.notify( + 'Impl: please input interface name e.g. io.Reader or receiver name e.g. GoImpl MyType' + ) -- print("Usage: GoImpl f *File io.Reader") end elseif #arg == 1 then @@ -158,19 +160,52 @@ local function complete(_, cmdline, _) local words = vim.split(cmdline, [[%s+]]) local gopls = require('go.gopls') local last = words[#words] + log(words) + -- by default complete with local type local iface = get_interface_name() local query = require('go.ts.go').query_type_declaration local bufnr = vim.api.nvim_get_current_buf() - if iface ~= nil then + local all_nodes = function(except) local nodes = require('go.ts.nodes').nodes_in_buf(query, 'go', nil, bufnr, 100000, 100000) local ns = {} log(nodes) for _, node in ipairs(nodes) do table.insert(ns, node.name) end - log(ns) - return vfn.uniq(ns) + if except then + log('remove', except) + for i, n in ipairs(ns) do + if n == except then + table.remove(ns, i) + break + end + end + if #words > 1 and #last > 1 then + local pkgs = vfn.uniq(vfn.sort(gopls.list_pkgs())) + -- attach ns in front of pkgs + for _, n in ipairs(ns) do + table.insert(pkgs, 1, n) + end + return pkgs + else + return ns + end + else + return vfn.uniq(ns) + end + end + if iface ~= nil then + local iname = vim.split(iface, '%.') + iname = iname[#iname] + log('iface', iface) + return all_nodes(iname) + end + + local struct = get_type_name() + if struct ~= nil then + log('structs', struct) + return all_nodes(struct) end if string.match(last, '^.+%..*') ~= nil then diff --git a/lua/go/lsp.lua b/lua/go/lsp.lua index 53daed8..4e8cfff 100644 --- a/lua/go/lsp.lua +++ b/lua/go/lsp.lua @@ -219,6 +219,10 @@ local function request(method, params, handler) return vim.lsp.buf_request(0, method, params, handler) end +local function request_sync(method, params, timeout_ms) + return vim.lsp.buf_request_sync(0, method, params, timeout_ms) +end + function M.gen_return(lsp_result) if not lsp_result or not lsp_result.contents then return @@ -372,6 +376,24 @@ function M.hover_returns() end) end + +function M.document_symbols(opts) + opts = opts or {} + + local bufnr = opts.bufnr or vim.api.nvim_get_current_buf() + local params = vim.lsp.util.make_position_params() + params.context = { includeDeclaration = true } + params.query = opts.prompt or '' + local symbols + vim.lsp.for_each_buffer_client(bufnr, function(client, _, _bufnr) + if client.name == 'gopls' then + symbols = client.request_sync('textDocument/documentSymbol', params, opts.timeout or 1000, _bufnr) + return symbols + end + end) + return symbols +end + local change_type = { Created = 1, Changed = 2, diff --git a/lua/go/ts/go.lua b/lua/go/ts/go.lua index d523d8c..7dc38c4 100644 --- a/lua/go/ts/go.lua +++ b/lua/go/ts/go.lua @@ -13,7 +13,8 @@ local M = { query_struct_id = '(type_spec name:(type_identifier) @definition.struct (struct_type))', query_em_struct_id = '(field_declaration name:(field_identifier) @definition.struct (struct_type))', query_struct_block = [[((type_declaration (type_spec name:(type_identifier) @struct.name type: (struct_type)))@struct.declaration)]], - query_type_declaration = [[((type_declaration (type_spec name:(type_identifier)@type_decl.name type:(type_identifier)@type_decl.type))@type_decl.declaration)]], -- rename to gotype so not confuse with type + -- query_type_declaration = [[((type_declaration (type_spec name:(type_identifier)@type_decl.name type:(type_identifier)@type_decl.type))@type_decl.declaration)]], -- rename to gotype so not confuse with type + query_type_declaration = [[((type_declaration (type_spec name:(type_identifier)@type_decl.name)))]], query_em_struct_block = [[(field_declaration name:(field_identifier)@struct.name type: (struct_type)) @struct.declaration]], query_struct_block_from_id = [[(((type_spec name:(type_identifier) type: (struct_type)))@block.struct_from_id)]], -- query_em_struct = "(field_declaration name:(field_identifier) @definition.struct type: (struct_type))",