From d9c8310e3d0688b188bea3e3d8a3bd5a361c8b8d Mon Sep 17 00:00:00 2001 From: Hawtian Wang Date: Sun, 13 Aug 2023 22:11:47 +0200 Subject: [PATCH] implement postfix using resolveExpandParams. --- lua/luasnip/extras/postfix.lua | 93 +++----- tests/integration/postfix_snippet_spec.lua | 263 +++++++++++++-------- 2 files changed, 193 insertions(+), 163 deletions(-) diff --git a/lua/luasnip/extras/postfix.lua b/lua/luasnip/extras/postfix.lua index d9b35ddc0..dfca585a6 100644 --- a/lua/luasnip/extras/postfix.lua +++ b/lua/luasnip/extras/postfix.lua @@ -2,68 +2,47 @@ local snip = require("luasnip.nodes.snippet").S local events = require("luasnip.util.events") local extend_decorator = require("luasnip.util.extend_decorator") local node_util = require("luasnip.nodes.util") +local util = require("luasnip.util.util") local matches = { default = [[[%w%.%_%-%"%']+$]], line = "^.+$", } -local function generate_opts(match_pattern, user_callback) - return { - callbacks = { - [-1] = { - [events.pre_expand] = function(snippet, event_args) - local pos = event_args.expand_pos - -- [1]: returns table, gets text end-exclusive. - local line_to_cursor = vim.api.nvim_buf_get_text( - 0, - pos[1], - 0, - pos[1], - pos[2], - {} - )[1] - local postfix_match = line_to_cursor:match(match_pattern) - or "" - -- clear postfix_match-text. - vim.api.nvim_buf_set_text( - 0, - pos[1], - pos[2] - #postfix_match, - pos[1], - pos[2], - { "" } - ) - local user_env = {} - if user_callback then - user_env = user_callback(snippet, event_args) or {} - end - local postfix_env_override = { - env_override = { - POSTFIX_MATCH = postfix_match, - }, - } +local function wrap_resolve_expand_params(match_pattern, user_resolve) + return function(snippet, line_to_cursor, match, captures) + if line_to_cursor:sub(1, -1 - #match):match(match_pattern) == nil then + return nil + end - return vim.tbl_deep_extend( - "keep", - user_env, - postfix_env_override - ) - end, + local pos = util.get_cursor_0ind() + local line_to_cursor_except_match = + line_to_cursor:sub(1, #line_to_cursor - #match) + local postfix_match = line_to_cursor_except_match:match(match_pattern) + or "" + local res = { + clear_region = { + from = { pos[1], pos[2] - #postfix_match - #match }, + to = pos, }, - }, - } -end - -local function wrap_condition(user_condition, match_pattern) - if not user_condition then - user_condition = require("luasnip.util.util").yes - end + env_override = { + POSTFIX_MATCH = postfix_match, + }, + } - return function(line_to_cursor, matched_trigger, captures) - return line_to_cursor:sub(1, -1 - #matched_trigger):match(match_pattern) - ~= nil - and user_condition(line_to_cursor, matched_trigger, captures) + if user_resolve then + local user_res = + user_resolve(snippet, line_to_cursor, match, captures) + if user_res then + res.trigger = user_res.trigger + res.captures = user_res.captures + res.clear_region = user_res.clear_region or res.clear_region + res.env_override = vim.tbl_extend("force", res.env_override, user_res.env_override or {}) + else + return nil + end + end + return res end end @@ -80,13 +59,9 @@ local function postfix(context, nodes, opts) context = node_util.wrap_context(context) context.wordTrig = false local match_pattern = context.match_pattern or matches.default - context.condition = wrap_condition(context.condition, match_pattern) + context.resolveExpandParams = + wrap_resolve_expand_params(match_pattern, context.resolveExpandParams) - opts = vim.tbl_deep_extend( - "force", - opts, - generate_opts(match_pattern, user_callback) - ) return snip(context, nodes, opts) end extend_decorator.register( diff --git a/tests/integration/postfix_snippet_spec.lua b/tests/integration/postfix_snippet_spec.lua index a710b7e09..5b16efd16 100644 --- a/tests/integration/postfix_snippet_spec.lua +++ b/tests/integration/postfix_snippet_spec.lua @@ -27,127 +27,182 @@ describe("postfix snippets", function() it( "creates a postfix snippet which changes the previous text once expanded", function() - local postfix_snip = [[ - pf(".parens", { - f(function(_, parent) - return "(" .. parent.env.POSTFIX_MATCH .. ")" - end, {}) - }) - ]] - - feed("ibar") - exec_lua("ls.snip_expand(" .. postfix_snip .. ")") - screen:expect({ - grid = [[ - (bar)^ | - {0:~ }| - {2:-- INSERT --} | - ]], + exec_lua([[ + ls.add_snippets("all", { + pf(".parens", { + f(function(_, parent) + return "(" .. parent.env.POSTFIX_MATCH .. ")" + end, {}) + }) + }) + ]]) + + feed("ibar.parens") + exec_lua("ls.expand()") + screen:expect({grid = [[ + (bar)^ | + {0:~ }| + {2:-- INSERT --} |]], }) end ) it("default pattern works with a _, -, and .", function() - local postfix_snip = [[ - pf(".parens", { - f(function(_, parent) - return "(" .. parent.env.POSTFIX_MATCH .. ")" - end, {}) - }) - ]] - - feed("ithis_is-a.weird_variable") - exec_lua("ls.snip_expand(" .. postfix_snip .. ")") - - screen:expect({ - grid = [[ - (this_is-a.weird_variable)^ | - {0:~ }| - {2:-- INSERT --} | - ]], + exec_lua([[ + ls.add_snippets("all", { + pf(".parens", { + f(function(_, parent) + return "(" .. parent.env.POSTFIX_MATCH .. ")" + end, {}) + }) + }) + ]]) + + feed("ithis_is-a.weird_variable.parens") + exec_lua("ls.expand()") + + screen:expect({grid = [[ + (this_is-a.weird_variable)^ | + {0:~ }| + {2:-- INSERT --} |]], }) end) it("can take alternate matching strings", function() - local postfix_snip = [[ - pf({trig = ".parens", match_pattern = "^.+$"}, { - f(function(_, parent) - return "(" .. parent.env.POSTFIX_MATCH .. ")" - end, {}) - }) - ]] - - feed([[ithis should take the whole line]]) - exec_lua("ls.snip_expand(" .. postfix_snip .. ")") - - screen:expect({ - grid = [[ - (this should take the whole line)^ | - {0:~ }| - {2:-- INSERT --} | - ]], + exec_lua([[ + ls.add_snippets("all", { + pf({trig = ".parens", match_pattern = "^.+$"}, { + f(function(_, parent) + return "(" .. parent.env.POSTFIX_MATCH .. ")" + end, {}) + }) + }) + ]]) + + feed([[ithis should take the whole line.parens]]) + exec_lua("ls.expand()") + + screen:expect({grid = [[ + (this should take the whole line)^ | + {0:~ }| + {2:-- INSERT --} |]], }) end) it("wordTrig can't accidentally be set", function() - local postfix_snip = [[ - pf({trig = ".parens", match_pattern = "^.+$", wordTrig = true}, { - f(function(_, parent) - return "(" .. parent.env.POSTFIX_MATCH .. ")" - end, {}) - }) - ]] - - feed([[ithis should take the whole line]]) - exec_lua("ls.snip_expand(" .. postfix_snip .. ")") - - screen:expect({ - grid = [[ - (this should take the whole line)^ | - {0:~ }| - {2:-- INSERT --} | - ]], + exec_lua([[ + ls.add_snippets("all", { + pf({trig = ".parens", match_pattern = "^.+$", wordTrig = true}, { + f(function(_, parent) + return "(" .. parent.env.POSTFIX_MATCH .. ")" + end, {}) + }) + }) + ]]) + + feed([[ithis should take the whole line.parens]]) + exec_lua("ls.expand()") + + screen:expect({grid = [[ + (this should take the whole line)^ | + {0:~ }| + {2:-- INSERT --} |]], }) end) it("allows the user to set a callback on the same event", function() - local postfix_snip = [[ - pf( - ".parens", - { - f(function(_, parent) - return "(" - .. parent.env.POSTFIX_MATCH - .. " " - .. parent.env.another_field - .. ")" - end), - }, - { - callbacks = { - [-1] = { - [events.pre_expand] = function(snippet, event_args) - return { - env_override = { - another_field = "data from another env field", - }, - } - end, - }, - }, - } - ) - ]] - - feed([[ifoo]]) - exec_lua("ls.snip_expand(" .. postfix_snip .. ")") - - screen:expect({ - grid = [[ - (foo data from another env field)^ | - {0:~ }| - {2:-- INSERT --} | - ]], + exec_lua([[ + ls.add_snippets("all", { + pf( + ".parens", + { + f(function(_, parent) + return "(" + .. parent.env.POSTFIX_MATCH + .. " " + .. parent.env.another_field + .. ")" + end), + }, + { + callbacks = { + [-1] = { + [events.pre_expand] = function(snippet, event_args) + return { + env_override = { + another_field = "data from another env field", + }, + } + end, + }, + }, + } + ) + }) + ]]) + + feed([[ifoo.parens]]) + exec_lua("ls.expand()") + + screen:expect({grid = [[ + (foo data from another env field)^ | + {0:~ }| + {2:-- INSERT --} |]], }) end) + + -- test resolveExpandParams in general. + it("respects user-provided resolveExpandParams.", function() + exec_lua([[ + ls.add_snippets("all", { + pf({ + trig = ".parens", + match_pattern = "^.+$", + resolveExpandParams = function(snip, line_to_cursor, matched_trigger, captures) + return { + env_override = { asdf = "asdf" } + } + end + }, { + f(function(_, parent) + return "(" .. parent.env.POSTFIX_MATCH .. ")" .. parent.env.asdf + end, {}) + }) + }) + ]]) + + feed([[ithis should expand.parens]]) + exec_lua("ls.expand()") + + screen:expect{grid=[[ + (this should expand)asdf^ | + {0:~ }| + {2:-- INSERT --} |]]} + end) + + it("respects user-provided condition.", function() + exec_lua([[ + ls.add_snippets("all", { + pf({ + trig = ".parens", + match_pattern = "^.+$", + condition = function() + return false + end + }, { + f(function(_, parent) + return "(" .. parent.env.POSTFIX_MATCH .. ")" .. parent.env.asdf + end, {}) + }) + }) + ]]) + + feed([[ithis should not expand.parens]]) + exec_lua("ls.expand()") + + screen:expect{grid=[[ + this should not expand.parens^ | + {0:~ }| + {2:-- INSERT --} |]]} + end) end)