Créer des skills

Guide pas à pas pour ajouter une nouvelle expertise à ton projet Arc OS.


Avant d'écrire un nouveau skill — consulte la bibliothèque globale

Arc OS est livré avec plus de 40 skills génériques dans skills/ couvrant les rôles courants. Avant d'en écrire un nouveau, vérifie si un existant couvre ton besoin :

Domaine Skills disponibles
Ingénierie commit-discipline, tdd-flow, react-best-practices, postgres-patterns, mcp-builder
Frontend / Design frontend-design-principles, svg-graphics, slide-deck-html, service-design, scss-modular-architecture, responsive-mobile-first
Ops de startup market-analysis, gtm-strategy, financial-modeling, pitch-deck, customer-development, fundraising, founder-brand, metrics-dashboard, legal-startup
Marketing seo-foundations, founder-brand
Process standup-aggregator, commit-discipline
Base de données postgres-patterns

Parcours la liste complète : GET /api/crm/skills?category=<X> ou bun -e "console.log(JSON.stringify(require('./skills/_registry.json').skills.map(s=>s.name),null,2))".

Skill = déclenché par trigger, pas toujours actif

Un skill s'auto-injecte dans le prompt du worker quand le message correspond à ses triggers (dans _registry.json). Le champ description est la logique de trigger (« quand l'utiliser »), pas un résumé. Le Context Router choisit le top-5 des correspondances par message.


Qu'est-ce qu'un skill

Un skill est un jeu d'instructions portable qui enseigne une capacité spécifique à ton bot IA. Les skills vivent dans le répertoire skills/ et se composent de :

skills/
├── _registry.json              ← Central registry
├── my-new-skill/
│   ├── skill.md                ← What the AI should do
│   ├── my-new-skill.evals.json ← How to validate the output
│   └── references/             ← Context documents
└── library/
    └── domain-expert.md        ← Simple single-file skills

Étape 1 : Écris skill.md

C'est l'instruction principale. Claude la lit quand le skill est activé.

Modèle

# Skill Name

## Purpose
What this skill accomplishes in one sentence.

## When to Use
- Trigger condition 1
- Trigger condition 2

## Protocol
1. First action
2. Second action
3. Third action

## Output Format
What the response should look like.

## Constraints
- What NOT to do
- Safety boundaries

Recommandations

Exemple : Odoo Expert

# Odoo Expert

## Purpose
Odoo ERP module development: models, views, security, QWeb templates.

## When to Use
- Building or modifying Odoo modules
- Writing QWeb templates
- Configuring access rules and record rules
- Working with the ORM (create, write, search, browse)

## Protocol
1. Check if modifying an existing module or creating new
2. Follow Odoo 17 conventions (manifest, models/, views/, security/)
3. Use self.env['model.name'] for ORM operations
4. Always use _t() or t-call for translatable strings
5. Test with --test-tags after changes

## Constraints
- Never use cr.execute() for direct SQL — use ORM
- Never use sudo() unless security context explicitly requires it
- No inline JavaScript in QWeb templates

Étape 2 : Écris les evals (règles de qualité)

Les evals sont des règles déclaratives qui valident automatiquement chaque réponse. Elles s'exécutent après que Claude a généré sa sortie et ajoutent des notes d'avertissement si des règles échouent.

Nommage des fichiers

skills/<name>/<name>.evals.json

Schéma

{
  "version": 1,
  "skill": "my-new-skill",
  "rules": [
    {
      "id": "ms-001",
      "name": "Human-readable rule description",
      "type": "rule_type",
      "value": "for string/length types",
      "pattern": "for regex types",
      "severity": "warning"
    }
  ]
}

Types de règles disponibles

Type Ce qu'il vérifie Champ utilisé
string_contains La réponse inclut un texte littéral value (string)
string_not_contains La réponse n'inclut PAS un texte value (string)
regex_match La réponse correspond à une regex pattern (string)
regex_not_match La réponse ne correspond PAS à une regex pattern (string)
max_length Longueur de la réponse <= N caractères value (number)
min_length Longueur de la réponse >= N caractères value (number)

Niveaux de sévérité

