Skip to content

Instantly share code, notes, and snippets.

@eduardoarandah
Created February 4, 2026 23:14
Show Gist options
  • Select an option

  • Save eduardoarandah/5f51b24a2fa1e604e9253a6ac564b450 to your computer and use it in GitHub Desktop.

Select an option

Save eduardoarandah/5f51b24a2fa1e604e9253a6ac564b450 to your computer and use it in GitHub Desktop.
Neovim commands to simplify context creation in markdown files
-----------------------------------------------------------------
-- Neovim commands to simplify context creation in markdown files
--
-- Save as: lua/context.lua
--
-- How to use: require("_context").setup()
--
-----------------------------------------------------------------
local M = {}
--------------------------------
-- Copy quickfix files to clipboard
--------------------------------
local function copy_quickfix_files()
-- Get all quickfix entries
local qf_list = vim.fn.getqflist()
-- Use table as set to store unique filenames
local files = {}
for _, item in ipairs(qf_list) do
-- Get buffer name for each quickfix entry
local filename = vim.fn.bufname(item.bufnr)
if filename ~= "" then
files[filename] = true
end
end
-- Convert table keys to array and join with newlines
local file_list = {}
for filename, _ in pairs(files) do
table.insert(file_list, filename)
end
-- Copy to system clipboard and show message
vim.fn.setreg("+", table.concat(file_list, "\n"))
print("Copied " .. #file_list .. " files to clipboard")
end
-- Create user command
vim.api.nvim_create_user_command("CopyQuickFixFiles", copy_quickfix_files, { desc = "Copy all unique files from quickfix list to clipboard" })
--------------------------------
-- Copy list of open buffers to clipboard
--------------------------------
local function list_of_open_buffers()
local buffers = vim.api.nvim_list_bufs()
local cwd = vim.fn.getcwd()
local file_list = {}
for _, bufnr in ipairs(buffers) do
-- Only process loaded buffers
if vim.api.nvim_buf_is_loaded(bufnr) then
local bufname = vim.api.nvim_buf_get_name(bufnr)
-- Skip empty buffers, NvimTree, and non-existent files
if bufname ~= "" and not bufname:match("NvimTree") and vim.fn.filereadable(bufname) == 1 then
-- Convert to relative path
local relpath = vim.fn.substitute(bufname, cwd .. "/", "", "")
table.insert(file_list, relpath)
end
end
end
return file_list
end
local function copy_list_of_open_buffers()
local file_list = list_of_open_buffers()
-- Copy to clipboard
vim.fn.setreg("+", table.concat(file_list, "\n"))
vim.notify(string.format("Copied %d open buffers to clipboard", #file_list), vim.log.levels.INFO)
end
--------------------------------
-- Copy code snippet
--
-- this function copies selection and adds line number in markdown format, example:
--
-- dir/filename.abc:293
-- ```lua
-- (selection here)
-- ```
--------------------------------
local function get_code_snippet(start_line, end_line)
local file_name = vim.fn.expand("%:.")
local lines = vim.api.nvim_buf_get_lines(0, start_line, end_line, false)
local file_type = vim.api.nvim_get_option_value("filetype", { buf = 0 })
-- get total line count to detect if entire buffer is selected
local total_lines = vim.api.nvim_buf_line_count(0)
-- only add line number if not selecting entire buffer
local header = file_name
if not (start_line == 0 and end_line == total_lines) then
header = file_name .. ":" .. (start_line + 1)
end
return header .. "\n\n```" .. file_type .. "\n" .. table.concat(lines, "\n") .. "\n```\n\n"
end
------------------------
-- Commands and mappings
------------------------
function M.setup()
-- commands
vim.api.nvim_create_user_command("CopyListOfOpenBuffers", copy_list_of_open_buffers, { bang = true, desc = "Copy list of open buffers to clipboard" })
-- Copy filename and line number
-- example: src/filename.js:123
vim.api.nvim_create_user_command("CopyPathLine", function()
local value = vim.fn.expand("%:.") .. ":" .. vim.api.nvim_win_get_cursor(0)[1]
vim.fn.setreg("*", value)
vim.notify("Copied " .. value, vim.log.levels.INFO)
end, { bang = true, desc = "Copy filename and current line number" })
-- Copy filename path
vim.api.nvim_create_user_command("CopyFullPath", function()
local value = vim.fn.expand("%:p")
vim.fn.setreg("*", value)
vim.notify("Copied " .. value, vim.log.levels.INFO)
end, { bang = true, desc = "Copy absolute file path" })
-- Copy relative file path
vim.api.nvim_create_user_command("CopyPath", function()
local value = vim.fn.expand("%:.")
vim.fn.setreg("*", value)
vim.notify("Copied " .. value, vim.log.levels.INFO)
end, { bang = true, desc = "Copy relative file path <F6>" })
-- Copy file name with extension
vim.api.nvim_create_user_command("CopyFileNameWithExtension", function()
local value = vim.fn.expand("%:t")
vim.fn.setreg("*", value)
vim.notify("Copied " .. value, vim.log.levels.INFO)
end, { bang = true, desc = "Copy filename with extension" })
-- Copy file name without extension
vim.api.nvim_create_user_command("CopyFileName", function()
local value = vim.fn.expand("%:t:r")
vim.fn.setreg("*", value)
vim.notify("Copied " .. value, vim.log.levels.INFO)
end, { bang = true, desc = "Copy filename without extension" })
-- Copy code snippet
vim.api.nvim_create_user_command("CopyCodeSnippet", function(opts)
local start_line = vim.fn.line("'<") - 1
local end_line = vim.fn.line("'>")
vim.fn.setreg("*", get_code_snippet(start_line, end_line))
vim.notify("Added code snippet to clipboard", vim.log.levels.INFO)
end, { range = true, bang = true, desc = "Copy selection as markdown code snippet <F6>" })
-- F6 copies relative file path
vim.api.nvim_set_keymap("n", "<F6>", ":CopyPath<CR>", { noremap = true, desc = "Copy relative file path" })
-- map it to F6 on visual mode
vim.api.nvim_set_keymap("v", "<F6>", ":CopyCodeSnippet<CR>", { noremap = true, desc = "Copy selection as markdown code snippet" })
end
return M
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment