TL;DR Arranca con
claude --plugin-dir ./rutay tu copia local gana al plugin instalado con el mismo nombre durante esa sesión. Sin desinstalar, sin bumpear la versión, sin hacer push para verte el cambio.
Tienes un plugin instalado, tuyo o de tu equipo. Le tocas una skill, guardas y quieres verlo funcionando. Y ahí empieza el rodeo: commit, push, subir la versión en plugin.json, actualizar el marketplace y reinstalar. Mientras tanto, la sesión que tienes abierta sigue cargando la copia vieja y no te avisa de nada.
El flag que salta ese rodeo entero lleva tiempo en las docs, pero contado como "así pruebas el plugin que estás creando desde cero". La regla que lo hace útil de verdad está enterrada a mitad de una sección larga: una copia cargada con --plugin-dir pisa al plugin instalado que se llame igual, durante esa sesión.
La prueba, en mi propia máquina
Tengo craft instalado desde mi marketplace en la versión 3.0.0, y el repo en ~/code/craft por la 3.1.0. La diferencia entre las dos es una skill nueva, worktree, que solo existe en local.
Arrancando con --debug, Claude Code deja en ~/.claude/debug/<id-de-sesión>.txt de dónde ha cargado cada plugin. Sin el flag:
[DEBUG] Attempting to load skills from plugin craft default skillsPath:
/Users/juan.nunez/.claude/plugins/cache/craft/craft/3.0.0/skills
[DEBUG] Loaded 7 skills from plugin craft default directory
Y apuntando a mi copia local:
[DEBUG] Loaded inline plugin from path: craft
[DEBUG] Plugin "craft" from --plugin-dir overrides installed version
[DEBUG] Attempting to load skills from plugin craft default skillsPath:
/Users/juan.nunez/code/craft/skills
[DEBUG] Loaded 8 skills from plugin craft default directory
La segunda línea es la regla dicha por el propio producto, y esa frase no está en la documentación. Siete skills contra ocho, y la octava es worktree, la que solo tengo en local.
Ni namespace duplicado ni conflicto: la local sustituye a la instalada y el nombre sigue siendo craft. Al cerrar la sesión, todo vuelve a como estaba. No se ha desinstalado nada, no se ha tocado tu settings.json y el plugin instalado sigue en su sitio para el resto de sesiones.
La única excepción son los plugins que los managed settings de tu organización fuerzan a encendido o apagado. Esos no los pisa el flag.
El bucle mientras editas
Dentro de la sesión, /reload-plugins recoge lo que vayas cambiando sin reiniciar: skills, agentes, hooks y los servidores MCP y LSP del plugin.
Eso sí, recargar no sale gratis. Cambiar las definiciones de tools invalida la caché del prefijo, así que el turno siguiente reprocesa la conversación entera a precio completo. Con una sesión corta da igual; con una sesión de horas se nota. Si quieres verlo con un número en vez de a ojo, la línea de /cost te dice qué te rompió la caché y por qué, y tool definitions changed es exactamente esta causa. La táctica es la de siempre: junta varios cambios y recarga una vez, en vez de recargar después de cada guardado.
Una carpeta entera, no un plugin
Si mantienes varios plugins juntos, no hace falta repetir el flag por cada uno. Apúntalo a la carpeta madre y carga todos los que hay dentro:
claude --plugin-dir ./plugins
Lo he probado con tres plugins de mentira y un directorio suelto sin manifiesto, y el log de --debug lo cuenta en una sola línea:
[DEBUG] --plugin-dir ./plugins is a folder of plugins: loading alpha, beta,
gamma; no manifest in notaplugin
[DEBUG] Loaded 3 directory-loaded plugins
Lee solo el primer nivel: cada subcarpeta con .claude-plugin/plugin.json entra como plugin independiente, y lo que no lleve manifiesto se queda fuera sin dar error. Ahí tienes el motivo para arrancar con --debug la primera vez: en una sesión normal esa línea no se imprime, así que un plugin al que se le ha olvidado el manifiesto simplemente no aparece. Si algo no carga, claude plugin validate te dice por qué.
En sesión interactiva además vigila la carpeta: si añades un subdirectorio, entra como plugin nuevo en caliente, y si lo quitas, se descarga. Claude Code imprime una línea por cada cambio. Cuando aplicarlo a mitad de conversación rompería la caché, lo retiene y te dice que lances /reload-plugins tú.
Un zip que no está en tu disco
Para probar algo que ya viene empaquetado, un artefacto de CI o una release candidate, está la pareja del flag anterior:
claude --plugin-url https://example.com/mi-plugin.zip
Se descarga al arrancar y vive solo esa sesión. Si la descarga falla o el archivo está corrupto, Claude Code arranca igual y deja el error en la pestaña Errors del gestor de /plugin. Valen las mismas precauciones que con cualquier otra fuente: apúntalo solo a archivos que controlas.
Los dos flags se repiten para cargar varios, y --plugin-url acepta además varias URL separadas por espacios entre comillas.
Referencia
| Cómo lo cargas | Qué entra | Cuándo lo usas |
|---|---|---|
--plugin-dir ./mi-plugin |
Esa carpeta, como un plugin | Editas un plugin concreto |
--plugin-dir ./mi-plugin.zip |
El zip, descomprimido | Te han pasado un paquete |
--plugin-dir ./plugins |
Cada subcarpeta con manifiesto | Mantienes varios a la vez |
--plugin-url https://… |
Un zip remoto, solo esa sesión | Artefacto de CI, release candidate |
/plugin install |
Permanente, en tu config | Ya confías en él |
Los cuatro primeros no tocan tu configuración y desaparecen al cerrar la sesión. El que instala de verdad es el quinto, y a partir de ahí el peso ya viaja en cada mensaje.
Con esto el bucle de desarrollo se queda en editar, /reload-plugins y mirar. El commit pasa a ser lo último, no el peaje para probar. Si todavía no tienes un plugin, empieza por lo que es; cuando quieras repartirlo, el marketplace es el siguiente paso.
Documentación oficial: Create plugins
Requisitos
- Claude Code v2.1.265 o superior para apuntar
--plugin-dira una carpeta de plugins. El flag apuntado a un plugin suelto y a un.zipfunciona desde antes. - Todo lo de arriba está ejecutado en la v2.1.272. El
--plugin-urllo verifiqué sirviendo el zip desde un servidor local, no desde una URL pública. - La vigilancia en caliente de la carpeta es solo de sesión interactiva, y esa parte viene de la documentación: no la he capturado.
- En los bloques de
--debughe acortado las rutas absolutas de mi disco. El resto es literal.