feat: move handler field parsing logic to handlers (#92)

This commit is contained in:
Marc Jakobi
2024-09-16 22:47:28 +02:00
committed by GitHub
parent 4ea57c6324
commit 33796eae1d
13 changed files with 235 additions and 192 deletions
+15
View File
@@ -8,6 +8,20 @@ local state = require("lz.n.handler.state").new()
---@type lz.n.CmdHandler
local M = {
spec_field = "cmd",
---@param cmd_spec? string[]|string
parse = function(result, cmd_spec)
if cmd_spec then
result.cmd = {}
end
if type(cmd_spec) == "string" then
table.insert(result.cmd, cmd_spec)
elseif type(cmd_spec) == "table" then
---@param cmd_spec_ string
vim.iter(cmd_spec):each(function(cmd_spec_)
table.insert(result.cmd, cmd_spec_)
end)
end
end,
}
---@param name string
@@ -20,6 +34,7 @@ end
---@return string[] loaded_plugin_names
local function load(cmd)
vim.api.nvim_del_user_command(cmd)
---@diagnostic disable-next-line: return-type-mismatch
return state.each_pending(cmd, loader.load)
end
+14
View File
@@ -10,6 +10,20 @@ local state = require("lz.n.handler.state").new()
local M = {
augroup = nil,
spec_field = "colorscheme",
---@param colorscheme_spec? string[]|string
parse = function(plugin, colorscheme_spec)
if colorscheme_spec then
plugin.colorscheme = {}
end
if type(colorscheme_spec) == "string" then
table.insert(plugin.colorscheme, colorscheme_spec)
elseif type(colorscheme_spec) == "table" then
---@param colorscheme_spec_ string
vim.iter(colorscheme_spec):each(function(colorscheme_spec_)
table.insert(plugin.colorscheme, colorscheme_spec_)
end)
end
end,
}
---@param name string
+44 -28
View File
@@ -10,7 +10,6 @@ local loader = require("lz.n.loader")
---@class lz.n.EventHandler: lz.n.Handler
---@field events table<string,true>
---@field group number
---@field parse fun(spec: lz.n.EventSpec): lz.n.Event
local lz_n_events = {
DeferredUIEnter = { id = "DeferredUIEnter", event = "User", pattern = "DeferredUIEnter" },
@@ -21,40 +20,57 @@ lz_n_events["User DeferredUIEnter"] = lz_n_events.DeferredUIEnter
---@type lz.n.handler.State
local state = require("lz.n.handler.state").new()
---@param spec lz.n.EventSpec
local function parse(spec)
local ret = lz_n_events[spec]
if ret then
return ret
end
if type(spec) == "string" then
local event, pattern = spec:match("^(%w+)%s+(.*)$")
event = event or spec
return { id = spec, event = event, pattern = pattern }
elseif vim.islist(spec) then
ret = { id = table.concat(spec, "|"), event = spec }
else
ret = spec --[[@as lz.n.Event]]
if not ret.id then
---@diagnostic disable-next-line: assign-type-mismatch, param-type-mismatch
ret.id = type(ret.event) == "string" and ret.event or table.concat(ret.event, "|")
if ret.pattern then
---@diagnostic disable-next-line: assign-type-mismatch, param-type-mismatch
ret.id = ret.id
.. " "
.. (
type(ret.pattern) == "string" and ret.pattern
or table.concat(ret.pattern --[[@as table]], ", ")
)
end
end
end
return ret
end
---@type lz.n.EventHandler
local M = {
events = {},
group = vim.api.nvim_create_augroup("lz_n_handler_event", { clear = true }),
spec_field = "event",
---@param spec lz.n.EventSpec
parse = function(spec)
local ret = lz_n_events[spec]
if ret then
return ret
---@param event_spec? lz.n.EventSpec
parse = function(plugin, event_spec)
if event_spec then
plugin.event = {}
end
if type(spec) == "string" then
local event, pattern = spec:match("^(%w+)%s+(.*)$")
event = event or spec
return { id = spec, event = event, pattern = pattern }
elseif vim.islist(spec) then
ret = { id = table.concat(spec, "|"), event = spec }
else
ret = spec --[[@as lz.n.Event]]
if not ret.id then
---@diagnostic disable-next-line: assign-type-mismatch, param-type-mismatch
ret.id = type(ret.event) == "string" and ret.event or table.concat(ret.event, "|")
if ret.pattern then
---@diagnostic disable-next-line: assign-type-mismatch, param-type-mismatch
ret.id = ret.id
.. " "
.. (
type(ret.pattern) == "string" and ret.pattern
or table.concat(ret.pattern --[[@as table]], ", ")
)
end
end
if type(event_spec) == "string" or type(event_spec) == "table" and (event_spec.event or event_spec.pattern) then
local event = parse(event_spec)
table.insert(plugin.event, event)
elseif type(event_spec) == "table" then
---@param ev lz.n.EventSpec[]
vim.iter(event_spec):each(function(ev)
local event = parse(ev)
table.insert(plugin.event, event)
end)
end
return ret
end,
}
+28 -10
View File
@@ -1,21 +1,39 @@
local event = require("lz.n.handler.event")
---@class lz.n.FtHandler: lz.n.Handler
---@field parse fun(spec: lz.n.EventSpec): lz.n.Event
---@param value string
---@return lz.n.Event
local function parse(value)
return {
id = value,
event = "FileType",
pattern = value,
}
end
---@type lz.n.FtHandler
local M = {
spec_field = "ft",
---@param value string
---@return lz.n.Event
parse = function(value)
return {
id = value,
event = "FileType",
pattern = value,
}
end,
lookup = event.lookup,
---@param ft_spec? string[]|string
parse = function(plugin, ft_spec)
if ft_spec then
plugin.event = plugin.event or {}
---@diagnostic disable-next-line: inject-field
plugin.ft = nil
end
if type(ft_spec) == "string" then
local ft = parse(ft_spec)
table.insert(plugin.event, ft)
elseif type(ft_spec) == "table" then
---@param ft_spec_ string
vim.iter(ft_spec):each(function(ft_spec_)
local ft = parse(ft_spec_)
table.insert(plugin.event, ft)
end)
end
end,
}
---@param plugin lz.n.Plugin
+25 -9
View File
@@ -40,15 +40,6 @@ function M.lookup(name, opts)
return result and vim.deepcopy(result)
end
---@param spec lz.n.PluginSpec
---@return boolean
function M.is_lazy(spec)
---@diagnostic disable-next-line: undefined-field
return spec.lazy or vim.iter(handlers):any(function(spec_field, _)
return spec[spec_field] ~= nil
end)
end
---@param handler lz.n.Handler
---@return boolean success
function M.register_handler(handler)
@@ -97,6 +88,31 @@ local function enable(plugin)
end)
end
---@param spec lz.n.PluginSpec
---@return boolean
local function is_lazy(spec)
---@diagnostic disable-next-line: undefined-field
return spec.lazy or vim.iter(handlers):any(function(spec_field, _)
return spec[spec_field] ~= nil
end)
end
---Mutates the `plugin`.
---@param plugin lz.n.Plugin
---@param spec lz.n.PluginSpec
function M.parse(plugin, spec)
vim
.iter(handlers)
---@param spec_field string
---@param handler lz.n.Handler
:each(function(spec_field, handler)
if handler.parse then
handler.parse(plugin, spec[spec_field])
end
end)
plugin.lazy = is_lazy(spec)
end
---@param name string
function M.disable(name)
---@param handler lz.n.Handler
+29 -12
View File
@@ -5,7 +5,7 @@ local loader = require("lz.n.loader")
---@param value lz.n.KeysSpec
---@param mode? string
---@return lz.n.Keys
local function parse(value, mode)
local function parse_keys_spec(value, mode)
local ret = vim.deepcopy(value) --[[@as lz.n.Keys]]
ret.lhs = ret[1] or ""
ret.rhs = ret[2]
@@ -23,25 +23,42 @@ local function parse(value, mode)
return ret
end
---@param value string|lz.n.KeysSpec
---@return lz.n.Keys[]
local function parse(value)
value = type(value) == "string" and { value } or value --[[@as lz.n.KeysSpec]]
local modes = type(value.mode) == "string" and { value.mode } or value.mode --[[ @as string[] | nil ]]
if not modes then
return { parse_keys_spec(value) }
end
return vim.iter(modes)
:map(function(mode)
return parse_keys_spec(value, mode)
end)
:totable()
end
---@type lz.n.handler.State
local state = require("lz.n.handler.state").new()
---@type lz.n.KeysHandler
local M = {
spec_field = "keys",
---@param value string|lz.n.KeysSpec
---@return lz.n.Keys[]
parse = function(value)
value = type(value) == "string" and { value } or value --[[@as lz.n.KeysSpec]]
local modes = type(value.mode) == "string" and { value.mode } or value.mode --[[ @as string[] | nil ]]
if not modes then
return { parse(value) }
---@param keys_spec? string|string[]|lz.n.KeysSpec[]
parse = function(plugin, keys_spec)
if keys_spec then
plugin.keys = {}
end
return vim.iter(modes)
:map(function(mode)
return parse(value, mode)
if type(keys_spec) == "string" then
local keys = parse(keys_spec)
vim.list_extend(plugin.keys, keys)
elseif type(keys_spec) == "table" then
---@param keys_spec_ string | lz.n.KeysSpec
vim.iter(keys_spec):each(function(keys_spec_)
local keys = parse(keys_spec_)
vim.list_extend(plugin.keys, keys)
end)
:totable()
end
end,
}
+8 -3
View File
@@ -103,10 +103,15 @@
--- Lookup a plugin by name.
---@field lookup fun(name: string): lz.n.Plugin?
---
---For setting up handler specific triggers such as
---the `DeferredUIEnter` event created by the builtin
---event handler. Called once after each call to require("lz.n").load
--- For setting up handler specific triggers such as
--- the `DeferredUIEnter` event created by the builtin
--- event handler. Called once after each call to require("lz.n").load
---@field post_load? fun()
---
--- If a handler needs to transform the spec passed in by users
--- and add it to the plugin spec, this can be done here.
--- If unset, lz.n will add the `handler_spec` to the `lz.n.Plugin` as is.
---@field parse? fun(plugin: lz.n.Plugin, spec: unknown)
---@type lz.n.Config
vim.g.lz_n = vim.g.lz_n
+1 -69
View File
@@ -79,75 +79,7 @@ local function parse(spec)
local result = vim.deepcopy(spec)
result.name = spec[1]
result[1] = nil
local event_spec = spec.event
if event_spec then
result.event = {}
end
if type(event_spec) == "string" then
local event = require("lz.n.handler.event").parse(event_spec)
table.insert(result.event, event)
elseif type(event_spec) == "table" then
---@param ev lz.n.EventSpec[]
vim.iter(event_spec):each(function(ev)
local event = require("lz.n.handler.event").parse(ev)
table.insert(result.event, event)
end)
end
local ft_spec = spec.ft
if ft_spec then
result.event = result.event or {}
---@diagnostic disable-next-line: inject-field
result.ft = nil
end
if type(ft_spec) == "string" then
local ft = require("lz.n.handler.ft").parse(ft_spec)
table.insert(result.event, ft)
elseif type(ft_spec) == "table" then
---@param ft_spec_ string
vim.iter(ft_spec):each(function(ft_spec_)
local ft = require("lz.n.handler.ft").parse(ft_spec_)
table.insert(result.event, ft)
end)
end
local keys_spec = spec.keys
if keys_spec then
result.keys = {}
end
if type(keys_spec) == "string" then
local keys = require("lz.n.handler.keys").parse(keys_spec)
vim.list_extend(result.keys, keys)
elseif type(keys_spec) == "table" then
---@param keys_spec_ string | lz.n.KeysSpec
vim.iter(keys_spec):each(function(keys_spec_)
local keys = require("lz.n.handler.keys").parse(keys_spec_)
vim.list_extend(result.keys, keys)
end)
end
local cmd_spec = spec.cmd
if cmd_spec then
result.cmd = {}
end
if type(cmd_spec) == "string" then
table.insert(result.cmd, cmd_spec)
elseif type(cmd_spec) == "table" then
---@param cmd_spec_ string
vim.iter(cmd_spec):each(function(cmd_spec_)
table.insert(result.cmd, cmd_spec_)
end)
end
local colorscheme_spec = spec.colorscheme
if colorscheme_spec then
result.colorscheme = {}
end
if type(colorscheme_spec) == "string" then
table.insert(result.colorscheme, colorscheme_spec)
elseif type(colorscheme_spec) == "table" then
---@param colorscheme_spec_ string
vim.iter(colorscheme_spec):each(function(colorscheme_spec_)
table.insert(result.colorscheme, colorscheme_spec_)
end)
end
result.lazy = require("lz.n.handler").is_lazy(spec)
require("lz.n.handler").parse(result, spec)
return result
end