diff options
Diffstat (limited to 'lua/nvim-lsp-installer/ui/status-win/init.lua')
| -rw-r--r-- | lua/nvim-lsp-installer/ui/status-win/init.lua | 170 |
1 files changed, 117 insertions, 53 deletions
diff --git a/lua/nvim-lsp-installer/ui/status-win/init.lua b/lua/nvim-lsp-installer/ui/status-win/init.lua index 182370a7..9ab658c4 100644 --- a/lua/nvim-lsp-installer/ui/status-win/init.lua +++ b/lua/nvim-lsp-installer/ui/status-win/init.lua @@ -5,6 +5,8 @@ local Data = require "nvim-lsp-installer.data" local display = require "nvim-lsp-installer.ui.display" local settings = require "nvim-lsp-installer.settings" local lsp_servers = require "nvim-lsp-installer.servers" +local JobExecutionPool = require "nvim-lsp-installer.jobs.pool" +local jobs = require "nvim-lsp-installer.jobs.outdated-servers" local ServerHints = require "nvim-lsp-installer.ui.status-win.server_hints" local ServerSettingsSchema = require "nvim-lsp-installer.ui.status-win.components.settings-schema" @@ -53,6 +55,8 @@ local function Help(is_current_settings_expanded, vader_saber_ticks) { "Toggle server info", settings.current.ui.keymaps.toggle_server_expand }, { "Update server", settings.current.ui.keymaps.update_server }, { "Update all installed server", settings.current.ui.keymaps.update_all_servers }, + { "Check for new server version", settings.current.ui.keymaps.check_server_version }, + { "Check for new versions (all servers)", settings.current.ui.keymaps.check_outdated_servers }, { "Uninstall server", settings.current.ui.keymaps.uninstall_server }, { "Install server", settings.current.ui.keymaps.install_server }, { "Close window", CLOSE_WINDOW_KEYMAP_1 }, @@ -180,6 +184,23 @@ local function get_relative_install_time(time) end end +---@param outdated_packages OutdatedPackage[] +---@return string +local function format_new_package_versions(outdated_packages) + local result = {} + for _, outdated_package in ipairs(outdated_packages) do + table.insert( + result, + ("%s@%s → %s"):format( + outdated_package.name, + outdated_package.current_version, + outdated_package.latest_version + ) + ) + end + return table.concat(result, ", ") +end + ---@param server ServerState local function ServerMetadata(server) return Ui.Node(Data.list_not_nil( @@ -201,6 +222,12 @@ local function ServerMetadata(server) )) end), Ui.Table(Data.list_not_nil( + Data.lazy(#server.metadata.outdated_packages > 0, function() + return { + { "new version", "LspInstallerMuted" }, + { format_new_package_versions(server.metadata.outdated_packages), "LspInstallerGreen" }, + } + end), Data.lazy(server.metadata.install_timestamp_seconds, function() return { { "last updated", "LspInstallerMuted" }, @@ -253,26 +280,39 @@ end ---@param servers ServerState[] ---@param props ServerGroupProps local function InstalledServers(servers, props) - return Ui.Node(Data.list_map(function(server) - local is_expanded = props.expanded_server == server.name - return Ui.Node { - Ui.HlTextNode { - Data.list_not_nil( - { settings.current.ui.icons.server_installed, "LspInstallerGreen" }, - { " " .. server.name, "" }, - Data.when(server.deprecated, { " deprecated", "LspInstallerOrange" }) - ), - }, - Ui.Keybind(settings.current.ui.keymaps.toggle_server_expand, "EXPAND_SERVER", { server.name }), - Ui.Keybind(settings.current.ui.keymaps.update_server, "INSTALL_SERVER", { server.name }), - Ui.Keybind(settings.current.ui.keymaps.uninstall_server, "UNINSTALL_SERVER", { server.name }), - Ui.When(is_expanded, function() - return Indent { - ServerMetadata(server), - } - end), - } - end, servers)) + return Ui.Node(Data.list_map( + ---@param server ServerState + function(server) + local is_expanded = props.expanded_server == server.name + return Ui.Node { + Ui.HlTextNode { + Data.list_not_nil( + { settings.current.ui.icons.server_installed, "LspInstallerGreen" }, + { " " .. server.name, "" }, + Data.when(server.deprecated, { " deprecated", "LspInstallerOrange" }), + Data.when(server.is_checking_outdated_packages, { + " (checking for updates)", + "LspInstallerMuted", + }), + Data.when( + #server.metadata.outdated_packages > 0, + { " new version available", "LspInstallerGreen" } + ) + ), + }, + Ui.Keybind(settings.current.ui.keymaps.toggle_server_expand, "EXPAND_SERVER", { server.name }), + Ui.Keybind(settings.current.ui.keymaps.update_server, "INSTALL_SERVER", { server.name }), + Ui.Keybind(settings.current.ui.keymaps.check_server_version, "CHECK_SERVER_VERSION", { server.name }), + Ui.Keybind(settings.current.ui.keymaps.uninstall_server, "UNINSTALL_SERVER", { server.name }), + Ui.When(is_expanded, function() + return Indent { + ServerMetadata(server), + } + end), + } + end, + servers + )) end ---@param server ServerState @@ -473,6 +513,7 @@ local function create_initial_server_state(server) local server_state = { name = server.name, is_installed = server:is_installed(), + is_checking_outdated_packages = false, deprecated = server.deprecated, hints = tostring(ServerHints.new(server)), expanded_schema_properties = {}, @@ -485,6 +526,8 @@ local function create_initial_server_state(server) install_timestamp_seconds = nil, -- lazy install_dir = vim.fn.fnamemodify(server.root_dir, ":~"), filetypes = table.concat(server:get_supported_filetypes(), ", "), + ---@type OutdatedPackage[] + outdated_packages = {}, }, installer = { is_queued = false, @@ -519,6 +562,7 @@ local function init(all_servers) Ui.Keybind(HELP_KEYMAP, "TOGGLE_HELP", nil, true), Ui.Keybind(CLOSE_WINDOW_KEYMAP_1, "CLOSE_WINDOW", nil, true), Ui.Keybind(CLOSE_WINDOW_KEYMAP_2, "CLOSE_WINDOW", nil, true), + Ui.Keybind(settings.current.ui.keymaps.check_outdated_servers, "CHECK_OUTDATED_SERVERS", nil, true), Ui.Keybind(settings.current.ui.keymaps.update_all_servers, "UPDATE_ALL_SERVERS", nil, true), Header { is_showing_help = state.is_showing_help, @@ -598,12 +642,10 @@ local function init(all_servers) end) end - ---@alias ServerInstallTuple {[1]:Server, [2]: string|nil} - - ---@param server_tuple ServerInstallTuple + ---@param server Server + ---@param requested_version string|nil ---@param on_complete fun() - local function start_install(server_tuple, on_complete) - local server, requested_version = server_tuple[1], server_tuple[2] + local function start_install(server, requested_version, on_complete) mutate_state(function(state) state.servers[server.name].installer.is_queued = false state.servers[server.name].installer.is_running = true @@ -637,6 +679,9 @@ local function init(all_servers) state.servers[server.name].is_installed = success state.servers[server.name].installer.is_running = false state.servers[server.name].installer.has_run = true + if not state.expanded_server then + expand_server(server.name) + end end) if not get_state().expanded_server then expand_server(server.name) @@ -646,33 +691,9 @@ local function init(all_servers) end -- We have a queue because installers have a tendency to hog resources. - local queue - do - local max_running = settings.current.max_concurrent_installers - ---@type ServerInstallTuple[] - local q = {} - local r = 0 - - local check_queue - check_queue = vim.schedule_wrap(function() - if #q > 0 and r < max_running then - local dequeued_server = table.remove(q, 1) - r = r + 1 - start_install(dequeued_server, function() - r = r - 1 - check_queue() - end) - end - end) - - ---@param server Server - ---@param version string|nil - queue = function(server, version) - q[#q + 1] = { server, version } - check_queue() - end - end - + local job_pool = JobExecutionPool:new { + size = settings.current.max_concurrent_installers, + } ---@param server Server ---@param version string|nil local function install_server(server, version) @@ -687,7 +708,9 @@ local function init(all_servers) state.servers[server.name] = create_initial_server_state(server) state.servers[server.name].installer.is_queued = true end) - queue(server, version) + job_pool:supply(function(cb) + start_install(server, version, cb) + end) end ---@param server Server @@ -802,6 +825,27 @@ local function init(all_servers) end end + local has_opened = false + + local function identify_outdated_servers(servers) + -- Sort servers the same way as in the UI, gives a more structured impression + table.sort(servers, function(a, b) + return a.name < b.name + end) + jobs.identify_outdated_servers(servers, function(server) + mutate_state(function(state) + state.servers[server.name].is_checking_outdated_packages = true + end) + end, function(check_result) + mutate_state(function(state) + state.servers[check_result.server.name].is_checking_outdated_packages = false + if check_result.success and check_result:has_outdated_packages() then + state.servers[check_result.server.name].metadata.outdated_packages = check_result.outdated_packages + end + end) + end) + end + local function open() local open_filetypes = {} for _, open_bufnr in ipairs(vim.api.nvim_list_bufs()) do @@ -820,6 +864,13 @@ local function init(all_servers) state.prioritized_servers = Data.set_of(prioritized_servers) end) + if not has_opened then + -- Only do this automatically once - when opening the window the first time + vim.defer_fn(function() + identify_outdated_servers(lsp_servers.get_installed_servers()) + end, 100) + end + window.open { highlight_groups = { "hi def LspInstallerHeader gui=bold guifg=#ebcb8b", @@ -848,6 +899,18 @@ local function init(all_servers) ["CLOSE_WINDOW"] = function() close() end, + ["CHECK_OUTDATED_SERVERS"] = function() + vim.schedule(function() + identify_outdated_servers(lsp_servers.get_installed_servers()) + end) + end, + ["CHECK_SERVER_VERSION"] = function(e) + local server_name = e.payload[1] + local ok, server = lsp_servers.get_server(server_name) + if ok then + identify_outdated_servers { server } + end + end, ["TOGGLE_EXPAND_CURRENT_SETTINGS"] = function() mutate_state(function(state) state.is_current_settings_expanded = not state.is_current_settings_expanded @@ -902,6 +965,7 @@ local function init(all_servers) end, }, } + has_opened = true end return { |
