jackwener/OpenCLI · error · PluginError
Plugin "${pluginName}" is already installed at ${targetDir}
Error message
Plugin "${pluginName}" is already installed at ${targetDir} What it means
installSinglePlugin computes the target directory ~/.opencli/plugins/<pluginName> (name from the manifest or the source repo name) and throws a PluginError if that directory already exists. opencli refuses to silently overwrite an existing installation, telling the user to uninstall first or choose a different name.
Source
Thrown at src/plugin.ts:747
}
// Single plugin mode
return installSinglePlugin(tmpCloneDir, parsed.cloneUrl!, repoName, manifest);
});
}
/** Install a single (non-monorepo) plugin. */
function installSinglePlugin(
cloneDir: string,
cloneUrl: string,
name: string,
manifest: PluginManifest | null,
): string {
const pluginName = manifest?.name ?? name;
const targetDir = path.join(PLUGINS_DIR, pluginName);
if (fs.existsSync(targetDir)) {
throw new PluginError(`Plugin "${pluginName}" is already installed at ${targetDir}`, 'Use "opencli plugin uninstall" first, or pick a different name.');
}
ensureStandalonePluginReady(cloneDir);
publishStandalonePlugin(cloneDir, targetDir, (commitHash) => {
const lock = readLockFile();
if (commitHash) {
upsertLockEntry(lock, pluginName, {
source: { kind: 'git', url: cloneUrl },
commitHash,
});
writeLockFile(lock);
}
});
return pluginName;
}
/**View on GitHub (pinned to 49907e53dc)
Solutions
- Uninstall the existing plugin first: `opencli plugin uninstall <name>`.
- If you want the newer version of the same plugin, use `opencli plugin update <name>` instead of install.
- If the existing directory is a stale leftover, remove it: `rm -rf ~/.opencli/plugins/<name>`.
- If two distinct plugins collide, change the `name` in one plugin's opencli-plugin.json.
- Check `opencli plugin list` to see what is installed before installing.
Example fix
// before opencli plugin install github:user/repo // already installed // after opencli plugin update repo // or opencli plugin uninstall repo && opencli plugin install github:user/repo
Defensive patterns
Strategy: validation
Validate before calling
import * as fs from 'node:fs';
import * as path from 'node:path';
const pluginsDir = path.join(home, '.opencli', 'plugins');
const name = 'repo'; // manifest name or repo basename
if (fs.existsSync(path.join(pluginsDir, name))) {
// already installed: call update/uninstall instead of install
} Try / catch
try {
installPlugin(source);
} catch (err) {
if (err instanceof PluginError && err.message.includes('is already installed')) {
const name = err.message.match(/Plugin "([^"]+)"/)?.[1];
uninstallPlugin(name); // or updatePlugin(name); then retry install if needed
} else throw err;
} Prevention
- Check `opencli plugin list` before installing.
- Use `plugin update` for refreshing an existing plugin instead of `plugin install`.
- Ensure each plugin's manifest `name` is unique across your installed set.
- Clean stale leftovers in ~/.opencli/plugins rather than installing over them.
When it happens
Trigger: installPlugin('github:user/repo') when a plugin with the same name (manifest `name` field or repo basename) is already installed — whether from the same repo (double install), a different repo that claims the same manifest name, or a leftover directory in the plugins folder.
Common situations: Re-running the same install command instead of `plugin update`; two unrelated plugins whose manifests both set name to "utils"; plugins dir contains manual copies; previous install crashed after publish but before lock update.
Related errors
- Failed to clone plugin: ${getErrorMessage(err)}
- Expected monorepo plugin link at ${linkPath} to be a symlink
- npm install failed in ${dir}: ${getErrorMessage(err)}
- Invalid plugin source: "${source}" Supported formats: gith
- Plugin requires opencli ${manifest.opencli}, but current ver
AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29).
Data as JSON: /api/errors/27d1c99ec97abac9.
Report an issue: GitHub.