feat(neovim): add known_human checkpoint plugin#1053
Conversation
Adds a Lua plugin for Neovim that fires git-ai checkpoint known_human on file save with 500ms debounce per git repo root. Uses BufWritePost autocmd, vim.loop timers for debounce, and vim.loop.spawn for async non-blocking git-ai invocation. No auto-install; installer surfaces manual steps for lazy.nvim, packer, and native rtp. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
| if opts.enabled == false then | ||
| vim.g.git_ai_enabled = false | ||
| return |
There was a problem hiding this comment.
🟡 setup({ enabled = false }) silently overridden by auto-load shim because setup() doesn't set loaded_git_ai
The plugin/git-ai.lua shim guards on vim.g.loaded_git_ai (agent-support/neovim/plugin/git-ai.lua:3), but M.setup() never sets this variable. For native installs where init.lua runs before plugin/ files are sourced, a user calling require('git-ai').setup({ enabled = false }) in init.lua will have their setting silently overridden: setup() sets git_ai_enabled = false and returns early at line 128 without setting loaded_git_ai, then the shim sees loaded_git_ai is nil, proceeds to call setup() again with defaults, which sets git_ai_enabled = true and creates the autocmd. The user's explicit disable is lost.
Was this helpful? React with 👍 or 👎 to provide feedback.
| message: concat!( | ||
| "Neovim: Automatic installation is not supported. ", | ||
| "Install the plugin using one of these methods:\n", | ||
| "\n", | ||
| " lazy.nvim (recommended):\n", | ||
| " { 'git-ai-project/git-ai', opts = {} }\n", | ||
| "\n", | ||
| " packer.nvim:\n", | ||
| " use { 'git-ai-project/git-ai',\n", | ||
| " config = function() require('git-ai').setup() end }\n", | ||
| "\n", | ||
| " Native (~/.config/nvim/init.lua):\n", | ||
| " vim.opt.rtp:prepend('/path/to/agent-support/neovim')\n", | ||
| " require('git-ai').setup()", | ||
| ) |
There was a problem hiding this comment.
🔴 Neovim install_extras message is silently dropped because it doesn't match any display condition
The Neovim install_extras returns changed: false and a message "Neovim: Automatic installation is not supported. ...". In install_hooks.rs:570-588, the display logic only shows messages when: (1) result.changed is true, (2) message contains "already", or (3) message contains "Unable" or "manually". The Neovim message matches none of these conditions, so the manual installation instructions are never displayed to the user during git-ai install-hooks. Since the entire purpose of the Neovim installer is to show these instructions (it can't auto-install), the feature added by this PR is effectively non-functional.
Display condition matching
result.changed=false→ branches at lines 570 and 574 skip"already"→ not in"Automatic installation is not supported"→ line 578 skips"Unable"or"manually"→ not in the message → line 582 skips
Result: no spinner is created, no output is shown for Neovim.
| message: concat!( | |
| "Neovim: Automatic installation is not supported. ", | |
| "Install the plugin using one of these methods:\n", | |
| "\n", | |
| " lazy.nvim (recommended):\n", | |
| " { 'git-ai-project/git-ai', opts = {} }\n", | |
| "\n", | |
| " packer.nvim:\n", | |
| " use { 'git-ai-project/git-ai',\n", | |
| " config = function() require('git-ai').setup() end }\n", | |
| "\n", | |
| " Native (~/.config/nvim/init.lua):\n", | |
| " vim.opt.rtp:prepend('/path/to/agent-support/neovim')\n", | |
| " require('git-ai').setup()", | |
| ) | |
| message: concat!( | |
| "Neovim: Unable to install automatically. ", | |
| "Install the plugin using one of these methods:\n", | |
| "\n", | |
| " lazy.nvim (recommended):\n", | |
| " { 'git-ai-project/git-ai', opts = {} }\n", | |
| "\n", | |
| " packer.nvim:\n", | |
| " use { 'git-ai-project/git-ai',\n", | |
| " config = function() require('git-ai').setup() end }\n", | |
| "\n", | |
| " Native (~/.config/nvim/init.lua):\n", | |
| " vim.opt.rtp:prepend('/path/to/agent-support/neovim')\n", | |
| " require('git-ai').setup()", | |
| ) |
Was this helpful? React with 👍 or 👎 to provide feedback.
| local lines = vim.api.nvim_buf_get_lines(args.buf, 0, -1, false) | ||
| local content = table.concat(lines, '\n') |
There was a problem hiding this comment.
🟡 Missing trailing newline in dirty_files content causes spurious diffs
On line 104-105, nvim_buf_get_lines(buf, 0, -1, false) returns lines without terminators, and table.concat(lines, '\n') joins them—producing content that lacks a trailing newline. Most files on disk (and in git) end with \n, and the VSCode known-human extension at agent-support/vscode/src/known-human-checkpoint-manager.ts:90 uses doc.getText() which preserves it. Because the checkpoint pipeline compares dirty_files content against working-tree or tracked content (e.g. src/daemon.rs:1686: tracked_content != target_content), the systematically missing trailing newline will cause every file to appear "changed" on every save, generating unnecessary checkpoint work and potentially skewing character-level attribution by one byte.
Was this helpful? React with 👍 or 👎 to provide feedback.
…ion, cache repo root lookup Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
|
@heapwolf this was vibe coded fyi -- no idea what the right way to do this in (neo)vim would be |
Summary
agent-support/neovim/) that firesgit-ai checkpoint known_human --hook-input stdinon file save with 500ms debounce per git repo rootBufWritePostautocmd +vim.loop.new_timer()for debouncevim.loop.spawn()for non-blocking async git-ai invocationopts = {}/setup()conventionNeovimInstallerRust struct that detects nvim and surfaces manual install instructionsManual install steps (for docs site)
lazy.nvim (
~/.config/nvim/init.lua){ 'git-ai-project/git-ai', opts = {} }packer.nvim
Native install
Or add to
init.lua:Test plan
cargo clippy -- -D warningspassescargo testpasses🤖 Generated with Claude Code