wpnav_install_plugin
Install WordPress plugins from WordPress.org using plugin slugs, with optional activation and audit trail logging for tracking changes.
Instructions
Install a WordPress plugin from WordPress.org by slug. Changes are logged in audit trail.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| slug | Yes | Plugin slug from WordPress.org (e.g., "akismet") | |
| activate | No | Activate plugin after installation (default: false) |
Implementation Reference
- src/tools/plugins/index.ts:116-162 (handler)Executes the wpnav_install_plugin tool: validates input, POSTs to WP REST API /wp/v2/plugins with slug and optional status='active', returns success details or structured error (handles WRITES_DISABLED).handler: async (args, context) => { try { validateRequired(args, ['slug']); const installData: any = { slug: args.slug }; if (args.activate) { installData.status = 'active'; } const result = await context.wpRequest('/wp/v2/plugins', { method: 'POST', body: JSON.stringify(installData), }); return { content: [{ type: 'text', text: context.clampText(JSON.stringify({ plugin: result.plugin, name: result.name, version: result.version, status: result.status, message: 'Plugin installed successfully', }, null, 2)), }], }; } catch (error: any) { const errorMessage = error.message || 'Unknown error'; const isWritesDisabled = errorMessage.includes('WRITES_DISABLED'); return { content: [{ type: 'text', text: JSON.stringify({ error: isWritesDisabled ? 'writes_disabled' : 'operation_failed', code: isWritesDisabled ? 'WRITES_DISABLED' : 'INSTALL_FAILED', message: errorMessage, context: { resource_type: 'plugin', slug: args.slug, suggestion: isWritesDisabled ? 'Set WPNAV_ENABLE_WRITES=1 in MCP server config (.mcp.json env section)' : 'Check plugin slug exists on WordPress.org', }, }, null, 2), }], isError: true, }; } },
- src/tools/plugins/index.ts:104-115 (schema)Input schema and metadata (name, description) for the wpnav_install_plugin tool.definition: { name: 'wpnav_install_plugin', description: 'Install a WordPress plugin from WordPress.org by slug. Changes are logged in audit trail.', inputSchema: { type: 'object', properties: { slug: { type: 'string', description: 'Plugin slug from WordPress.org (e.g., "akismet")' }, activate: { type: 'boolean', description: 'Activate plugin after installation (default: false)', default: false }, }, required: ['slug'], }, },
- src/tools/plugins/index.ts:103-164 (registration)Full tool registration call for wpnav_install_plugin using toolRegistry.register, including definition, handler, and category.toolRegistry.register({ definition: { name: 'wpnav_install_plugin', description: 'Install a WordPress plugin from WordPress.org by slug. Changes are logged in audit trail.', inputSchema: { type: 'object', properties: { slug: { type: 'string', description: 'Plugin slug from WordPress.org (e.g., "akismet")' }, activate: { type: 'boolean', description: 'Activate plugin after installation (default: false)', default: false }, }, required: ['slug'], }, }, handler: async (args, context) => { try { validateRequired(args, ['slug']); const installData: any = { slug: args.slug }; if (args.activate) { installData.status = 'active'; } const result = await context.wpRequest('/wp/v2/plugins', { method: 'POST', body: JSON.stringify(installData), }); return { content: [{ type: 'text', text: context.clampText(JSON.stringify({ plugin: result.plugin, name: result.name, version: result.version, status: result.status, message: 'Plugin installed successfully', }, null, 2)), }], }; } catch (error: any) { const errorMessage = error.message || 'Unknown error'; const isWritesDisabled = errorMessage.includes('WRITES_DISABLED'); return { content: [{ type: 'text', text: JSON.stringify({ error: isWritesDisabled ? 'writes_disabled' : 'operation_failed', code: isWritesDisabled ? 'WRITES_DISABLED' : 'INSTALL_FAILED', message: errorMessage, context: { resource_type: 'plugin', slug: args.slug, suggestion: isWritesDisabled ? 'Set WPNAV_ENABLE_WRITES=1 in MCP server config (.mcp.json env section)' : 'Check plugin slug exists on WordPress.org', }, }, null, 2), }], isError: true, }; } }, category: ToolCategory.PLUGINS, });
- src/tools/index.ts:29-29 (registration)Invocation of registerPluginTools() within registerAllTools(), which registers all plugin tools including wpnav_install_plugin.registerPluginTools();
- src/tools.ts:925-944 (schema)Tool schema definition exported in tools list, likely used for MCP manifest or client-side validation.{ name: 'wpnav_install_plugin', description: 'Install a WordPress plugin from WordPress.org by slug. Changes are logged in audit trail.', inputSchema: { type: 'object' as const, properties: { slug: { type: 'string' as const, description: 'Plugin slug from WordPress.org (e.g., "akismet")', }, activate: { type: 'boolean' as const, description: 'Activate plugin after installation (default: false)', default: false, }, }, required: ['slug'], }, },