An agent orchestrator for Neovim that makes avante.nvim feel more like a
Cursor-style agent: one-key switching between provider/model/API-key profiles,
an auto-generated project brief that is injected into the system prompt, and a
two-tier context strategy that pulls deep context on demand via MCP tools.
- Profiles — bundle a provider, model, API key, and optional persona together and switch between them with one key.
- Indexer — generates a committable project brief (
AVANTE.md) and refreshes it on save. - Two-tier context — the brief is always injected into the system prompt (cheap, structural); deep context is pulled on demand via MCP tools (semantic search, repo map, call graphs) so the model only spends tokens when it actually needs deeper context.
- Neovim 0.10+ (tested against 0.12)
- avante.nvim (for the chat UI)
- Optional: mcphub.nvim + a
semantic indexer (
ripvec,semnav) for on-demand retrieval - Optional: snacks.nvim for the profile
picker (falls back to
vim.ui.selectwhen absent)
{
"whitecat1331/agent_core.nvim",
config = function()
require("agent_core").setup()
end,
}use {
"whitecat1331/agent_core.nvim",
config = function()
require("agent_core").setup()
end,
}Plug 'whitecat1331/agent_core.nvim'Then in your config:
require("agent_core").setup()agent_core exposes get_brief_prompt() for the system prompt and the active
persona via vim.g.agent_persona. A minimal avante.nvim integration:
require("avante").setup({
system_prompt = function()
local parts = { "You are a senior software engineer." }
local persona = vim.g.agent_persona
if persona and persona ~= "" then
table.insert(parts, persona)
end
local ok, core = pcall(require, "agent_core")
if ok and core.get_brief_prompt then
table.insert(parts, core.get_brief_prompt())
end
return table.concat(parts, "\n\n")
end,
})| Command | Keymap | Purpose |
|---|---|---|
:AgentSwitch |
<leader>aP |
Pick an agent/key profile |
:AgentIndex |
<leader>aI |
Regenerate AVANTE.md for the current repo |
:AgentProfile |
<leader>ap |
Show the active profile |
require("agent_core").setup({
brief_filename = "AVANTE.md", -- filename written at the project root
semnav_bin = "semnav", -- semnav binary (resolved via exepath)
brief_prompt_max_chars = 8000, -- token budget for the injected brief
refresh_debounce_ms = 5000, -- debounce for auto-refresh after saves
profiles = nil, -- nil = use built-in defaults
excluded_dirs = { ".git", "node_modules", ".venv", "vendor" },
})Profiles live in lua/agent_core/profiles.lua (M.defaults). Each bundles
name, provider, model, api_key_name, and an optional description /
system_prompt. Pass your own profiles table to setup() to override the
defaults.
- API keys are resolved env-first:
profile.api_key>os.getenv(api_key_name)~/.config/nvim/agent_keys.json(chmod 0600). Prefer settingDEEPSEEK_API_KEY/GEMINI_API_KEYin achmod 600file sourced by your shell. Never put real keys inprofiles.luaor commitagent_keys.json. - The generated brief is structural only — file paths, language counts, key files, and build/test commands. It never embeds file contents, so it cannot leak secrets, and it is safe to commit.
- See SECURITY.md for the full model and reporting policy.
:AgentIndexwritesAVANTE.mdat the git root (or cwd when not a repo).- It auto-refreshes (debounced) after every
BufWritePost, but only if a brief already exists — run:AgentIndexonce per repo to opt in. - Extend
agent_core.indexerto redact additional patterns if ever needed.
-
mcphub.nvimmerges~/.config/mcphub/servers.json(global) with a per-project.mcphub/servers.json. -
ripvec— semantic + BM25 + LSP search. Registered globally; zero setup. -
semnav— LSP semantic graph. Opted in per project::AgentIndexdetects a supported language (Go/Rust/JS/Python), writes the project.mcphub/servers.json, and runs a one-timesemnav indexif<repo>/.semnav/graph.dbis missing. Tracked daemons are stopped onVimLeavePre.semnavneeds the relevant LSP server onPATH(gopls,rust-analyzer,pyright, ortypescript-language-server). Add.semnav/and.mcphub/to.gitignorein opted-in repos.
See CONTRIBUTING.md for development setup (Windows/Cursor and WSL/nvim), running the checks, and the Conventional Commits style.