Anatomía de una skill
Si tomaste Claude Code desde cero, ya creaste skills con $ARGUMENTS, datos en vivo con !`comando` y disable-model-invocation. Aquí abrimos la skill por completo: cómo se carga, qué hace cada campo, dónde vive y qué pasa con ella cuando la conversación se compacta.
Al terminar podrás:
- explicar los tres niveles de carga progresiva y su costo;
- usar todos los campos del frontmatter que admite Claude Code;
- elegir la ubicación correcta y entender cómo se resuelven los nombres;
- escribir skills que sigan funcionando en sesiones largas.
Las tres capas de una skill
El estándar abierto Agent Skills, que Claude Code sigue, describe la carga progresiva en tres niveles:
| Nivel | Qué carga | Cuándo | Tamaño orientativo |
|---|---|---|---|
| 1. Metadatos | name y description |
Al inicio de la sesión, para todas las skills | Unos 100 tokens por skill |
| 2. Instrucciones | El cuerpo de SKILL.md |
Cuando la skill se activa | Menos de 5,000 tokens recomendados |
| 3. Recursos | Archivos en scripts/, references/, assets/ |
Solo cuando hacen falta | Sin límite práctico |
De ahí la recomendación oficial de mantener SKILL.md por debajo de 500 líneas y mover lo detallado a archivos aparte.
En Claude Code, el nivel 1 tiene presupuesto: la lista de skills ocupa como máximo el 1% de la ventana de contexto y el texto de description más when_to_use de cada skill se corta a 1,536 caracteres. Con muchas skills, se quitan primero las descripciones de las que menos usas.
Frontmatter: la referencia completa
Todos los campos son opcionales; solo description es recomendado. Los nombres deben escribirse exactamente como en la tabla, con guiones: Claude Code ignora en silencio un campo que no reconoce.
| Campo | Para qué sirve |
|---|---|
name |
Nombre del comando en el menú /. Por defecto, el nombre de la carpeta |
description |
Qué hace y cuándo usarla. Claude la usa para decidir si la activa |
when_to_use |
Contexto adicional: frases de activación o ejemplos de pedidos. Se suma a la descripción |
argument-hint |
Pista de argumentos en el autocompletado, como [rfc] [mes] |
arguments |
Argumentos con nombre para usar $nombre en el cuerpo |
disable-model-invocation |
true: solo tú puedes invocarla; su descripción no entra al contexto |
user-invocable |
false: solo Claude la invoca; no aparece en el menú / |
allowed-tools |
Herramientas que se aprueban sin preguntar durante el turno en que se invoca |
disallowed-tools |
Herramientas que se retiran mientras la skill está activa |
model |
Modelo para el resto del turno actual |
effort |
Nivel de esfuerzo: low, medium, high, xhigh, max, según el modelo |
context |
fork para ejecutarla en un subagente aislado |
agent |
Tipo de subagente cuando usas context: fork |
background |
Con context: fork, false para esperar el resultado en el mismo turno |
hooks |
Hooks que se registran al invocar la skill y siguen activos el resto de la sesión |
paths |
Patrones glob: Claude la carga automáticamente solo al trabajar con archivos que coincidan |
shell |
bash (por defecto) o powershell para los comandos !`...` |
metadata, license, compatibility |
Datos del estándar que Claude Code acepta pero no usa |
Dos reglas de formato que causan muchos dolores de cabeza:
- El
---de apertura debe estar en la primera línea. Con una línea en blanco antes, Claude Code trata todo como contenido. - Si el YAML no se puede interpretar, la skill carga sin ningún campo: se invoca con
/nombre, pero Claude no puede activarla por su descripción.
Portabilidad. Para subir una skill a claude.ai o usarla con la API de Skills, solo se admiten los seis campos del estándar: name, description, license, compatibility, metadata y allowed-tools; cualquier otro produce un error al empaquetar. El estándar pide además que name tenga de 1 a 64 caracteres en minúsculas, números y guiones, y coincida con el nombre de la carpeta.
Dos skills de Cobra Fácil
La primera es una skill de referencia: conocimiento que Claude aplica mientras trabaja. Vive en .claude/skills/convenciones-facturacion/SKILL.md:
---
name: convenciones-facturacion
description: Convenciones de código del módulo de facturación de cobra-api (CFDI 4.0). Aplica al crear o modificar código en app/facturacion, al armar XML de CFDI o al tocar catálogos del SAT.
paths:
- "app/facturacion/**"
- "tests/facturacion/**"
user-invocable: false
---
## Reglas del módulo
- Montos con Decimal y dos decimales al serializar; nunca float.
- RFC siempre en mayúsculas y validado antes de armar el XML.
- Toda función que arme un nodo del XML tiene una prueba en
tests/facturacion/ con un caso válido y uno inválido.
- Errores hacia el cliente: HTTP 422 con {"error": "...", "campo": "..."}.
Con paths, Claude solo la considera al trabajar en esos archivos. Con user-invocable: false, no aparece en el menú, porque no es una acción que alguien vaya a ejecutar.
La segunda es una skill de tarea, con argumentos con nombre. Vive en .claude/skills/nueva-migracion/SKILL.md:
---
name: nueva-migracion
description: Crea una migración de Alembic para cobra-api con su prueba de ida y vuelta.
argument-hint: "[tabla] [cambio]"
arguments: [tabla, cambio]
disable-model-invocation: true
allowed-tools: Bash(uv run alembic *) Bash(uv run pytest *)
---
Crea una migración de Alembic para la tabla $tabla con este cambio: $cambio
1. Ejecuta uv run alembic revision -m "<resumen en minúsculas>".
2. Escribe upgrade() y downgrade(). downgrade() debe dejar la tabla
exactamente como estaba.
3. Agrega en tests/migraciones/ una prueba que aplique upgrade y downgrade.
4. Ejecuta uv run pytest tests/migraciones y muestra el resultado.
Al ejecutar /nueva-migracion cobros "agregar columna referencia_spei varchar(30)", $tabla se reemplaza por cobros y $cambio por el texto entre comillas. Si un argumento con nombre no llega, queda como cadena vacía. Ojo con los montos: un $1.00 literal en el cuerpo se toma como argumento; escríbelo \$1.00.
Dónde vive una skill
| Ubicación | Ruta | Alcance |
|---|---|---|
| Empresa | .claude/skills/ dentro del directorio de configuración administrada |
Todos los usuarios de la organización |
| Personal | ~/.claude/skills/<nombre>/SKILL.md |
Todos tus proyectos en esta computadora |
| Proyecto | .claude/skills/<nombre>/SKILL.md |
Este repositorio; se comparte con Git |
| Anidada | <subcarpeta>/.claude/skills/<nombre>/SKILL.md |
Se carga cuando Claude trabaja con archivos de esa subcarpeta |
| Plugin | <plugin>/skills/<nombre>/SKILL.md |
Donde el plugin esté activo, como /plugin:nombre |
| Cuenta de claude.ai | Skills activadas en tu cuenta | Cowork, sesiones en la nube y terminal con esa cuenta |
Consecuencias prácticas para un equipo:
- Choques de nombre. Gana empresa sobre personal y personal sobre proyecto. Si Iván tiene una skill personal
deploy,/deployencobra-apiejecuta la suya, no la del repositorio. Las de plugin no chocan porque llevan prefijo. - Monorepos. Se cargan las skills del directorio donde arrancas y de los superiores hasta la raíz; las de subcarpetas inferiores, cuando Claude toca un archivo ahí.
- Sesiones en la nube. No leen tu
~/.claude/skills/; sube la skill al repositorio o actívala en tu cuenta. - Cambios en vivo. Los cambios en
SKILL.mdse detectan sin reiniciar. Si creas una carpeta de skills de primer nivel nueva, ejecuta/reload-skills.
Cómo se invoca
Claude la activa cuando tu pedido coincide con la descripción (salvo con disable-model-invocation: true), o tú escribes su nombre. La posición del nombre importa:
| Dónde escribes el nombre | Qué ocurre |
|---|---|
Al inicio del mensaje: /nueva-migracion cobros "..." |
Claude Code ejecuta la skill directamente |
Después de otro texto: oye, usa /nueva-migracion para esto |
No se ejecuta directo; cuenta como permiso y Claude decide según tu redacción |
También puedes apilar hasta seis skills al inicio de un mensaje; el texto final se pasa como argumentos a cada una.
Qué pasa después de invocarla
Es el detalle que más se ignora. El contenido de una skill invocada entra a la conversación como un solo mensaje y se queda en los turnos siguientes; Claude Code no vuelve a leer el archivo. El permiso de allowed-tools, en cambio, se borra con tu siguiente mensaje.
Al compactar, Claude Code vuelve a adjuntar la invocación más reciente de cada skill, pero solo sus primeros 5,000 tokens, con un presupuesto combinado de 25,000 que empieza por la más reciente. En sesiones largas, las skills más antiguas pueden desaparecer.
Tres hábitos se derivan de esto:
- Pon las reglas más importantes al inicio de
SKILL.md. - Escribe instrucciones que apliquen a toda la tarea ("corre las pruebas después de cada cambio"), no pasos de una sola vez.
- Si Claude deja de seguir una skill después de compactar, vuelve a invocarla.
Para depurar: /skills lista las skills y las ordena por tokens, claude --debug muestra errores de YAML y claude plugin validate .claude/skills revisa el frontmatter de todas las skills del proyecto.
Práctica
- Crea
convenciones-facturacion(o la equivalente de tu proyecto) conpathsyuser-invocable: false. - En una sesión nueva, pide un cambio fuera de esos patrones y luego uno dentro. Observa cuándo carga la skill.
- Crea
nueva-migracionconargumentsy pruébala con un valor que tenga espacios entre comillas. - Agrega una línea en blanco antes del
---inicial, revisa/skillsy corrígela. - Ejecuta
claude plugin validate .claude/skillsy corrige cualquier advertencia. - En
/skills, ordena por tokens y anota tus tres skills más costosas.
Resumen
- Una skill carga en tres niveles: metadatos siempre, cuerpo al activarse, recursos solo si hacen falta.
- La lista de descripciones tiene presupuesto (1% del contexto) y cada entrada se corta a 1,536 caracteres.
- Los campos del frontmatter deben escribirse exactos; los desconocidos se ignoran en silencio.
- Para portabilidad fuera de Claude Code, usa solo los seis campos del estándar.
- El contenido de una skill invocada se queda en la conversación, pero tras compactar solo sobreviven sus primeros 5,000 tokens.