summary refs log tree commit diff
path: root/.vim/lua
diff options
context:
space:
mode:
Diffstat (limited to '.vim/lua')
-rw-r--r--.vim/lua/_globals.lua16
-rw-r--r--.vim/lua/internal/commit-preview.lua67
-rw-r--r--.vim/lua/internal/completion.lua154
-rw-r--r--.vim/lua/internal/cursor.lua11
-rw-r--r--.vim/lua/internal/dap.lua173
-rw-r--r--.vim/lua/internal/find.lua106
-rw-r--r--.vim/lua/internal/hardmode.lua10
-rw-r--r--.vim/lua/internal/job.lua181
-rw-r--r--.vim/lua/internal/lsp.lua319
-rw-r--r--.vim/lua/internal/lsp_symbols.lua36
-rw-r--r--.vim/lua/internal/misc.lua223
-rw-r--r--.vim/lua/internal/notify.lua105
-rw-r--r--.vim/lua/internal/plugins/aerial.lua13
-rw-r--r--.vim/lua/internal/plugins/colorizer.lua16
-rw-r--r--.vim/lua/internal/plugins/colorschemes.lua11
-rw-r--r--.vim/lua/internal/plugins/completion.lua60
-rw-r--r--.vim/lua/internal/plugins/csv.lua20
-rw-r--r--.vim/lua/internal/plugins/gentoo.lua15
-rw-r--r--.vim/lua/internal/plugins/git.lua108
-rw-r--r--.vim/lua/internal/plugins/icons.lua12
-rw-r--r--.vim/lua/internal/plugins/indent.lua28
-rw-r--r--.vim/lua/internal/plugins/lsp.lua276
-rw-r--r--.vim/lua/internal/plugins/mediawiki.lua6
-rw-r--r--.vim/lua/internal/plugins/mini.lua35
-rw-r--r--.vim/lua/internal/plugins/oil.lua21
-rw-r--r--.vim/lua/internal/plugins/telescope.lua137
-rw-r--r--.vim/lua/internal/plugins/todo.lua46
-rw-r--r--.vim/lua/internal/plugins/treesitter.lua124
-rw-r--r--.vim/lua/internal/plugins/whichkey.lua9
-rw-r--r--.vim/lua/internal/plugins/writing.lua123
-rw-r--r--.vim/lua/internal/plugins/zk.lua35
-rw-r--r--.vim/lua/internal/snippets.lua129
-rw-r--r--.vim/lua/internal/snips.lua159
-rw-r--r--.vim/lua/internal/sortline.lua78
-rw-r--r--.vim/lua/internal/spell.lua8
-rw-r--r--.vim/lua/internal/statusline.lua206
-rw-r--r--.vim/lua/internal/syncbg.lua46
-rw-r--r--.vim/lua/internal/zk.lua7
-rw-r--r--.vim/lua/plugins.lua1578
-rw-r--r--.vim/lua/telescope/_extensions/jobs.lua84
40 files changed, 1378 insertions, 3413 deletions
diff --git a/.vim/lua/_globals.lua b/.vim/lua/_globals.lua
deleted file mode 100644
index 6aef29b..0000000
--- a/.vim/lua/_globals.lua
+++ /dev/null
@@ -1,16 +0,0 @@
----@diagnostic disable: undefined-global
-
-_G.augroup = function(tbl)
-  for name, autocmds in pairs(tbl) do
-    local group = vim.api.nvim_create_augroup(name, { clear = true })
-    for _, au in ipairs(autocmds) do
-      vim.api.nvim_create_autocmd(au[1], {
-        pattern = au[2],
-        command = au[3],
-        group = group,
-      })
-    end
-  end
-end
-
-_G.floating_win_border = 'solid'
diff --git a/.vim/lua/internal/commit-preview.lua b/.vim/lua/internal/commit-preview.lua
deleted file mode 100644
index 512b3fb..0000000
--- a/.vim/lua/internal/commit-preview.lua
+++ /dev/null
@@ -1,67 +0,0 @@
-local M = {}
-
-function M.under_cursor()
-  require('internal.cursor').word(require('internal.commit-preview').commit_preview)
-end
-
-function M.commit_preview(commit, on_attach)
-  if not commit then return end
-
-  local result = require('internal.job')
-      .jobstart({
-        command = 'git',
-        args = { 'show', '--stat', '--patch', commit },
-        format_title = function(_, _)
-          return 'git-show'
-        end,
-        populate_quickfix = false,
-      })
-      :wait()
-      :result()
-
-  -- create buffer
-  local bufnr = vim.api.nvim_create_buf(false, true)
-  assert(bufnr, 'Failed to create buffer')
-  vim.api.nvim_buf_set_name(bufnr, commit)
-  vim.api.nvim_set_option_value('filetype', 'commitpreview', { buf = bufnr })
-
-  -- add lines
-  vim.api.nvim_set_option_value('modifiable', true, { buf = bufnr })
-  vim.api.nvim_buf_set_lines(bufnr, 0, -1, true, result)
-  vim.api.nvim_set_option_value('modifiable', false, { buf = bufnr })
-
-  -- create window
-  local winpos = 'belowright'
-  local winheight = #result <= 25 and #result or 25
-  vim.cmd(string.format('%s %dsplit', winpos, winheight)) -- open split
-  local winid = vim.api.nvim_get_current_win()
-  vim.api.nvim_win_set_buf(winid, bufnr)
-  vim.cmd('wincmd p')
-
-  vim.keymap.set('n', 'gd', M.under_cursor, { buffer = bufnr })
-  vim.keymap.set('n', 'q', function() vim.api.nvim_win_close(winid, true) end, { buffer = bufnr })
-
-  if on_attach then on_attach(bufnr, winid) end
-  -- close on CursorMoved (anywhere but git-show-buf)
-  -- local old_cursor = vim.api.nvim_win_get_cursor(beforewin)
-  -- local group = vim.api.nvim_create_augroup('gitcommit_win_' .. winid, {})
-  -- vim.api.nvim_create_autocmd({ 'CursorMoved', 'CursorMovedI' }, {
-  --   group = group,
-  --   callback = function()
-  --     local cursor = vim.api.nvim_win_get_cursor(0)
-  --     if
-  --         (old_cursor[1] ~= cursor[1] or old_cursor[2] ~= cursor[2])
-  --         and vim.api.nvim_get_current_win() ~= winid
-  --     then
-  --       close()
-  --       return
-  --     end
-  --     old_cursor = cursor
-  --   end,
-  -- })
-
-  -- focus
-  vim.api.nvim_set_current_win(winid)
-end
-
-return M
diff --git a/.vim/lua/internal/completion.lua b/.vim/lua/internal/completion.lua
new file mode 100644
index 0000000..552a45e
--- /dev/null
+++ b/.vim/lua/internal/completion.lua
@@ -0,0 +1,154 @@
+vim.opt.completeopt = { 'menu', 'menuone', 'noselect' }
+vim.opt.shortmess:append('c')
+vim.opt.pumheight = 20 -- max height of completion window
+
+-- re-link the highlight group for the 3rd field in the completion popup
+-- which is populated with the completion source
+vim.schedule(function()
+  local hl = vim.api.nvim_set_hl
+
+  hl(0, 'CmpItemMenu', { link = 'Comment', force = true })
+
+  hl(0, 'CmpItemAbbrMatch', { bold = true, force = true })
+  hl(0, 'CmpItemAbbrMatchFuzzy', { link = 'CmpItemAbbrMatch', force = true })
+
+  hl(0, 'CmpItemKindVariable', { link = 'Normal', force = true })
+  hl(0, 'CmpItemKindInterface', { link = 'CmpItemKindVariable', force = true })
+  hl(0, 'CmpItemKindText', { link = 'CmpItemKindVariable', force = true })
+
+  hl(0, 'CmpItemKindFunction', { link = 'Function', force = true })
+  hl(0, 'CmpItemKindMethod', { link = 'CmpItemKindFunction', force = true })
+
+  hl(0, 'CmpItemKindKeyword', { link = 'Keyword', force = true })
+  hl(0, 'CmpItemKindProperty', { link = 'CmpItemKindKeyword', force = true })
+  hl(0, 'CmpItemKindUnit', { link = 'CmpItemKindKeyword', force = true })
+end)
+
+local cmp = require('cmp')
+
+cmp.setup({
+  sources = {
+    { name = 'nvim_lsp', keyword_length = 1, group_index = 1 },
+    { name = 'nvim_lsp_signature_help', keyword_length = 1, group_index = 1 },
+    { name = 'luasnip', keyword_length = 2, group_index = 1 },
+    -- { name = 'spell' },
+    { name = 'async_path', group_index = 2 },
+    { name = 'buffer', keyword_length = 3, group_index = 2 },
+  },
+
+  mapping = {
+    ['<c-n>'] = cmp.mapping(
+      cmp.mapping.select_next_item({ behavior = cmp.SelectBehavior.Insert }),
+      { 'i', 'c' }
+    ),
+    ['<c-p>'] = cmp.mapping(
+      cmp.mapping.select_prev_item({ behavior = cmp.SelectBehavior.Insert }),
+      { 'i', 'c' }
+    ),
+    ['<tab>'] = cmp.mapping(
+      cmp.mapping.confirm({
+        behavior = cmp.ConfirmBehavior.Insert,
+        select = true,
+      }),
+      { 'i', 'c' }
+    ),
+  },
+
+  -- enable snippet expansion
+  snippet = {
+    expand = function(args)
+      vim.snippet.expand(args.body)
+    end,
+  },
+
+  experimental = {
+    ghost_text = false,
+    native_menu = false,
+  },
+
+  window = {
+    completion = {
+      scrollbar = true,
+      -- align 'abbr' with cursor, necessary due to 'kind' appearing first
+      col_offset = -3,
+    },
+  },
+
+  formatting = {
+    fields = { 'kind', 'abbr', 'menu' },
+    expandable_indicator = true,
+    format = function(entry, item)
+      item.dup = 0 -- dedup items from the same source, first one wins
+      item.menu = '░ ' .. entry.source.name
+      return require('lspkind').cmp_format({
+        mode = 'symbol',
+        symbol_map = {
+          -- 󰆼  󱆃
+          Array = '󰨾 ',
+          Boolean = '󰦍 ',
+          Class = '󰙀 ',
+          Color = '󰉦 ',
+          Constant = '󰐀 ',
+          Constructor = '󱇿 ',
+          Enum = '󱃢 ',
+          EnumMember = '󱃡 ',
+          Event = '󱐋 ',
+          -- Field = '󰽜 ',
+          Field = '󰆈 ',
+          File = '󰈔 ',
+          Folder = '󰝰 ',
+          Function = '󰊕 ',
+          Interface = '󱦜 ',
+          Key = '󰌋 ',
+          Keyword = '󰓽 ',
+          Method = '󰒓 ',
+          Module = '󰏖 ',
+          Namespace = '󰆧 ',
+          Null = '󰎣 ',
+          Object = '󰘦 ',
+          Operator = '󱓉 ',
+          Property = '󰐱 ',
+          Package = '󰏗 ',
+          Reference = '󰌹 ',
+          Snippet = '󰯁 ',
+          Struct = '󰙅 ',
+          Text = '󰉿 ',
+          TypeParameter = '󰌨 ',
+          Unit = '󰠱 ',
+          Value = '󰎠 ',
+          Variable = '󱄑 ',
+        },
+      })(entry, item)
+    end,
+  },
+})
+
+cmp.setup.cmdline({ ':', '/', '?', '@' }, {
+  sources = {
+    { name = 'cmdline', group_index = 1 },
+    { name = 'cmdline_history', group_index = 1 },
+    { name = 'nvim_lsp_document_symbol', keyword_length = 1, group_index = 1 },
+    { name = 'async_path', group_index = 1 },
+    { name = 'buffer', group_index = 1 },
+  },
+
+  matching = {
+    disallow_symbol_nonprefix_matching = false,
+  },
+
+  view = {
+    entries = { selection_order = 'near_cursor' },
+  },
+
+  formatting = {
+    fields = { 'abbr', 'menu' },
+  },
+})
+
+cmp.setup.cmdline({ '/', '?' }, {
+  sources = {
+    { name = 'nvim_lsp_document_symbol', keyword_length = 1, group_index = 1 },
+    { name = 'path', max_item_count = 12, group_index = 1 },
+    { name = 'buffer', group_index = 2 },
+  },
+})
diff --git a/.vim/lua/internal/cursor.lua b/.vim/lua/internal/cursor.lua
deleted file mode 100644
index ad8d8b2..0000000
--- a/.vim/lua/internal/cursor.lua
+++ /dev/null
@@ -1,11 +0,0 @@
-local M = {}
-
-function impl(obj, cb) return cb(vim.fn.expand(vim.fn.expand(obj))) end
-
-function M.word(cb) return impl('<cword>', cb) end
-
-function M.expr(cb) return impl('<cexpr>', cb) end
-
-function M.file(cb) return impl('<cfile>', cb) end
-
-return M
diff --git a/.vim/lua/internal/dap.lua b/.vim/lua/internal/dap.lua
deleted file mode 100644
index 4b1d776..0000000
--- a/.vim/lua/internal/dap.lua
+++ /dev/null
@@ -1,173 +0,0 @@
--- vim: fdm=marker
-
-local dap = require('dap')
-dap.defaults.fallback.terminal_win_cmd = 'belowright 10new'
-dap.defaults.fallback.focus_terminal = false
-
--- open repl when session starts
-dap.listeners.after['event_initialized']['me'] = function()
-  -- dap.repl.toggle()
-end
-
--- try loading dap-launch.json
--- require('dap.ext.vscode').load_launchjs(vim.fn.getcwd() .. '/dap-launch.json')
-
--- signs
-vim.fn.sign_define({
-  { name = 'DapBreakpoint', text = '🞱', texthl = 'DapBreakpoint', linehl = 'DapBreakpointLn' },
-})
-vim.fn.sign_define({
-  { name = 'DapStopped', text = '→', texthl = 'DapStopped', linehl = 'DapStoppedLn' },
-})
-
--- keymaps
-vim.keymap.set('n', '<leader>dd', dap.toggle_breakpoint, { desc = 'toggle breakpoint' }) -- convenience
-vim.keymap.set('n', '<leader>db', dap.toggle_breakpoint, { desc = 'toggle breakpoint' })
-vim.keymap.set('n', '<leader>dc', dap.continue, { desc = 'continue' })
-vim.keymap.set('n', '<leader>ds', dap.step_over, { desc = 'step over' })
-vim.keymap.set('n', '<leader>di', dap.step_into, { desc = 'step into' })
-vim.keymap.set('n', '<leader>do', dap.step_out, { desc = 'step out' })
-vim.keymap.set('n', '<leader>dR', dap.repl.toggle, { desc = 'toggle REPL' })
-vim.keymap.set('n', '<leader>dL', dap.run_last, { desc = 'run last' })
-vim.keymap.set('n', '<leader>dq', dap.terminate, { desc = 'terminate' })
-
-local widgets = require('dap.ui.widgets')
-vim.keymap.set('n', '<leader>dh', widgets.hover, { desc = 'hover' })
-vim.keymap.set(
-  'n',
-  '<leader>dB',
-  require('telescope').extensions.dap.list_breakpoints,
-  { desc = 'list breakpoints' }
-)
-
--- Common
-local bin_from_var_or_pick = function()
-  local ok, retval = pcall(vim.api.nvim_get_var, 'dap_bin') -- global let g:dap_bin
-  if ok then
-    local workspace_folders = vim.lsp.buf.list_workspace_folders()
-    if #workspace_folders >= 1 then
-      retval = retval:gsub(':workspace', workspace_folders[1])
-    end
-    return retval
-  end
-  -- NOTE: try to resolve binaries from build system
-  local bin = nil
-  vim.ui.input({ prompt = 'DAP: binary to launch: ' }, function(choice)
-    bin = choice
-  end)
-  if not bin == nil then
-    return bin
-  end
-  return false
-end
-
--- Go {{{
-dap.adapters.go_dlv_local = function(callback, config) -- {{{
-  local stdout = vim.loop.new_pipe()
-  local handle
-  local pid_or_err
-  local port = 38697
-  local opts = {
-    stdio = { nil, stdout },
-    args = { 'dap', '-l', '127.0.0.1:' .. port },
-    detached = true,
-  }
-  handle, pid_or_err = vim.loop.spawn('dlv', opts, function(exit)
-    stdout:close()
-    handle:close()
-    if exit ~= 0 then
-      vim.notify('dlv exited with exit code ' .. exit)
-    end
-  end)
-  assert(handle, 'Error running dlv: ' .. tostring(pid_or_err))
-  stdout:read_start(function(err, chunk)
-    assert(not err, err)
-    if chunk then
-      vim.schedule(function()
-        require('dap.repl').append(chunk)
-      end)
-    end
-  end)
-  vim.defer_fn(function()
-    callback({ type = 'server', host = '127.0.0.1', port = port })
-  end, 100)
-end -- }}}
-
-dap.adapters.go_dlv_remote = {
-  type = 'server',
-  host = '127.0.0.1',
-  port = 38697,
-}
-
-dap.configurations.go = {
-  {
-    name = 'Debug (local)',
-    type = 'go_dlv_local',
-    request = 'launch',
-    program = '${file}',
-  },
-  {
-    name = 'Debug (remote)',
-    type = 'go_dlv_remote',
-    request = 'launch',
-    mode = 'exec',
-    program = bin_from_var_or_pick,
-  },
-}
--- end of Go }}}
-
--- C/C++/Rust {{{
-dap.adapters.lldb = {
-  type = 'executable',
-  command = '/usr/bin/lldb-vscode',
-  name = 'lldb',
-}
-
-dap.configurations.c = {
-  {
-    name = 'Launch',
-    type = 'lldb',
-    request = 'launch',
-    program = bin_from_var_or_pick,
-    args = {},
-    cwd = '${workspaceFolder}',
-    stopOnEntry = false,
-  },
-  {
-    name = 'Attach',
-    type = 'lldb',
-    request = 'attach',
-    pid = require('dap.utils').pick_process,
-    args = {},
-  },
-}
-dap.configurations.cpp = dap.configurations.c
-
--- enable rust types
-dap.configurations.rust = vim.tbl_extend('force', dap.configurations.c, {
-  initCommands = function()
-    local rustc_sysroot = vim.fn.trim(vim.fn.system('rustc --print sysroot'))
-
-    local script_import = 'command script import "'
-        .. rustc_sysroot
-        .. '/lib/rustlib/etc/lldb_lookup.py"'
-    local commands_file = rustc_sysroot .. '/lib/rustlib/etc/lldb_commands'
-
-    local commands = {}
-    local file = io.open(commands_file, 'r')
-    if file then
-      for line in file:lines() do
-        table.insert(commands, line)
-      end
-      file:close()
-    end
-    table.insert(commands, 1, script_import)
-
-    return commands
-  end,
-})
--- end of C/C++/Rust }}}
-
-local dapui = require('dapui')
-dapui.setup {}
-vim.keymap.set('n', '<leader>du', dapui.toggle, { desc = 'toggle ui' })
diff --git a/.vim/lua/internal/find.lua b/.vim/lua/internal/find.lua
deleted file mode 100644
index 32bdea5..0000000
--- a/.vim/lua/internal/find.lua
+++ /dev/null
@@ -1,106 +0,0 @@
-local M = {}
-
-local get_searchdirs = function(dirs)
-  dirs = dirs or {}
-  if type(dirs) == 'table' and #dirs > 0 then
-    return dirs
-  elseif type(dirs) == 'string' and (dirs == ':workspace') then
-    dirs = vim.lsp.buf.list_workspace_folders()
-  elseif type(dirs) == 'string' and not (dirs == '') then
-    dirs = vim.split(dirs, ',')
-  end
-  -- skip asking if we're looking at known filetypes
-  local ft = vim.api.nvim_buf_get_option(0, 'filetype')
-  if #dirs == 0 and (ft == 'dirbuf' or ft == 'NvimTree' or ft == 'alpha') then
-    dirs = { '%:p:h' }
-  end
-  -- ask user
-  if #dirs == 0 then
-    vim.ui.input({ prompt = 'Search directories: ', default = '%:p:h' }, function(result)
-      dirs = { result }
-    end)
-  end
-  -- default to something reasonable
-  if #dirs == 0 then
-    dirs = { '%:p:h' }
-  end
-  -- finally return
-  return dirs
-end
-
-function onchoice(opts, cb)
-  if not cb then
-    return
-  end
-  opts.attach_mappings = function(prompt_bufnr)
-    require('telescope.actions').select_default:replace(function()
-      local selection = require('telescope.actions.state').get_selected_entry()
-      if selection == nil then
-        return
-      end
-      require('telescope.actions').close(prompt_bufnr)
-      on_choice(selection.path)
-    end)
-    return true
-  end
-end
-
-function search_shim(fn, search_dirs, opts, cb)
-  opts = opts or {}
-  opts.search_dirs = get_searchdirs(search_dirs)
-  opts.prompt_title = vim.fn.expand(table.concat(opts.search_dirs, ','))
-  onchoice(opts, cb)
-  fn(opts)
-end
-
-function M.live_grep(search_dirs, opts, cb)
-  search_shim(require('telescope.builtin').live_grep, search_dirs, opts, cb)
-end
-
-function M.find_files(search_dirs, opts, cb)
-  -- convenience aliases
-  if type(search_dirs) == 'string' and search_dirs == 'data' then
-    search_dirs = vim.fn.stdpath('data')
-  end
-  search_shim(require('telescope.builtin').find_files, search_dirs, opts, cb)
-end
-
-function M.setup(opts)
-  vim.keymap.set('n', ';f', function()
-    vim.notify('use gsf', vim.log.levels.ERROR)
-  end, { desc = 'find files' })
-  vim.keymap.set('n', ';g', function()
-    vim.notify('use gsg', vim.log.levels.ERROR)
-  end, { desc = 'live grep' })
-
-  vim.keymap.set('n', 'gsg', function()
-    M.live_grep(':workspace')
-  end, { desc = 'live grep in workspace' })
-  vim.keymap.set('n', 'gsG', M.live_grep, { desc = 'live grep ask' })
-  vim.keymap.set('n', 'gs-', function()
-    M.live_grep('%:p:h')
-  end, { desc = 'live grep in parent' })
-
-  vim.keymap.set('n', 'gsf', function()
-    M.find_files(':workspace')
-  end, { desc = 'find files in workspace' })
-  vim.keymap.set('n', 'gsF', M.find_files, { desc = 'find files ask' })
-
-  vim.api.nvim_create_user_command('Grep', function(o)
-    M.live_grep(table.concat(o.fargs))
-  end, {
-    desc = 'live grep (rg)',
-    nargs = '*',
-    complete = 'dir',
-  })
-
-  vim.api.nvim_create_user_command('Find', function(o)
-    M.find_files(table.concat(o.fargs))
-  end, {
-    desc = 'find files (fd)',
-    nargs = '*',
-    complete = 'dir',
-  })
-end
-
-return M
diff --git a/.vim/lua/internal/hardmode.lua b/.vim/lua/internal/hardmode.lua
deleted file mode 100644
index 2774ead..0000000
--- a/.vim/lua/internal/hardmode.lua
+++ /dev/null
@@ -1,10 +0,0 @@
--- hard mode means we're not using the arrow keys!
-
-local bail = function()
-  vim.cmd([[silent! echohl ErrorMsg | echo "HARD MODE: hjkl operation only" | echohl None]])
-end
-
-vim.keymap.set({ 'n', 'v', 'i' }, '<up>', bail)
-vim.keymap.set({ 'n', 'v', 'i' }, '<down>', bail)
-vim.keymap.set({ 'n', 'v', 'i' }, '<left>', bail)
-vim.keymap.set({ 'n', 'v', 'i' }, '<right>', bail)
diff --git a/.vim/lua/internal/job.lua b/.vim/lua/internal/job.lua
deleted file mode 100644
index 2e97f16..0000000
--- a/.vim/lua/internal/job.lua
+++ /dev/null
@@ -1,181 +0,0 @@
-local M = {
-  current_jobs = {},
-}
-
-local strip_ansi = function(line)
-  line, _ = line:gsub(string.char(27) .. '[[0-9;]*m', '')
-  return line
-end
-local setqf = function(opts, pid, data)
-  if data == nil then
-    return
-  end
-  vim.fn.setqflist({}, 'a', {
-    title = opts.format_title,
-    lines = { strip_ansi(data) },
-    efm = '%m',
-    context = {
-      cmd = { opts.command, unpack(opts.args) },
-      pid = pid,
-      source = 'jobstart',
-    },
-  })
-  vim.cmd.doautocmd('QuickFixCmdPost')
-end
-
---create a new job and register
---@return ~/.local/share/nvim/site/pack/packer/start/plenary.nvim/lua/plenary/job.lua
-function M.jobstart(opts)
-  opts = opts or {}
-
-  opts = vim.tbl_extend('keep', opts or {}, {
-    enable_spinner = vim.g.job_enable_spinner,
-    populate_quickfix = vim.g.job_populate_quickfix,
-    attach = vim.g.job_attach,
-  })
-
-  -- vim.notify_once(vim.inspect(opts), vim.log.levels.DEBUG)
-
-  if opts.attach then
-    return vim.schedule_wrap(function()
-      vim.cmd.terminal({ args = { opts.command, unpack(opts.args) } })
-    end)()
-  end
-
-  local spinner = {}
-  if opts.enable_spinner then
-    local ok = false
-    ok, spinner = pcall(require, 'spinner.core')
-    if not ok then
-      opts.enable_spinner = false
-    end
-  end
-
-  if opts.format_title == nil then
-    opts.format_title = table.concat({ opts.command, unpack(opts.args) }, ' ')
-  elseif type(opts.format_title) == 'function' then
-    opts.format_title = opts.format_title(opts.command, opts.args)
-  elseif type(opts.format_title) == 'string' then
-    -- noop
-  else
-    error(string.format('Invalid field "format_title" of type %s', type(opts.format_title)))
-  end
-
-  opts.on_start = vim.schedule_wrap(function(j)
-    M.current_jobs[j.pid] = j
-
-    if opts.populate_quickfix then
-      vim.fn.setqflist({}, 'r') -- clear quickfix
-    end
-    if opts.enable_spinner then
-      spinner.on_attach(j.pid, opts.format_title, vim.fn.bufnr())
-      spinner.on_progress('begin', j.pid, j.pid)
-    end
-  end)
-
-  opts.on_exit = vim.schedule_wrap(function(j, code)
-    M.current_jobs[j.pid] = nil
-
-    if not (code == 0) then
-      vim.notify(string.format('[%d] exit %d', j.pid, code), vim.log.levels.ERROR)
-    end
-    if opts.enable_spinner then
-      spinner.on_progress('end', j.pid, j.pid)
-      spinner.on_exit(nil, nil, j.pid)
-    end
-    if opts.populate_quickfix then
-      vim.cmd.doautocmd('QuickFixCmdPost')
-    end
-  end)
-
-  opts.on_stdout = vim.schedule_wrap(function(err, data, j)
-    if err ~= nil then
-      vim.notify(string.format('[%d] error: %s', j.pid, err), vim.log.levels.ERROR)
-    end -- handle error?
-
-    if opts.populate_quickfix and opts.populate_quickfix ~= 'onerror' then
-      setqf(opts, j.pid, data)
-    end
-  end)
-
-  opts.on_stderr = vim.schedule_wrap(function(err, data, j)
-    if err ~= nil then
-      vim.notify(string.format('[%d] error: %s', j.pid, err), vim.log.levels.ERROR)
-    end -- handle error?
-
-    if opts.populate_quickfix then
-      setqf(opts, j.pid, data)
-    end
-  end)
-
-  -- run vim.fn.expand() on all args
-  for i = 1, #opts.args do
-    opts.args[i] = vim.fn.expandcmd(opts.args[i])
-  end
-
-  local j = require('plenary.job'):new(opts)
-  j:start()
-
-  return j
-end
-
-function M.sh(command, opts)
-  return M.jobstart(vim.tbl_extend('keep', opts or {}, {
-    command = vim.env.SHELL,
-    args = { '-c', command },
-    -- strip 'sh -c' from the title (used by progress reporting etc.)
-    format_title = function(_, args)
-      return table.concat({ unpack(args, 2, #args) }, ' ')
-    end,
-  }))
-end
-
-function M.make(opts)
-  opts = opts or {}
-
-  local makeprg = vim.fn.expandcmd(vim.opt.makeprg:get())
-  local cwd = vim.fn.expand('%:p:h')
-
-  if not (string.match(makeprg, 'make') == nil) then
-    -- detect makefile
-    opts.cwd = require('lspconfig.util').root_pattern('Makefile')(cwd)
-  end
-
-  return M.sh(makeprg, opts)
-end
-
-function M.list()
-  require('telescope._extensions').manager['jobs']['jobs']()
-end
-
-function M.setup(opts)
-  opts = vim.tbl_extend('keep', opts, { telescope = true, mappings = true })
-
-  -- defaults
-  vim.g.job_enable_spinner = true
-  vim.g.job_populate_quickfix = 'onerror'
-  vim.g.job_attach = false
-
-  if opts.telescope then
-    require('telescope').load_extension('jobs')
-    vim.api.nvim_create_user_command('Jobs', M.list, { desc = 'list jobs managed by internal.job' })
-    if opts.mappings then
-      vim.keymap.set('n', '<leader>jl', M.list, { desc = 'list jobs managed by internal.job' })
-    end
-  end
-
-  vim.api.nvim_create_user_command('Make', function(a)
-    require('internal.job').make(a.fargs)
-  end, { nargs = '*', desc = 'run make target or &makeprg with internal.job' })
-
-  vim.api.nvim_create_user_command('Sh', function(a)
-    require('internal.job').sh(table.concat(a.fargs, ' '))
-  end, { nargs = '*', desc = 'run shell command with internal.job' })
-
-  if opts.mappings then
-    vim.keymap.set('n', '<leader>jm', M.make, { desc = 'run &makeprg with internal.job' })
-    vim.keymap.set('n', '<leader>js', ':Sh ', { desc = 'run shell commands with internal.job' })
-  end
-end
-
-return M
diff --git a/.vim/lua/internal/lsp.lua b/.vim/lua/internal/lsp.lua
deleted file mode 100644
index b0aa7dc..0000000
--- a/.vim/lua/internal/lsp.lua
+++ /dev/null
@@ -1,319 +0,0 @@
--- TODO vim.api.nvim_create_autocmd('LspAttach', {
--- 	callback = function(args)
--- 		local client = vim.lsp.get_client_by_id(args.data.client_id)
--- 		local bufnr = args.buf
--- 	end,
--- })
-
-local my_attach = function(client, bufnr)
-  if vim.opt.diff:get() then
-    vim.notify('not running LSP client in diff mode', vim.log.levels.WARN)
-    vim.lsp.stop_client(client)
-    return
-  end
-
-  local group = vim.api.nvim_create_augroup('LspOnAttach', {})
-  vim.api.nvim_create_autocmd('CursorHold', {
-    buffer = bufnr,
-    group = group,
-    callback = function()
-      if _G.diagnostic_hidden then
-        return
-      end
-      -- evalutate if there's already a floating preview buffer
-      local existing = vim.F.npcall(vim.api.nvim_buf_get_var, bufnr, 'lsp_floating_preview')
-      if not existing or not vim.api.nvim_win_is_valid(existing) then
-        vim.diagnostic.open_float()
-      end
-    end,
-  })
-
-  require('lsp-status').on_attach(client)
-  if client.supports_method('textDocument/documentSymbol') then
-    require('nvim-navic').attach(client, bufnr)
-    -- require('aerial').on_attach(client, bufnr)
-    -- vim.keymap.set('n', 'g0', vim.lsp.buf.document_symbol, {buffer = bufnr})
-  end
-  if client.supports_method('workspace/symbol') then
-    vim.keymap.set(
-      'n',
-      'gW',
-      vim.lsp.buf.workspace_symbol,
-      { buffer = bufnr, desc = 'goto symbol' }
-    )
-    vim.keymap.set(
-      'n',
-      ';s',
-      require('telescope.builtin').lsp_workspace_symbols,
-      { desc = 'lsp workspace symbols' }
-    )
-  end
-  if client.supports_method('textDocument/definition') then
-    vim.keymap.set(
-      'n',
-      '<C-]>',
-      vim.lsp.buf.definition,
-      { buffer = bufnr, desc = 'goto definition' }
-    )
-    vim.keymap.set('n', 'gd', vim.lsp.buf.definition, { buffer = bufnr, desc = 'goto definition' })
-    vim.keymap.set('n', 'gR', vim.lsp.buf.references, { buffer = bufnr, desc = 'goto references' })
-    vim.keymap.set(
-      'n',
-      ';R',
-      require('telescope.builtin').lsp_references,
-      { desc = 'lsp references' }
-    )
-  end
-  if client.supports_method('textDocument/hover') then
-    vim.keymap.set('n', 'K', vim.lsp.buf.hover, { buffer = bufnr, desc = 'hover' })
-  end
-  if client.supports_method('textDocument/rename') then
-    vim.keymap.set('n', 'grr', vim.lsp.buf.rename, { buffer = bufnr, desc = 'rename' })
-  end
-  if client.supports_method('signatureHelp') then
-    vim.keymap.set(
-      'n',
-      '<c-h>',
-      vim.lsp.buf.signature_help,
-      { buffer = bufnr, desc = 'signature help' }
-    )
-  end
-  if client.supports_method('textDocument/formatting') then
-    -- if client.server_capabilities.documentFormattingProvider then
-    vim.api.nvim_set_option_value('formatexpr', 'v:lua.vim.lsp.formatexpr()', { buf = bufnr })
-    vim.keymap.set('n', '<leader>f', vim.lsp.buf.format, { buffer = bufnr, desc = 'format' })
-    vim.api.nvim_create_autocmd('BufWritePre', {
-      buffer = bufnr,
-      callback = function()
-        vim.cmd.mkview({ bang = true })
-        require('internal.lsp').format(vim.fn.expand('<afile>:p'))
-      end,
-      group = vim.api.nvim_create_augroup('LspAutoFormat', {}),
-    })
-  end
-  if client.supports_method('textDocument/typeDefinition') then
-    vim.keymap.set(
-      'n',
-      'gT',
-      vim.lsp.buf.type_definition,
-      { buffer = bufnr, desc = 'goto typedef' }
-    )
-  end
-  if client.supports_method('textDocument/declaration') then
-    vim.keymap.set(
-      'n',
-      'gD',
-      vim.lsp.buf.declaration,
-      { buffer = bufnr, desc = 'goto declaration' }
-    )
-  end
-  if client.supports_method('textDocument/implementation') then
-    vim.keymap.set(
-      'n',
-      'gI',
-      vim.lsp.buf.implementation,
-      { buffer = bufnr, desc = 'goto implementation' }
-    )
-  end
-  if client.supports_method('textDocument/codeAction') then
-    -- vim.keymap.set('n', 'ga', vim.lsp.buf.code_action, { buffer = bufnr, desc = 'code action' })
-    vim.keymap.set('n', 'ga', vim.cmd.CodeActionMenu, { buffer = bufnr, desc = 'code action' })
-  end
-  if client.supports_method('textDocument/documentHighlight') then
-    vim.keymap.set(
-      'n',
-      '<leader>8',
-      vim.lsp.buf.document_highlight,
-      { buffer = bufnr, desc = 'document highlight' }
-    )
-    -- vim.keymap.set('n', '', vim.lsp.buf.clear_references, {buffer = bufnr, desc = 'clear references'})
-    vim.api.nvim_create_autocmd('CursorMoved', {
-      callback = vim.lsp.buf.clear_references,
-      buffer = bufnr,
-    })
-  end
-end
-
-local my_exit = function(_, _, _) end
-
-local capabilities = function()
-  local caps = vim.lsp.protocol.make_client_capabilities()
-
-  -- enable lsp-based snippets
-  caps = vim.tbl_extend('keep', caps or {}, require('cmp_nvim_lsp').default_capabilities())
-
-  -- add window/workDoneProgress capability
-  caps = vim.tbl_extend('keep', caps or {}, require('lsp-status').capabilities)
-  return caps
-end
-
-local servers = {
-  clangd = {
-    cmd = {
-      'clangd',
-      '--clang-tidy',
-      '--header-insertion=iwyu',
-      '--import-insertions',
-      '--header-insertion-decorators',
-    }
-  },
-  elixirls = {
-    cmd = { 'elixir-ls' },
-    settings = {
-      elixirLS = {
-        dialyzerEnabled = false,
-      },
-    },
-  },
-  gopls = {
-    settings = {
-      gopls = {
-        analyses = {
-          --  composites = false,
-          fieldalignment = true,
-          nilness = true,
-          shadow = false,
-          unusedparams = true,
-          unusedwrite = true,
-        },
-        gofumpt = true,
-        -- hoverKind = 'Structured',
-      },
-    },
-  },
-  lua_ls = {
-    -- cmd = { 'lua-language-server' },
-    cmd = { 'luals' }, -- custom firejail-wrapped
-    settings = {
-      Lua = {
-        runtime = {
-          version = 'LuaJIT',
-          path = vim.split(package.path, ';'),
-        },
-        diagnostics = {
-          globals = {
-            '_G',
-            'assert',
-            'error',
-            'os',
-            'package',
-            'pairs',
-            'ipairs',
-            'pcall',
-            'require',
-            'string',
-            'table',
-            'type',
-            'unpack',
-            'vim',
-            'xpcall',
-          },
-          neededFileStatus = {
-            ['code-style-check'] = 'Any',
-          },
-        },
-        format = {
-          enable = true,
-          defaultConfig = {
-            indent_style = 'space',
-            indent_size = '2',
-          },
-        },
-        workspace = {
-          -- library = vim.api.nvim_get_runtime_file("", true),
-          library = {
-            [vim.env.VIMRUNTIME .. '/lua'] = true,
-            [vim.env.VIMRUNTIME .. '/lua/vim/lsp'] = true,
-            [vim.fn.stdpath('config') .. '/lua'] = true,
-          },
-        },
-        telemetry = {
-          enable = false,
-        },
-      },
-    },
-  },
-  rust_analyzer = {
-    -- cmd = { 'env', 'CARGO_TARGET_DIR=/tmp', 'RUST_SRC_PATH=/usr/src/rustlib/library', 'rust-analyzer' },
-    settings = {
-      ['rust-analyzer'] = {
-        checkOnSave = {
-          command = { 'cargo', 'clippy' },
-        },
-      },
-    },
-  },
-  tsserver = {},
-  pylsp = {},
-  zls = {},
-}
-
-local setup = function()
-  -- configure floating win handlers
-  vim.lsp.handlers['textDocument/hover'] = vim.lsp.with(vim.lsp.handlers.hover, {
-    focus = false,
-    zindex = 100,
-    border = _G.floating_win_border,
-  })
-  vim.lsp.handlers['textDocument/signature_help'] =
-      vim.lsp.with(vim.lsp.handlers.signature_help, { border = _G.floating_win_border })
-
-  local caps = capabilities()
-  for server, opts in pairs(servers) do
-    if not opts.disabled then
-      opts = vim.tbl_extend('error', opts, {
-        on_attach = my_attach,
-        on_exit = my_exit,
-        capabilities = caps,
-      })
-      -- lsp-status custom handlers
-      local ok, lspstatus_ext = pcall(require('lsp-status').extensions[server])
-      if ok then
-        opts = vim.tbl_extend('error', opts, {
-          handlers = lspstatus_ext.setup(),
-        })
-      end
-      require('lspconfig')[server].setup(opts)
-    end
-  end
-end
-
-local format = function(afile)
-  if vim.g.nofmt then
-    return
-  end
-
-  local errhandler = function(err)
-    vim.notify('internal.lsp.format: ' .. err, vim.log.levels.ERROR)
-    return err
-  end
-
-  -- save folds
-  pcall(vim.cmd.mkview, { bang = true })
-
-  -- run lsp format
-  xpcall(vim.lsp.buf.format, errhandler)
-
-  -- run organize imports for go
-  if string.match(afile, '.go$') then
-    xpcall(
-      vim.lsp.buf.code_action,
-      errhandler,
-      { context = { only = { 'source.organizeImports' } }, apply = true }
-    )
-  end
-
-  -- restore folds
-  pcall(vim.cmd.silent, { 'loadview', bank = true })
-
-  -- vim.notify('%#MoreMsg#󰃢%#Italic# fmt', vim.log.levels.INFO)
-  vim.notify('internal.lsp.format: 󰃢', vim.log.levels.INFO)
-end
-
-return {
-  my_attach = my_attach,
-  my_exit = my_exit,
-  capabilities = capabilities,
-  setup = setup,
-  format = format,
-}
diff --git a/.vim/lua/internal/lsp_symbols.lua b/.vim/lua/internal/lsp_symbols.lua
deleted file mode 100644
index 97a1b0e..0000000
--- a/.vim/lua/internal/lsp_symbols.lua
+++ /dev/null
@@ -1,36 +0,0 @@
-return {
-  -- 󰆼  󱆃
-  Array = '󰨾 ',
-  Boolean = '󰦍 ',
-  Class = '󰙀 ',
-  Color = '󰉦 ',
-  Constant = '󰐀 ',
-  Constructor = '󱇿 ',
-  Enum = '󱃢 ',
-  EnumMember = '󱃡 ',
-  Event = '󱐋 ',
-  -- Field = '󰽜 ',
-  Field = '󰆈 ',
-  File = '󰈔 ',
-  Folder = '󰝰 ',
-  Function = '󰊕 ',
-  Interface = '󱦜 ',
-  Key = '󰌋 ',
-  Keyword = '󰓽 ',
-  Method = '󰒓 ',
-  Module = '󰏖 ',
-  Namespace = '󰆧 ',
-  Null = '󰎣 ',
-  Object = '󰘦 ',
-  Operator = '󱓉 ',
-  Property = '󰐱 ',
-  Package = '󰏗 ',
-  Reference = '󰌹 ',
-  Snippet = '󰯁 ',
-  Struct = '󰙅 ',
-  Text = '󰉿 ',
-  TypeParameter = '󰌨 ',
-  Unit = '󰠱 ',
-  Value = '󰎠 ',
-  Variable = '󱄑 ',
-}
diff --git a/.vim/lua/internal/misc.lua b/.vim/lua/internal/misc.lua
deleted file mode 100644
index a92b7aa..0000000
--- a/.vim/lua/internal/misc.lua
+++ /dev/null
@@ -1,223 +0,0 @@
--- misc stuff implemented in lua
-
-local M = {}
-
-local function get_visual_selection()
-  local top = vim.fn.getpos("'<")
-  top = { ln = top[2], col = top[3] }
-  local bot = vim.fn.getpos("'>")
-  bot = { ln = bot[2], col = bot[3] }
-  local lines = vim.api.nvim_buf_get_lines(0, (top.ln - 1), bot.ln, false)
-  if vim.opt.selection:get() == 'inclusive' then
-    lines[#lines] = lines[#lines]:sub(1, bot.col)
-  else
-    lines[#lines] = lines[#lines]:sub(1, (bot.col - 1))
-  end
-  lines[1] = lines[1]:sub(top.col)
-  return top, bot, lines
-end
-
-function M.sort_lines(_, preview_ns, preview_bufnr)
-  local bufnr = vim.api.nvim_get_current_buf()
-
-  local top, bot, lines = get_visual_selection()
-  for i = 1, #lines do
-    lines[i] = vim.fn.join(vim.fn.sort(vim.fn.split(lines[i], ' ')))
-  end
-
-  if not preview_ns then
-    vim.api.nvim_buf_set_lines(bufnr, top.ln - 1, bot.ln, false, lines)
-    vim.notify('no preview')
-    return 0
-  end
-
-  -- inccommand preview
-  if preview_ns ~= nil then
-    for i, line in ipairs(lines) do
-      vim.api.nvim_buf_set_extmark(bufnr, preview_ns, top.ln + i - 2, 0, {
-        hl_mode = 'combine',
-        virt_text_pos = 'overlay',
-        virt_text = { { line, 'Substitute' } },
-      })
-
-      if preview_bufnr ~= nil then
-        local prefix = string.format('|%d| ', top.ln + i - 1)
-        vim.api.nvim_buf_set_lines(preview_bufnr, i - 1, -1, false, { prefix .. line })
-        vim.api.nvim_buf_add_highlight(
-          preview_bufnr,
-          preview_ns,
-          'Substitute',
-          i,
-          #prefix,
-          #prefix + #line
-        )
-      end
-    end
-    return (#lines > 1 and 2 or 1)
-  end
-end
-
-local get_searchdirs = function(dirs)
-  if type(dirs) == 'table' and #dirs > 0 then
-    return dirs
-  elseif type(dirs) == 'string' and not (dirs == '') then
-    dirs = vim.split(dirs, ',')
-  end
-  -- skip asking if we're looking at known filetypes
-  local ft = vim.api.nvim_buf_get_option(0, 'filetype')
-  if #dirs == 0 and (ft == 'dirbuf' or ft == 'alpha') then
-    dirs = { '%:p:h' }
-  end
-  -- ask user
-  if #dirs == 0 then
-    vim.ui.input({ prompt = 'Search directories: ' }, function(result)
-      dirs = { result }
-    end)
-  end
-  -- default to something reasonable
-  if #dirs == 0 then
-    dirs = { '%:p:h' }
-  end
-  -- finally return
-  for i = 1, #dirs do
-    dirs[i] = vim.fn.expand(dirs[i])
-  end
-  return dirs
-end
-
-local function onchoice(opts, cb)
-  if not cb then
-    return
-  end
-  opts.attach_mappings = function(prompt_bufnr)
-    require('telescope.actions').select_default:replace(function()
-      local selection = require('telescope.actions.state').get_selected_entry()
-      if selection == nil then
-        return
-      end
-      require('telescope.actions').close(prompt_bufnr)
-      cb(selection.path)
-    end)
-    return true
-  end
-end
-
-function M.live_grep(dirs, opts, cb)
-  opts = opts or {}
-  local search_dirs = get_searchdirs(dirs)
-  opts.search_dirs = search_dirs
-  opts.prompt_title = 'Grep: ' .. vim.inspect(search_dirs)
-  onchoice(opts, cb)
-  require('telescope.builtin').live_grep(opts)
-end
-
-function M.find_files(dirs, opts, cb)
-  -- convenience aliases
-  if dirs == 'plugins' then
-    dirs = vim.fn.stdpath('data') .. '/site/pack/'
-  end
-
-  opts = opts or {}
-  local search_dirs = dirs
-  if type(dirs) == 'string' then
-    search_dirs = get_searchdirs(dirs)
-  end
-  opts.search_dirs = search_dirs
-  opts.prompt_title = 'Find: ' .. vim.inspect(search_dirs)
-  onchoice(opts, cb)
-  require('telescope.builtin').find_files(opts)
-end
-
-function M.fold_block() -- {{{
-  local Comment = require('Comment.api')
-  local m = vim.api.nvim_buf_get_mark
-  local inital_cusor_pos = vim.api.nvim_win_get_cursor(0)
-  local spos, epos = m(0, '<'), m(0, '>')
-
-  -- do start of selection
-  vim.api.nvim_win_set_cursor(0, spos)
-  Comment.insert_linewise_eol()
-  vim.api.nvim_feedkeys('\\<esc>', 'ni', true)
-  local sln = vim.api.nvim_get_current_line()
-  vim.api.nvim_set_current_line(sln .. '{{{')
-
-  -- do end of selection
-  vim.api.nvim_win_set_cursor(0, epos)
-  Comment.insert_linewise_eol()
-  vim.api.nvim_feedkeys('\\<esc>', 'ni', true)
-  local eln = vim.api.nvim_get_current_line()
-  vim.api.nvim_set_current_line(eln .. '}}}')
-
-  -- restore initial cursor postition
-  vim.api.nvim_win_set_cursor(0, inital_cusor_pos)
-end -- }}}
-
-function M.link_preview()
-  local link = vim.fn.expand('<cfile>')
-  if not link then
-    return
-  end
-
-  local buf = vim.api.nvim_get_current_buf()
-  local ln = vim.api.nvim_win_get_cursor(0)[1] - 1
-
-  require('job')
-      .jobstart({
-        format_title = function()
-          return 'link-preview'
-        end,
-        command = vim.env.SHELL,
-        args = {
-          '-c',
-          [[ curl -sSfL ]]
-          .. link
-          .. [[ | grep -iPo '(?<=property="og:title" content=")([^\"]+)(?=")' ]],
-        },
-        populate_quickfix = false,
-        enable_recording = true,
-      })
-      :after_success(vim.schedule_wrap(function(j, code, _)
-        local results = j:result()
-        if not code == 0 or #results == 0 then
-          return
-        end
-
-        local ns = vim.api.nvim_create_namespace('')
-        vim.api.nvim_buf_set_extmark(buf, ns, ln, 0, {
-          virt_text = { { results[1], 'Error' } },
-          virt_text_pos = 'eol',
-        })
-      end))
-end
-
-function M.setup(opts)
-  opts = opts or {}
-
-  if opts.sortline then
-    vim.api.nvim_create_user_command(
-      'SortLine',
-      M.sort_lines,
-      { desc = 'sort line', range = '%', preview = M.sort_lines }
-    )
-  end
-  if opts.grep then
-    vim.api.nvim_create_user_command('Grep', function(o)
-      M.live_grep(table.concat(o.fargs))
-    end, {
-      desc = 'live grep (rg)',
-      nargs = '*',
-      complete = 'dir',
-    })
-  end
-  if opts.find then
-    vim.api.nvim_create_user_command('Find', function(o)
-      M.find_files(table.concat(o.fargs))
-    end, {
-      desc = 'find files (fd)',
-      nargs = '*',
-      complete = 'dir',
-    })
-  end
-end
-
-return M
diff --git a/.vim/lua/internal/notify.lua b/.vim/lua/internal/notify.lua
deleted file mode 100644
index 5445f4f..0000000
--- a/.vim/lua/internal/notify.lua
+++ /dev/null
@@ -1,105 +0,0 @@
--- notifications cache
-_G.statusline_notifications = {}
-_G.statusline_notifications_archive = {}
-
--- out vim.notify implementation
-local notify = function(m, l, o)
-  local lvl_string = l
-  local hi = nil
-  if l and type(l) == 'number' then
-    if l == vim.log.levels.TRACE then
-      hi = 'deEmph'
-    elseif l == vim.log.levels.DEBUG then
-      hi = 'DiagnosticHint'
-    elseif l == vim.log.levels.INFO then
-      hi = 'DiagnosticInfo'
-    elseif l == vim.log.levels.WARN then
-      hi = 'DiagnosticWarn'
-    elseif l == vim.log.levels.ERROR then
-      hi = 'DiagnosticError'
-    end
-    -- get level string
-    lvl_string = vim.lsp.log_levels[l]
-  end
-  local display = m
-  if lvl_string then
-    display = lvl_string .. ' ' .. display
-  end
-  table.insert(_G.statusline_notifications, {
-    message = m,
-    level = l,
-    options = o,
-    lvl_string = lvl_string,
-    hi = hi,
-    display = display,
-  })
-
-  if _G.statusline_enable_notifysend then
-    local args = {}
-    if lvl_string then
-      if lvl_string == 'ERROR' then
-        table.insert(args, '--category=error')
-      end
-      if lvl_string == 'WARN' then
-        table.insert(args, '--category=warning')
-      end
-    end
-    table.insert(args, 'nvim')
-    table.insert(args, display)
-    require('internal.job').jobstart({ command = 'notify-send', args = args })
-  end
-end
-
--- overwrite vim.notify
-vim.notify = function(m, l, o)
-  if vim.in_fast_event() then
-    vim.schedule(function()
-      notify(m, l, o)
-    end)
-  else
-    return notify(m, l, o)
-  end
-end
-
-vim.keymap.set('n', '<leader>n', function()
-  local pickers = require('telescope.pickers')
-  local finders = require('telescope.finders')
-  local conf = require('telescope.config').values
-  local actions = require('telescope.actions')
-  -- local action_state = require('telescope.actions.state')
-  -- local previewers = require('telescope.previewers')
-
-  local opts = {}
-  pickers
-    .new(opts, {
-      prompt_title = 'Notifications',
-      finder = finders.new_dynamic({
-        fn = function()
-          return _G.statusline_notifications_archive
-        end,
-        entry_maker = function(n)
-          return {
-            value = n,
-            display = n.display,
-            ordinal = n.message,
-          }
-        end,
-      }),
-      sorter = conf.generic_sorter(opts),
-      attach_mappings = function(prompt_bufnr, _)
-        actions.select_default:replace(function()
-          actions.close(prompt_bufnr)
-          -- noop
-          -- local sel = action_state.get_selected_entry()
-          -- vim.notify(sel.value.message, sel.value.level, sel.value.options)
-        end)
-        return true
-      end,
-      -- previewer = previewers.new_buffer_previewer {
-      --   define_preview = function(self, entry)
-      --     vim.api.nvim_buf_set_lines(self.state.bufnr, 0, -1, false, {entry.value.display})
-      --   end,
-      -- },
-    })
-    :find()
-end, { desc = 'notifications' })
diff --git a/.vim/lua/internal/plugins/aerial.lua b/.vim/lua/internal/plugins/aerial.lua
new file mode 100644
index 0000000..a5fb4b3
--- /dev/null
+++ b/.vim/lua/internal/plugins/aerial.lua
@@ -0,0 +1,13 @@
+return {
+  {
+    'stevearc/aerial.nvim',
+    opts = {},
+    dependencies = {
+      'nvim-treesitter/nvim-treesitter',
+      'echasnovski/mini.icons',
+    },
+    keys = {
+      { '<leader>b', '<cmd>AerialToggle<cr>' },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/colorizer.lua b/.vim/lua/internal/plugins/colorizer.lua
new file mode 100644
index 0000000..cf55336
--- /dev/null
+++ b/.vim/lua/internal/plugins/colorizer.lua
@@ -0,0 +1,16 @@
+return {
+  {
+    'NvChad/nvim-colorizer.lua',
+    -- 'norcalli/nvim-colorizer.lua',
+    -- events = { 'VeryLazy' },
+    lazy = false,
+    opts = {
+      name = true,
+      RRGGBB = true,
+      RRGGBBAA = false,
+      rgb_fn = true,
+      hsl_fn = true,
+      mode = 'background',
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/colorschemes.lua b/.vim/lua/internal/plugins/colorschemes.lua
new file mode 100644
index 0000000..9371229
--- /dev/null
+++ b/.vim/lua/internal/plugins/colorschemes.lua
@@ -0,0 +1,11 @@
+return {
+  {
+    enabled = false,
+    'xero/evangelion.nvim',
+    lazy = false,
+    priority = 1000,
+    config = function()
+      vim.cmd('colorscheme evangelion')
+    end,
+  },
+}
diff --git a/.vim/lua/internal/plugins/completion.lua b/.vim/lua/internal/plugins/completion.lua
new file mode 100644
index 0000000..db96085
--- /dev/null
+++ b/.vim/lua/internal/plugins/completion.lua
@@ -0,0 +1,60 @@
+return {
+  {
+    -- 'hrsh7th/nvim-cmp',
+    'iguanacucumber/magazine.nvim', -- perf improvements
+    name = 'nvim-cmp',
+
+    lazy = false,
+    -- event = {'InsertEnter', 'CmdlineEnter' },
+    priority = 100,
+    dependencies = {
+      'hrsh7th/cmp-buffer',
+      'hrsh7th/cmp-nvim-lsp',
+      'https://codeberg.org/FelipeLema/cmp-async-path',
+      -- 'hrsh7th/cmp-nvim-lua',
+      'hrsh7th/cmp-nvim-lsp-signature-help', -- used to provide function signature completion
+      'hrsh7th/cmp-cmdline',
+      'dmitmel/cmp-cmdline-history',
+      'hrsh7th/cmp-nvim-lsp-document-symbol', -- used by cmdline completion
+      -- 'f3fora/cmp-spell',
+
+      { 'L3MON4D3/LuaSnip', run = 'make install_jsregexp' },
+      'saadparwaiz1/cmp_luasnip',
+
+      'onsails/lspkind.nvim',
+    },
+    config = function()
+      require('internal.snippets')
+      require('internal.completion')
+    end,
+  },
+
+  -- { -- TODO: try when it doesnt require nightly rust, i dont want binary blobs
+  --
+  --   'saghen/blink.cmp',
+  --   lazy = false,
+  --   -- use a release tag to download pre-built binaries
+  --   -- version = 'v0.*',
+  --   -- OR build from source, requires nightly: https://rust-lang.github.io/rustup/concepts/channels.html#working-with-nightly-rust
+  --   build = 'cargo build --release',
+  --
+  --   opts = {
+  --     highlight = {
+  --       -- sets the fallback highlight groups to nvim-cmp's highlight groups
+  --       -- useful for when your theme doesn't support blink.cmp
+  --       -- will be removed in a future release, assuming themes add support
+  --       use_nvim_cmp_as_default = true,
+  --     },
+  --
+  --     -- set to 'mono' for 'Nerd Font Mono' or 'normal' for 'Nerd Font'
+  --     -- adjusts spacing to ensure icons are aligned
+  --     nerd_font_variant = 'normal',
+  --
+  --     -- experimental auto-brackets support
+  --     -- accept = { auto_brackets = { enabled = true } }
+  --
+  --     -- experimental signature help support
+  --     -- trigger = { signature_help = { enabled = true } }
+  --   },
+  -- },
+}
diff --git a/.vim/lua/internal/plugins/csv.lua b/.vim/lua/internal/plugins/csv.lua
new file mode 100644
index 0000000..bc4cb2c
--- /dev/null
+++ b/.vim/lua/internal/plugins/csv.lua
@@ -0,0 +1,20 @@
+return {
+  {
+    'emmanueltouzery/decisive.nvim',
+    lazy = true,
+    ft = { 'csv' },
+    main = 'decisive',
+    keys = {
+      {
+        '<leader>a',
+        function()
+          require('decisive').align_csv({})
+          require('decisive').show_sticky_header()
+        end,
+        desc = 'decisive: Align CSV',
+      },
+      { '[,', ":lua require('decisive').align_csv_prev_col()<cr>", desc = 'decisive: Prev column' },
+      { '],', ":lua require('decisive').align_csv_next_col()<cr>", desc = 'decisive: Next column' },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/gentoo.lua b/.vim/lua/internal/plugins/gentoo.lua
new file mode 100644
index 0000000..142374c
--- /dev/null
+++ b/.vim/lua/internal/plugins/gentoo.lua
@@ -0,0 +1,15 @@
+return {
+  {
+    'gentoo/gentoo-syntax',
+    lazy = false,
+    config = function()
+      vim.api.nvim_create_autocmd('LspAttach', {
+        callback = function(args)
+          if vim.bo.filetype == 'ebuild' then
+            vim.lsp.stop_client(vim.lsp.get_clients({ bufnr = args.bufnr }))
+          end
+        end,
+      })
+    end,
+  },
+}
diff --git a/.vim/lua/internal/plugins/git.lua b/.vim/lua/internal/plugins/git.lua
new file mode 100644
index 0000000..d907161
--- /dev/null
+++ b/.vim/lua/internal/plugins/git.lua
@@ -0,0 +1,108 @@
+return {
+  {
+    'lewis6991/gitsigns.nvim',
+    lazy = false,
+    opts = {
+      signs = {
+        change = { text = '▋' },
+        add = { text = '▋' },
+      },
+    },
+    keys = {
+      {
+        ']c',
+        function()
+          if vim.wo.diff then
+            vim.cmd.normal({ ']c', bang = true })
+          else
+            require('gitsigns').nav_hunk('next')
+          end
+        end,
+        desc = 'Gitsigns: next hunk',
+      },
+      {
+        '[c',
+        function()
+          if vim.wo.diff then
+            vim.cmd.normal({ '[c', bang = true })
+          else
+            require('gitsigns').nav_hunk('prev')
+          end
+        end,
+        desc = 'Gitsigns: prev hunk',
+      },
+      { '<leader>gb', '<cmd>Gitsigns blame<cr>', desc = 'Gitsigns: blame' },
+      { '<leader>gs', '<cmd>Gitsigns<cr>', desc = 'Gitsigns: select action' },
+      {
+        ';c',
+        function()
+          require('gitsigns').setqflist('all', { open = false })
+          require('telescope.builtin').quickfix({ prompt_title = 'Git changesets' })
+        end,
+        desc = 'Telescope: list hunks via gitsigns',
+      },
+    },
+  },
+
+  {
+    'linrongbin16/gitlinker.nvim',
+    cmd = { 'GitLink' },
+    dependencies = { 'nvim-lua/plenary.nvim' },
+    opts = {
+      message = true,
+    },
+    keys = {
+      {
+        '<leader>gl',
+        vim.cmd.GitLink,
+        desc = 'gitlinker: clipboard',
+      },
+    },
+  },
+
+  {
+    'moyiz/git-dev.nvim',
+    lazy = true,
+    cmd = { 'GitDevOpen', 'GitDevCleanAll' },
+    opts = {
+      read_only = false,
+    },
+  },
+
+  {
+    'isakbm/gitgraph.nvim',
+    dependencies = { 'sindrets/diffview.nvim' },
+    opts = {
+      symbols = {
+        merge_commit = 'M',
+        commit = '∙',
+      },
+      format = {
+        timestamp = '%d-%m-%Y %H:%M:%S %z',
+        fields = { 'hash', 'timestamp', 'author', 'branch_name', 'tag' },
+      },
+    },
+    init = vim.schedule_wrap(function()
+      vim.api.nvim_set_hl(0, 'GitGraphBranch1', { fg = 'NvimLightGray1' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranch2', { fg = 'NvimLightMagenta' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranch3', { fg = 'NvimLightRed' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranch4', { fg = 'NvimDarkCyan' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranch5', { fg = 'NvimDarkYellow' })
+      vim.api.nvim_set_hl(0, 'GitGraphHash', { fg = 'NvimLightMagenta' })
+      vim.api.nvim_set_hl(0, 'GitGraphAuthor', { fg = 'NvimLightGray4', italic = true })
+      vim.api.nvim_set_hl(0, 'GitGraphTimestamp', { fg = 'NvimLightCyan' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranchName', { fg = 'NvimLightYellow' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranchTag', { fg = 'NvimLightYellow' })
+      vim.api.nvim_set_hl(0, 'GitGraphBranchMsg', { link = 'Normal' })
+    end),
+    keys = {
+      {
+        'g-',
+        function()
+          require('gitgraph').draw({}, { all = true, max_count = 5000 })
+        end,
+        desc = 'git graph',
+      },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/icons.lua b/.vim/lua/internal/plugins/icons.lua
new file mode 100644
index 0000000..3d503dc
--- /dev/null
+++ b/.vim/lua/internal/plugins/icons.lua
@@ -0,0 +1,12 @@
+return {
+  {
+    'echasnovski/mini.icons',
+    version = false,
+    events = { 'VeryLazy' },
+    config = function(_, opts)
+      require('mini.icons').setup(opts)
+      ---@diagnostic disable-next-line: undefined-global
+      MiniIcons.mock_nvim_web_devicons()
+    end,
+  },
+}
diff --git a/.vim/lua/internal/plugins/indent.lua b/.vim/lua/internal/plugins/indent.lua
new file mode 100644
index 0000000..a27a328
--- /dev/null
+++ b/.vim/lua/internal/plugins/indent.lua
@@ -0,0 +1,28 @@
+return {
+  -- show indents using virtual text
+  {
+    'lukas-reineke/indent-blankline.nvim',
+    lazy = false,
+    main = 'ibl',
+    opts = {
+      indent = {
+        char = '▏',
+      },
+      scope = {
+        enabled = true,
+        show_start = false,
+        show_end = false,
+      },
+    },
+  },
+  -- detect indent from the buffer contents
+  {
+    'NMAC427/guess-indent.nvim',
+    lazy = false,
+    opts = {
+      auto_cmd = true,
+      filetype_exclude = { 'netrw', 'tutor', 'dirbuf', 'nvimtree', 'oil' },
+      buftype_exclude = { 'help', 'nofile', 'terminal', 'prompt' },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/lsp.lua b/.vim/lua/internal/plugins/lsp.lua
new file mode 100644
index 0000000..d138c6c
--- /dev/null
+++ b/.vim/lua/internal/plugins/lsp.lua
@@ -0,0 +1,276 @@
+return {
+  {
+    'neovim/nvim-lspconfig',
+    lazy = false,
+    dependencies = {
+      { 'j-hui/fidget.nvim', opts = {} },
+      'stevearc/conform.nvim',
+    },
+    config = function()
+      local capabilities = nil
+      if pcall(require, 'cmp_nvim_lsp') then
+        capabilities = require('cmp_nvim_lsp').default_capabilities()
+      end
+
+      local lspconfig = require('lspconfig')
+
+      local servers = {
+        clangd = {
+          cmd = {
+            'clangd',
+            '--clang-tidy',
+            '--header-insertion=iwyu',
+            '--import-insertions',
+            '--header-insertion-decorators',
+          },
+        },
+        elixirls = {
+          cmd = { 'elixir-ls' },
+          settings = {
+            elixirLS = {
+              dialyzerEnabled = false,
+            },
+          },
+        },
+        gopls = {
+          settings = {
+            gopls = {
+              hints = {
+                assignVariableTypes = true,
+                compositeLiteralFields = true,
+                compositeLiteralTypes = true,
+                constantValues = true,
+                functionTypeParameters = true,
+                parameterNames = true,
+                rangeVariableTypes = true,
+              },
+              analyses = {
+                --  composites = false,
+                nilness = true,
+                shadow = false,
+                unusedparams = true,
+                unusedwrite = true,
+              },
+              gofumpt = true,
+              -- hoverKind = 'Structured',
+            },
+          },
+        },
+        lua_ls = {
+          cmd = { 'luals' }, -- custom firejail-wrapped
+          -- cmd = { 'lua-language-server' },
+          settings = {
+            Lua = {
+              runtime = {
+                version = 'LuaJIT',
+                path = vim.split(package.path, ';'),
+              },
+              diagnostics = {
+                globals = {
+                  '_G',
+                  'assert',
+                  'error',
+                  'os',
+                  'package',
+                  'pairs',
+                  'ipairs',
+                  'pcall',
+                  'require',
+                  'string',
+                  'table',
+                  'type',
+                  'unpack',
+                  'vim',
+                  'xpcall',
+                },
+                neededFileStatus = {
+                  ['code-style-check'] = 'Any',
+                },
+              },
+              format = {
+                enable = true,
+                defaultConfig = {
+                  indent_style = 'space',
+                  indent_size = '2',
+                },
+              },
+              workspace = {
+                library = {
+                  [vim.env.VIMRUNTIME .. '/lua'] = true,
+                  [vim.env.VIMRUNTIME .. '/lua/vim/lsp'] = true,
+                  [vim.fn.stdpath('config') .. '/lua'] = true,
+                },
+              },
+              telemetry = {
+                enable = false,
+              },
+            },
+          },
+        },
+        rust_analyzer = {
+          settings = {
+            ['rust-analyzer'] = {
+              checkOnSave = {
+                command = { 'cargo', 'clippy' },
+              },
+            },
+          },
+        },
+        ts_ls = {
+          init_options = {
+            tsserver = {
+              path = '/usr/lib/node_modules/typescript/lib',
+            },
+          },
+        },
+        pylsp = {},
+        zls = {
+          cmd = {
+            'zls',
+            '--enable-debug-log',
+            '--enable-message-tracing',
+          },
+        },
+        bashls = {},
+        cssls = {},
+        jsonls = {},
+        html = {},
+        superhtml = {},
+        kotlin_language_server = {
+          -- cmd = vim.lsp.rpc.connect('127.0.0.1', 20100),
+          cmd = {
+            'distrobox',
+            'enter',
+            '-n',
+            'android-dev',
+            '--',
+            '/usr/local/kotlin-langserver/bin/kotlin-language-server',
+          },
+          init_options = {
+            formatting = {
+              formatter = 'none', -- disable because we use ktlint via gradle
+            },
+          },
+        },
+      }
+
+      for name, opts in pairs(servers) do
+        opts = vim.tbl_deep_extend('force', {
+          capabilities = capabilities,
+        }, opts)
+        lspconfig[name].setup(opts)
+      end
+
+      vim.api.nvim_create_autocmd('LspAttach', {
+        callback = function()
+          -- local client =
+          --   assert(vim.lsp.get_client_by_id(args.data.client_id), 'must have valid client')
+
+          vim.opt_local.omnifunc = 'v:lua.vim.lsp.omnifunc'
+
+          vim.keymap.set('n', 'gd', vim.lsp.buf.definition, { buffer = true })
+          vim.keymap.set('n', 'gR', vim.lsp.buf.references, { buffer = true })
+          vim.keymap.set('n', 'gD', vim.lsp.buf.declaration, { buffer = true })
+          vim.keymap.set('n', 'gT', vim.lsp.buf.type_definition, { buffer = true })
+          vim.keymap.set('n', 'K', vim.lsp.buf.hover, { buffer = true })
+          vim.keymap.set('n', 'grr', vim.lsp.buf.rename, { buffer = true })
+          vim.keymap.set('n', 'ga', vim.lsp.buf.code_action, { buffer = true })
+        end,
+      })
+    end,
+  },
+
+  {
+    'folke/lazydev.nvim',
+    ft = 'lua',
+    -- could add a completion source to cmp?
+  },
+
+  -- formatting
+  {
+    'stevearc/conform.nvim',
+    lazy = false,
+    opts = {
+      formatters_by_ft = {
+        lua = { 'stylua' },
+        go = { 'goimports', 'gofmt' },
+        python = { 'ruff_format' },
+      },
+    },
+    config = function(_, opts)
+      require('conform').setup(opts)
+
+      vim.api.nvim_create_autocmd('BufWritePre', {
+        callback = function(args)
+          if vim.g.nofmt then
+            return
+          end
+          require('conform').format({
+            bufnr = args.buf,
+            lsp_fallback = true,
+            quiet = true,
+          })
+        end,
+      })
+    end,
+  },
+
+  -- linting
+  {
+    'nvimtools/none-ls.nvim',
+    dependencies = { 'nvim-lua/plenary.nvim' },
+    event = { 'VeryLazy' },
+    config = function()
+      local nls = require('null-ls')
+      nls.setup({
+        sources = {
+          -- https://github.com/nvimtools/none-ls.nvim/blob/main/doc/BUILTINS.md
+          -- nls.builtins.code_actions.gitsigns,
+          nls.builtins.code_actions.impl,
+
+          -- nls.builtins.completion.spell,
+
+          -- nls.builtins.diagnostics.checkmake,
+          -- nls.builtins.diagnostics.cmake_lint,
+          -- nls.builtins.diagnostics.cppcheck,
+          -- nls.builtins.diagnostics.gccdiag,
+          nls.builtins.diagnostics.golangci_lint,
+          nls.builtins.diagnostics.hadolint,
+          -- nls.builtins.diagnostics.pylint,
+          -- nls.builtins.diagnostics.selene,
+          -- nls.builtins.diagnostics.semgrep,
+          nls.builtins.diagnostics.sqlfluff,
+          -- nls.builtins.diagnostics.stylelint,
+          -- nls.builtins.diagnostics.textidote,
+          nls.builtins.diagnostics.vale,
+        },
+      })
+    end,
+  },
+
+  -- diagnostics
+  {
+    'rachartier/tiny-inline-diagnostic.nvim',
+    event = 'VeryLazy',
+    opts = {
+      signs = {
+        left = ' ',
+        right = '',
+        diag = '',
+        arrow = '◂   ',
+        up_arrow = '▴   ',
+      },
+      options = {
+        throttle = 0,
+        show_source = true,
+      },
+    },
+    config = function(_, opts)
+      vim.diagnostic.config({ virtual_text = false })
+      require('tiny-inline-diagnostic').setup(opts)
+      if vim.opt.background:get() == 'light' then
+        require('tiny-inline-diagnostic').change({}, { mixing_color = '#aaaaaa' })
+      end
+    end,
+  },
+}
diff --git a/.vim/lua/internal/plugins/mediawiki.lua b/.vim/lua/internal/plugins/mediawiki.lua
new file mode 100644
index 0000000..f557627
--- /dev/null
+++ b/.vim/lua/internal/plugins/mediawiki.lua
@@ -0,0 +1,6 @@
+return {
+  {
+    'chikamichi/mediawiki.vim',
+    ft = { 'mediawiki' },
+  },
+}
diff --git a/.vim/lua/internal/plugins/mini.lua b/.vim/lua/internal/plugins/mini.lua
new file mode 100644
index 0000000..1886766
--- /dev/null
+++ b/.vim/lua/internal/plugins/mini.lua
@@ -0,0 +1,35 @@
+return {
+  {
+    'echasnovski/mini.align',
+    version = false,
+    opts = {},
+    keys = {
+      { mode = 'n', 'ga' },
+      { mode = 'n', 'gA' },
+      { mode = 'v', 'ga' },
+      { mode = 'v', 'gA' },
+      {
+        mode = 'v',
+        '<cr>',
+        function()
+          vim.cmd([[silent! echohl ErrorMsg | echo "use ga/gA" | echohl None]])
+        end,
+      },
+    },
+  },
+  {
+    'echasnovski/mini.surround',
+    lazy = false,
+    version = false,
+    opts = {
+      mappings = {
+        delete = 'ds',
+        replace = 'cs',
+      },
+    },
+    keys = {
+      { mode = 'n', 'cs' },
+      { mode = 'n', 'ds' },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/oil.lua b/.vim/lua/internal/plugins/oil.lua
new file mode 100644
index 0000000..401fe8b
--- /dev/null
+++ b/.vim/lua/internal/plugins/oil.lua
@@ -0,0 +1,21 @@
+return {
+  {
+    'stevearc/oil.nvim',
+    lazy = false,
+    opts = {
+      keymaps = {
+        ['gt'] = {
+          function()
+            local cwd = require('oil').get_current_dir()
+            vim.cmd('silent !footclient --no-wait -D ' .. cwd)
+          end,
+          nowait = true,
+          desc = 'Open current directory with foot',
+        },
+      },
+    },
+    keys = {
+      { mode = 'n', '-', '<cmd>Oil<cr>', desc = 'oil: open parent directory' },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/telescope.lua b/.vim/lua/internal/plugins/telescope.lua
new file mode 100644
index 0000000..6339a2c
--- /dev/null
+++ b/.vim/lua/internal/plugins/telescope.lua
@@ -0,0 +1,137 @@
+return {
+  {
+    'nvim-telescope/telescope.nvim',
+    lazy = false,
+    dependencies = {
+      { 'nvim-lua/plenary.nvim' },
+      {
+        'nvim-telescope/telescope-fzf-native.nvim',
+        build = 'cmake -S. -Bbuild -GNinja -DCMAKE_BUILD_TYPE=Release && cmake --build build --config Release',
+      },
+      { 'nvim-telescope/telescope-ui-select.nvim' },
+    },
+    config = function(spec, _)
+      require('telescope').setup({
+        defaults = require('telescope.themes').get_ivy({
+          prompt = false,
+          borderchars = {
+            preview = { '─', '│', '─', '│', '┌', '┐', '┘', '└' },
+          },
+        }),
+
+        extensions = {
+          wrap_results = true,
+
+          fzf = {},
+
+          ['ui-select'] = {
+            require('telescope.themes').get_ivy({
+              prompt = false,
+              -- sharp edges please
+              borderchars = {
+                preview = { '─', '│', '─', '│', '┌', '┐', '┘', '└' },
+              },
+              layout_config = { height = 9 },
+            }),
+          },
+        },
+      })
+
+      pcall(require('telescope').load_extension, 'fzf')
+      pcall(require('telescope').load_extension, 'ui-select')
+
+      -- user commands
+      vim.api.nvim_create_user_command(
+        'F',
+        'Telescope find_files search_dirs=<args>',
+        { desc = 'Telescope find_files', nargs = '?' }
+      )
+      vim.api.nvim_create_user_command(
+        'G',
+        'Telescope live_grep search_dirs=<args>',
+        { desc = 'Telescope live_grep', nargs = '?' }
+      )
+
+      -- keymaps
+      local builtin = require('telescope.builtin')
+      for _, o in ipairs(spec.keys) do
+        if not o[2] then
+          local mod = vim.split(o.desc, ': ')[2]
+          vim.keymap.set(o.mode, o[1], builtin[mod], { desc = o.desc })
+        end
+      end
+
+      -- highlights
+      vim.schedule(function()
+        vim.api.nvim_set_hl(0, 'TelescopeBorder', { fg = 'NvimDarkGrey4', force = true })
+        vim.api.nvim_set_hl(0, 'TelescopeTitle', { fg = 'NvimLightMagenta', force = true })
+        vim.api.nvim_set_hl(0, 'NormalFloat', { link = 'TelescopeNormal', force = true })
+      end)
+    end,
+    keys = {
+      { mode = 'n', ';/', desc = 'telescope: current_buffer_fuzzy_find' },
+      { mode = 'n', ';b', desc = 'telescope: buffers' },
+      { mode = 'n', ';f', desc = 'telescope: find_files' },
+      { mode = 'n', ';g', desc = 'telescope: live_grep' },
+      { mode = 'n', ';d', desc = 'telescope: diagnostics' },
+      {
+        mode = 'n',
+        ';v',
+        function()
+          require('telescope.builtin').find_files({
+            prompt_title = 'vimrc',
+            search_dirs = {
+              vim.fn.stdpath('config'),
+            },
+          })
+        end,
+        desc = 'telescope: vim_config',
+      },
+      {
+        mode = 'n',
+        ';;t',
+        '<cmd>Telescope<cr>',
+        desc = 'telescope: select (interactive)',
+      },
+      {
+        mode = 'n',
+        ';;f',
+        function()
+          local dir
+          if vim.opt.filetype:get() == 'oil' then
+            dir = require('oil').get_current_dir()
+          else
+            dir = vim.fn.expand('%:p')
+          end
+          _G.feedkeys(':Telescope find_files search_dirs=' .. dir)
+        end,
+        desc = 'telescope: find_files (interactive)',
+      },
+      {
+        mode = 'n',
+        ';;g',
+        function()
+          local dir
+          if vim.opt.filetype:get() == 'oil' then
+            dir = require('oil').get_current_dir()
+          else
+            dir = vim.fn.expand('%:p')
+          end
+          _G.feedkeys(':Telescope live_grep search_dirs=' .. dir)
+        end,
+        desc = 'telescope: live_grep (interactive)',
+      },
+    },
+  },
+
+  {
+    'prochri/telescope-all-recent.nvim',
+    lazy = false,
+    dependencies = {
+      'nvim-telescope/telescope.nvim',
+      'kkharji/sqlite.lua',
+    },
+    after = { 'nvim-telescope/telescope-ui-select.nvim' },
+    opts = {},
+  },
+}
diff --git a/.vim/lua/internal/plugins/todo.lua b/.vim/lua/internal/plugins/todo.lua
new file mode 100644
index 0000000..e7ae0a7
--- /dev/null
+++ b/.vim/lua/internal/plugins/todo.lua
@@ -0,0 +1,46 @@
+return {
+  {
+    'folke/todo-comments.nvim',
+    dependencies = { 'nvim-lua/plenary.nvim' },
+    lazy = false,
+    cmd = { 'TodoTelescope' },
+    opts = {
+      merge_keywords = true,
+      keywords = {
+        FIX = { icon = '󰃤' },
+        TODO = { icon = '󰸞' },
+        HACK = { icon = '󰈸' },
+        WARN = { icon = '󱇎' },
+        PERF = { icon = '󰅒' },
+        NOTE = { icon = '󰐃' },
+        TEST = { icon = '󰂓' },
+      },
+      highlight = {
+        keyword = 'bg',
+        pattern = [[<(KEYWORDS)(|\(.+\))(:|)]],
+      },
+      search = {
+        pattern = [[\b(KEYWORDS)(|\(.+\))(:|)]],
+      },
+    },
+    keys = {
+      { mode = 'n', ';t', '<cmd>TodoTelescope<cr>', desc = 'telescope: todos' },
+      {
+        mode = 'n',
+        ']t',
+        function()
+          require('todo-comments').jump_next()
+        end,
+        desc = 'todo: next',
+      },
+      {
+        mode = 'n',
+        '[t',
+        function()
+          require('todo-comments').jump_prev()
+        end,
+        desc = 'todo: prev',
+      },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/treesitter.lua b/.vim/lua/internal/plugins/treesitter.lua
new file mode 100644
index 0000000..b8b1d56
--- /dev/null
+++ b/.vim/lua/internal/plugins/treesitter.lua
@@ -0,0 +1,124 @@
+return {
+  {
+    'nvim-treesitter/nvim-treesitter',
+    dependencies = {
+      -- TODO: https://github.com/nvim-treesitter/nvim-treesitter-context
+      { 'nvim-treesitter/nvim-treesitter-refactor', lazy = false },
+      { 'nvim-treesitter/nvim-treesitter-textobjects', lazy = false },
+      { 'nvim-treesitter/playground', cmd = { 'TSPlayground' } },
+    },
+    lazy = false,
+    build = ':TSUpdate',
+    config = function(_, opts)
+      -- TODO: overwrite parser configs, insert gotmpl
+
+      require('nvim-treesitter.configs').setup(opts)
+
+      -- use bash parser for gentoo ebuilds
+      vim.treesitter.language.register('bash', 'ebuild')
+
+      -- register mediawiki parser
+      -- local parser_configs = require('nvim-treesitter.parsers').get_parser_configs()
+      -- parser_configs.mediawiki = {
+      --   install_info = {
+      --     url = 'github.com/Ordoviz/tree-sitter-mediawiki',
+      --     files = { 'src/parser.c' },
+      --     branch = 'main',
+      --     generate_requires_npm = false,
+      --     requires_generate_from_grammar = false,
+      --   },
+      --   filetype = 'mediawiki',
+      -- }
+    end,
+    opts = {
+      ensure_installed = {
+        'bash',
+        'bibtex',
+        'c',
+        'c_sharp',
+        'cmake',
+        'comment',
+        'cpp',
+        'css',
+        'dockerfile',
+        'go',
+        'gomod',
+        'gotmpl',
+        'gowork',
+        'hare',
+        'hcl',
+        'html',
+        'java',
+        'javascript',
+        'json',
+        'jsonc',
+        'kotlin',
+        'latex',
+        'ledger',
+        'lua',
+        'make',
+        'markdown',
+        'markdown_inline',
+        'ninja',
+        'norg',
+        'python',
+        'query',
+        'regex',
+        'rust',
+        'scss',
+        'sql',
+        'toml',
+        'typescript',
+        'vim',
+        'vimdoc',
+        'yaml',
+        'zig',
+
+        -- external parsers
+        -- 'mediawiki', -- TODO: missing queries
+      },
+      highlight = {
+        enable = true,
+        additional_vim_regex_highlighting = { 'markdown' },
+      },
+      indent = {
+        enable = true,
+      },
+      refactor = {
+        navigation = {
+          enable = true,
+          keymaps = {
+            goto_definition = 'gd',
+          },
+        },
+        smart_rename = {
+          enable = true,
+          keymaps = {
+            smart_rename = 'grr',
+          },
+        },
+      },
+      textobjects = {
+        select = {
+          enable = true,
+          keymaps = {
+            ['ib'] = '@block.inner',
+            ['ab'] = '@block.outer',
+            -- ['ic'] = '@conditional.inner',
+            -- ['ac'] = '@conditional.outer',
+            ['if'] = '@function.inner',
+            ['af'] = '@function.outer',
+            ['il'] = '@loop.inner',
+            ['al'] = '@loop.outer',
+            ['is'] = '@scopename.inner',
+            ['as'] = '@scopename.outer',
+            ['ic'] = '@comment.outer',
+          },
+          selection_mode = {
+            ['@comment.outer'] = 'V',
+          },
+        },
+      },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/whichkey.lua b/.vim/lua/internal/plugins/whichkey.lua
new file mode 100644
index 0000000..3c9e802
--- /dev/null
+++ b/.vim/lua/internal/plugins/whichkey.lua
@@ -0,0 +1,9 @@
+return {
+  {
+    'folke/which-key.nvim',
+    event = 'VeryLazy',
+    opts = {
+      icons = { separator = '→ ', group = '🞱 ' },
+    },
+  },
+}
diff --git a/.vim/lua/internal/plugins/writing.lua b/.vim/lua/internal/plugins/writing.lua
new file mode 100644
index 0000000..4792697
--- /dev/null
+++ b/.vim/lua/internal/plugins/writing.lua
@@ -0,0 +1,123 @@
+return {
+  {
+    'folke/zen-mode.nvim',
+    cmd = { 'ZenMode' },
+    opts = {
+      window = {
+        -- width = 0.9,
+        -- height = 0.9,
+        options = {
+          cursorline = true,
+        },
+      },
+      plugins = {
+        options = {
+          number = false,
+          ruler = false,
+          showcmd = false,
+        },
+        gitsigns = { enabled = false },
+        twilight = { enabled = true },
+      },
+      on_open = function()
+        vim.diagnostic.enable(false)
+      end,
+      on_close = function()
+        vim.diagnostic.enable(true)
+      end,
+    },
+    -- init = function()
+    --   vim.api.nvim_create_autocmd({ 'BufWinEnter', 'BufWinLeave' }, {
+    --     pattern = { '*.md' },
+    --     command = [[ZenMode]],
+    --   })
+    -- end,
+    dependencies = {
+      {
+        'folke/twilight.nvim',
+        opts = {
+          context = 24,
+          dimming = {
+            alpha = 0.5,
+            color = { 'Normal', '#ffffff' },
+          },
+        },
+      },
+    },
+  },
+  {
+    'tadmccorkle/markdown.nvim',
+    ft = { 'markdown' },
+    opts = {
+      mappings = false,
+    },
+    config = function(_, opts)
+      require('markdown').setup(opts)
+
+      local set = vim.keymap.set
+      set('n', '[[', [[<Plug>(markdown_go_prev_heading)]], { desc = 'md: previous heading' })
+      set('n', ']]', [[<Plug>(markdown_go_next_heading)]], { desc = 'md: next heading' })
+      set('n', '<s-tab>', [[:MDTaskToggle<cr>]], { desc = 'md: toggle task' })
+      set('x', '<c-l>', [[<esc>gv<Plug>(markdown_add_link_visual)]], { desc = 'md: make link' })
+      local toggle_emph = function(key)
+        return [[<esc>gv<cmd>lua require('markdown.inline').toggle_emphasis_visual(']]
+          .. key
+          .. [[')<cr>]]
+      end
+      set('x', '<c-b>', toggle_emph('b'), { desc = 'md: make bold' })
+      set('x', '<c-i>', toggle_emph('i'), { desc = 'md: make italic' })
+      set('x', '<c-s>', toggle_emph('s'), { desc = 'md: make strikethrough' })
+      set('x', '<c-c>', toggle_emph('c'), { desc = 'md: make code' })
+    end,
+  },
+  {
+    'MeanderingProgrammer/markdown.nvim',
+    name = 'render-markdown', -- needed if used together with markdown.nvim above
+    main = 'render-markdown',
+    dependencies = {
+      'nvim-treesitter/nvim-treesitter',
+      'echasnovski/mini.icons',
+    },
+    ft = { 'markdown' },
+    opts = {
+      heading = {
+        -- icons = { '❶  ', '❷  ', '❸  ', '❹  ', '❺  ', '❻  ' },
+        icons = {
+          ' ',
+          ' ',
+          ' ',
+          ' ',
+          ' ',
+          ' ',
+        },
+        signs = { 'ⅰ', 'ⅱ', 'ⅲ', 'ⅳ', 'ⅴ', 'ⅵ' },
+      },
+      bullet = {
+        icons = { '∙', '∘', '⋅', '⋄' },
+      },
+      checkbox = {
+        checked = { icon = '󰄲 ' },
+        unchecked = { icon = '󰄱 ' },
+        custom = {
+          todo = { raw = '[-]', rendered = '󰔟 ', highlight = 'RenderMarkdownTodo' },
+        },
+      },
+    },
+    init = vim.schedule_wrap(function()
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH1Bg', { bg = 'NvimDarkBlue' })
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH1Fg', { fg = 'NvimLightBlue' })
+
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH2Bg', { bg = 'NvimDarkMagenta' })
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH2Fg', { fg = 'NvimLightMagenta' })
+
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH3Bg', { bg = 'NvimDarkYellow' })
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH3Fg', { fg = 'NvimLightYellow' })
+
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH4Bg', { bg = 'NvimDarkCyan' })
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH4Fg', { fg = 'NvimLightCyan' })
+
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH6Bg', { bg = 'NvimDarkRed' })
+      vim.api.nvim_set_hl(0, 'RenderMarkdownH6Fg', { fg = 'NvimLightRed' })
+    end),
+  },
+}
diff --git a/.vim/lua/internal/plugins/zk.lua b/.vim/lua/internal/plugins/zk.lua
new file mode 100644
index 0000000..76cbcb3
--- /dev/null
+++ b/.vim/lua/internal/plugins/zk.lua
@@ -0,0 +1,35 @@
+return {
+  {
+    lazy = false,
+    'zk-org/zk-nvim',
+    main = 'zk',
+    opts = {
+      picker = 'telescope',
+    },
+    keys = {
+      -- these will work everywhere
+      { ';zc', ':ZkNew ' },
+      { ';zz', '<cmd>ZkNotes {sort={"modified"}}<cr>' },
+      { ';zl', '<cmd>ZkLinks<cr>' },
+      { ';zb', '<cmd>ZkBacklinks<cr>' },
+      { ';zt', '<cmd>ZkTags<cr>' },
+      -- { ';zj', '<cmd>ZkNotes { dir = "500_journals" }<cr>' },
+    },
+    init = function()
+      if not vim.env.ZK_NOTEBOOK_DIR then
+        return
+      end
+      vim.api.nvim_create_autocmd({ 'BufEnter' }, {
+        pattern = vim.env.ZK_NOTEBOOK_DIR .. '/*',
+        callback = function()
+          local o = { remap = true, silent = false, buffer = true }
+          -- these will only work in a zettel
+          vim.keymap.set('n', '-', ':call feedkeys(";zz")<cr>', o)
+          vim.keymap.set('n', '<cr>', '<cmd>lua vim.lsp.buf.definition()<cr>', o)
+        end,
+        group = vim.api.nvim_create_augroup('zk-binds', { clear = true }),
+        once = true,
+      })
+    end,
+  },
+}
diff --git a/.vim/lua/internal/snippets.lua b/.vim/lua/internal/snippets.lua
new file mode 100644
index 0000000..be00884
--- /dev/null
+++ b/.vim/lua/internal/snippets.lua
@@ -0,0 +1,129 @@
+local ls = require('luasnip')
+local types = require('luasnip.util.types')
+
+-- attach to builtin snippet hooks
+
+vim.snippet.expand = ls.lsp_expand
+
+---@diagnostic disable-next-line: duplicate-set-field
+vim.snippet.active = function(filter)
+  filter = filter or {}
+  filter.direction = filter.direction or 1
+
+  if filter.direction == 1 then
+    return ls.expand_or_jumpable()
+  else
+    return ls.jumpable(filter.direction)
+  end
+end
+
+---@diagnostic disable-next-line: duplicate-set-field
+vim.snippet.jump = function(direction)
+  if direction == 1 then
+    if ls.expandable() then
+      return ls.expand_or_jump()
+    else
+      return ls.jumpable(1) and ls.jump(1)
+    end
+  else
+    return ls.jumpable(-1) and ls.jump(-1)
+  end
+end
+
+vim.snippet.stop = ls.unlink_current
+
+local snip_env = {
+  -- snippet helpers
+  nl = function()
+    return ls.t({ '', '' })
+  end,
+  exec = function(command)
+    return ls.f(function(_, _, ...)
+      local job = require('plenary.job'):new({
+        command = vim.env.SHELL,
+        args = { '-c', ... },
+        enable_recording = true,
+      })
+      local res, exitcode = job:sync()
+      if not exitcode == 0 or #res == 0 then
+        error(string.format('exec "%s" failed', ...))
+      end
+      return res
+    end, {}, { user_args = { command } })
+  end,
+  -- condition helpers
+  cond = {
+    ts = function(capture)
+      return function()
+        return vim.tbl_contains(vim.treesitter.get_captures_at_cursor(), capture)
+      end
+    end,
+  },
+}
+
+ls.config.set_config({
+  enable_autosnippets = true,
+  history = true,
+  updateevents = 'TextChanged,TextChangedI',
+  override_builtin = true,
+  snip_env = vim.tbl_deep_extend('error', ls.session.config.snip_env, snip_env),
+  ext_opts = {
+    [types.choiceNode] = {
+      active = {
+        virt_text = { { '◂    󰬊 ', 'NonText' } },
+      },
+    },
+    [types.insertNode] = {
+      active = {
+        virt_text = { { '◂    󰬐 ', 'NonText' } },
+      },
+    },
+  },
+})
+
+require('luasnip.loaders.from_lua').lazy_load({ paths = './snippets' })
+
+vim.keymap.set({ 'i', 's' }, '<c-j>', function()
+  return vim.snippet.active({ direction = 1 }) and vim.snippet.jump(1)
+end, { silent = true, desc = 'snippet: jump next' })
+
+vim.keymap.set({ 'i', 's' }, '<c-k>', function()
+  return vim.snippet.active({ direction = -1 }) and vim.snippet.jump(-1)
+end, { silent = true, desc = 'snippet: jump prev' })
+
+vim.keymap.set({ 'i', 's' }, '<c-n>', function()
+  if ls.choice_active() then
+    ls.change_choice(1)
+  end
+end, { silent = true, desc = 'snippet: next choice' })
+
+vim.keymap.set({ 'i', 's' }, '<c-p>', function()
+  if ls.choice_active() then
+    ls.change_choice(-1)
+  end
+end, { silent = true, desc = 'snippet: prev choice' })
+
+vim.api.nvim_create_user_command('EditSnippets', require('luasnip.loaders').edit_snippet_files, {})
+
+-- vim.api.nvim_create_autocmd('User', {
+--   pattern = 'LuasnipChoiceNodeEnter',
+--   callback = function()
+--     vim.schedule(function()
+--       assert(ls.session.active_choice_nodes[vim.api.nvim_get_current_buf()], 'No active choiceNode')
+--       vim.ui.select(
+--         ls.get_current_choices(),
+--         -- TODO: patch luasnip.extras.select_choice to fix missing prompt
+--         { prompt = 'LuaSnip: choice node', kind = 'luasnip' },
+--         function(_, idx)
+--           if not idx then
+--             return
+--           end
+--           -- feed+immediately execute i to enter INSERT after vim.ui.input closes.
+--           vim.api.nvim_feedkeys('i', 'x', false)
+--           ls.set_choice(idx)
+--           ls.unlink_current()
+--         end
+--       )
+--     end)
+--   end,
+-- })
diff --git a/.vim/lua/internal/snips.lua b/.vim/lua/internal/snips.lua
deleted file mode 100644
index bb9fdef..0000000
--- a/.vim/lua/internal/snips.lua
+++ /dev/null
@@ -1,159 +0,0 @@
-local ls = require('luasnip')
-local types = require('luasnip.util.types')
-
-vim.api.nvim_set_hl(0, 'LuasnipIndicator', {
-  fg = vim.g.terminal_color_15,
-  bg = vim.g.terminal_color_1,
-  italic = true,
-  nocombine = true,
-})
-
--- autowrap: wraps the function in top and bot if there is any content
-local autowrap = function(top, bot, inner)
-  local autoinsert = function(args, _, _, wrap_with)
-    local nodes = {}
-    if vim.trim(table.concat(args[1] or {})) ~= '' then
-      table.insert(nodes, wrap_with)
-    end
-    return ls.sn(nil, nodes)
-  end
-
-  local argnodes = {}
-  local maxpos = -1
-  for _, e in ipairs(inner) do
-    if e.pos ~= nil then
-      table.insert(argnodes, e.pos)
-      if e.pos > maxpos then
-        maxpos = e.pos
-      end
-    end
-  end
-
-  local nodes = {}
-  table.insert(nodes, ls.d(maxpos + 1, autoinsert, argnodes, { user_args = { top } }))
-  for _, e in ipairs(inner) do
-    table.insert(nodes, e)
-  end
-  table.insert(nodes, ls.d(maxpos + 2, autoinsert, argnodes, { user_args = { bot } }))
-  return nodes
-end
-
--- comment: wraps the content in &commentstring (or a blockcomment)
-local comment = function(wrapped, blockcomment)
-  -- commentstring helper
-  local get_cstring = function()
-    local cs = require('Comment.ft').calculate({
-      ctype = blockcomment and 2 or 1,
-      range = require('Comment.utils').get_region(),
-    })
-    local tbl = vim.split(cs or '', '%s', { plain = true, trimempty = true })
-    return (#tbl == 0) and { '', '' }
-        or ((#tbl == 1) and { tbl[1] .. ' ', '' } or { tbl[1], tbl[2] })
-  end
-
-  if type(wrapped) ~= 'table' then
-    wrapped = { wrapped }
-  end
-
-  local nodes = {}
-  table.insert(
-    nodes,
-    ls.f(function()
-      return get_cstring()[1]
-    end)
-  )
-  for _, n in ipairs(wrapped) do
-    table.insert(nodes, n)
-  end
-  table.insert(
-    nodes,
-    ls.f(function()
-      return get_cstring()[2]
-    end)
-  )
-  return nodes
-end
-
--- exec: inserts the output of command
-local exec = function(command)
-  return ls.f(function(_, _, ...)
-    local results, code = require('plenary.job')
-        :new({
-          command = vim.env.SHELL,
-          args = { '-c', ... },
-          enable_recording = true,
-        })
-        :sync()
-    if not code == 0 or #results == 0 then
-      error(string.format('exec "%s" failed', ...))
-    end
-    return results
-  end, {}, { user_args = { command } })
-end
-
-local file_contents = function(path, vargs)
-  return ls.d(1, function(_, _, _, ...)
-    local lines = {}
-    for line in io.lines(path) do
-      table.insert(lines, line)
-    end
-    return ls.sn(nil, require('luasnip.extras.fmt').fmt(table.concat(lines, '\n'), ...))
-  end, {}, { user_args = { vargs } })
-end
-
-ls.setup({
-  history = true,
-  update_events = 'TextChanged,TextChangedI',
-  delete_check_events = 'TextChanged',
-
-  ext_opts = {
-    [types.snippet] = {
-      active = {
-        virt_text = { { '<-- snippet', 'LuasnipIndicator' } },
-        virt_text_pos = 'right_align',
-      },
-    },
-    [types.insertNode] = {
-      unvisited = { hl_group = 'LuasnipIndicator' },
-    },
-    [types.choiceNode] = {
-      active = {
-        virt_text = { { '<-- choice node', 'LuasnipIndicator' } },
-      },
-    },
-  },
-  snip_env = vim.tbl_extend('keep', ls.session.config.snip_env, {
-    f = ls.f,
-    i = ls.i,
-    s = ls.s,
-    t = ls.t,
-    c = ls.c,
-    sn = ls.sn,
-    fmt = require('luasnip.extras.fmt').fmt,
-    autowrap = autowrap,
-    exec = exec,
-    comment = comment,
-    file_contents = file_contents,
-    user_email = {
-      exec([[git config --get user.name]]),
-      ls.t(' <'),
-      ls.c(1, {
-        exec([[git config --get user.email]]),
-        ls.t([[robert.gunzler@postman.com]]),
-        ls.t([[robert@gnzler.io]]),
-      }),
-      ls.t('>'),
-    },
-  }),
-})
-
--- snipmate snippets
--- require('luasnip.loaders.from_snipmate').lazy_load({ paths = './after/snippets' })
--- lua snippets
-require('luasnip.loaders.from_lua').lazy_load({ paths = './snippets' })
-
-vim.api.nvim_create_user_command('LuaSnipUnlinkAll', function()
-  while #package.loaded.luasnip.session.current_nodes > 0 do
-    package.loaded.luasnip.unlink_current()
-  end
-end, { desc = 'unlink all active snippets' })
diff --git a/.vim/lua/internal/sortline.lua b/.vim/lua/internal/sortline.lua
deleted file mode 100644
index 69f7f64..0000000
--- a/.vim/lua/internal/sortline.lua
+++ /dev/null
@@ -1,78 +0,0 @@
-local M = {}
-
-local function get_visual_selection(intact)
-  intact = intact or false
-  local top = vim.fn.getpos("'<")
-  top = { ln = top[2], col = top[3] }
-  local bot = vim.fn.getpos("'>")
-  bot = { ln = bot[2], col = bot[3] }
-  local lines = vim.api.nvim_buf_get_lines(0, (top.ln - 1), bot.ln, false)
-  if not intact then
-    if vim.opt.selection:get() == 'inclusive' then
-      lines[#lines] = lines[#lines]:sub(1, bot.col)
-    else
-      lines[#lines] = lines[#lines]:sub(1, (bot.col - 1))
-    end
-    lines[1] = lines[1]:sub(top.col)
-  end
-  return top, bot, lines
-end
-
-local function sortline(line, a, o, separator)
-  separator = separator or ' '
-  local result, _ = string.gsub(line, string.sub(line, a, o),
-    table.concat(vim.fn.sort(vim.fn.split(string.sub(line, a, o), separator)), separator), 1)
-  return result
-end
-
-function M.sort_lines(_, preview_ns, preview_bufnr)
-  local bufnr = vim.api.nvim_get_current_buf()
-
-  local top, bot, lines = get_visual_selection(true)
-  vim.pretty_print(top, bot, lines)
-  for i = 1, #lines do
-    local a = 0; if i == 1 then a = top.col end
-    local o = -1; if i == #lines then o = bot.col end
-    lines[i] = sortline(lines[i], a, o, ' ')
-  end
-
-  if not preview_ns then
-    vim.api.nvim_buf_set_lines(bufnr, top.ln - 1, bot.ln, false, lines)
-    return 0
-  end
-
-  -- inccommand preview
-  if preview_ns ~= nil then
-    for i, line in ipairs(lines) do
-      vim.api.nvim_buf_set_extmark(bufnr, preview_ns, top.ln + i - 2, 0, {
-        hl_mode = 'combine',
-        virt_text_pos = 'overlay',
-        virt_text = { { line, 'Substitute' } },
-      })
-
-      if preview_bufnr ~= nil then
-        local prefix = string.format('|%d| ', top.ln + i - 1)
-        vim.api.nvim_buf_set_lines(preview_bufnr, i - 1, -1, false, { prefix .. line })
-        vim.api.nvim_buf_add_highlight(
-          preview_bufnr,
-          preview_ns,
-          'Substitute',
-          i,
-          #prefix,
-          #prefix + #line
-        )
-      end
-    end
-    return (#lines > 1 and 2 or 1)
-  end
-end
-
-function M.setup(opts)
-  vim.api.nvim_create_user_command(
-    'SortLine',
-    M.sort_lines,
-    { desc = 'sort line', range = '%', preview = M.sort_lines }
-  )
-end
-
-return M
diff --git a/.vim/lua/internal/spell.lua b/.vim/lua/internal/spell.lua
deleted file mode 100644
index 3c37dad..0000000
--- a/.vim/lua/internal/spell.lua
+++ /dev/null
@@ -1,8 +0,0 @@
-vim.opt_local.spell = true
-vim.opt.spellfile = vim.fn['spellfile#WritableSpellDir']() .. '/spellfile.utf-8.add'
-vim.opt.spellcapcheck = ''
-vim.opt.spelloptions = { 'camel' }
-vim.opt.spellsuggest = 'double'
-
-vim.keymap.set('n', '<C-l>', require('telescope.builtin').spell_suggest)
-vim.keymap.set('n', '<C-l>', [[<c-g>u<esc>[s1z=`]a<c-g>u]])
diff --git a/.vim/lua/internal/statusline.lua b/.vim/lua/internal/statusline.lua
deleted file mode 100644
index 8ed5cae..0000000
--- a/.vim/lua/internal/statusline.lua
+++ /dev/null
@@ -1,206 +0,0 @@
-function _G.statusline()
-  local bufnr = vim.fn.bufnr() or 0
-  local hi = statusline_color(vim.fn.mode())
-
-  local sl = hi
-  -- sl = sl .. statusline_append([[ ⢷]], 'StatusLineIcon', hi)
-
-  sl = sl .. [[%-h%-w%-q%-f %-m %-r]]
-
-  sl = sl .. statusline_append(statusline_grapple(bufnr), 'StatusLineGrapple', hi)
-
-  -- sl = sl .. statusline_append(statusline_ts(), 'StatusLineTreesitter', hi)
-
-  sl = sl .. [[ %= ]] -- spacer
-
-  sl = sl .. statusline_append(statusline_lsp_diagnostics(bufnr, hi), 'StatusLineDiagnostics', hi)
-
-  sl = sl .. statusline_append(statusline_lspstatus(), 'StatusLineLsp', hi)
-
-  sl = sl .. statusline_append(statusline_dap(), 'StatusLineDap', hi)
-
-  -- sl = sl .. [[ %= ]] -- spacer
-
-  sl = sl .. statusline_append(statusline_notify(hi), 'StatusLineNotify', hi)
-
-  sl = sl .. statusline_append(statusline_spinner(bufnr), 'StatusLineJobs', hi)
-
-  sl = sl .. [[%-l:%-v --%p%%-- %-Y]]
-
-  return sl
-end
-
-function _G.statusline_color(mode)
-  local hi = '%*'
-  if mode == 'i' then
-    -- hi = '%#StatusLineInsert#'
-  elseif mode == 'c' then
-    -- hi = '%#StatusLineCommand#'
-  elseif mode == 'v' or mode == 'V' or mode == '' then
-    hi = '%#StatusLineVisual#'
-  elseif mode == 'R' or mode == 'Rv' then
-    hi = '%#StatusLineReplace#'
-  end
-  -- return '%{g:actual_curwin==win_getid()?'.. hi ..':%#StatusLineNC#}'
-  return hi
-end
-
--- does item highlighting and conditionnal spacing
-function _G.statusline_append(element, hi, default_hi, opts)
-  if not element or element == '' then
-    return ''
-  end
-  opts = opts or { append_space = true }
-
-  if hi ~= nil then
-    hi = '%#' .. hi .. '#'
-  end
-  if not (default_hi == '%*') then
-    hi = default_hi
-  end
-  local el = hi .. element .. default_hi
-  if opts.append_space then
-    el = el .. ' '
-  end
-  return el
-end
-
-function _G.statusline_combine_hi(outer_name, inner_name)
-  local outer = vim.api.nvim_get_hl(0, { name = outer_name, create = false })
-  local inner = vim.api.nvim_get_hl(0, { name = inner_name, create = false })
-  local name = ('auto' .. outer_name .. inner_name)
-  vim.api.nvim_get_hl(0,
-    { name = name, create = true })
-  local hi = inner
-  hi.bg = inner.fg
-  hi.fg = outer.bg
-  vim.api.nvim_set_hl(0, name, hi)
-  return name
-end
-
-function _G.statusline_lsp_diagnostics(bufnr, default_hi)
-  local error_num = vim.diagnostic.get(bufnr, { severity = vim.diagnostic.severity.ERROR })
-  local warn_num = vim.diagnostic.get(bufnr, { severity = vim.diagnostic.severity.WARN })
-
-  local s = ''
-  if #error_num > 0 then
-    local errs = vim.fn.sign_getdefined('DiagnosticSignError')[1].text .. #error_num
-    s = s
-        .. statusline_append(
-          errs,
-          statusline_combine_hi('StatusLine', 'DiagnosticError'),
-          default_hi
-        )
-  end
-  if #warn_num > 0 then
-    local warns = vim.fn.sign_getdefined('DiagnosticSignWarn')[1].text .. #warn_num
-    s = s
-        .. statusline_append(
-          warns,
-          statusline_combine_hi('StatusLine', 'DiagnosticWarn'),
-          default_hi
-        )
-  end
-  return vim.trim(s)
-end
-
-function _G.statusline_ts()
-  local navic = package.loaded['nvim-navic']
-  if not navic then
-    return ''
-  end
-  local data = navic.get_data()
-  if not data then
-    return ''
-  end
-  local s = {}
-  for i = 1, #data do
-    table.insert(
-      s,
-      string.format(
-        '%%#CmpItemKind%s#%s%%* %%#StatusLine#%s%%*',
-        data[i].type,
-        data[i].icon,
-        data[i].name
-      )
-    )
-  end
-  return table.concat(s, ' > ')
-end
-
-function _G.statusline_grapple(bufnr)
-  local g = package.loaded.grapple
-  if not g then return '' end
-  return g.statusline()
-  -- if not g or not g.exists({ buffer = bufnr }) then
-  --   return ''
-  -- end
-  -- return '➥ ' .. g.key({ buffer = bufnr })
-end
-
-function _G.statusline_lspstatus()
-  local lst = package.loaded['lsp-status']
-  if not lst then
-    return ''
-  end
-  return vim.trim(lst.status())
-end
-
-function _G.statusline_spinner(bufnr)
-  local sp = package.loaded.spinner
-  if not sp then
-    return ''
-  end
-  return sp.status(bufnr)
-end
-
-function _G.statusline_dap()
-  local dap = package.loaded.dap
-  if not dap then
-    return ''
-  end
-  local s = dap.status()
-  if s == '' then
-    return s
-  end
-  return '[DAP: ' .. s .. ']'
-end
-
-function _G.statusline_notify(default_hi)
-  if not _G.statusline_notifications or #_G.statusline_notifications == 0 then
-    return ''
-  end
-  local n = _G.statusline_notifications[1]
-  local timeout = (n.options and n.options.timeout) or 2000
-  -- pop message after <timeout> and move to archive
-  vim.defer_fn(function()
-    local n_ = table.remove(_G.statusline_notifications, 1)
-    table.insert(_G.statusline_notifications_archive, n_)
-    -- make sure archive is never longer than 20 notifications
-    if #_G.statusline_notifications_archive > 20 then
-      table.remove(_G.statusline_notifications_archive, 1)
-    end
-  end, timeout)
-
-  local s = ''
-  if n.hi then
-    s = s
-        .. statusline_append(
-          n.lvl_string .. ' ',
-          statusline_combine_hi('StatusLineNotify', n.hi),
-          default_hi,
-          { append_space = false }
-        )
-  end
-  s = s .. statusline_append(vim.inspect(n.message), 'StatusLineNotify', default_hi)
-  return vim.trim(s)
-end
-
-vim.opt.statusline = '%{%v:lua.statusline()%}'
-
--- WINBAR --
--- vim.opt.winbar = [[%h%w%q%f %-m %-r %= %#WinBarCwd#%{%getcwd()%}%*]] -- keep it simple
--- function _G.winbar()
---   return [[%<%F %-m %-r]]
--- end
--- vim.opt.winbar = '%{%v:lua.winbar()%}'
diff --git a/.vim/lua/internal/syncbg.lua b/.vim/lua/internal/syncbg.lua
deleted file mode 100644
index 418e17e..0000000
--- a/.vim/lua/internal/syncbg.lua
+++ /dev/null
@@ -1,46 +0,0 @@
-local M = {}
-
-M.init = function()
-  -- get tty
-  local tty_handle = io.popen('tty')
-  if tty_handle == nil then return end
-  local tty = tty_handle:read('*a')
-  tty_handle:close()
-  if tty:find("not a tty") then error('not a tty') end
-
-  M.tty = tty
-end
-
-M.update = function()
-  if M.tty == nil then return end
-
-  if not M.normal then
-    -- get colorscheme Normal highlight
-    local normal = vim.api.nvim_get_hl(0, { name = 'Normal', create = false })
-    if (normal.bg == nil) then return end
-    -- cache old value for use with VimResume
-    M.normal = normal
-  end
-
-  -- emit CSI to change terminal background to Normal.bg
-  os.execute('printf "\\033]11;' .. string.format('#%06x', M.normal.bg) .. '\\007" > ' .. M.tty)
-
-  -- set colorscheme Normal.bg to NONE, making it transparent
-  vim.cmd [[hi Normal ctermbg=NONE guibg=NONE]]
-end
-
-M.reset = function()
-  if M.tty == nil then return end
-
-  os.execute('printf "\\033]111\\007" > ' .. M.tty)
-end
-
-M.setup = function(opts)
-  opts = opts or {}
-
-  M.init()
-  vim.api.nvim_create_autocmd({ 'ColorScheme', 'UIEnter', 'VimResume' }, { callback = M.update })
-  vim.api.nvim_create_autocmd({ 'UILeave' }, { callback = M.reset })
-end
-
-return M
diff --git a/.vim/lua/internal/zk.lua b/.vim/lua/internal/zk.lua
deleted file mode 100644
index 5e17786..0000000
--- a/.vim/lua/internal/zk.lua
+++ /dev/null
@@ -1,7 +0,0 @@
--- vim.keymap.set('n', '<leader>zn', function() require('zk').new() end, {buffer=true})
--- vim.keymap.set('n', '<leader>zi', function() require('zk').index() end, {buffer=true})
--- vim.cmd [[ command! -nargs=* ZettelkastenNew lua require('zk').new(nil, <f-args>) ]]
-
-vim.keymap.set('n', 'gt', function()
-  require('telescope._extensions.todo-comments').exports.todo({ cwd = vim.env.ZK_NOTEBOOK_DIR })
-end, { desc = 'show zk todos', buffer = true })
diff --git a/.vim/lua/plugins.lua b/.vim/lua/plugins.lua
deleted file mode 100644
index d53eaf6..0000000
--- a/.vim/lua/plugins.lua
+++ /dev/null
@@ -1,1578 +0,0 @@
--- disable distribution plugins
-vim.g.loaded_gzip = 1
-vim.g.loaded_tar = 1
-vim.g.loaded_tarPlugin = 1
-vim.g.loaded_zip = 1
-vim.g.loaded_zipPlugin = 1
-vim.g.loaded_getscript = 1
-vim.g.loaded_getscriptPlugin = 1
-vim.g.loaded_vimball = 1
-vim.g.loaded_vimballPlugin = 1
-vim.g.loaded_matchit = 1
--- vim.g.loaded_matchparen        = 1
-vim.g.loaded_2html_plugin = 1
-vim.g.loaded_logiPat = 1
-vim.g.loaded_rrhelper = 1
-vim.g.loaded_netrw = 1
-vim.g.loaded_netrwPlugin = 1
-vim.g.loaded_netrwSettings = 1
-vim.g.loaded_netrwFileHandlers = 1
-
-local lazypath = vim.fn.stdpath('data') .. '/lazy/lazy.nvim'
-if not vim.uv.fs_stat(lazypath) then
-  vim.fn.system({
-    'git',
-    'clone',
-    '--filter=blob:none',
-    'https://github.com/folke/lazy.nvim.git',
-    '--branch=stable',
-    lazypath,
-  })
-end
-vim.opt.rtp:prepend(lazypath)
-
-local pluginspec = {
-  {
-    'lewis6991/gitsigns.nvim',
-    lazy = false,
-    opts = {
-      signs = {
-        change = { hl = 'GitSignsChange', text = '▋', numhl = 'GitSignsChangeLn' },
-        add = { hl = 'GitSignsAdd', text = '▋', numhl = 'GitSignsAddLn' },
-        delete = { hl = 'GitSignsDelete', text = '_', numhl = 'GitSignsDeleteLn' },
-        topdelete = { hl = 'GitSignsDelete', text = '‾', numhl = 'GitSignsDeleteLn' },
-        changedelete = { hl = 'GitSignsChange', text = '~', numhl = 'GitSignsChangeLn' },
-      },
-      signcolumn = true,
-      numhl = false,
-      linehl = false,
-      word_diff = false,
-      preview_config = {
-        border = _G.floating_win_border,
-      },
-      on_attach = function(bufnr)
-        local gs = require('gitsigns')
-        vim.keymap.set('n', ']c', function()
-          if vim.wo.diff then
-            return ']c'
-          end
-          vim.schedule(gs.next_hunk)
-          return '<Ignore>'
-        end, { buffer = bufnr, expr = true, desc = 'next hunk' })
-        vim.keymap.set('n', '[c', function()
-          if vim.wo.diff then
-            return '[c'
-          end
-          vim.schedule(gs.prev_hunk)
-          return '<Ignore>'
-        end, { buffer = bufnr, expr = true, desc = 'previous hunk' })
-        vim.keymap.set('n', '<leader>hb', function()
-          gs.blame_line({ full = true })
-        end, { buffer = bufnr, desc = 'show line blame (full)' })
-        vim.keymap.set('n', '<leader>hB', function()
-          gs.blame_line({ full = false })
-        end, { buffer = bufnr, desc = 'show line blame (compact)' })
-        vim.keymap.set(
-          'n',
-          '<leader>hp',
-          gs.preview_hunk,
-          { buffer = bufnr, desc = 'preview hunk' }
-        )
-        vim.keymap.set('n', '<leader>hd', gs.diffthis, { buffer = bufnr, desc = 'diff this' })
-        vim.keymap.set('n', '<leader>hl', function()
-          gs.setqflist(0, { open = false })
-          vim.schedule(function()
-            require('telescope.builtin').quickfix()
-          end)
-        end, { buffer = bufnr, desc = 'list hunks' })
-        vim.keymap.set('n', '<leader>gs', vim.cmd.Gitsigns, {
-          buffer = bufnr,
-          desc = 'gitsigns',
-        })
-      end,
-    },
-  },
-
-  {
-    'lukas-reineke/indent-blankline.nvim',
-    lazy = false,
-    main = 'ibl',
-    opts = {
-      indent = {
-        char = '▏',
-        highlight = { 'NonText' },
-      },
-      exclude = {
-        filetypes = { 'alpha' },
-      },
-      scope = {
-        enabled = true,
-        show_start = false,
-        show_end = false,
-        highlight = { 'Comment' },
-      },
-    },
-    keys = {
-      {
-        '<leader>ti',
-        vim.cmd.IBLToggle,
-        desc = 'toggle indent-blankline',
-      },
-    },
-  },
-
-  {
-    'numToStr/Comment.nvim',
-    opts = {
-      opleader = { block = 'gC' },
-    },
-    keys = {
-      'gcc',
-      { 'gc', mode = 'v' },
-      { 'gC', mode = 'v' },
-    },
-  },
-
-  {
-    'windwp/nvim-autopairs',
-    priority = 40,
-    event = 'InsertEnter',
-    config = true,
-  },
-
-  {
-    'elihunter173/dirbuf.nvim',
-    enabled = true,
-    dev = true,
-    lazy = false,
-    keys = {
-      {
-        '<M-l>',
-        function()
-          local cpath = require('dirbuf').get_cursor_path()
-          for _, w in ipairs(vim.api.nvim_list_wins()) do
-            if vim.api.nvim_get_option_value('previewwindow', { win = w }) then
-              if vim.api.nvim_buf_get_name(vim.api.nvim_win_get_buf(w)) == cpath then
-                vim.cmd.pclose()
-                return
-              end
-            end
-          end
-          require('dirbuf').enter('pedit')
-        end,
-        desc = 'Dirbuf: preview file',
-      },
-    },
-  },
-  {
-    'nvim-tree/nvim-tree.lua',
-    version = '*',
-    main = 'nvim-tree',
-    enabled = false,
-    lazy = false,
-    dependencies = { 'nvim-tree/nvim-web-devicons' },
-    opts = {
-      renderer = {
-        icons = {
-          show = {
-            file = false,
-            folder = false,
-            folder_arrow = true,
-            git = false,
-          },
-          glyphs = {
-            default = '󰈤 ',
-            symlink = '󰌹 ',
-            bookmark = 'b',
-            folder = {
-              arrow_open = '▾',
-              arrow_closed = '▸',
-              default = '󰉖 ',
-              open = '󰷏 ',
-              empty = '󱞞 ',
-              symlink = '󰌹 ',
-            },
-          },
-        },
-      },
-      -- on_attach = function(bufnr)
-      -- end,
-    },
-    keys = {
-      {
-        '-',
-        function()
-          require('nvim-tree.api').tree.open({
-            current_window = true,
-            path = vim.fn.expand('%:p:h'),
-          })
-        end,
-        desc = 'NvimTree: open containing directory',
-      },
-      {
-        'gt',
-        function()
-          require('nvim-tree.api').tree.toggle()
-        end,
-        desc = 'NvimTree: toggle',
-      },
-    },
-  },
-
-  {
-    'nvim-treesitter/nvim-treesitter',
-    lazy = false,
-    build = ':TSUpdateSync',
-    config = function(_, opts)
-      local tsconf = require('nvim-treesitter.parsers').get_parser_configs()
-      tsconf.gotmpl = {
-        install_info = {
-          url = 'https://github.com/ngalaiko/tree-sitter-go-template',
-          files = { 'src/parser.c' },
-        },
-        filetype = 'gotmpl',
-        used_by = { 'gotmpl.html', 'gotmpl.yaml', 'gotmpl' },
-      }
-      require('nvim-treesitter.configs').setup(opts)
-    end,
-    opts = {
-      ensure_installed = {
-        'bash',
-        'bibtex',
-        'c',
-        'c_sharp',
-        'cpp',
-        'cmake',
-        'comment',
-        'css',
-        'dockerfile',
-        'go',
-        'gomod',
-        'gowork',
-        'hcl',
-        'html',
-        'java',
-        'javascript',
-        'json',
-        'jsonc',
-        'latex',
-        'ledger',
-        'lua',
-        'make',
-        'markdown',
-        'markdown_inline',
-        'ninja',
-        'norg',
-        'query',
-        'regex',
-        'rust',
-        'scss',
-        'toml',
-        'typescript',
-        'vim',
-        'vimdoc',
-        'yaml',
-        'zig',
-        'yuck', -- eww
-        -- experimental
-        'hare',
-        'gotmpl',
-      },
-      highlight = {
-        enable = true,
-        additional_vim_regex_highlighting = { 'markdown' },
-      },
-      indent = {
-        enable = true,
-      },
-      incremental_selection = {
-        enable = true,
-        keymaps = {
-          init_selection = 'gnn',
-          node_incremental = 'grn',
-          node_decremental = 'grm',
-        },
-      },
-      refactor = {
-        navigation = {
-          enable = true,
-          keymaps = {
-            goto_definition = '<c-]>',
-          },
-        },
-        smart_rename = {
-          enable = true,
-          keymaps = {
-            smart_rename = 'grr',
-          },
-        },
-      },
-      textobjects = {
-        select = {
-          enable = true,
-          keymaps = {
-            ['ib'] = '@block.inner',
-            ['ob'] = '@block.outer',
-            ['ic'] = '@conditional.inner',
-            ['oc'] = '@conditional.outer',
-            ['if'] = '@function.inner',
-            ['of'] = '@function.outer',
-            ['il'] = '@loop.inner',
-            ['ol'] = '@loop.outer',
-            ['is'] = '@scopename.inner',
-            ['os'] = '@scopename.outer',
-          },
-        },
-      },
-    },
-  },
-  { 'nvim-treesitter/nvim-treesitter-refactor', keys = { '<c-]>', 'grr' } },
-  {
-    'nvim-treesitter/nvim-treesitter-textobjects',
-    keys = { 'ib', 'ob', 'ic', 'oc', 'if', 'of', 'il', 'ol', 'is', 'os' },
-  },
-  {
-    'nvim-treesitter/playground',
-    cmd = { 'TSPlaygroundToggle', 'TSHighlightCapturesUnderCursor' },
-  },
-
-  {
-    'neovim/nvim-lspconfig',
-    lazy = false,
-    -- event = 'InsertEnter',
-    priority = 100,
-    dependencies = {
-      {
-        'nvim-lua/lsp-status.nvim',
-        config = function()
-          local lspstatus = require('lsp-status')
-          lspstatus.config({
-            diagnostics = false,
-            current_function = false,
-            status_symbol = '',
-          })
-          lspstatus.register_progress()
-        end,
-      },
-    },
-    config = function()
-      require('telescope').load_extension('lsp_handlers')
-      require('internal.lsp').setup()
-    end,
-  },
-
-  {
-    'hrsh7th/nvim-cmp',
-    event = { 'InsertEnter', 'CmdlineEnter' },
-    dependencies = {
-      -- 'hrsh7th/cmp-buffer',
-      'hrsh7th/cmp-cmdline',
-      'hrsh7th/cmp-path',
-      'hrsh7th/cmp-nvim-lua',
-      'hrsh7th/cmp-nvim-lsp',
-      'hrsh7th/cmp-nvim-lsp-document-symbol',
-      'hrsh7th/cmp-nvim-lsp-signature-help',
-      'saadparwaiz1/cmp_luasnip',
-      'f3fora/cmp-spell',
-    },
-    config = function()
-      local cmp = require('cmp')
-      local luasnip = require('luasnip')
-      cmp.setup({
-        experimental = {
-          ghost_text = { hl_group = 'NonText' },
-          native_menu = false,
-        },
-        -- disable completion in comments
-        enabled = function()
-          local ok, enable = pcall(function()
-            local ctx = require('cmp.config.context')
-            if vim.api.nvim_get_mode().mode == 'i' then
-              if ctx.in_treesitter_capture('comment') or ctx.in_syntax_group('Comment') then
-                return false
-              end
-              if vim.opt.filetype:get() == 'TelescopePrompt' then
-                return false
-              end
-            end
-            return true
-          end)
-          return not ok or enable
-        end,
-        -- performance = {
-        --   max_view_entries = 20,
-        -- },
-        preselect = cmp.PreselectMode.Item,
-        window = {
-          completion = {
-            scrollbar = true,
-            border = 'none',
-          },
-          documentation = {
-            border = 'solid',
-          },
-        },
-        completion = {
-          autocomplete = false,
-        },
-        sorting = {
-          comparators = {
-            cmp.config.compare.offset,
-            cmp.config.compare.exact,
-            cmp.config.compare.recently_used,
-            require("clangd_extensions.cmp_scores"),
-            cmp.config.compare.kind,
-            cmp.config.compare.sort_text,
-            cmp.config.compare.length,
-            cmp.config.compare.order,
-          },
-        },
-        mapping = {
-          ['<c-space>'] = cmp.mapping.complete({ reason = cmp.ContextReason.Auto }),
-          ['<c-x>'] = cmp.mapping.complete({ reason = cmp.ContextReason.Auto }),
-          ['<cr>'] = cmp.mapping.confirm({ select = true }),
-          ['<c-n>'] = cmp.mapping.select_next_item({ behavior = require('cmp.types').cmp.SelectBehavior.Select }),
-          ['<c-p>'] = cmp.mapping.select_prev_item({ behavior = require('cmp.types').cmp.SelectBehavior.Select }),
-          ['<tab>'] = cmp.mapping.confirm({ select = true }),
-          ['<s-tab>'] = cmp.mapping(function(fallback)
-            if cmp.visible() then
-              -- NOTE: poor mans replacement for cmp.confirm without expanding snippet
-              cmp.select_next_item({ behavior = require('cmp.types').cmp.SelectBehavior.Insert })
-              cmp.close()
-            else
-              fallback()
-            end
-          end, { 'i', 's' }),
-          ['<c-tab>'] = cmp.mapping(function(fallback)
-            if luasnip.expand_or_locally_jumpable() then
-              luasnip.expand_or_jump()
-            else
-              fallback()
-            end
-          end, { 'i', 's' }),
-          ['<c-s-tab>'] = cmp.mapping(function(fallback)
-            if luasnip.locally_jumpable(-1) then
-              luasnip.jump(-1)
-            else
-              fallback()
-            end
-          end, { 'i', 's' }),
-          -- map c-j/k for luasnip choice nodes
-          ['<c-j>'] = cmp.mapping(function(fallback)
-            if luasnip.choice_active() then
-              luasnip.change_choice(1)
-            else
-              fallback()
-            end
-          end, { 'i', 's' }),
-          ['<c-k>'] = cmp.mapping(function(fallback)
-            if luasnip.choice_active() then
-              luasnip.change_choice(-1)
-            else
-              fallback()
-            end
-          end, { 'i', 's' }),
-          ['<s-pagedown>'] = cmp.mapping.scroll_docs(-4),
-          ['<s-pageup>'] = cmp.mapping.scroll_docs(4),
-        },
-        snippet = {
-          expand = function(args)
-            require('luasnip').lsp_expand(args.body)
-          end,
-        },
-        sources = cmp.config.sources({
-          { name = 'nvim_lsp' },
-          { name = 'nvim_lsp_signature_help' },
-          { name = 'luasnip' },
-          { name = 'nvim_lua' },
-        }, {
-          -- { name = 'neorg' },
-          -- { name = 'orgmode' },
-          { name = 'spell', keyword_length = 3, max_item_count = 5 },
-          { name = 'path' },
-          -- { name = 'buffer', keyword_length = 3 },
-        }),
-        formatting = {
-          fields = { 'kind', 'abbr', 'menu' },
-          format = function(entry, item)
-            local menus = {
-              nvim_lsp = '░ lsp',
-              luasnip = '░ snip',
-              nvim_lua = '░ nvim',
-              -- orgmode  = '░ org',
-              spell = '░ spell',
-              path = '░ path',
-              buffer = '░ buf',
-            }
-            item.kind = require('internal.lsp_symbols')[item.kind] or ''
-            item.menu = menus[entry.source.name]
-            local maxw = vim.api.nvim_win_get_width(0) - 25
-            item.abbr = string.sub(item.abbr, 1, (#item.abbr > maxw) and maxw or #item.abbr)
-            return item
-          end,
-          expandable_indicator = true,
-        },
-      })
-      cmp.setup.cmdline({ '/', '?', '@' }, {
-        mapping = cmp.mapping.preset.cmdline(),
-        sources = cmp.config.sources({
-          { name = 'nvim_lsp_document_symbol' },
-          -- { name = 'buffer' }
-        }),
-        formatting = {
-          fields = { 'abbr', 'menu' },
-        },
-      })
-      cmp.setup.cmdline(':', {
-        mapping = {
-          ['<c-r>'] = cmp.mapping({
-            c = function()
-              vim.cmd.Telescope('command_history')
-            end,
-          }),
-          ['<c-n>'] = cmp.mapping({
-            c = cmp.mapping.select_next_item({ behavior = require('cmp.types').cmp.SelectBehavior.Insert }),
-          }),
-          ['<c-p>'] = cmp.mapping({
-            c = cmp.mapping.select_prev_item({ behavior = require('cmp.types').cmp.SelectBehavior.Insert }),
-          }),
-        },
-        sources = cmp.config.sources({
-          { name = 'path' },
-        }, {
-          { name = 'cmdline' },
-        }),
-        formatting = {
-          fields = { 'abbr', 'menu' },
-        },
-      })
-      -- insert `(` after selecting function/method items
-      cmp.event:on(
-        'confirm_done',
-        require('nvim-autopairs.completion.cmp').on_confirm_done({
-          map_char = { tex = '' },
-        })
-      )
-    end,
-  },
-
-  {
-    'L3MON4D3/LuaSnip',
-    config = function()
-      require('internal.snips')
-    end,
-  },
-
-  {
-    'nvim-telescope/telescope.nvim',
-    cmd = 'Telescope',
-    dependencies = {
-      'nvim-lua/popup.nvim',
-      'nvim-lua/plenary.nvim',
-      {
-        'nvim-telescope/telescope-fzf-native.nvim',
-        build = 'make',
-        config = function()
-          require('telescope').load_extension('fzf')
-        end,
-      },
-      {
-        'nvim-telescope/telescope-ui-select.nvim',
-        config = function()
-          require('telescope').load_extension('ui-select')
-        end,
-      },
-      'gbrlsnchs/telescope-lsp-handlers.nvim',
-    },
-    config = function()
-      require('telescope').setup({
-        defaults = {
-          prompt_prefix = '',
-          selection_caret = '⯈ ',
-          sorting_strategy = 'ascending',
-          preview = false,
-          results_title = false,
-          layout_strategy = 'bottom_pane',
-          layout_config = {
-            -- preview_cutoff = 1,
-            -- height = 20,
-          },
-          border = true,
-          borderchars = {
-            preview = { '─', '│', '─', '│', '┌', '┐', '┘', '└' },
-            prompt = { '─', '', '', '', '╾', '╼', '', '' },
-            results = { '' },
-          },
-          file_previewer = require('telescope.previewers').vim_buffer_cat.new,
-          grep_previewer = require('telescope.previewers').vim_buffer_vimgrep.new,
-          qflist_previewer = require('telescope.previewers').vim_buffer_qflist.new,
-          mappings = {
-            i = {
-              ['<C-Space>'] = require('telescope.actions.layout').toggle_preview,
-            },
-            n = {
-              ['<C-Space>'] = require('telescope.actions.layout').toggle_preview,
-              [';<bs>'] = function()
-                vim.cmd.Telescope('resume')
-              end,
-            },
-          },
-        },
-        pickers = {
-          buffers = {
-            sort_mru = true,
-            mappings = {
-              i = {
-                ["<C-w>"] = require('telescope.actions').delete_buffer,
-              }
-            }
-          }
-        },
-        extensions = {
-          ['fzf'] = {
-            fuzzy = true,
-            override_generic_sorter = true,
-            override_file_sorter = true,
-            case_mode = 'smart_case',
-          },
-          ['lsp_handlers'] = {
-            disable = {
-              -- ['textDocument/codeAction'] = true,
-            },
-          },
-          ['ui-select'] = {
-            require('telescope.themes').get_cursor({
-              initial_mode = 'normal',
-              previewer = false,
-            }),
-          },
-        },
-      })
-    end,
-    keys = {
-      {
-        ';Q',
-        function()
-          require('telescope.builtin').quickfix()
-        end,
-        desc = 'quickfix',
-      },
-      {
-        ';C',
-        function()
-          require('telescope.builtin').loclist()
-        end,
-        desc = 'loclist',
-      },
-      {
-        ';H',
-        function()
-          require('telescope.builtin').help_tags()
-        end,
-        desc = 'help_tags',
-      },
-      {
-        ';b',
-        function()
-          require('telescope.builtin').buffers()
-        end,
-        desc = 'buffer',
-      },
-      {
-        ';c',
-        function()
-          require('telescope.builtin').commands()
-        end,
-        desc = 'commands',
-      },
-      {
-        ';f',
-        function()
-          require('telescope.builtin').fd()
-        end,
-        desc = 'fd',
-      },
-      {
-        ';g',
-        function()
-          require('telescope.builtin').live_grep()
-        end,
-        desc = 'grep',
-      },
-      {
-        ';h',
-        function()
-          require('telescope.builtin').command_history()
-        end,
-        desc = 'command history',
-      },
-      {
-        ';bf',
-        function()
-          require('telescope.builtin').current_buffer_fuzzy_find()
-        end,
-        desc = 'buffer',
-      },
-      {
-        ';o',
-        function()
-          require('telescope.builtin').oldfiles()
-        end,
-        desc = 'oldfiles',
-      },
-      {
-        ';d',
-        function()
-          require('telescope.builtin').diagnostics()
-        end,
-        desc = 'diagnostics',
-      },
-      {
-        ';j',
-        function()
-          require('telescope.builtin').jumplist()
-        end,
-        desc = 'jumplist',
-      },
-      {
-        ';v',
-        function()
-          require('telescope.builtin').find_files({
-            prompt_title = 'vimrc',
-            previewer = false,
-            search_dirs = {
-              vim.fn.stdpath('config'),
-              vim.fn.stdpath('data') .. '/lazy',
-            }
-          })
-        end,
-        desc = 'vim config',
-      },
-      {
-        'gw',
-        function()
-          require('internal.cursor').word(function(s)
-            require('telescope.builtin').grep_string({ search = s })
-          end)
-        end,
-        desc = 'grep for word under cursor',
-      },
-    },
-  },
-
-  {
-    'norcalli/nvim-colorizer.lua',
-    lazy = false,
-    config = function()
-      require('colorizer').setup(nil, {
-        name = true,
-        RRGGBB = true,
-        RRGGBBAA = false,
-        rgb_fn = true,
-        hsl_fn = true,
-        mode = 'background',
-      })
-    end,
-    build = [[git cherry-pick patch]],
-  },
-
-  { 'gentoo/gentoo-syntax',                     lazy = false },
-
-  {
-    'NMAC427/guess-indent.nvim',
-    lazy = false,
-    opts = {
-      auto_cmd = true,
-      filetype_exclude = { 'netrw', 'tutor', 'dirbuf', 'nvimtree' },
-      buftype_exclude = { 'help', 'nofile', 'terminal', 'prompt' },
-    },
-  },
-
-  {
-    'echasnovski/mini.align',
-    version = false,
-    opts = {},
-    keys = { 'ga', 'gA' }
-  },
-
-  {
-    url = 'https://git.sr.ht/~robertgzr/spinner.nvim',
-    opts = {
-      spinner = { '⠋', '⠙', '⠹', '⠸', '⠼', '⠴', '⠦', '⠧', '⠇', '⠏' },
-      interval = 120, -- spinner frame rate in ms
-    },
-  },
-
-  {
-    'stevearc/aerial.nvim',
-    cmd = { 'AerialOpen', 'AerialToggle' },
-    keys = { { '<space><space>', vim.cmd.AerialToggle, desc = 'Toggle aerial' } },
-    opts = {
-      backends = { 'lsp', 'treesitter', 'markdown' },
-      filter_kind = {
-        -- default:
-        'Class',
-        'Constructor',
-        'Enum',
-        'Function',
-        'Interface',
-        'Module',
-        'Method',
-        'Struct',
-        -- custom:
-        'Constant',
-        'Variable',
-      },
-      icons = require('internal.lsp_symbols'),
-      close_automatic_events = { 'unsupported' },
-      placement = 'edge',
-      open_automatic = false,
-      -- open_automatic = function(bufnr)
-      --     return vim.api.nvim_buf_line_count(bufnr) > 200
-      --       and package.loaded.aerial.num_symbols(bufnr) > 4
-      --       and not package.loaded.aerial.was_closed()
-      -- end,
-      default_keybinds = false,
-      show_guides = true,
-    },
-  },
-
-  {
-    'SmiteshP/nvim-navic',
-    opts = {
-      icons = require('internal.lsp_symbols'),
-    },
-  },
-
-  -- {'kosayoda/nvim-lightbulb',
-  --   config = {
-  --     ignore = {'null-ls'},
-  --     sign         = { enabled = false },
-  --     virtual_text = { enabled = false, text = '←  󰌵' },
-  --     status_text  = { enabled = true, text = '󰌵', text_unavailable = '' },
-  --     autocmd      = { enabled = true },
-  --   },
-  --   init = function()
-  --     vim.fn.sign_define({{name='LightBulbSign', text='󰌵', texthl='LightBulbSign'}})
-  --   end,
-  -- },
-
-  {
-    'weilbith/nvim-code-action-menu',
-    event = 'VeryLazy',
-    config = function()
-      vim.lsp.handlers['textDocument/codeAction'] =
-          require('code_action_menu').open_code_action_menu
-    end,
-  },
-
-  {
-    'jose-elias-alvarez/null-ls.nvim',
-    enabled = false,
-    ft = {
-      'sh',
-      'bash',
-      'lua',
-      'rust',
-      'c',
-      'cpp',
-      'css',
-      'scss',
-      'html',
-      'javascript',
-      'markdown',
-    },
-    dependencies = { 'nvim-lua/plenary.nvim' },
-    config = function()
-      local nls = require('null-ls')
-      local nls_h = require('null-ls.helpers')
-
-      local beautifier = nls_h.make_builtin({
-        name = 'beautifier',
-        method = nls.methods.FORMATTING,
-        generator_opts = {
-          args = { '--file', '-', '--editorconfig' },
-          to_stdin = true,
-        },
-        env = {
-          ['PATH'] = (vim.env.HOME .. '/.yarn/bin') .. ':' .. vim.env.PATH,
-        },
-        factory = nls_h.formatter_factory,
-      })
-
-      nls.setup({
-        debug = true,
-        on_attach = require('internal.lsp').my_attach,
-        sources = {
-          nls.builtins.diagnostics.shellcheck,
-          nls.builtins.formatting.shfmt,
-          -- nls.builtins.formatting.yapf, -- python
-          nls.builtins.formatting.clang_format,
-          nls.builtins.formatting.rustfmt,
-          nls.builtins.formatting.stylua,
-          -- nls.builtins.formatting.gofumpt,
-          -- nls.builtins.formatting.json_tool,
-          -- nls.builtins.formatting.mdformat,
-
-          -- custom sources
-          beautifier.with({ filetypes = { 'html', 'gotmpl.html' }, command = 'html-beautify' }),
-          beautifier.with({ filetypes = { 'css', 'scss' }, command = 'css-beautify' }),
-          beautifier.with({ filetypes = { 'javascript' }, command = 'js-beautify' }),
-        },
-      })
-    end,
-  },
-
-  {
-    'mfussenegger/nvim-dap',
-    dependencies = {
-      'nvim-telescope/telescope-dap.nvim',
-      'rcarriga/nvim-dap-ui',
-    },
-    config = function()
-      require('telescope').load_extension('dap')
-      require('internal.dap')
-    end,
-    keys = {
-      '<leader>d',
-    },
-  },
-  { 'farmergreg/vim-lastplace',        event = 'VeryLazy' }, -- restore last cursor position (and handle many edge cases)
-  { 'tpope/vim-surround',              event = 'VeryLazy' },
-  { 'tpope/vim-repeat',                event = 'VeryLazy' }, -- extend '.' to plugins
-  { 'michaeljsmith/vim-indent-object', event = 'VeryLazy' }, -- indentation text-objects
-  -- {'kshenoy/vim-signature'}, -- toggle, display and navigate marks
-  -- {'rhysd/conflict-marker.vim'},
-  -- {'kassio/neoterm'},
-
-  {
-    'kristijanhusak/orgmode.nvim',
-    ft = 'org',
-    build = function()
-      require('orgmode').setup_ts_grammar()
-      vim.cmd.TSUpdate()
-    end,
-    opts = {
-      org_agenda_files = { vim.env.HOME .. '/documents/org/*.org' },
-      org_default_notes_file = vim.env.HOME .. '/documents/org/todo.org',
-      org_todo_keywords = { 'TODO', 'DONE' },
-      -- org_indent_mode = 'noindent',
-      org_agenda_templates = {
-        t = {
-          description = 'Todo',
-          template = '* TODO %?',
-        },
-        n = {
-          description = 'Note',
-          template = '* %?',
-          target = vim.env.HOME .. '/documents/org/notes.org',
-        },
-      },
-      mappings = {
-        agenda = {
-          org_agenda_close = nil,
-        },
-      },
-    },
-    -- keys = {
-    --   { mode = 's', ';O', function()
-    --     local pickers = require('telescope.pickers')
-    --     local finders = require('telescope.finders')
-    --     pickers.new(opts, {
-    --       prompt_title = 'Orgmode',
-    --       finder = finders.new_table(require('orgmode.config'):get_all_files()),
-    --     }):find()
-    --   end },
-    -- },
-  },
-
-  {
-    'nvim-neorg/neorg',
-    enabled = false,
-    ft = 'norg',
-    cmd = { 'Neorg' },
-    build = ':Neorg sync-parsers',
-    dependencies = {
-      'nvim-lua/plenary.nvim',
-      'nvim-neorg/neorg-telescope',
-      'nvim-treesitter/nvim-treesitter',
-    },
-    init = function()
-      -- vim.cmd [[autocmd BufRead,BufNewFile *.norg setlocal filetype=norg]],
-    end,
-    opts = {
-      load = {
-        ['core.defaults'] = {},
-        ['core.keybinds'] = {
-          config = { default_keybinds = true },
-        },
-        ['core.norg.concealer'] = {
-          config = { icons = { todo = { enabled = true } } },
-        },
-        ['core.norg.dirman'] = {
-          config = {
-            workspaces = {
-              default = '$HOME/documents/neorg/default',
-              work = '$HOME/documents/neorg/work',
-              gtd = '$HOME/documents/neorg/gtd',
-            },
-          },
-        },
-        ['core.norg.completion'] = {
-          config = { engine = 'nvim-cmp' },
-        },
-        ['core.integrations.telescope'] = {},
-        ['core.norg.qol.todo_items'] = {},
-        ['core.presenter'] = {},
-        ['core.gtd.base'] = {
-          config = { workspace = 'gtd' },
-        },
-      },
-    },
-  },
-
-  {
-    'zk-org/zk-nvim',
-    cmd = { 'ZkNew', 'ZkNotes' },
-    ft = { 'markdown', 'neorg' },
-    config = function()
-      require('telescope').load_extension('zk')
-      require('zk').setup({
-        picker = 'telescope',
-        lsp = {
-          config = {
-            cmd = { 'zk', 'lsp', '--log', '/tmp/zk-lsp.log' },
-            on_attach = require('internal.lsp').my_attach,
-            on_exit = require('internal.lsp').my_exit,
-            capabilities = require('internal.lsp').capabilities(),
-          },
-          auto_attach = {
-            enabled = true,
-            filetypes = { 'markdown' },
-          },
-        },
-      })
-    end,
-    keys = {
-      {
-        ';zn',
-        vim.cmd.ZkNotes,
-        desc = 'zk notes',
-      },
-      {
-        ';zb',
-        vim.cmd.ZkBacklinks,
-        desc = 'zk backlinks',
-      },
-      {
-        ';zt',
-        vim.cmd.ZkTags,
-        desc = 'zk tags',
-      },
-      {
-        ';zl',
-        vim.cmd.ZkLinks,
-        desc = 'zk links',
-      },
-      {
-        ';zN',
-        function()
-
-        end,
-        desc = 'zk new note',
-      },
-    },
-  },
-
-  -- {'rhysd/vim-grammarous',
-  --   ft = {'markdown', 'latex', 'tex'}
-  -- },
-
-  {
-    'lervag/vimtex',
-    enabled = false,
-    ft = { 'latex', 'tex' },
-    config = function()
-      local g = vim.g
-      g.tex_flavor = 'latex'
-      g.vimtex_compiler_enabled = 0
-      g.vimtex_compiler_method = 'tectonic'
-      g.vimtex_compiler_tectonic = "{'executable': 'tectonic'}"
-      g.vimtex_view_method = 'zathura'
-    end,
-  },
-
-  {
-    'preservim/vim-markdown',
-    ft = 'markdown',
-    enabled = true,
-    config = function()
-      vim.g.vim_markdown_frontmatter = 0         -- handled by tre-sitter
-      vim.g.vim_markdown_strikethrough = 1
-      vim.g.vim_markdown_conceal_code_blocks = 0 -- doesn't work due to tree-sitter: https://github.com/nvim-treesitter/nvim-treesitter/issues/2825
-      vim.g.vim_markdown_no_default_key_mappings = 1
-    end,
-  },
-
-  {
-    'https://git.sr.ht/~p00f/clangd_extensions.nvim',
-  },
-
-  {
-    'folke/zen-mode.nvim',
-    dependencies = {
-      {
-        'folke/twilight.nvim',
-        opts = {
-          context = 15,
-          dimming = {
-            alpha = 0.3,
-            color = { 'Normal', '#ffffff' },
-          },
-        },
-      },
-    },
-    cmd = { 'ZenMode' },
-    opts = {
-      window = {
-        -- backdrop = 1,
-        -- width = 0.3,
-        -- height = 1,
-        options = {
-          number = false,
-          list = false,
-        },
-      },
-      plugins = {
-        options = {
-          enabled = true,
-          ruler = false,
-          showcmd = false,
-        },
-        twilight = { enabled = true },
-        gitsigns = { enabled = false },
-      },
-    },
-  },
-
-  {
-    'folke/which-key.nvim',
-    event = 'VeryLazy',
-    opts = {
-      icons = { separator = '→ ', group = '🞱 ' },
-      triggers = { '<leader>', '<localleader>', ';', 'g', '[', ']' },
-    },
-  },
-
-  {
-    'goolord/alpha-nvim',
-    enabled = false,
-    cmd = 'Alpha',
-    config = function()
-      local MAX_WIDTH = 80
-      local alpha = require('alpha')
-      local them = require('alpha.themes.theta')
-      local button = function(...)
-        local b = require('alpha.themes.dashboard').button(...)
-        b.opts = vim.tbl_extend('force', b.opts, {
-          hl = 'Normal',
-          width = MAX_WIDTH,
-        })
-        return b
-      end
-      local fit_path = function(path, max_width)
-        local Path = require('plenary.path')
-        path = vim.fn.fnamemodify(path, ':.')
-        if vim.fn.strdisplaywidth(path) > max_width then
-          path = Path.new(path):shorten(1, { -2, -1 })
-        end
-        if vim.fn.strdisplaywidth(path) > max_width then
-          path = '_ ' .. path:sub((vim.fn.strdisplaywidth(path) - max_width), -1)
-        end
-        return path
-      end
-      local hr = function(margin, max_width, label, opts)
-        max_width = max_width - (2 * margin)
-        label = label and (' ' .. label .. ' ') or ''
-        opts = vim.tbl_extend('force', opts or {}, { position = 'center', hl = 'Comment' })
-        return {
-          type = 'text',
-          opts = opts,
-          val = function()
-            local label_len = vim.fn.strdisplaywidth(label)
-            -- exit here if we're not showing a label
-            if label_len == 0 then
-              return string.rep(' ', margin)
-                  .. string.rep('─', max_width)
-                  .. string.rep(' ', margin)
-            end
-            if label_len > max_width then
-              return error('overfull box: ' .. label)
-            end
-            max_width = max_width - label_len
-            return string.rep(' ', margin)
-                .. string.rep('─', max_width / 2)
-                .. label
-                .. string.rep('─', max_width / 2)
-                .. string.rep(' ', margin)
-          end,
-        }
-      end
-      local fortune = function(margin, max_width)
-        max_width = max_width - (margin * 2)
-        --   local Job = require('plenary.job')
-        --   local ok, j = pcall(Job.new, Job, {
-        --     command = 'sh',
-        --     args = {'-c', 'fortune ' .. vim.env.HOME..'/devel/projects/zig/fortune/fortunes' .. ' | fmt -w ' .. max_width},
-        --     enable_recording = true,
-        --   })
-        --   if not ok then return {} end
-        --     local lines, exit_code = j:sync()
-        --   if not exit_code == 0 then return {} end
-        --   local val = {}
-        --   for i = 1, #lines do
-        --     if vim.fn.strdisplaywidth(lines[i]) > max_width then
-        --     return error('overful box: ' .. lines[i])
-        --     end
-        --     table.insert(val,
-        --     (string.rep(' ', margin) .. lines[i] .. string.rep(' ', margin)))
-        --   end
-        --   if vim.trim(val[#val]) == '' then table.remove(val, #val) end
-        return {
-          type = 'text',
-          val = 'noop',
-          opts = {
-            position = 'center',
-            hl = 'AlphaFortune',
-          },
-        }
-      end
-      local mru = function(max_width)
-        return {
-          type = 'group',
-          val = function()
-            local items = {}
-
-            -- initialize the oldfiles table
-            local oldfiles = {}
-            local cwd = vim.uv.cwd()
-            for _, v in pairs(vim.v.oldfiles) do
-              if #oldfiles == 10 then
-                break
-              end
-              if vim.startswith(v, cwd) and (vim.fn.filereadable(v) == 1) then
-                table.insert(oldfiles, v)
-              end
-            end
-            -- exit early if there's nothing to show
-            if not oldfiles or #oldfiles == 0 then
-              return {}
-            end
-
-            table.insert(items, hr(0, max_width, 'MRU: ' .. fit_path(cwd, max_width)))
-            table.insert(items, { type = 'padding', val = 1 })
-            for i, fn in pairs(oldfiles) do
-              table.insert(
-                items,
-                button(
-                  tostring(i - 1), -- keybind is <n>
-                  fit_path(fn, max_width),
-                  ':edit ' .. fn .. ' <cr>'
-                )
-              )
-            end
-            return items
-          end,
-          opts = {
-            position = 'center',
-          },
-        }
-      end
-      local buffers = function(max_width)
-        return {
-          type = 'group',
-          val = function()
-            local items = {}
-
-            -- get listed buffers
-            local bufnrs = vim.tbl_filter(function(bufnr)
-              if 1 ~= vim.fn.buflisted(bufnr) then
-                return false
-              end
-              return true
-            end, vim.api.nvim_list_bufs())
-
-            --sort by last_used
-            table.sort(bufnrs, function(a, b)
-              return vim.fn.getbufinfo(a)[1].lastused > vim.fn.getbufinfo(b)[1].lastused
-            end)
-
-            -- exit early if there's nothing to show
-            if not bufnrs or #bufnrs == 0 then
-              return {}
-            end
-
-            table.insert(items, { type = 'padding', val = 1 })
-            table.insert(items, hr(0, max_width, 'Buffers'))
-            table.insert(items, { type = 'padding', val = 1 })
-
-            for _, bufnr in ipairs(bufnrs) do
-              local bufpath =
-                  require('plenary.path').new(vim.fn.getbufinfo(bufnr)[1].name):shorten(1, { -2, -1 })
-              table.insert(items, button('b' .. bufnr, bufpath, ':b' .. bufnr .. '<cr>'))
-            end
-            return items
-          end,
-          opts = {
-            position = 'center',
-          },
-        }
-      end
-      them.config.layout = {
-        { type = 'padding', val = 2 },
-        require('alpha.themes.dashboard').section.header,
-        { type = 'padding', val = 1 },
-        fortune(5, MAX_WIDTH),
-        { type = 'padding', val = 1 },
-        hr(0, MAX_WIDTH),
-        { type = 'padding', val = 1 },
-        {
-          type = 'group',
-          val = {
-            button('e', '󰈔  new', [[<cmd>ene <bar> startinsert<cr>]]),
-            button('r', '󰈸  live grep', [[<cmd>lua require('internal.misc').live_grep()<cr>]]),
-            button('f', '󰝰  find files', [[<cmd>lua require('internal.misc').find_files()<cr>]]),
-            button('m', '󰥔  mru', [[<cmd>lua require('telescope.builtin').oldfiles()<cr>]]),
-            button(
-              'o',
-              '󰃶  orgmode',
-              [[<cmd>lua require('orgmode').action('agenda.prompt')<cr>]]
-            ),
-            button(
-              't',
-              '󰃶  todos',
-              [[<cmd>lua require('telescope._extensions.todo-comments').exports.todo {cwd=vim.env.ZK_NOTEBOOK_DIR}<cr>]]
-            ),
-            button('u', '󰚰  update plugins', [[<cmd>lua require('lazy').update()<cr>]]),
-            button(
-              'v',
-              '󰂓  edit config',
-              [[<cmd>lua require('telescope.builtin').find_files {search_dirs={vim.env.HOME..'/.vim/'}}<cr>]]
-            ),
-          },
-        },
-        { type = 'padding', val = 1 },
-        mru(MAX_WIDTH),
-        buffers(MAX_WIDTH),
-      }
-      alpha.setup(them.config)
-    end,
-    keys = {
-      { '<leader>a', vim.cmd.Alpha, desc = 'alpha' },
-    },
-  },
-
-  {
-    'linrongbin16/gitlinker.nvim',
-    cmd = { 'GitLink' },
-    dependencies = { 'nvim-lua/plenary.nvim' },
-    opts = {
-      message = true,
-    },
-    keys = {
-      {
-        '<leader>gl',
-        vim.cmd.GitLink,
-        desc = 'gitlinker -> clipboard',
-      },
-    },
-  },
-
-  {
-    'rhysd/git-messenger.vim',
-    cmd = { 'GitMessenger' },
-    config = function()
-      -- vim.g.git_messenger_include_diff = false
-      vim.g.git_messenger_always_into_popup = true
-      vim.g.git_messenger_close_on_cursor_moved = true
-      vim.g.git_messenger_no_default_mappings = true
-    end,
-    keys = {
-      { '<leader>gb', vim.cmd.GitMessenger, desc = 'blame (git-messenger)' },
-    },
-  },
-
-  {
-    'folke/todo-comments.nvim',
-    lazy = false,
-    cmd = { 'TodoTelescope' },
-    config = {
-      keywords = {
-        FIX = { icon = '󰃤' },
-        TODO = { icon = '󰸞' },
-        HACK = { icon = '󰈸' },
-        WARN = { icon = '󱇎' },
-        PERF = { icon = '󰅒' },
-        NOTE = { icon = '󰐃' },
-        TEST = { icon = '󰂓' },
-      },
-      search = {
-        pattern = [[\b(KEYWORDS)(|\(.+\)):]],
-      },
-      highlight = {
-        keyword = "bg",
-        pattern = [[(KEYWORDS)]],
-      }
-    },
-    keys = {
-      { ';t', vim.cmd.TodoTelescope,                               desc = 'todo-comments' },
-      { "]t", function() require("todo-comments").jump_next() end, desc = "Next todo comment" },
-      { "[t", function() require("todo-comments").jump_prev() end, desc = "Previous todo comment" },
-    },
-  },
-
-  {
-    'cbochs/grapple.nvim',
-    dependencies = { 'nvim-lua/plenary.nvim' },
-    cmd = { 'GrapplePopup' },
-    opts = {
-      icons = false,
-      popup_options = {
-        border = 'none',
-      },
-    },
-    keys = {
-      {
-        '<leader>ml',
-        function()
-          require('grapple').toggle_tags()
-        end,
-        desc = 'grapple: show tags',
-      },
-      {
-        '<leader>ms',
-        function()
-          require('grapple').popup_scopes()
-        end,
-        desc = 'grapple: show scopes',
-      },
-      {
-        '<leader>mm',
-        function()
-          require('grapple').toggle()
-        end,
-        desc = 'grapple: anonymous tag',
-      },
-      {
-        '<leader>mn',
-        function()
-          require('grapple').cycle_forward()
-        end,
-        desc = 'grapple: next tag',
-      },
-      {
-        '<leader>mp',
-        function()
-          require('grapple').cycle_backward()
-        end,
-        desc = 'grapple: prev tag',
-      },
-    },
-  },
-
-  {
-    'tjdevries/sg.nvim',
-    enabled = false,
-    lazy = false,
-    build = 'cargo build --workspace',
-    dependencies = { 'nvim-lua/plenary.nvim' },
-    config = function()
-      require('sg').setup({
-        on_attach = require('internal.lsp').my_attach,
-      })
-    end,
-    keys = {
-      {
-        '<leader>s',
-        function()
-          require('sg.telescope').fuzzy_search_results()
-        end,
-        desc = 'sg.nvim: fuzzy search results',
-      },
-    },
-  },
-
-  {
-    url = 'https://git.sr.ht/~robertgzr/karafuru',
-    dev = true,
-    lazy = false,
-    enabled = false,
-    priority = 1000,
-    cond = (vim.opt.background:get() == 'dark'),
-    config = function(plugin)
-      vim.opt.rtp:append(plugin.dir .. '/vim')
-      vim.cmd.colorscheme('karafuru')
-    end,
-  },
-
-  {
-    'yorik1984/newpaper.nvim',
-    lazy = false,
-    enabled = false,
-    priority = 1000,
-    cond = (vim.opt.background:get() == 'light'),
-    config = function()
-      vim.cmd.colorscheme('newpaper')
-    end,
-  },
-
-  {
-    'nyoom-engineering/oxocarbon.nvim',
-    lazy = false,
-    enabled = false,
-    priority = 1000,
-    cond = (vim.opt.background:get() == 'dark'),
-    config = function()
-      vim.opt.background = 'dark'
-      vim.cmd.colorscheme('oxocarbon')
-    end,
-  },
-
-  {
-    'mcchrish/zenbones.nvim',
-    dependencies = { 'rktjmp/lush.nvim' },
-    lazy = false,
-    enabled = false,
-    priority = 1000,
-    config = function()
-      vim.opt.termguicolors = true
-      local scheme = 'tokyobones'
-      vim.g[scheme] = {
-        lighten_non_text = 20,
-        transparent_background = (vim.opt.background:get() == 'dark'),
-      }
-      vim.cmd.colorscheme(scheme)
-    end,
-  },
-
-  -- quarantine
-  {
-    'zbirenbaum/copilot.lua',
-    enabled = false,
-    cmd = { 'Copilot' },
-    opts = {
-      panel = { auto_refresh = true },
-      suggestion = { auto_trigger = true },
-    },
-  },
-  {
-    'Kicamon/markdown-table-mode.nvim',
-    enabled = true,
-    ft = { 'markdown' },
-  },
-}
-
-require('lazy').setup(pluginspec, {
-  defaults = { lazy = true },
-  dev = { path = '~/src' },
-})
diff --git a/.vim/lua/telescope/_extensions/jobs.lua b/.vim/lua/telescope/_extensions/jobs.lua
deleted file mode 100644
index be55a47..0000000
--- a/.vim/lua/telescope/_extensions/jobs.lua
+++ /dev/null
@@ -1,84 +0,0 @@
-local job = require('internal.job')
-
-local pickers = require('telescope.pickers')
-local finders = require('telescope.finders')
-local conf = require('telescope.config').values
-local actions = require('telescope.actions')
-local action_state = require('telescope.actions.state')
-local entry_display = require('telescope.pickers.entry_display')
-
-local function job_entry_maker(_)
-  return function(j)
-    local displayer = entry_display.create({
-      separator = ' ',
-      items = {
-        { width = 8 },
-        { remaining = true },
-      },
-    })
-    local make_display = function(e)
-      return displayer({
-        { e.value.pid, 'TelescopeResultsNumber' },
-        (e.value.command .. ' ' .. table.concat(e.value.args, ' ')),
-      })
-    end
-    return {
-      value = j,
-      display = make_display,
-      ordinal = tostring(j.pid),
-    }
-  end
-end
-
-local function list_jobs(opts)
-  local jobs = {}
-  for _, j in pairs(job.current_jobs) do
-    table.insert(jobs, j)
-  end
-  if #jobs == 0 then
-    vim.notify('no jobs')
-    return
-  end
-
-  opts = vim.tbl_extend('force', { prompt_title = 'Jobs' }, opts or {})
-  pickers
-    .new(opts, {
-      finder = finders.new_table({
-        results = jobs,
-        entry_maker = job_entry_maker(opts),
-      }),
-      sorter = conf.generic_sorter(opts),
-      attach_mappings = function(prompt_bufnr, _)
-        actions.select_default:replace(function()
-          local entry = action_state.get_selected_entry()
-          if not entry then
-            return
-          end
-          actions.close(prompt_bufnr)
-          vim.ui.select(
-            { 'Terminate', 'Kill', 'Show', 'Cancel' },
-            { prompt = 'Select an action:' },
-            function(choice)
-              if choice == 'Cancel' then
-                return
-              elseif choice == 'Show' then
-                vim.fn.getqflist({ id = entry.value.pid })
-              elseif choice == 'Kill' then
-                entry.value.handle:kill('sigkill')
-              elseif choice == 'Terminate' then
-                entry.value.handle:kill('sigterm')
-              end
-            end
-          )
-        end)
-        return true
-      end,
-    })
-    :find()
-end
-
-return require('telescope').register_extension({
-  exports = {
-    jobs = list_jobs,
-  },
-})