vim_command
Execute Vim commands directly within the MCP server, enabling integration of Vim’s native text editing workflows and optional shell command execution for enhanced productivity.
Instructions
Execute Vim commands with optional shell command support
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| command | Yes | Vim command to execute (use ! prefix for shell commands if enabled) |
Implementation Reference
- src/index.ts:99-134 (registration)MCP server.tool registration for 'vim_command', including description, input schema, and thin handler wrapperserver.tool( "vim_command", "Execute Vim commands with optional shell command support", { command: z.string().describe("Vim command to execute (use ! prefix for shell commands if enabled)") }, async ({ command }) => { try { // Check if this is a shell command if (command.startsWith('!')) { const allowShellCommands = process.env.ALLOW_SHELL_COMMANDS === 'true'; if (!allowShellCommands) { return { content: [{ type: "text", text: "Shell command execution is disabled. Set ALLOW_SHELL_COMMANDS=true environment variable to enable shell commands." }] }; } } const result = await neovimManager.sendCommand(command); return { content: [{ type: "text", text: result }] }; } catch (error) { return { content: [{ type: "text", text: error instanceof Error ? error.message : 'Error executing command' }] }; } } );
- src/index.ts:102-102 (schema)Zod input schema defining the 'command' parameter for vim_command tool{ command: z.string().describe("Vim command to execute (use ! prefix for shell commands if enabled)") },
- src/index.ts:103-133 (handler)Tool handler function: checks for shell command permission and delegates execution to NeovimManager.sendCommand, with error handling and MCP response formattingasync ({ command }) => { try { // Check if this is a shell command if (command.startsWith('!')) { const allowShellCommands = process.env.ALLOW_SHELL_COMMANDS === 'true'; if (!allowShellCommands) { return { content: [{ type: "text", text: "Shell command execution is disabled. Set ALLOW_SHELL_COMMANDS=true environment variable to enable shell commands." }] }; } } const result = await neovimManager.sendCommand(command); return { content: [{ type: "text", text: result }] }; } catch (error) { return { content: [{ type: "text", text: error instanceof Error ? error.message : 'Error executing command' }] }; } }
- src/neovim.ts:151-209 (helper)Core helper method in NeovimManager that implements the actual Vim command execution via Neovim API, handles shell commands (! prefix), captures output and errors using execute() and errmsgpublic async sendCommand(command: string): Promise<string> { if (!command || command.trim().length === 0) { throw new NeovimValidationError('Command cannot be empty'); } try { const nvim = await this.connect(); // Remove leading colon if present const normalizedCommand = command.startsWith(':') ? command.substring(1) : command; // Handle shell commands (starting with !) if (normalizedCommand.startsWith('!')) { if (process.env.ALLOW_SHELL_COMMANDS !== 'true') { return 'Shell command execution is disabled. Set ALLOW_SHELL_COMMANDS=true environment variable to enable shell commands.'; } const shellCommand = normalizedCommand.substring(1).trim(); if (!shellCommand) { throw new NeovimValidationError('Shell command cannot be empty'); } try { // Execute the command and capture output directly const output = await nvim.eval(`system('${shellCommand.replace(/'/g, "''")}')`); if (output) { return String(output).trim(); } return 'No output from command'; } catch (error) { console.error('Shell command error:', error); const errorMessage = error instanceof Error ? error.message : 'Unknown error occurred'; throw new NeovimCommandError(`!${shellCommand}`, errorMessage); } } // For regular Vim commands await nvim.setVvar('errmsg', ''); // Execute the command and capture its output using the execute() function const output = await nvim.call('execute', [normalizedCommand]); // Check for errors const vimerr = await nvim.getVvar('errmsg'); if (vimerr) { console.error('Vim error:', vimerr); throw new NeovimCommandError(normalizedCommand, String(vimerr)); } // Return the actual command output if any return output ? String(output).trim() : 'Command executed (no output)'; } catch (error) { if (error instanceof NeovimCommandError || error instanceof NeovimValidationError) { throw error; } console.error('Error sending command:', error); throw new NeovimCommandError(command, error instanceof Error ? error.message : 'Unknown error'); } }