Exemple

{
  "version": 1,
  "skill": "odoo-expert",
  "rules": [
    {
      "id": "oe-001",
      "name": "Must use ORM, not raw SQL",
      "type": "string_not_contains",
      "value": "cr.execute",
      "severity": "warning"
    },
    {
      "id": "oe-002",
      "name": "Must use translation helpers",
      "type": "regex_match",
      "pattern": "_t\\(|t-call|t-esc",
      "severity": "warning"
    },
    {
      "id": "oe-003",
      "name": "Response under 5000 chars",
      "type": "max_length",
      "value": 5000,
      "severity": "info"
    }
  ]
}

Astuces


Étape 3 : Enregistre dans _registry.json

Le registry informe le Context Router de ton skill pour qu'il puisse être recommandé sur les messages pertinents.

Ajoute une entrée

{
  "name": "my-new-skill",
  "description": "One sentence (shown in SKILLS_HINT, max 80 chars).",
  "triggers": ["direct-command", "explicit-request", "пряма команда"],
  "keywords": ["broader", "semantic", "related-term"],
  "agents": ["rick"],
  "category": ["complex"],
  "phase": "21.5"
}

Triggers vs Keywords

Triggers (2 points chacun) : Signaux d'invocation directe. L'utilisateur veut explicitement ce skill.

Keywords (1 point chacun) : Termes plus larges qui suggèrent la pertinence sans être des commandes.

Recommandations


Étape 4 : Skills de bibliothèque (format simple)

Pour une expertise de domaine qui n'a pas besoin d'evals ni d'un répertoire dédié, utilise skills/library/ :

skills/library/
├── docker-ops.md
├── postgres-pro.md
└── react-patterns.md

Ce sont des fichiers .md uniques. Pas de répertoire, pas d'evals, pas de références. Bien pour les skills riches en connaissances et légers en validation.


Checklist


Ce qui se passe au runtime

1. Bot starts → loadRegistry() reads _registry.json
                 loadEvals() reads all .evals.json files
                 loadLearnings() reads learnings.md

2. Message arrives → routeContext() scores skills → SKILLS_HINT injected
                     formatForPrompt() adds LEARNINGS block

3. Claude responds → checkOutput() runs eval rules
                     formatEvalWarnings() appends footnotes

4. Fix It / thumbs-down → addLearning() writes to learnings.md
                          qualityTracker logs feedback

5. Nightly → findUnderperformingSkills() checks metrics
             Proposals sent to CEO for approval

Semer des skills dans la DB globale

Les skills en DB (table skills_global) sont la SSOT du Context Router. Le fichier sur disque est la source de vérité pour le contenu ; la DB est l'index rapide pour le matching + l'auto-injection. Ils se synchronisent via des scripts de seeding.

Seeder générique par catégorie

# Reads skills/_registry.json, filters by category, upserts skills_global rows.
# Idempotent + drift-aware (skip if no change, update on content drift).
bun scripts/seed-skill-category.ts --category engineering
bun scripts/seed-skill-category.ts --category frontend
bun scripts/seed-skill-category.ts --category marketing

Fonctionne pour toute catégorie présente dans _registry.json. Prend la première catégorie du tableau comme valeur de colonne DB.

Seeders spécifiques

Quand l'exécuter

Vérification

sqlite3 data/citadel.db "SELECT name, category, owner_project FROM skills_global ORDER BY id"

owner_project = NULL → global (visible par tous les projets). owner_project = 'my-project' → projet uniquement (ce projet seulement).


Skills projet-uniquement vs globaux

Type de skill owner_project Cas d'usage
Global (template) NULL Méthodologie générique (TDD, Conventional Commits, AARRR) — utile pour tout projet
Projet uniquement '<project-name>' Documents spécifiques à NOTRE codebase (ex. crm-api-reference ne vit que dans arc-v2)

Déplace un skill existant en projet-uniquement :

sqlite3 data/citadel.db "UPDATE skills_global SET owner_project='my-project' WHERE name='internal-api-docs'"

Le filtre listForProject cadre la visibilité : les autres projets ne verront pas un skill projet-uniquement.