From a89862a187a5781cae654f96f303173bdb27fea5 Mon Sep 17 00:00:00 2001 From: Prad Nukala Date: Fri, 19 Sep 2025 15:08:14 -0400 Subject: [PATCH] feat: add Dockerfile for easier project setup --- .luarc.json | 5 + .neoconf.json | 36 +- Dockerfile | 0 init.lua | 63 +- lua/community.lua | 55 +- lua/lazy_setup.lua | 16 +- lua/overseer/template/user/devbox.lua | 61 -- lua/overseer/template/user/templ_gen.lua | 20 - lua/plugins/aider.lua | 40 -- lua/plugins/astrocore.lua | 732 +++++++++++++++++++++-- lua/plugins/astrolsp.lua | 109 ---- lua/plugins/astroui.lua | 222 ++++++- lua/plugins/bufferline.lua | 151 +++++ lua/plugins/explorer.lua | 439 ++++++++++++++ lua/plugins/mason.lua | 8 +- lua/plugins/neotree.lua | 256 -------- lua/plugins/none-ls.lua | 24 - lua/plugins/obsidian.lua | 76 +++ lua/plugins/sessions.lua | 64 -- lua/plugins/snacks_lsp_mappings.lua | 17 - lua/plugins/supermaven.lua | 29 - lua/plugins/treesitter.lua | 15 - lua/plugins/user.lua | 138 ----- lua/polish.lua | 180 +++--- neovim.yml | 2 - 25 files changed, 1744 insertions(+), 1014 deletions(-) create mode 100644 .luarc.json create mode 100644 Dockerfile delete mode 100644 lua/overseer/template/user/devbox.lua delete mode 100644 lua/overseer/template/user/templ_gen.lua delete mode 100644 lua/plugins/aider.lua delete mode 100644 lua/plugins/astrolsp.lua create mode 100644 lua/plugins/bufferline.lua create mode 100644 lua/plugins/explorer.lua delete mode 100644 lua/plugins/neotree.lua delete mode 100644 lua/plugins/none-ls.lua create mode 100644 lua/plugins/obsidian.lua delete mode 100644 lua/plugins/sessions.lua delete mode 100644 lua/plugins/snacks_lsp_mappings.lua delete mode 100644 lua/plugins/supermaven.lua delete mode 100644 lua/plugins/treesitter.lua delete mode 100644 lua/plugins/user.lua diff --git a/.luarc.json b/.luarc.json new file mode 100644 index 0000000..1406fef --- /dev/null +++ b/.luarc.json @@ -0,0 +1,5 @@ +{ + "diagnostics.disable": [ + "deprecated" + ] +} \ No newline at end of file diff --git a/.neoconf.json b/.neoconf.json index 2d7a81f..e009683 100644 --- a/.neoconf.json +++ b/.neoconf.json @@ -1,20 +1,20 @@ { - "neodev": { - "library": { - "enabled": true, - "plugins": true - } - }, - "neoconf": { - "plugins": { - "lua_ls": { - "enabled": true - } - } - }, - "lspconfig": { - "lua_ls": { - "Lua.format.enable": false - } - } + "neodev": { + "library": { + "enabled": true, + "plugins": true + } + }, + "neoconf": { + "plugins": { + "lua_ls": { + "enabled": true + } + } + }, + "lspconfig": { + "lua_ls": { + "Lua.format.enable": false + } + } } diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..e69de29 diff --git a/init.lua b/init.lua index 2ce1cdd..fce43b2 100644 --- a/init.lua +++ b/init.lua @@ -1,19 +1,54 @@ --- This file simply bootstraps the installation of Lazy.nvim and then calls other files for execution --- This file doesn't necessarily need to be touched, BE CAUTIOUS editing this file and proceed at your own risk. -local lazypath = vim.env.LAZY or vim.fn.stdpath "data" .. "/lazy/lazy.nvim" -if not (vim.env.LAZY or (vim.uv or vim.loop).fs_stat(lazypath)) then - -- stylua: ignore - vim.fn.system({ "git", "clone", "--filter=blob:none", "https://github.com/folke/lazy.nvim.git", "--branch=stable", lazypath }) +-- Bootstrap Lazy.nvim and load config safely across environments +local uv = vim.uv or vim.loop +pcall(function() + if vim.loader then vim.loader.enable() end +end) + +-- Set leaders early for consistency +vim.g.mapleader = " " +vim.g.maplocalleader = "," + +-- Allow overriding lazy path via LAZY env +local lazypath = vim.env.LAZY or (vim.fn.stdpath "data" .. "/lazy/lazy.nvim") + +-- Bootstrap lazy.nvim only if not provided via env and not installed +if not vim.env.LAZY and not (uv and uv.fs_stat(lazypath)) then + if vim.fn.executable "git" == 1 then + local result = vim.fn.system { + "git", + "clone", + "--filter=blob:none", + "https://github.com/folke/lazy.nvim.git", + "--branch=stable", + lazypath, + } + if vim.v.shell_error ~= 0 then vim.notify(("Error cloning lazy.nvim:\n%s"):format(result), vim.log.levels.ERROR) end + else + vim.notify("git not found; skipping lazy.nvim bootstrap", vim.log.levels.WARN) + end +end + +-- Add to runtimepath if available, else exit quietly (headless-safe) +if uv and uv.fs_stat(lazypath) then + vim.opt.rtp:prepend(lazypath) +else + vim.notify(("lazy.nvim not available at %s"):format(lazypath), vim.log.levels.WARN) + return end -vim.opt.rtp:prepend(lazypath) -- validate that lazy is available -if not pcall(require, "lazy") then - -- stylua: ignore - vim.api.nvim_echo({ { ("Unable to load lazy from: %s\n"):format(lazypath), "ErrorMsg" }, { "Press any key to exit...", "MoreMsg" } }, true, {}) - vim.fn.getchar() - vim.cmd.quit() +local ok_lazy = pcall(require, "lazy") +if not ok_lazy then + vim.notify(("Unable to load lazy from: %s"):format(lazypath), vim.log.levels.ERROR) + return end -require "lazy_setup" -require "polish" +-- Load specs and final polish with guards +local ok_setup = pcall(require, "lazy_setup") +if not ok_setup then + vim.notify("Failed to load lazy_setup", vim.log.levels.ERROR) + return +end + +-- Polish is optional; don't fail startup if it's missing +pcall(require, "polish") diff --git a/lua/community.lua b/lua/community.lua index ebf8ee2..faafb19 100644 --- a/lua/community.lua +++ b/lua/community.lua @@ -5,50 +5,29 @@ ---@type LazySpec return { "AstroNvim/astrocommunity", + version = false, -- Use latest astrocommunity + { import = "astrocommunity.pack.astro" }, + { import = "astrocommunity.pack.bash" }, + { import = "astrocommunity.pack.biome" }, + { import = "astrocommunity.pack.chezmoi" }, + { import = "astrocommunity.pack.lua" }, + { import = "astrocommunity.pack.markdown" }, + { import = "astrocommunity.pack.json" }, + { import = "astrocommunity.pack.mdx" }, + { import = "astrocommunity.pack.go" }, + { import = "astrocommunity.pack.html-css" }, + { import = "astrocommunity.pack.templ" }, + { import = "astrocommunity.pack.tailwindcss" }, + { import = "astrocommunity.pack.typescript-all-in-one" }, + { import = "astrocommunity.pack.yaml" }, + { import = "astrocommunity.git.octo-nvim" }, { import = "astrocommunity.bars-and-lines.bufferline-nvim" }, { import = "astrocommunity.code-runner.overseer-nvim" }, { import = "astrocommunity.colorscheme.cyberdream-nvim" }, { import = "astrocommunity.completion.supermaven-nvim" }, - { import = "astrocommunity.completion.avante-nvim" }, { import = "astrocommunity.completion.blink-cmp" }, - { import = "astrocommunity.completion.copilot-lua-cmp" }, - { import = "astrocommunity.completion.nvim-cmp" }, + { import = "astrocommunity.editing-support.auto-save-nvim" }, { import = "astrocommunity.editing-support.conform-nvim" }, - { import = "astrocommunity.debugging.persistent-breakpoints-nvim" }, - { import = "astrocommunity.icon.mini-icons" }, - { import = "astrocommunity.keybinding.mini-clue" }, { import = "astrocommunity.lsp.inc-rename-nvim" }, { import = "astrocommunity.lsp.nvim-lsp-file-operations" }, - { import = "astrocommunity.lsp.nvim-lint" }, - { import = "astrocommunity.markdown-and-latex.markview-nvim" }, - { import = "astrocommunity.motion.flash-nvim" }, - { import = "astrocommunity.motion.leap-nvim" }, - { import = "astrocommunity.motion.mini-basics" }, - { import = "astrocommunity.motion.nvim-surround" }, - { import = "astrocommunity.motion.portal-nvim" }, - { import = "astrocommunity.pack.docker" }, - { import = "astrocommunity.pack.lua" }, - { import = "astrocommunity.pack.go" }, - { import = "astrocommunity.pack.markdown" }, - { import = "astrocommunity.pack.mdx" }, - { import = "astrocommunity.pack.pkl" }, - { import = "astrocommunity.pack.templ" }, - { import = "astrocommunity.pack.tailwindcss" }, - { import = "astrocommunity.pack.typescript" }, - { import = "astrocommunity.pack.yaml" }, - { import = "astrocommunity.quickfix.quicker-nvim" }, - { import = "astrocommunity.recipes.picker-nvchad-theme" }, - { import = "astrocommunity.recipes.picker-lsp-mappings" }, - { import = "astrocommunity.utility.telescope-lazy-nvim" }, - { import = "astrocommunity.utility.telescope-fzy-native-nvim" }, - { import = "astrocommunity.utility.mason-tool-installer-nvim" }, - { import = "astrocommunity.utility.noice-nvim" }, - { import = "astrocommunity.recipes.ai" }, - { import = "astrocommunity.recipes.astrolsp-auto-signature-help" }, - { import = "astrocommunity.recipes.heirline-nvchad-statusline" }, - { import = "astrocommunity.recipes.heirline-vscode-winbar" }, - { import = "astrocommunity.recipes.picker-lsp-mappings" }, - { import = "astrocommunity.recipes.telescope-lsp-mappings" }, - - -- import/override with your plugins folder } diff --git a/lua/lazy_setup.lua b/lua/lazy_setup.lua index 33149d4..31c378c 100644 --- a/lua/lazy_setup.lua +++ b/lua/lazy_setup.lua @@ -1,21 +1,19 @@ require("lazy").setup({ { "AstroNvim/AstroNvim", - version = "^5", -- Remove version tracking to elect for nightly AstroNvim + version = "^4", -- Ensure we use AstroNvim v4+ import = "astronvim.plugins", - opts = { -- AstroNvim options must be set here with the `import` key - mapleader = " ", -- This ensures the leader key must be configured before Lazy is set up - maplocalleader = ",", -- This ensures the localleader key must be configured before Lazy is set up - icons_enabled = true, -- Set to false to disable icons (if no Nerd Font is available) - pin_plugins = nil, -- Default will pin plugins when tracking `version` of AstroNvim, set to true/false to override - update_notifications = false, -- Enable/disable notification about running `:Lazy update` twice to update pinned plugins + opts = { + -- Leaders are set early in init.lua to ensure consistency + icons_enabled = (vim.g.have_nerd_font ~= false), + pin_plugins = nil, + update_notifications = false, }, }, { import = "community" }, { import = "plugins" }, } --[[@as LazySpec]], { - -- Configure any other `lazy.nvim` configuration options here - install = { colorscheme = { "astrotheme", "habamax" } }, + install = { colorscheme = { "astrotheme" } }, ui = { backdrop = 100 }, performance = { rtp = { diff --git a/lua/overseer/template/user/devbox.lua b/lua/overseer/template/user/devbox.lua deleted file mode 100644 index 31b6ff3..0000000 --- a/lua/overseer/template/user/devbox.lua +++ /dev/null @@ -1,61 +0,0 @@ -local files = require "overseer.files" -local overseer = require "overseer" - ----@type overseer.TemplateFileDefinition -local tmpl = { - priority = 60, - params = { - args = { optional = true, type = "list", delimiter = " " }, - cwd = { optional = true }, - }, - builder = function(params) - return { - cmd = { "sh" }, - args = { "-c", table.concat(params.args, " && ") }, - cwd = params.cwd, - } - end, -} - ----@param opts overseer.SearchParams ----@return string|nil -local function get_devbox_file(opts) - return vim.fs.find("devbox.json", { - upward = true, - type = "file", - path = opts.dir, - })[1] -end - -return { - cache_key = function(opts) return get_devbox_file(opts) end, - condition = { - callback = function(opts) - local devbox_file = get_devbox_file(opts) - if not devbox_file then return false, "No devbox.json file found" end - return true - end, - }, - generator = function(opts, cb) - local devbox_file = get_devbox_file(opts) - if not devbox_file then - cb {} - return - end - local data = files.load_json_file(devbox_file) - local ret = {} - if data.shell and data.shell.scripts then - for k, v in pairs(data.shell.scripts) do - table.insert( - ret, - overseer.wrap_template( - tmpl, - { name = string.format("devbox run %s", k) }, - { args = v, cwd = vim.fs.dirname(devbox_file) } - ) - ) - end - end - cb(ret) - end, -} diff --git a/lua/overseer/template/user/templ_gen.lua b/lua/overseer/template/user/templ_gen.lua deleted file mode 100644 index 8b03483..0000000 --- a/lua/overseer/template/user/templ_gen.lua +++ /dev/null @@ -1,20 +0,0 @@ --- /home/stevearc/.config/nvim/lua/overseer/template/user/run_script.lua -return { - name = "run script", - builder = function() - local file = vim.fn.expand "%:p" - local cmd = { file } - if vim.bo.filetype == "templ" then cmd = { "templ", "generate" } end - return { - cmd = cmd, - components = { - { "on_output_quickfix", set_diagnostics = true }, - "on_result_diagnostics", - "default", - }, - } - end, - condition = { - filetype = { "templ" }, - }, -} diff --git a/lua/plugins/aider.lua b/lua/plugins/aider.lua deleted file mode 100644 index e13933f..0000000 --- a/lua/plugins/aider.lua +++ /dev/null @@ -1,40 +0,0 @@ -return { - "GeorgesAlkhouri/nvim-aider", - cmd = { - "AiderTerminalToggle", - "AiderHealth", - }, - keys = { - { "a/", "AiderTerminalToggle", desc = "Open Aider" }, - { "as", "AiderTerminalSend", desc = "Send to Aider", mode = { "n", "v" } }, - { "ac", "AiderQuickSendCommand", desc = "Send Command To Aider" }, - { "ab", "AiderQuickSendBuffer", desc = "Send Buffer To Aider" }, - { "a+", "AiderQuickAddFile", desc = "Add File to Aider" }, - { "a-", "AiderQuickDropFile", desc = "Drop File from Aider" }, - { "ar", "AiderQuickReadOnlyFile", desc = "Add File as Read-Only" }, - -- Example nvim-tree.lua integration if needed - { "a+", "AiderTreeAddFile", desc = "Add File from Tree to Aider", ft = "NvimTree" }, - { "a-", "AiderTreeDropFile", desc = "Drop File from Tree from Aider", ft = "NvimTree" }, - }, - dependencies = { - "folke/snacks.nvim", - --- The below dependencies are optional - "catppuccin/nvim", - "nvim-tree/nvim-tree.lua", - --- Neo-tree integration - { - "nvim-neo-tree/neo-tree.nvim", - opts = function(_, opts) - -- Example mapping configuration (already set by default) - opts.window = { - mappings = { - ["+"] = { "nvim_aider_add", desc = "add to aider" }, - ["-"] = { "nvim_aider_drop", desc = "drop from aider" }, - }, - } - require("nvim_aider.neo_tree").setup(opts) - end, - }, - }, - config = true, -} diff --git a/lua/plugins/astrocore.lua b/lua/plugins/astrocore.lua index 56b7b4a..e2a75ca 100644 --- a/lua/plugins/astrocore.lua +++ b/lua/plugins/astrocore.lua @@ -1,3 +1,199 @@ +local Terminal = require("toggleterm.terminal").Terminal + +-- Track closed buffers +local closed_buffers = {} + +-- Shared ignore patterns from neotree configuration +local ignore_patterns = { + -- Hidden patterns + "chain_*.json", + ".typecopy", + ".python-version", + "*.pb.go", + "*config.*.js", + "*config.js", + "deps.mjs", + ".parcelrc", + "worker-configuration.d.ts", + "wrangler.jsonc", + "*.pkl.go", + ".trunk", + ".config", + ".cz.toml", + "*_integration.go", + "*_test.go", + "*_query_docs.md", + "*_tx_docs.md", + "*_mock.go", + "biome*", + -- Never show patterns + "CLAUDE*", + ".pkl-lsp", + ".tsbuildinfo", + "contrib", + "interchaintest", + "package-lock.json", + ".prettierrc", + "node_modules", + "PULL_REQUEST_TEMPLATE.md", + ".DocumentRevisions-V100", + ".Spotlight-V100", + ".TemporaryItems", + ".Trashes", + ".fseventsd", + ".editorconfig", + "*.min.js", + ".gitpod.*", + "cspell.*", + "*.lock", + "*.lockb", + "*.pulsar.go", + "*.pb.gorm.go", + "*.pb.gw.go", + "*_templ.go", + "*.tmp", + "*.work.*", + "*.sum", + ".wrangler", + "*.wasm", + "*.png", + "*.jpg", + ".parcel-cache", + "*.icns", + "*.ico", + ".aider.tags.cache.v4", + "*.iml", + "Icon?", + "iCloud~", + "com~", + "readme.md", + ".conform*", + ".null-ls_*", + -- Additional never show items + ".git", + "pnpm-lock.yaml", + ".next", + ".task", + ".devbox", + ".dart_tool", + ".idea", + ".metadata", + ".venv", + ".gradle", + "gradle.bat", + ".aider.chat.history.md", + ".aider.input.history", + ".aider.tags.cache.v3", + ".devcontainer", + "heighliner", + ".tmp", + "go.work.sum", + ".DS_Store", + "LICENSE", + "tmp", + "sonr.log", + "DISCUSSION_TEMPLATE", + "ISSUE_TEMPLATE", + ".timemachine", + "junit.xml", + ".jj", + ".spawn", + ".turbo", +} + +-- Create a custom transform function to filter out ignored files +local function create_file_filter() + return function(item) + if not item or not item.file then return item end + + local file = item.file + local basename = vim.fn.fnamemodify(file, ":t") + local dir = vim.fn.fnamemodify(file, ":h:t") + + -- Check each ignore pattern + for _, pattern in ipairs(ignore_patterns) do + -- Convert glob pattern to Lua pattern + local lua_pattern = pattern:gsub("%.", "%%."):gsub("%*", ".*"):gsub("%?", ".") + + -- Check if the pattern matches the basename or path + if basename:match("^" .. lua_pattern .. "$") or file:match(lua_pattern) then + return nil -- Filter out this item + end + end + + -- Also filter out specific directory names + local ignored_dirs = { + "contracts", + "crypto", + "api", + "chains", + "test", + "examples", + "scripts", + "bridge", + "client", + "translations", + "env", + ".husky", + } + + for _, ignored in ipairs(ignored_dirs) do + if dir == ignored or file:match("/" .. ignored .. "/") then return nil end + end + + return item + end +end + +local file_filter = create_file_filter() + +local yazi = Terminal:new { + cmd = "yazi", + hidden = true, + direction = "tab", + close_on_exit = true, -- function to run on opening the terminal + on_open = function(term) + vim.cmd "startinsert!" + vim.api.nvim_buf_set_keymap(term.bufnr, "n", "q", "close", { noremap = true, silent = true }) + end, +} + +local scooter = Terminal:new { + cmd = "scooter", + hidden = true, + direction = "vertical", -- function to run on opening the terminal + on_open = function(term) + vim.cmd "startinsert!" + vim.api.nvim_buf_set_keymap(term.bufnr, "n", "q", "close", { noremap = true, silent = true }) + end, +} + +local lazyjournal = Terminal:new { + cmd = "lazyjournal", + hidden = true, + direction = "float", -- function to run on opening the terminal + on_open = function(term) + vim.cmd "startinsert!" + vim.api.nvim_buf_set_keymap(term.bufnr, "n", "q", "close", { noremap = true, silent = true }) + end, +} + +local mk = Terminal:new { + cmd = "mk", + hidden = true, + direction = "vertical", -- function to run on opening the terminal + on_open = function(term) + vim.cmd "startinsert!" + vim.api.nvim_buf_set_keymap(term.bufnr, "n", "q", "close", { noremap = true, silent = true }) + end, +} + +-- Toggle Functions (global so they can be used in other files) +function _G.Lazyjournal_toggle() lazyjournal:toggle() end +function _G.Mk_toggle() mk:toggle() end +function _G.Scooter_toggle() scooter:toggle() end +function _G.Yazi_toggle() yazi:toggle() end + return { "AstroNvim/astrocore", ---@type AstroCoreOpts @@ -11,18 +207,12 @@ return { "lsp", -- highest priority is getting workspace from running language servers { ".git", "_darcs", ".hg", ".bzr", ".svn" }, -- next check for a version controlled parent directory { - "lua", - "Taskfile.yml", - "devbox.json", - "Cargo.toml", "go.work", - "Pipfile", - "Makefile", - "requirements.txt", - "README.md", - "devbox.json", "package.json", - "go.mod", + "lua", + "Cargo.toml", + "Pipfile", + "docs.json", }, -- lastly check for a file named `main` }, -- ignore things from root detection @@ -33,7 +223,7 @@ return { -- automatically update working directory (update manually with `:AstroRoot`) autochdir = true, -- scope of working directory to change ("global"|"tab"|"win") - scope = "tab", -- Changed from "win" to "global" to make directory changes apply globally + scope = "win", -- Changed from "win" to "global" to make directory changes apply globally -- show notification on every working directory change notify = false, }, @@ -41,14 +231,14 @@ return { -- Configure core features of AstroNvim features = { autopairs = true, -- enable autopairs at start - diagnostics_mode = 3, -- diagnostic mode on start (0 = off, 1 = no signs/virtual text, 2 = no virtual text, 3 = on) + diagnostics_mode = 1, -- diagnostic mode on start (0 = off, 1 = no signs/virtual text, 2 = no virtual text, 3 = on) highlighturl = true, -- highlight URLs at start notifications = false, -- enable notifications at start }, -- Diagnostics configuration (for vim.diagnostics.config({...})) when diagnostics are on diagnostics = { - virtual_text = true, + virtual_text = false, underline = true, }, -- vim options can be configured here @@ -58,6 +248,7 @@ return { number = true, -- sets vim.opt.number spell = false, -- sets vim.opt.spell wrap = true, -- sets vim.opt.wrap + clipboard = "unnamedplus", -- use system clipboard for all operations }, g = { -- vim.g. -- configure global vim variables (vim.g) @@ -71,40 +262,493 @@ return { -- first key is the mode n = { -- navigate buffer tabs - ["L"] = { function() require("astrocore.buffer").nav(vim.v.count1) end, desc = "Next buffer" }, - ["H"] = { function() require("astrocore.buffer").nav(-vim.v.count1) end, desc = "Previous buffer" }, - ["K"] = { "g;", desc = "Go to previous edited line" }, - ["J"] = { "g,", desc = "Go to next edited line" }, - ["vv"] = { "gg0VG$", desc = "Select all contents in buffer" }, - [""] = { "Telescope oldfiles", desc = "Recent Files" }, - [""] = { "OverseerRun", desc = "Overseer" }, - [""] = { "Telescope lsp_document_symbols", desc = "Show Symbols" }, - [""] = { function() vim.cmd "bd" end, desc = "Close window" }, - [""] = { "waqa!", desc = "Save and Quit Neovim" }, - [""] = { vim.lsp.buf.rename, desc = "LSP Rename Symbol" }, - [""] = { "Neotree toggle", desc = "Show Explorer" }, - [""] = { "p", desc = "Paste" }, - }, - v = { - [""] = { "Neotree toggle", desc = "Show Explorer" }, - }, - - t = { - [""] = { + [""] = { function() - -- Check if we're in an Aider terminal buffer - local current_buf = vim.api.nvim_get_current_buf() - local buf_name = vim.api.nvim_buf_get_name(current_buf) - - -- If the buffer name contains "Aider" (as seen in the screenshot) - if buf_name:match "Aider" then - vim.cmd "AiderTerminalToggle" - else - -- Default behavior: exit terminal mode - vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes([[]], true, false, true), "n", false) + -- Save the buffer path before closing + local bufname = vim.api.nvim_buf_get_name(0) + if bufname ~= "" then + table.insert(closed_buffers, bufname) + -- Keep only the last 10 closed buffers + if #closed_buffers > 10 then table.remove(closed_buffers, 1) end + end + vim.cmd "wa" + vim.cmd "bd" + end, + desc = "Save and close buffer", + }, + ["F"] = { "za", desc = "Toggle fold under cursor" }, + ["L"] = { "BufferLineCycleNext", desc = "Next buffer" }, + ["H"] = { "BufferLineCyclePrev", desc = "Previous buffer" }, + [""] = { + function() require("snacks").explorer.reveal() end, + desc = "Reveal file in Explorer", + }, + [""] = { "OverseerRun", desc = "Run Overseer" }, + [""] = { "b#", desc = "Return to last buffer" }, + ["e"] = { + function() require("snacks").explorer.reveal() end, + desc = "Reveal file in Explorer", + }, + [""] = { + function() require("snacks").picker.smart() end, + desc = "Find files", + }, + ["b"] = { "BufferLinePick", desc = "Pick buffer" }, + ["f"] = { + function() require("snacks").picker.buffers() end, + desc = "Find buffers", + }, + ["c"] = { + function() + local current_buffer = vim.api.nvim_get_current_buf() + for _, buf in ipairs(vim.api.nvim_list_bufs()) do + if buf ~= current_buffer then vim.api.nvim_buf_delete(buf, { force = true }) end end end, - desc = "Exit terminal mode or toggle Aider terminal", + desc = "Close all buffers except the current one", + }, + ["g"] = { + function() + local groups = { "DEX", "DID", "DWN", "SVC", "Tests", "Actions", "Claude", "Docs", "Config" } + for _, group in ipairs(groups) do + vim.cmd("BufferLineGroupToggle " .. group) + end + end, + desc = "Toggle all buffer groups", + }, + ["z"] = { + function() + if #closed_buffers > 0 then + local last_closed = table.remove(closed_buffers) + vim.cmd("e " .. vim.fn.fnameescape(last_closed)) + vim.notify("Reopened: " .. vim.fn.fnamemodify(last_closed, ":t")) + else + vim.notify("No recently closed buffer found", vim.log.levels.WARN) + end + end, + desc = "Reopen last closed buffer", + }, + -- Quick group toggles + ["l"] = { + function() require("snacks").picker.lines() end, + desc = "Find in line", + }, + ["1"] = { "BufferLineGroupToggle DEX", desc = "Toggle DEX group" }, + ["2"] = { "BufferLineGroupToggle DID", desc = "Toggle DID group" }, + ["3"] = { "BufferLineGroupToggle DWN", desc = "Toggle DWN group" }, + ["4"] = { "BufferLineGroupToggle SVC", desc = "Toggle SVC group" }, + ["t"] = { "BufferLineGroupToggle Tests", desc = "Toggle Tests group" }, + ["k"] = { "BufferLinePickClose", desc = "Pick buffer to close" }, + ["o"] = { "!gh repo view --web", desc = "Open Repo on Web" }, + ["h"] = { + function() + require("snacks").terminal("gh dash", { + hidden = true, + auto_close = true, + interactive = true, + }) + end, + desc = "Dashboard", + }, + ["g"] = { + function() + require("snacks").terminal("lazygit", { + hidden = true, + auto_close = true, + interactive = true, + }) + end, + desc = "Lazygit", + }, + ["d"] = { + function() require("snacks").picker.git_diff() end, + desc = "Search git diffs", + }, + ["b"] = { + function() require("snacks").picker.git_branches() end, + desc = "Search git branches", + }, + ["d"] = { + desc = "Devbox Services", + }, + ["du"] = { + function() + require("snacks").terminal("devbox services up", { + hidden = true, + auto_close = true, + start_in_insert = true, + interactive = true, + }) + end, + desc = "Devbox Services Up", + noremap = true, + }, + ["dd"] = { + function() + require("snacks").terminal("devbox services down", { + hidden = true, + auto_close = true, + start_in_insert = true, + interactive = true, + }) + end, + desc = "Devbox Services Down", + noremap = true, + }, + ["da"] = { + function() + require("snacks").terminal("devbox services attach", { + hidden = true, + auto_close = false, + start_in_insert = true, + interactive = true, + }) + end, + desc = "Devbox Services Attach", + noremap = true, + }, + ["."] = { _G.Yazi_toggle, desc = "Yazi Toggle" }, + ["t"] = { + function() require("snacks").terminal() end, + desc = "Toggle Terminal", + }, + ["K"] = { function() vim.diagnostic.goto_prev() end, desc = "Previous Diagnostic" }, + ["J"] = { function() vim.diagnostic.goto_next() end, desc = "Next Diagnostic" }, + ["vv"] = { "gg0VG$", desc = "Select all contents in buffer" }, + ["T"] = { "gg", desc = "Go to top of file" }, + + ["r"] = { + _G.Scooter_toggle, + desc = "Find and replace", + }, + ["d"] = { + function() require("snacks").picker.diagnostics() end, + desc = "Find diagnostics", + }, + ["l"] = { + function() require("snacks").picker.lines() end, + desc = "Find diagnostics", + }, + ["f"] = { + function() require("snacks").picker.git_files { transform = file_filter } end, + desc = "Find files", + }, + ["o"] = { + function() require("snacks").picker.recent() end, + desc = "Find recent files", + }, + [""] = { + function() require("snacks").picker.projects() end, + desc = "Find projects", + }, + ["gc"] = { + function() + local claude_dir = vim.fn.getcwd() .. "/.claude" + -- Check if directory exists + if vim.fn.isdirectory(claude_dir) == 0 then + vim.notify("No .claude directory found in current project", vim.log.levels.WARN) + return + end + -- Use files picker to find Claude files + require("snacks").picker.files { + cwd = claude_dir, + transform = file_filter, + } + end, + desc = "Find Claude files", + }, + ["go"] = { "ObsidianSearch", desc = "Find in Obsidian" }, + ["p"] = { desc = "Find Package files" }, + ["P"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/code/github.com/sonr-io/sonr/proto" }, + ft = { "proto" }, + } + end, + desc = "Find Proto files", + }, + ["W"] = { + function() + require("snacks").picker.files { + dirs = { + "/home/prad/code/github.com/sonr-io/sonr/packages", + "/home/prad/code/github.com/sonr-io/sonr/web", + }, + exclude = { "packages/**/dist", "web/**/dist" }, + ft = { "ts", "tsx", "js", "html", "css", "json", "yaml" }, + } + end, + desc = "Find Web Dev files", + }, + ["pp"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/code/github.com/sonr-io/sonr/packages/pkl" }, + exclude = { "packages/pkl/dist" }, + ft = { "ts", "tsx", "js" }, + } + end, + desc = "Find @sonr.io/es files", + }, + ["ps"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/code/github.com/sonr-io/sonr/packages/sdk" }, + exclude = { "packages/sdk/dist" }, + ft = { "ts", "tsx", "js" }, + } + end, + desc = "Find @sonr.io/sdk files", + }, + ["pu"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/code/github.com/sonr-io/sonr/packages/ui" }, + exclude = { "packages/ui/dist" }, + ft = { "ts", "tsx", "js" }, + } + end, + desc = "Find @sonr.io/ui files", + }, + ["m"] = { desc = "Find Module files" }, + ["me"] = { + function() + require("snacks").picker.files { + dirs = { + "/home/prad/code/github.com/sonr-io/sonr/proto/dex", + "/home/prad/code/github.com/sonr-io/sonr/x/dex", + }, + ft = { "go", "md", "proto" }, + } + end, + desc = "Find x/dex files", + }, + ["mi"] = { + function() + require("snacks").picker.files { + dirs = { + "/home/prad/code/github.com/sonr-io/sonr/proto/did", + "/home/prad/code/github.com/sonr-io/sonr/x/did", + }, + ft = { "go", "md", "proto" }, + } + end, + desc = "Find x/did files", + }, + ["md"] = { + function() + require("snacks").picker.files { + dirs = { + "/home/prad/code/github.com/sonr-io/sonr/proto/dwn", + "/home/prad/code/github.com/sonr-io/sonr/x/dwn", + }, + ft = { "go", "md", "proto" }, + } + end, + desc = "Find x/dwn files", + }, + ["ms"] = { + function() + require("snacks").picker.files { + dirs = { + "/home/prad/code/github.com/sonr-io/sonr/proto/svc", + "/home/prad/code/github.com/sonr-io/sonr/x/svc", + }, + ft = { "go", "md", "proto" }, + } + end, + desc = "Find x/svc files", + }, + ["g"] = { + desc = "Find by Group", + }, + ["gw"] = { + function() + local workflows_dir = vim.fn.getcwd() .. "/.github/workflows" + -- Check if directory exists + if vim.fn.isdirectory(workflows_dir) == 0 then + vim.notify("No .github/workflows directory found in current project", vim.log.levels.WARN) + return + end + -- Use files picker to find workflow files + require("snacks").picker.files { + cwd = workflows_dir, + transform = file_filter, + } + end, + desc = "Find GitHub Workflow files", + }, + ["gd"] = { + function() + require("snacks").picker.files { + cmd = "fd", + args = { + "devbox.json|process-compose.yaml|Dockerfile|docker-compose.yaml|compose.yaml", + }, + } + end, + desc = "Find Devbox/Docker files", + }, + ["gm"] = { + function() + require("snacks").picker.files { + cmd = "fd", + args = { + "Makefile", + }, + } + end, + desc = "Find Makefile files", + }, + ["gp"] = { + function() + require("snacks").picker.files { + cmd = "fd", + args = { + "package.json", + }, + } + end, + desc = "Find Package.json files", + }, + ["."] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/.local/share/chezmoi" }, + } + end, + desc = "Find dotfiles", + }, + ["c"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/.local/share/chezmoi/dot_config" }, + } + end, + desc = "Find chezmoi config files", + }, + ["e"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/.local/share/chezmoi/extensions" }, + } + end, + desc = "Find chezmoi extension files", + }, + ["l"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/.local/share/chezmoi/dot_local" }, + } + end, + desc = "Find chezmoi local files", + }, + ["n"] = { + function() + require("snacks").picker.files { + dirs = { "/home/prad/.local/share/chezmoi/dot_config/nvim" }, + } + end, + desc = "Find chezmoi neovim files", + }, + ["a"] = { function() vim.lsp.buf.code_action() end, desc = "LSP Code Action" }, + ["h"] = { function() vim.lsp.buf.hover() end, desc = "LSP Hover" }, + ["d"] = { + function() require("snacks").picker.lsp_definitions() end, + desc = "Find LSP definitions", + }, + ["r"] = { + function() require("snacks").picker.lsp_references() end, + desc = "Find LSP references", + }, + ["s"] = { + function() require("snacks").picker.lsp_symbols() end, + desc = "Find LSP symbols", + }, + -- Terminal launcher + }, + i = { + [""] = { "wa", desc = "Save and return to normal mode" }, + [""] = { "wabd", desc = "Save, close buffer, and return to normal mode" }, + [""] = { "wabd", desc = "Save, close buffer, and return to normal mode" }, -- Added C-x for insert mode + }, + v = { + [""] = { + function() + -- Toggle explorer using the proper Snacks.explorer API + local snacks = require "snacks" + -- Check if there's an active explorer picker + local pickers = snacks.picker.get { source = "explorer" } + if #pickers > 0 then + -- Close the explorer + for _, picker in ipairs(pickers) do + picker:close() + end + else + -- Open the explorer + snacks.explorer() + end + end, + desc = "Toggle Explorer", + }, + [""] = { "wbd", desc = "Save and close buffer" }, -- Modified to save and close buffer + [""] = { "wbd", desc = "Save and close buffer" }, -- Added C-x for visual mode + }, + t = { + [""] = { + function() + -- Toggle explorer using the proper Snacks.explorer API + local snacks = require "snacks" + -- Check if there's an active explorer picker + local pickers = snacks.picker.get { source = "explorer" } + if #pickers > 0 then + -- Close the explorer + for _, picker in ipairs(pickers) do + picker:close() + end + else + -- Open the explorer + snacks.explorer() + end + end, + desc = "Toggle Explorer", + }, + ["f"] = { + function() require("snacks").picker.buffers() end, + desc = "Find buffers", + }, + -- Exit terminal mode and close window + [""] = { + function() + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes([[]], true, false, true), "n", false) + vim.cmd "close" + end, + desc = "Exit terminal and close window", + }, + [""] = { + function() + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes([[h]], true, false, true), "n", false) + end, + desc = "Navigate to left window", + }, + [""] = { + function() + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes([[j]], true, false, true), "n", false) + end, + desc = "Navigate to bottom window", + }, + [""] = { + function() + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes([[k]], true, false, true), "n", false) + end, + desc = "Navigate to top window", + }, + [""] = { + function() + vim.api.nvim_feedkeys(vim.api.nvim_replace_termcodes([[l]], true, false, true), "n", false) + end, + desc = "Navigate to right window", }, }, }, diff --git a/lua/plugins/astrolsp.lua b/lua/plugins/astrolsp.lua deleted file mode 100644 index b8f00f7..0000000 --- a/lua/plugins/astrolsp.lua +++ /dev/null @@ -1,109 +0,0 @@ --- AstroLSP allows you to customize the features in AstroNvim's LSP configuration engine --- Configuration documentation can be found with `:h astrolsp` --- NOTE: We highly recommend setting up the Lua Language Server (`:LspInstall lua_ls`) --- as this provides autocomplete and documentation while editing - ----@type LazySpec -return { - "AstroNvim/astrolsp", - ---@type AstroLSPOpts - opts = { - -- Configuration table of features provided by AstroLSP - features = { - codelens = true, -- enable/disable codelens refresh on start - inlay_hints = false, -- enable/disable inlay hints on start - semantic_tokens = true, -- enable/disable semantic token highlighting - signature_help = true, -- enable/disable signature help on start - }, - -- customize lsp formatting options - formatting = { - -- control auto formatting on save - format_on_save = { - enabled = true, -- enable or disable format on save globally - allow_filetypes = { -- enable format on save for specified filetypes only - "go", - "templ", - "md", - "json", - "pkl", - "yaml", - }, - ignore_filetypes = { -- disable format on save for specified filetypes - -- "python", - }, - }, - disabled = { -- disable formatting capabilities for the listed language servers - -- disable lua_ls formatting capability if you want to use StyLua to format your lua code - -- "lua_ls", - }, - timeout_ms = 1000, -- default format timeout - -- filter = function(client) -- fully override the default formatting function - -- return true - -- end - }, - -- enable servers that you already have installed without mason - servers = { - -- "pyright" - }, - -- customize language server configuration options passed to `lspconfig` - ---@diagnostic disable: missing-fields - config = { - -- clangd = { capabilities = { offsetEncoding = "utf-8" } }, - }, - -- customize how language servers are attached - handlers = { - -- a function without a key is simply the default handler, functions take two parameters, the server name and the configured options table for that server - -- function(server, opts) require("lspconfig")[server].setup(opts) end - - -- the key is the server that is being setup with `lspconfig` - -- rust_analyzer = false, -- setting a handler to false will disable the set up of that language server - -- pyright = function(_, opts) require("lspconfig").pyright.setup(opts) end -- or a custom handler function can be passed - }, - -- Configure buffer local auto commands to add when attaching a language server - autocmds = { - -- first key is the `augroup` to add the auto commands to (:h augroup) - lsp_codelens_refresh = { - -- Optional condition to create/delete auto command group - -- can either be a string of a client capability or a function of `fun(client, bufnr): boolean` - -- condition will be resolved for each client on each execution and if it ever fails for all clients, - -- the auto commands will be deleted for that buffer - cond = "textDocument/codeLens", - -- cond = function(client, bufnr) return client.name == "lua_ls" end, - -- list of auto commands to set - { - -- events to trigger - event = { "InsertLeave", "BufEnter" }, - -- the rest of the autocmd options (:h nvim_create_autocmd) - desc = "Refresh codelens (buffer)", - callback = function(args) - if require("astrolsp").config.features.codelens then vim.lsp.codelens.refresh { bufnr = args.buf } end - end, - }, - }, - }, - -- mappings to be set up on attaching of a language server - mappings = { - n = { - -- a `cond` key can provided as the string of a server capability to be required to attach, or a function with `client` and `bufnr` parameters from the `on_attach` that returns a boolean - gD = { - function() vim.lsp.buf.declaration() end, - desc = "Declaration of current symbol", - cond = "textDocument/declaration", - }, - ["uY"] = { - function() require("astrolsp.toggles").buffer_semantic_tokens() end, - desc = "Toggle LSP semantic highlight (buffer)", - cond = function(client) - return client.supports_method "textDocument/semanticTokens/full" and vim.lsp.semantic_tokens ~= nil - end, - }, - }, - }, - -- A custom `on_attach` function to be run after the default `on_attach` function - -- takes two parameters `client` and `bufnr` (`:h lspconfig-setup`) - on_attach = function(client, bufnr) - -- this would disable semanticTokensProvider for all clients - -- client.server_capabilities.semanticTokensProvider = nil - end, - }, -} diff --git a/lua/plugins/astroui.lua b/lua/plugins/astroui.lua index 8fd417b..0271b1e 100644 --- a/lua/plugins/astroui.lua +++ b/lua/plugins/astroui.lua @@ -1,37 +1,197 @@ --- AstroUI provides the basis for configuring the AstroNvim User Interface --- Configuration documentation can be found with `:h astroui` --- NOTE: We highly recommend setting up the Lua Language Server (`:LspInstall lua_ls`) --- as this provides autocomplete and documentation while editing - ----@type LazySpec return { - "AstroNvim/astroui", - ---@type AstroUIOpts - opts = { - -- change colorscheme - colorscheme = "cyberdream", - -- AstroUI allows you to easily modify highlight groups easily for any and all colorschemes - highlights = { - init = { -- this table overrides highlights in all themes - -- Normal = { bg = "#000000" }, + { + "AstroNvim/astroui", + ---@type AstroUIOpts + opts = { + colorscheme = "cyberdream", + -- add new user interface icon + icons = { + VimIcon = "", + ScrollText = "", + GitBranch = "", + GitAdd = "", + GitChange = "", + GitDelete = "", }, - astrodark = { -- a table of overrides/changes when applying the astrotheme theme - -- Normal = { bg = "#000000" }, + -- modify variables used by heirline but not defined in the setup call directly + status = { + -- define the separators between each section + separators = { + left = { "", "" }, -- separator for the left side of the statusline + right = { "", "" }, -- separator for the right side of the statusline + tab = { "", "" }, + }, + -- add new colors that can be used by heirline + colors = function(hl) + local get_hlgroup = require("astroui").get_hlgroup + -- use helper function to get highlight group properties + local comment_fg = get_hlgroup("Comment").fg + hl.git_branch_fg = comment_fg + hl.git_added = comment_fg + hl.git_changed = comment_fg + hl.git_removed = comment_fg + hl.blank_bg = get_hlgroup("Folded").fg + hl.file_info_bg = get_hlgroup("Visual").bg + hl.nav_icon_bg = get_hlgroup("String").fg + hl.nav_fg = hl.nav_icon_bg + hl.folder_icon_bg = get_hlgroup("Error").fg + return hl + end, + attributes = { + mode = { bold = true }, + }, + icon_highlights = { + file_icon = { + statusline = false, + }, + }, }, }, - -- Icons can be configured throughout the interface - icons = { - -- configure the loading of the lsp in the status line - LSPLoading1 = "⠋", - LSPLoading2 = "⠙", - LSPLoading3 = "⠹", - LSPLoading4 = "⠸", - LSPLoading5 = "⠼", - LSPLoading6 = "⠴", - LSPLoading7 = "⠦", - LSPLoading8 = "⠧", - LSPLoading9 = "⠇", - LSPLoading10 = "⠏", - }, + }, + { + "rebelot/heirline.nvim", + opts = function(_, opts) + local status = require "astroui.status" + -- Disable heirline's tabline since we're using bufferline + opts.tabline = nil + opts.statusline = { + -- default highlight for the entire statusline + hl = { fg = "fg", bg = "bg" }, + -- each element following is a component in astroui.status module + + -- add the vim mode component + status.component.mode { + -- enable mode text with padding as well as an icon before it + mode_text = { + icon = { kind = "VimIcon", padding = { right = 1, left = 1 } }, + }, + -- surround the component with a separators + surround = { + -- it's a left element, so use the left separator + separator = "left", + -- set the color of the surrounding based on the current mode using astronvim.utils.status module + color = function() return { main = status.hl.mode_bg(), right = "blank_bg" } end, + }, + }, + -- we want an empty space here so we can use the component builder to make a new section with just an empty string + status.component.builder { + { provider = "" }, + -- define the surrounding separator and colors to be used inside of the component + -- and the color to the right of the separated out section + surround = { + separator = "left", + color = { main = "blank_bg", right = "file_info_bg" }, + }, + }, + -- add a section for the currently opened file information + status.component.file_info { + -- enable the file_icon and disable the highlighting based on filetype + filename = { fallback = "Empty" }, + -- disable some of the info + filetype = false, + file_read_only = false, + -- add padding + padding = { right = 1 }, + -- define the section separator + surround = { separator = "left", condition = false }, + }, + -- add a component for the current git branch if it exists and use no separator for the sections + status.component.git_branch { + git_branch = { padding = { left = 1 } }, + surround = { separator = "none" }, + }, + -- add a component for the current git diff if it exists and use no separator for the sections + status.component.git_diff { + padding = { left = 1 }, + surround = { separator = "none" }, + }, + -- fill the rest of the statusline + -- the elements after this will appear in the middle of the statusline + status.component.fill(), + -- add a component to display if the LSP is loading, disable showing running client names, and use no separator + status.component.lsp { + lsp_client_names = false, + surround = { separator = "none", color = "bg" }, + }, + -- fill the rest of the statusline + -- the elements after this will appear on the right of the statusline + status.component.fill(), + -- add a component for the current diagnostics if it exists and use the right separator for the section + status.component.diagnostics { surround = { separator = "right" }, padding = { right = 1 } }, + -- add a component to display LSP clients, disable showing LSP progress, and use the right separator + status.component.lsp { + lsp_progress = false, + padding = { right = 1 }, + surround = { separator = "right" }, + }, + -- NvChad has some nice icons to go along with information, so we can create a parent component to do this + -- all of the children of this table will be treated together as a single component + { + flexible = 1, + { + -- define a simple component where the provider is just a folder icon + status.component.builder { + -- astronvim.get_icon gets the user interface icon for a closed folder with a space after it + { provider = require("astroui").get_icon "FolderClosed" }, + -- add padding after icon + padding = { right = 1 }, + -- set the foreground color to be used for the icon + hl = { fg = "bg" }, + -- use the right separator and define the background color + surround = { separator = "right", color = "folder_icon_bg" }, + }, + -- add a file information component and only show the current working directory name + status.component.file_info { + -- we only want filename to be used and we can change the fname + -- function to get the current working directory name + filename = { + fname = function(nr) return vim.fn.getcwd(nr) end, + padding = { left = 1, right = 1 }, + }, + -- disable all other elements of the file_info component + filetype = false, + file_icon = false, + file_modified = false, + file_read_only = false, + -- use no separator for this part but define a background color + surround = { + separator = "none", + color = "file_info_bg", + condition = false, + }, + }, + }, + {}, + }, + -- the final component of the NvChad statusline is the navigation section + -- this is very similar to the previous current working directory section with the icon + { -- make nav section with icon border + -- define a custom component with just a file icon + status.component.builder { + { provider = require("astroui").get_icon "ScrollText" }, + -- add padding after icon + padding = { right = 1 }, + -- set the icon foreground + hl = { fg = "bg" }, + -- use the right separator and define the background color + -- as well as the color to the left of the separator + surround = { + separator = "right", + color = { main = "nav_icon_bg", left = "file_info_bg" }, + }, + }, + -- add a navigation component and just display the percentage of progress in the file + status.component.nav { + -- add some padding for the percentage provider + percentage = { padding = { right = 1 } }, + -- disable all other providers + ruler = false, + scrollbar = false, + -- use no separator and define the background color + surround = { separator = "none", color = "file_info_bg" }, + }, + }, + } + end, }, } diff --git a/lua/plugins/bufferline.lua b/lua/plugins/bufferline.lua new file mode 100644 index 0000000..8748313 --- /dev/null +++ b/lua/plugins/bufferline.lua @@ -0,0 +1,151 @@ +-- Bufferline configuration with AstroNvim integration +return { + "akinsho/bufferline.nvim", + version = "*", + dependencies = { "nvim-tree/nvim-web-devicons", "AstroNvim/astrocore" }, + event = "VeryLazy", + config = function() + local bufferline = require "bufferline" + local groups = require "bufferline.groups" + + bufferline.setup { + options = { + mode = "buffers", + numbers = "none", + close_command = function(n) require("astrocore.buffer").close(n) end, + right_mouse_command = function(n) require("astrocore.buffer").close(n) end, + separator_style = "thick", + indicator = { style = "icon", icon = "▎" }, + diagnostics = "nvim_lsp", + diagnostics_indicator = function(_, _, diagnostics_dict) + local s = " " + for e, _ in pairs(diagnostics_dict) do + local sym = e == "error" and " " or (e == "warning" and " " or " ") + s = s .. sym + end + return s + end, + always_show_bufferline = true, + show_buffer_close_icons = true, + show_close_icon = true, + modified_icon = "●", + buffer_close_icon = "󰅖", + close_icon = "", + left_trunc_marker = "", + right_trunc_marker = "", + offsets = { + { filetype = "snacks_picker", text = "", padding = 0 }, + }, + groups = { + options = { toggle_hidden_on_enter = true }, + items = { + groups.builtin.ungrouped, + + -- Module groups + { + name = "", + auto_close = true, + highlight = { fg = "#5ef1ff" }, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "x/dex/.*%.go$" or bufname:match "proto/dex/.*%.proto$" + end, + }, + { + name = "DID", + auto_close = true, + highlight = { fg = "#5ef1ff" }, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "x/did/.*%.go$" or bufname:match "proto/did/.*%.proto$" + end, + }, + { + name = "DWN", + auto_close = true, + highlight = { fg = "#5ef1ff" }, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "x/dwn/.*%.go$" or bufname:match "proto/dwn/.*%.proto$" + end, + }, + { + name = "SVC", + highlight = { fg = "#5ef1ff" }, + auto_close = true, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "x/svc/.*%.go$" or bufname:match "proto/svc/.*%.proto$" + end, + }, + + -- Tests + { + name = "Tests", + auto_close = true, + highlight = { fg = "#ff5ea0" }, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "_test%.go$" or bufname:match "/test/" + end, + }, + + -- Auto-close groups + { + name = "Actions", + highlight = { fg = "#ff5ef1" }, + auto_close = true, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "%.ya?ml$" and bufname:match "%.github/" + end, + }, + { + name = "Claude", + highlight = { fg = "#ffbd5e" }, + auto_close = true, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "%.claude/" or bufname:match "CLAUDE%.md$" + end, + }, + { + name = "Docs", + highlight = { fg = "#ffffff" }, + auto_close = true, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return bufname:match "%.mdx?$" or bufname:match "/docs/" + end, + }, + { + name = "Config", + highlight = { fg = "#3c4048" }, + auto_close = true, + matcher = function(buf) + local bufname = vim.api.nvim_buf_get_name(buf.id) + return (bufname:match "%.ya?ml$" and not bufname:match "%.github/") + or bufname:match "%.json$" + or bufname:match "%.toml$" + or bufname:match "%.sh$" + end, + }, + }, + }, + }, + highlights = { + group_label = { fg = "#ffffff", bg = "#423f5a", bold = true }, + group_separator = { fg = "#585b70" }, + buffer_selected = { fg = "#89dceb", bold = true }, + buffer_visible = { fg = "#585b70" }, + background = { fg = "#585b70" }, + hint = { fg = "#94e2d5" }, + hint_selected = { fg = "#94e2d5", bold = true }, + warning = { fg = "#f9e2af" }, + warning_selected = { fg = "#f9e2af", bold = true }, + error = { fg = "#f38ba8" }, + error_selected = { fg = "#f38ba8", bold = true }, + }, + } + end, +} diff --git a/lua/plugins/explorer.lua b/lua/plugins/explorer.lua new file mode 100644 index 0000000..220746c --- /dev/null +++ b/lua/plugins/explorer.lua @@ -0,0 +1,439 @@ +-- Function to read patterns from .rgignore file +local function read_rgignore_patterns() + local patterns = {} + local git_root = vim.fn.systemlist("git rev-parse --show-toplevel")[1] + + if git_root and git_root ~= "" then + local rgignore_path = git_root .. "/.rgignore" + local file = io.open(rgignore_path, "r") + + if file then + for line in file:lines() do + -- Skip comments and empty lines + if line ~= "" and not line:match "^#" then + -- Remove leading ./ if present + line = line:gsub("^%./", "") + -- Add the pattern + table.insert(patterns, line) + end + end + file:close() + end + end + + return patterns +end + +-- Build exclude patterns for snacks.explorer +local function build_exclude_patterns() + -- Get patterns from .rgignore + local rgignore_patterns = read_rgignore_patterns() + + -- Default hide patterns (from original neotree config) + local hide_patterns = { + "chain_*.json", + "Library", + ".typecopy", + ".python-version", + "*.pb.go", + "*config.*.js", + "*config.js", + "deps.mjs", + ".parcelrc", + "worker-configuration.d.ts", + "wrangler.jsonc", + "*.pkl.go", + ".trunk", + ".config", + ".cz.toml", + "*_mock.go", + } + + -- Never show by pattern (from original neotree config) + local never_show_by_pattern = { + "*DS_Store", + ".obsidian", + ".pkl-lsp", + ".tsbuildinfo", + "package-lock.json", + ".prettierrc", + "node_modules", + ".DocumentRevisions-V100", + ".Spotlight-V100", + ".TemporaryItems", + ".Trashes", + ".fseventsd", + ".editorconfig", + "*.min.js", + "*.lock", + "*lock*", + "*.lockb", + "*.pulsar.go", + "*.pb.gorm.go", + "*.pb.gw.go", + "*_templ.go", + "*.tmp", + "*.work.*", + "*.sum", + ".parcel-cache", + "*.icns", + "*.ico", + ".aider.tags.cache.v4", + "*.iml", + "Icon?", + "iCloud~", + "com~", + "*.icns", + ".conform*", + ".null-ls_*", + } + + -- Never show directories (from original neotree config) + local never_show = { + ".git", + "pnpm-lock.yaml", + ".next", + ".task", + ".devbox", + ".dart_tool", + ".idea", + ".metadata", + ".venv", + ".gradle", + "gradle.bat", + ".aider.chat.history.md", + ".aider.input.history", + ".aider.tags.cache.v3", + ".devcontainer", + "heighliner", + ".tmp", + "go.work.sum", + ".DS_Store", + ".git", + "LICENSE", + "tmp", + "sonr.log", + "DISCUSSION_TEMPLATE", + "ISSUE_TEMPLATE", + ".devbox", + ".timemachine", + "junit.xml", + ".jj", + ".spawn", + ".turbo", + } + + -- Merge all patterns + local all_patterns = {} + + -- Add default hide patterns + for _, pattern in ipairs(hide_patterns) do + table.insert(all_patterns, pattern) + end + + -- Add rgignore patterns + for _, pattern in ipairs(rgignore_patterns) do + table.insert(all_patterns, pattern) + end + + -- Add never show by pattern + for _, pattern in ipairs(never_show_by_pattern) do + table.insert(all_patterns, pattern) + end + + -- Add never show directories + for _, pattern in ipairs(never_show) do + table.insert(all_patterns, pattern) + end + + return all_patterns +end + +-- Custom transform function to filter items +local function create_transform_filter() + local exclude_patterns = build_exclude_patterns() + + return function(item, ctx) + if not item then return false end + + local name = item.name or (item.file and vim.fn.fnamemodify(item.file, ":t")) or "" + local path = item.file or "" + + -- Check each pattern + for _, pattern in ipairs(exclude_patterns) do + -- Convert glob pattern to Lua pattern + local lua_pattern = pattern + :gsub("([%.%+%-%[%]%(%)%$%^%%%?])", "%%%1") -- Escape special chars except * + :gsub("%*%*", ".*") -- ** matches any characters including / + :gsub("%*", "[^/]*") -- * matches any characters except / + :gsub("%?", ".") -- ? matches single character + + -- Check against filename + if name:match("^" .. lua_pattern .. "$") then + return false -- Filter out this item + end + + -- Check against full path + if path:match("/" .. lua_pattern .. "$") or path:match("/" .. lua_pattern .. "/") then + return false -- Filter out this item + end + end + + return item -- Keep the item + end +end + +return { + { + "folke/snacks.nvim", + priority = 1000, + lazy = false, + ---@type snacks.Config + opts = function() + return { + -- Enable explorer and replace netrw + explorer = { + replace_netrw = true, + }, + -- Dashboard configuration + dashboard = { + preset = { + header = table.concat({ + "", + "", + " ████████ ", + " ██████████████ ", + " ████████████████ ", + " ██████████ █████ ", + " ██████████ █ ", + " ██████████ █████ ", + " █████████ █████████ ", + " █████████ ████ █████████ ", + " ████████ ████████ ████████ ", + "███████ ████████████ ███████", + "███████ ██████████████ ██████", + "███████ ████████████ ███████", + " ████████ ████████ ████████ ", + " █████████ ████ █████████ ", + " ████████ ██████████ ", + " ██████ ██████████ ", + " ██ █████████ ", + " ████ ██████████ ", + " ████████████████ ", + " ██████████████ ", + " ████████ ", + "", + "", + }, "\n"), + }, + sections = { + { section = "header" }, + { + pane = 2, + section = "terminal", + cmd = "colorscript -e square", + height = 5, + padding = 1, + }, + { section = "keys", gap = 1, padding = 1 }, + { + pane = 2, + icon = " ", + desc = "Browse Repo", + padding = 1, + key = "b", + action = function() require("snacks").gitbrowse() end, + }, + function() + local in_git = require("snacks").git.get_root() ~= nil + local cmds = { + { + title = "Notifications", + cmd = "gh notify -s -a -n5", + action = function() vim.ui.open "https://github.com/notifications" end, + key = "n", + icon = " ", + height = 5, + enabled = true, + }, + { + title = "Open Issues", + cmd = "gh issue list -L 3", + key = "i", + action = function() vim.fn.jobstart("gh issue list --web", { detach = true }) end, + icon = " ", + height = 7, + }, + { + icon = " ", + title = "Open PRs", + cmd = "gh pr list -L 3", + key = "P", + action = function() vim.fn.jobstart("gh pr list --web", { detach = true }) end, + height = 7, + }, + { + icon = " ", + title = "Git Status", + cmd = "git --no-pager diff --stat -B -M -C", + height = 10, + }, + } + return vim.tbl_map( + function(cmd) + return vim.tbl_extend("force", { + pane = 2, + section = "terminal", + enabled = in_git, + padding = 1, + ttl = 5 * 60, + indent = 3, + }, cmd) + end, + cmds + ) + end, + { section = "startup" }, + }, + }, + -- Configure the explorer picker source + picker = { + sources = { + explorer = { + -- Explorer configuration matching neotree + tree = true, + hidden = true, -- Show hidden files by default (. files) + ignored = false, -- Don't show gitignored files + follow_file = true, + git_status = true, + git_untracked = true, + diagnostics = true, + watch = true, + -- Use transform to filter out unwanted files/directories + transform = create_transform_filter(), + focus = "list", + auto_close = false, + jump = { close = true }, -- Close explorer when jumping to a file + layout = { + preset = "sidebar", + preview = false, + layout = { + width = 34, + }, + }, + formatters = { + file = { filename_only = true }, + }, + matcher = { sort_empty = false, fuzzy = false }, + win = { + list = { + keys = { + -- Navigation (matching neotree) + ["H"] = "explorer_up", -- Navigate to parent directory + ["L"] = "explorer_focus", -- Open file/expand directory (with auto-close for files) + [""] = "confirm", -- Open file/expand directory (with auto-close for files) + [""] = "confirm", -- Open without closing + [""] = "explorer_close_all", -- Collapse all folders + ["!"] = "toggle_ignored", -- Toggle ignored files + ["."] = "toggle_hidden", -- Toggle hidden files + ["/"] = function(self) + -- Focus search input + self:focus "input" + end, + ["f"] = function(self) + -- Focus search input (filter) + self:focus "input" + end, + [""] = function(self) + -- Clear filter + self.input:set "" + end, + ["s"] = "edit_vsplit", -- Open in vertical split + ["S"] = "edit_split", -- Open in horizontal split + ["t"] = "tab", -- Open in new tab + + -- File operations + ["a"] = "explorer_add", -- Add file + ["d"] = "explorer_del", -- Delete + ["r"] = "explorer_rename", -- Rename + ["y"] = "explorer_yank", -- Copy + ["x"] = "explorer_move", -- Cut/Move + ["p"] = "explorer_paste", -- Paste + ["c"] = "explorer_yank", -- Copy to clipboard + ["R"] = "explorer_update", -- Refresh + -- Git keybindings from neotree + ["o"] = function() vim.cmd "!gh repo view --web" end, + ["h"] = function() + require("snacks").terminal("gh dash", { + hidden = true, + auto_close = false, + interactive = true, + }) + end, + ["g"] = function() + require("snacks").terminal("lazygit", { + hidden = true, + auto_close = true, + interactive = true, + }) + end, + ["d"] = function() require("snacks").picker.git_diff() end, + ["b"] = function() require("snacks").picker.git_branches() end, + -- Terminal keybindings from neotree + ["m"] = function() _G.Mk_toggle() end, + ["j"] = function() _G.Lazyjournal_toggle() end, + ["l"] = function() + require("snacks").terminal("lazydocker", { + hidden = true, + auto_close = true, + start_in_insert = true, + interactive = true, + }) + end, + ["du"] = function() + require("snacks").terminal("devbox services up", { + hidden = true, + auto_close = false, + start_in_insert = true, + interactive = true, + }) + end, + ["dd"] = function() + require("snacks").terminal("devbox services down", { + hidden = true, + auto_close = false, + start_in_insert = true, + interactive = true, + }) + end, + ["da"] = function() + require("snacks").terminal("devbox services attach", { + hidden = true, + auto_close = false, + start_in_insert = true, + interactive = true, + }) + end, + ["."] = function() _G.Yazi_toggle() end, + ["t"] = function() require("snacks").terminal() end, + -- Additional navigation + ["h"] = "explorer_close", -- Close directory + ["l"] = "confirm", -- Open/expand + ["o"] = "explorer_open", -- Open with system application + ["P"] = "toggle_preview", + ["I"] = "toggle_ignored", + ["Z"] = "explorer_close_all", + ["]g"] = "explorer_git_next", + ["[g"] = "explorer_git_prev", + ["]d"] = "explorer_diagnostic_next", + ["[d"] = "explorer_diagnostic_prev", + }, + }, + }, + }, + }, + }, + } + end, + }, +} diff --git a/lua/plugins/mason.lua b/lua/plugins/mason.lua index 2d79b5f..de9307e 100644 --- a/lua/plugins/mason.lua +++ b/lua/plugins/mason.lua @@ -1,5 +1,3 @@ -if true then return {} end -- WARN: REMOVE THIS LINE TO ACTIVATE THIS FILE - -- Customize Mason ---@type LazySpec @@ -13,6 +11,8 @@ return { ensure_installed = { -- install language servers "lua-language-server", + "golangci-lint-langserver", + "pkl-lsp", -- install formatters "stylua", @@ -22,6 +22,10 @@ return { -- install any other package "tree-sitter-cli", + "protols", + "protolint", + "templ", + "yamlfmt", }, }, }, diff --git a/lua/plugins/neotree.lua b/lua/plugins/neotree.lua deleted file mode 100644 index 7dfd315..0000000 --- a/lua/plugins/neotree.lua +++ /dev/null @@ -1,256 +0,0 @@ -return { - { - "neo-tree.nvim", - opts = { - popup_border_style = "rounded", - enable_git_status = true, - enable_diagnostics = true, - sort_case_insensitive = false, - auto_expand_width = false, - git_status_async = true, -- Asynchronous git status. Improves performance. - hide_root_node = true, -- Hide the root node. - retain_hidden_root_indent = true, -- IF the root node is hidden, keep the indentation anyhow. - use_libuv_file_watcher = true, - -- Add custom title function to show host/org/repo - window = { - position = "left", - width = 40, - title = function() - -- Get current working directory - local cwd = vim.fn.getcwd() - - -- Extract host/org/repo from path (assuming ghq structure) - -- This pattern looks for Code/host.com/org/repo in the path - local pattern = ".*/Code/([^/]+/[^/]+/[^/]+)" - local match = string.match(cwd, pattern) - - if match then - return match - else - return "SonrVim" - end - end, - mappings = { - [""] = "navigate_up", - [">"] = "set_root", - ["."] = "toggle_hidden", - ["/"] = "fuzzy_finder", - ["f"] = "filter_on_submit", - [""] = "clear_filter", - [""] = "open_and_close_neotree", - [""] = "open", - }, - header = { - highlight = "NeoTreeHeader", - }, - }, - - default_component_configs = { - container = { - enable_character_fade = true, - }, - indent = { - indent_size = 2, - padding = 1, -- extra padding on left hand side - -- indent guides - with_markers = true, - indent_marker = "│", - last_indent_marker = "└", - highlight = "NeoTreeIndentMarker", - -- expander config, needed for nesting files - expander_collapsed = "", - expander_expanded = "", - expander_highlight = "NeoTreeExpander", - }, - name = { - trailing_slash = false, -- append a trailing slash to folder names - use_git_status_colors = true, -- use git status colors instead of the default colors - highlight = "NeoTreeFileName", - }, - git_status = { - symbols = { - -- Change type - added = "", -- or "✚", but this is redundant info if you use git_status_colors on the name - modified = "", -- or "", but this is redundant info if you use git_status_colors on the name - deleted = "✖", -- this can only be used in the git_status source - renamed = "󰁕", -- this can only be used in the git_status source - -- Status type - untracked = "", - ignored = "", - unstaged = "󰄱", - staged = "", - conflict = "", - }, - }, - -- If you don't want to use these columns, you can set `enabled = false` for each of them individually - file_size = { - enabled = true, - width = 12, -- width of the column - required_width = 48, -- min width of window required to show this column - }, - type = { - enabled = true, - width = 10, -- width of the column - required_width = 122, -- min width of window required to show this column - }, - last_modified = { - enabled = true, - width = 20, -- width of the column - required_width = 88, -- min width of window required to show this column - }, - created = { - enabled = true, - width = 20, -- width of the column - required_width = 110, -- min width of window required to show this column - }, - symlink_target = { - enabled = false, - }, - }, - - buffers = { - follow_current_file = { - enabled = true, - }, - }, - - -- Filesystem specific settings - filesystem = { - commands = { - -- If item is a file it will close neotree after opening it. - open_and_close_neotree = function(state) - require("neo-tree.sources.filesystem.commands").open(state) - - local tree = state.tree - local success, node = pcall(tree.get_node, tree) - - if not success then return end - - if node.type == "file" then require("neo-tree.command").execute { action = "close" } end - end, - }, - bind_to_cwd = true, - follow_current_file = { - enabled = true, - leave_dirs_open = true, - }, - filtered_items = { - force_visible_in_empty_folder = true, - group_empty = true, - show_hidden_count = false, - hide_dotfiles = true, - hide_gitignored = true, - hide_by_pattern = { - "dist", - ".python-version", - "*.pb.go", - "*_templ.go", - "buf.gen.*", - "*config.*.js", - "*config.js", - "deps.mjs", - "test_*.go", - ".trunk", - ".config", - }, - hide_by_name = { - ".github", - "settings.json", - ".gitignore", - "analysis_options.yaml", - "decorators", - "slumber.yml", - "devbox.d", - "matrix", - "env", - "package-lock.json", - ".husky", - "translations", - "LICENSE.md", - ".tmuxinator.yml", - ".envrc", - }, - never_show_by_pattern = { - "node_modules", - "PULL_REQUEST_TEMPLATE.md", - ".DocumentRevisions-V100", - ".Spotlight-V100", - ".TemporaryItems", - ".Trashes", - ".fseventsd", - ".trunk", - ".editorconfig", - ".eslint*", - "*.min.js", - ".gitpod.*", - "cspell.*", - "*.lock", - "*.lockb", - "*.pulsar.go", - "*.pb.gorm.go", - "*.pb.gw.go", - "*_templ.go", - "*.tmp", - "*.work.*", - "*.sum", - ".wrangler", - "*.wasm", - "*.png", - "*.min.js", - "*.jpg", - "*.icns", - "*.ico", - "build", - "PklProject.deps.json", - ".aider.tags.cache.v4", - "*.iml", - "Icon?", - }, - never_show = { - ".dart_tool", - ".idea", - ".metadata", - ".venv", - ".gradle", - "gradle.bat", - ".aider.chat.history.md", - ".aider.input.history", - ".aider.tags.cache.v3", - ".devcontainer", - "heighliner", - ".tmp", - "go.work.sum", - ".DS_Store", - ".git", - "LICENSE", - "tmp", - "sonr.log", - "DISCUSSION_TEMPLATE", - "ISSUE_TEMPLATE", - ".devbox", - ".timemachine", - }, - }, - }, - diagnostics = { - enable = false, - icons = { - hint = "", - info = "", - warning = "", - error = "", - }, - }, - - source_selector = { - winbar = false, - statusline = false, - }, - - -- Main sources - sources = { - "filesystem", - }, - }, - }, -} diff --git a/lua/plugins/none-ls.lua b/lua/plugins/none-ls.lua deleted file mode 100644 index 2b0ed18..0000000 --- a/lua/plugins/none-ls.lua +++ /dev/null @@ -1,24 +0,0 @@ -if true then return {} end -- WARN: REMOVE THIS LINE TO ACTIVATE THIS FILE - --- Customize None-ls sources - ----@type LazySpec -return { - "nvimtools/none-ls.nvim", - opts = function(_, opts) - -- opts variable is the default configuration table for the setup function call - -- local null_ls = require "null-ls" - - -- Check supported formatters and linters - -- https://github.com/nvimtools/none-ls.nvim/tree/main/lua/null-ls/builtins/formatting - -- https://github.com/nvimtools/none-ls.nvim/tree/main/lua/null-ls/builtins/diagnostics - - -- Only insert new sources, do not replace the existing ones - -- (If you wish to replace, use `opts.sources = {}` instead of the `list_insert_unique` function) - opts.sources = require("astrocore").list_insert_unique(opts.sources, { - -- Set a formatter - -- null_ls.builtins.formatting.stylua, - -- null_ls.builtins.formatting.prettier, - }) - end, -} diff --git a/lua/plugins/obsidian.lua b/lua/plugins/obsidian.lua new file mode 100644 index 0000000..32531ab --- /dev/null +++ b/lua/plugins/obsidian.lua @@ -0,0 +1,76 @@ +return { + "obsidian-nvim/obsidian.nvim", + -- the obsidian vault in this default config ~/obsidian-vault + -- If you want to use the home shortcut '~' here you need to call 'vim.fn.expand': + event = { "bufreadpre " .. vim.fn.expand "~" .. "/Notes/**.md" }, + dependencies = { + "nvim-lua/plenary.nvim", + { "hrsh7th/nvim-cmp", optional = true }, + { + "AstroNvim/astrocore", + opts = { + mappings = { + n = { + ["gf"] = { + function() + if require("obsidian").util.cursor_on_markdown_link() then + return "Obsidian follow_link" + else + return "gf" + end + end, + desc = "Obsidian Follow Link", + }, + }, + }, + }, + }, + }, + opts = function(_, opts) + local astrocore = require "astrocore" + return astrocore.extend_tbl(opts, { + workspaces = { + { + path = vim.env.HOME .. "/Notes", -- specify the vault location. no need to call 'vim.fn.expand' here + }, + }, + open = { + use_advanced_uri = true, + }, + finder = (astrocore.is_available "snacks.pick" and "snacks.pick") + or (astrocore.is_available "telescope.nvim" and "telescope.nvim") + or (astrocore.is_available "fzf-lua" and "fzf-lua") + or (astrocore.is_available "mini.pick" and "mini.pick"), + + templates = { + subdir = "2 - Areas/Templates", + date_format = "%Y-%m-%d-%a", + time_format = "%H:%M", + }, + daily_notes = { + folder = "3 - Journals", + }, + completion = { + nvim_cmp = astrocore.is_available "nvim-cmp", + blink = astrocore.is_available "blink", + }, + + note_frontmatter_func = function(note) + -- This is equivalent to the default frontmatter function. + local out = { id = note.id, aliases = note.aliases, tags = note.tags } + -- `note.metadata` contains any manually added fields in the frontmatter. + -- So here we just make sure those fields are kept in the frontmatter. + if note.metadata ~= nil and not vim.tbl_isempty(note.metadata) then + for k, v in pairs(note.metadata) do + out[k] = v + end + end + return out + end, + + -- Optional, by default when you use `:ObsidianFollowLink` on a link to an external + -- URL it will be ignored but you can customize this behavior here. + follow_url_func = vim.ui.open, + }) + end, +} diff --git a/lua/plugins/sessions.lua b/lua/plugins/sessions.lua deleted file mode 100644 index 8677994..0000000 --- a/lua/plugins/sessions.lua +++ /dev/null @@ -1,64 +0,0 @@ --- function for calculating the current session name -local get_session_name = function() - local name = vim.fn.getcwd() - local branch = vim.fn.system "git branch --show-current" - if vim.v.shell_error == 0 then - return name .. vim.trim(branch --[[@as string]]) - else - return name - end -end - -return { - "AstroNvim/astrocore", - ---@type AstroCoreOpts - opts = { - sessions = { - -- disable the auto-saving of directory sessions - autosave = { cwd = false }, - }, - mappings = { - n = { - -- update save dirsession mapping to get the correct session name - ["SS"] = { - function() require("resession").save(get_session_name(), { dir = "dirsession" }) end, - desc = "Save this dirsession", - }, - -- update load dirsession mapping to get the correct session name - ["S."] = { - function() require("resession").load(get_session_name(), { dir = "dirsession" }) end, - desc = "Load current dirsession", - }, - }, - }, - autocmds = { - -- disable alpha autostart - alpha_autostart = false, - git_branch_sessions = { - -- auto save directory sessions on leaving - { - event = "VimLeavePre", - desc = "Save git branch directory sessions on close", - callback = vim.schedule_wrap(function() - if require("astrocore.buffer").is_valid_session() then - require("resession").save(get_session_name(), { dir = "dirsession", notify = false }) - end - end), - }, - -- auto restore previous previous directory session, remove if necessary - { - event = "VimEnter", - desc = "Restore previous directory session if neovim opened with no arguments", - nested = true, -- trigger other autocommands as buffers open - callback = function() - -- Only load the session if nvim was started with no args - if vim.fn.argc(-1) == 0 then - -- try to load a directory session using the current working directory - require("resession").load(get_session_name(), { dir = "dirsession", silence_errors = true }) - end - end, - }, - }, - }, - }, -} diff --git a/lua/plugins/snacks_lsp_mappings.lua b/lua/plugins/snacks_lsp_mappings.lua deleted file mode 100644 index cce4b86..0000000 --- a/lua/plugins/snacks_lsp_mappings.lua +++ /dev/null @@ -1,17 +0,0 @@ -return { - "AstroNvim/astrolsp", - ---@param opts AstroLSPOpts - opts = function(_, opts) - if opts.mappings.n.gd then opts.mappings.n.gd[1] = function() require("snacks.picker").lsp_definitions() end end - if opts.mappings.n.gI then opts.mappings.n.gI[1] = function() require("snacks.picker").lsp_implementations() end end - if opts.mappings.n.gy then - opts.mappings.n.gy[1] = function() require("snacks.picker").lsp_type_definitions() end - end - if opts.mappings.n["lG"] then - opts.mappings.n["lG"][1] = function() require("snacks.picker").lsp_workspace_symbols() end - end - if opts.mappings.n["lR"] then - opts.mappings.n["lR"][1] = function() require("snacks.picker").lsp_references() end - end - end, -} diff --git a/lua/plugins/supermaven.lua b/lua/plugins/supermaven.lua deleted file mode 100644 index fdcbd02..0000000 --- a/lua/plugins/supermaven.lua +++ /dev/null @@ -1,29 +0,0 @@ -return { - "supermaven-inc/supermaven-nvim", - event = "InsertEnter", - cmd = { "SupermavenUseFree", "SupermavenUsePro" }, - opts = { - keymaps = { - accept_suggestion = nil, -- handled by completion engine - }, - }, - specs = { - { - "AstroNvim/astrocore", - opts = { - options = { - g = { - -- set the ai_accept function - ai_accept = function() - local suggestion = require "supermaven-nvim.completion_preview" - if suggestion.has_suggestion() then - vim.schedule(function() suggestion.on_accept_suggestion() end) - return true - end - end, - }, - }, - }, - }, - }, -} diff --git a/lua/plugins/treesitter.lua b/lua/plugins/treesitter.lua deleted file mode 100644 index 94436aa..0000000 --- a/lua/plugins/treesitter.lua +++ /dev/null @@ -1,15 +0,0 @@ -if true then return {} end -- WARN: REMOVE THIS LINE TO ACTIVATE THIS FILE - --- Customize Treesitter - ----@type LazySpec -return { - "nvim-treesitter/nvim-treesitter", - opts = { - ensure_installed = { - "lua", - "vim", - -- add more arguments for adding more treesitter parsers - }, - }, -} diff --git a/lua/plugins/user.lua b/lua/plugins/user.lua deleted file mode 100644 index d707697..0000000 --- a/lua/plugins/user.lua +++ /dev/null @@ -1,138 +0,0 @@ --- You can also add or configure plugins by creating files in this `plugins/` folder --- PLEASE REMOVE THE EXAMPLES YOU HAVE NO INTEREST IN BEFORE ENABLING THIS FILE --- Here are some examples: - ----@type LazySpec -return { - - -- == Examples of Adding Plugins == - - "andweeb/presence.nvim", - { - "ray-x/lsp_signature.nvim", - event = "BufRead", - config = function() require("lsp_signature").setup() end, - }, - - -- == Examples of Overriding Plugins == - { - "kdheepak/lazygit.nvim", - lazy = true, - cmd = { - "LazyGit", - "LazyGitConfig", - "LazyGitCurrentFile", - "LazyGitFilter", - "LazyGitFilterCurrentFile", - }, - -- optional for floating window border decoration - dependencies = { - "nvim-lua/plenary.nvim", - }, - -- setting the keybinding for LazyGit with 'keys' is recommended in - -- order to load the plugin when the command is run for the first time - keys = { - { "", "LazyGit", desc = "LazyGit" }, - }, - }, - { - "brianhuster/live-preview.nvim", - dependencies = { - -- You can choose one of the following pickers - "nvim-telescope/telescope.nvim", - "ibhagwan/fzf-lua", - "echasnovski/mini.pick", - }, - }, - { - "toppair/peek.nvim", - event = { "VeryLazy" }, - build = "deno task --quiet build:fast", - config = function() - require("peek").setup() - vim.api.nvim_create_user_command("PeekOpen", require("peek").open, {}) - vim.api.nvim_create_user_command("PeekClose", require("peek").close, {}) - end, - }, - { - "chrisgrieser/nvim-rip-substitute", - cmd = "RipSubstitute", - keys = { - { - "", - function() require("rip-substitute").sub() end, - mode = { "n", "x" }, - desc = " rip substitute", - }, - }, - }, - -- customize dashboard options - { - "folke/snacks.nvim", - opts = { - dashboard = { - preset = { - header = table.concat({ - " ▗▄████▄▖ ", - " ▟███▛███▛▘ ", - " ▄███▜▝ ▘▀ ▗ ", - " ▗▟██▜▞▘ ▟██▖ ", - " ▟██▛█▘ ▄▙▖ ▝▜█▜█▙ ", - "▟██▜▀ ▄████▄ ▀██▟▙", - "██▟▌ ▐████▟█▜ ▐▟██", - "▜▛██▄ ▀▜▟█▛▀ ▄██▛▛", - " ▜█▛█▙▖ ▝▀▌▘ ▗▟█▟▙▛ ", - " ▝▜█▛▘ ▟██▟█▘ ", - " ▘ ▄▄ ▄███▟▀ ", - " ▗▟▜▛██▜█▜▞▘ ", - " ▝▀████▀▘ ", - }, "\n"), - }, - }, - }, - }, - - -- You can disable default plugins as follows: - { "max397574/better-escape.nvim", enabled = false }, - - -- You can also easily customize additional setup of plugins that is outside of the plugin's setup call - { - "L3MON4D3/LuaSnip", - config = function(plugin, opts) - require "astronvim.plugins.configs.luasnip"(plugin, opts) -- include the default astronvim config that calls the setup call - -- add more custom luasnip configuration such as filetype extend or custom snippets - local luasnip = require "luasnip" - luasnip.filetype_extend("javascript", { "javascriptreact" }) - end, - }, - - { - "windwp/nvim-autopairs", - config = function(plugin, opts) - require "astronvim.plugins.configs.nvim-autopairs"(plugin, opts) -- include the default astronvim config that calls the setup call - -- add more custom autopairs configuration such as custom rules - local npairs = require "nvim-autopairs" - local Rule = require "nvim-autopairs.rule" - local cond = require "nvim-autopairs.conds" - npairs.add_rules( - { - Rule("$", "$", { "tex", "latex" }) - -- don't add a pair if the next character is % - :with_pair(cond.not_after_regex "%%") - -- don't add a pair if the previous character is xxx - :with_pair( - cond.not_before_regex("xxx", 3) - ) - -- don't move right when repeat character - :with_move(cond.none()) - -- don't delete if the next character is xx - :with_del(cond.not_after_regex "xx") - -- disable adding a newline when you press - :with_cr(cond.none()), - }, - -- disable for .vim files, but it work for another filetypes - Rule("a", "a", "-vim") - ) - end, - }, -} diff --git a/lua/polish.lua b/lua/polish.lua index f3bd08d..244f2a4 100644 --- a/lua/polish.lua +++ b/lua/polish.lua @@ -1,87 +1,101 @@ --- This will run last in the setup process and is a good place to configure --- things like custom filetypes. This just pure lua so anything that doesn't --- fit in the normal config locations above can go here --- Map to toggle Aider terminal in all modes -require("telescope").setup { - pickers = { - oldfiles = { - cwd_only = true, - }, - }, -} +-- Polish configuration: Final setup and overrides +-- This runs last in the setup process -require("overseer").setup { - strategy = { - "toggleterm", - use_shell = false, - size = vim.o.columns * 0.25, - auto_scroll = true, - close_on_exit = false, - quit_on_exit = "success", - open_on_start = true, - hidden = true, - }, -} +-- Remove h mapping (conflicts with Telescope) +vim.api.nvim_del_keymap("n", "h") -require("nvim_aider").setup { - -- Command that executes Aider - aider_cmd = "aider", - -- Command line arguments passed to aider - args = { - "--no-auto-commits", - "--pretty", - "--stream", - "--dark-mode", -- Enable dark mode in Aider - }, - -- Theme colors (dark mode palette) - theme = { - -- Dark mode-friendly colors - user_input_color = "#a6da95", -- Soft green for user input - tool_output_color = "#8aadf4", -- Soft blue for tool output - tool_error_color = "#ed8796", -- Soft red for errors - tool_warning_color = "#eed49f", -- Soft yellow for warnings - assistant_output_color = "#c6a0f6", -- Soft purple for assistant output - completion_menu_color = "#a5adcb", -- Slightly dimmer text for completion menu - completion_menu_bg_color = "#1e1e2e", -- Darker background for completion menu - completion_menu_current_color = "#89dceb", -- Cyan for selected item - completion_menu_current_bg_color = "#313244", -- Slightly lighter than bg for selection - }, - -- snacks.picker.layout.Config configuration - picker_cfg = { - preset = "vscode", - -- Add dark mode settings for picker - theme = "dark", - }, - -- Other snacks.terminal.Opts options - config = { - os = { editPreset = "nvim-remote" }, - gui = { - nerdFontsVersion = "3", - theme = "dark", -- Ensure terminal uses dark theme +-- Overseer setup and template (optional) +local ok_overseer, overseer = pcall(require, "overseer") +if ok_overseer then + overseer.setup { + strategy = { + "toggleterm", + use_shell = false, + auto_scroll = true, + close_on_exit = false, + direction = "vertical", + quit_on_exit = "success", + open_on_start = true, + hidden = true, }, - term = { - -- Terminal settings for better dark mode appearance - defaultBg = "#1e1e2e", -- Dark background - defaultFg = "#cdd6f4", -- Light text color - }, - }, - win = { - wo = { - winbar = "Aider", - winhighlight = "Normal:NormalFloat,FloatBorder:FloatBorder", -- Ensure proper highlighting - }, - position = "right", - width = 0.33, -- This will make the terminal take up 1/3 of the total window width - -- Additional window settings for dark mode - border = "rounded", -- Rounded borders look nice in dark mode - style = "minimal", -- Minimal UI style - }, - -- Additional dark mode settings - appearance = { - dark_mode = true, -- Explicitly set dark mode - }, -} + } +end --- This will run last in the setup process and is a good place to configure --- things like custom filetypes. This is just pure lua so anything that doesn't --- fit in the normal config locations above can go here +-- ToggleTerm setup (optional) +local ok_toggleterm, toggleterm = pcall(require, "toggleterm") +if ok_toggleterm then + toggleterm.setup { + size = function(term) + if term.direction == "horizontal" then + return 15 + elseif term.direction == "vertical" then + return math.floor(vim.o.columns * 0.35) + else + return 20 + end + end, + shade_terminals = false, + start_in_insert = true, + } +end + +-- Register Devbox template for Overseer (if available) +if ok_overseer then + overseer.register_template { + name = "devbox", + params = { + script = { + type = "string", + optional = false, + desc = "The devbox script to run", + }, + }, + condition = { + callback = function() + if vim.fn.executable "git" == 0 then return false, "git not found" end + local git_root = vim.fn.systemlist("git rev-parse --show-toplevel")[1] + if vim.v.shell_error ~= 0 or not git_root or git_root == "" then return false, "Not in a git repository" end + local devbox_file = git_root .. "/devbox.json" + if vim.fn.filereadable(devbox_file) == 0 then return false, "No devbox.json found in git root" end + if vim.fn.executable "devbox" == 0 then return false, "devbox command not found" end + return true + end, + }, + generator = function(_, cb) + local git_root = vim.fn.systemlist("git rev-parse --show-toplevel")[1] + if vim.v.shell_error ~= 0 or not git_root or git_root == "" then + cb {} + return + end + local devbox_file = git_root .. "/devbox.json" + + local file = io.open(devbox_file, "r") + if not file then + cb {} + return + end + local content = file:read "*all" + file:close() + local ok, data = pcall(vim.json.decode, content) + if not ok or not data then + cb {} + return + end + + local tasks = {} + if data.shell and data.shell.scripts then + for script_name, _ in pairs(data.shell.scripts) do + table.insert(tasks, { + name = "devbox run " .. script_name, + builder = function() return { cmd = { "devbox" }, args = { "run", script_name }, cwd = git_root } end, + }) + end + end + table.insert(tasks, { + name = "devbox shell", + builder = function() return { cmd = { "devbox" }, args = { "shell" }, cwd = git_root } end, + }) + cb(tasks) + end, + } +end diff --git a/neovim.yml b/neovim.yml index b9235ab..e308339 100644 --- a/neovim.yml +++ b/neovim.yml @@ -1,6 +1,4 @@ ---- base: lua51 - globals: vim: any: true