aboutsummaryrefslogtreecommitdiff
path: root/test/functional
diff options
context:
space:
mode:
Diffstat (limited to 'test/functional')
-rw-r--r--test/functional/treesitter/query_spec.lua78
1 files changed, 78 insertions, 0 deletions
diff --git a/test/functional/treesitter/query_spec.lua b/test/functional/treesitter/query_spec.lua
index fb3eaa1518..170f448f97 100644
--- a/test/functional/treesitter/query_spec.lua
+++ b/test/functional/treesitter/query_spec.lua
@@ -696,4 +696,82 @@ void ui_refresh(void)
'((identifier) @id \n(#eq? @id\n@ok.capture\n))'
)
end)
+
+ describe('Query:iter_captures', function()
+ it('includes metadata for all captured nodes #23664', function()
+ insert([[
+ const char *sql = "SELECT * FROM Students WHERE name = 'Robert'); DROP TABLE Students;--";
+ ]])
+
+ local query = [[
+ (declaration
+ type: (_)
+ declarator: (init_declarator
+ declarator: (pointer_declarator
+ declarator: (identifier)) @_id
+ value: (string_literal
+ (string_content) @injection.content))
+ (#set! injection.language "sql")
+ (#contains? @_id "sql"))
+ ]]
+
+ local result = exec_lua(
+ [=[
+ local query = vim.treesitter.query.parse("c", ...)
+ local parser = vim.treesitter.get_parser(0, "c")
+ local root = parser:parse()[1]:root()
+ local t = {}
+ for id, node, metadata in query:iter_captures(root, 0) do
+ t[query.captures[id]] = metadata
+ end
+ return t
+ ]=],
+ query
+ )
+
+ eq({
+ ['_id'] = { ['injection.language'] = 'sql' },
+ ['injection.content'] = { ['injection.language'] = 'sql' },
+ }, result)
+ end)
+
+ it('only evaluates predicates once per match', function()
+ insert([[
+ void foo(int x, int y);
+ ]])
+ local query = [[
+ (declaration
+ type: (_)
+ declarator: (function_declarator
+ declarator: (identifier) @function.name
+ parameters: (parameter_list
+ (parameter_declaration
+ type: (_)
+ declarator: (identifier) @argument)))
+ (#eq? @function.name "foo"))
+ ]]
+
+ local result = exec_lua(
+ [[
+ local query = vim.treesitter.query.parse("c", ...)
+ local match_preds = query.match_preds
+ local called = 0
+ function query:match_preds(...)
+ called = called + 1
+ return match_preds(self, ...)
+ end
+ local parser = vim.treesitter.get_parser(0, "c")
+ local root = parser:parse()[1]:root()
+ local captures = {}
+ for id, node in query:iter_captures(root, 0) do
+ captures[#captures + 1] = id
+ end
+ return { called, captures }
+ ]],
+ query
+ )
+
+ eq({ 2, { 1, 1, 2, 2 } }, result)
+ end)
+ end)
end)