← Retour aux projets

PetForge

Live · npm v3.6.0

Couche RPG local-first pour Claude Code — pet ASCII déterministe qui évolue à partir de l'activité de codage réelle (5 hooks officiels, 6 phases, 46 achievements médaillés, 19 espèces, collecteur OTel intégré, web view PWA mobile). Shippé sur npm en 2 jours / 64 commits / 9 releases.

FR EN
46 Achievements
19 Espèces
6 Phases
5 Hooks Claude
313 Tests
~9.6K Lignes TS

Pourquoi j'ai construit ça

Anthropic a livré Claude Buddy en avril 2026 — un tamagotchi terminal natif dans Claude Code, avec 18 espèces, 5 raretés, 5 stats. Brillant produit. Mais il s'arrête là : pas de niveaux, pas d'évolution, pas de progression. La communauté demande ça sur GitHub dès la première semaine. Personne ne livre. J'ai vu un gap structurel — pas cosmétique — et j'ai construit la couche manquante. PetForge n'est ni un fork, ni une extension, ni une copie : c'est un moteur indépendant qui peut afficher Buddy quand il est là, et générer son propre pet quand il ne l'est pas. 64 commits / 9 releases publiques en 2 jours calendaires, shippé sur npm comme `@mindvisionstudio/petforge`.

Décisions techniques structurantes

01
Local-first absolu, hardening cross-platform inhabituel

Tout l'état tient dans ~/.petforge/state.json (file-locké via proper-lockfile sur sentinelle dédiée, écriture atomique tmp+fsync+rename). Zéro telemetry, zéro account, zéro phone-home. Hardening Windows-specific : retry EPERM/EBUSY/ENOENT/EACCES sur fs.rename (Defender, OneDrive, indexeurs) avec backoff exponentiel 50/150/400 ms, max 4 tentatives sous le timeout 1s du hook. Recovery silencieuse : un state.json corrompu est sauvegardé en .corrupt.<ts>.json puis recréé — un hook ne crashe jamais Claude Code.

02
Trademark-clean by design + Buddy integration consensuelle

Pas un seul "claude" ou "buddy" dans le nom du package, du repo, du CLI, ou des assets. Buddy invoqué uniquement en runtime via `claude /buddy card` (= lecture stdout publique). L'intégration `petforge buddy import` parse une carte ASCII Anthropic depuis stdin/fichier, strip-out les lignes de stats pour éviter les doublons, et stocke le visuel localement sans redistribution. Aucun scraping, aucun fetch automatique, aucune copie de fichier interne.

03
Engine PetForge core + collecteur OTel custom + PWA mobile

L'engine déterministe est le produit (19 espèces × 6 phases × 5 raretés × shiny = 570 combinaisons visuelles). Au-delà : collecteur OTLP/HTTP/JSON daemon `petforge collect` qui ingère les métriques officielles Claude Code (code.lines.added, tokens.in/out, cost.usd, pull_request.created…) et débloque 12 achievements gated sur la qualité réelle de la session (Code Architect 10K, Cache Lord ≥80 %, Frugal Coder 100p ≤ $1). Web view single-file (`page.ts`, 1 033 L de HTML+CSS+JS dans un template literal) servie en SSE temps réel + manifest PWA installable mobile.

04
2 pivots stratégiques v1 → v2 → v3 + 9 versions publiques en 2 jours

v1 : sprites + extension VS Code (rejeté — friction install, audience trop restreinte). v2 : RPG layer over Buddy (rejeté après revue licence + risque de dépendance directe). v3 (livré) : engine standalone, Buddy en option, Apache 2.0 trademark-clean. Trois itérations de design avant la première ligne de code, puis 9 releases npm en 2 jours (v1.0, v1.1, v1.2, v2.0, v2.0.1, v2.0.2, v2.1, v3.0, v3.1, v3.2, v3.3, v3.4) — capacité d'itération rapide démontrée. Pas de dette : 0 erreur TS, 1 `any` sur 9 596 lignes, biome clean.

Le challenge non-trivial

Construire au-dessus d'un produit Anthropic sans se faire absorber, copier, ou bloquer

Trois risques en parallèle : (1) Anthropic ship la même feature (medium probability, low impact si l'engine PetForge est core et Buddy juste optionnel) ; (2) Buddy se déprecate ou change son format (mitigé — Buddy détecté en runtime, fallback silencieux) ; (3) plainte trademark si on flirte avec Buddy/Claude dans le naming ou si on copie des assets (very low probability, critical impact — couvert par la séparation absolue : zéro mot Anthropic, zéro asset copié, runtime invoke uniquement). Le vrai challenge n'est pas technique, c'est juridique-stratégique : trouver le bon découpage qui te laisse exister sans dépendre, copier, ou provoquer. Plus le challenge cross-platform : faire tenir 5 hooks Claude Code en sub-50ms sans bloquer le workflow utilisateur, sur Windows où Defender hold parfois state.json post-write.

Leçon retenue

Build on top of validated concepts when the gap is structural, not cosmetic. Buddy a validé l'appétit pour un compagnon terminal — la communauté a déjà voté avec ses GitHub issues sur ce qu'il manque. Construire la couche manquante avec un vrai produit indépendant est plus défensif (pas une extension Anthropic à leur merci) et plus enseignant (la spec a été refaite trois fois pour minimiser la dépendance) que d'attendre qu'ils livrent eux-mêmes. Le shipping en 2 jours / 9 releases ne se fait pas sans le `Spec → Plan → Blitz → Polish` : 5 specs design + 6 plans d'implémentation existaient AVANT le premier commit.

Fonctionnalités

🥚
6 phases d'évolution

Egg → Hatchling → Junior → Adult → Elder → Mythic, déclenchées par seuils de niveau

🏆
46 achievements médaillés

13 familles bronze/silver/gold (+platinum sur streak), backfill idempotent, 12 OTel-gated

🐣
19 espèces déterministes

Octopus, Dragon, Capybara, Axolotl… seed = SHA-256(user + host), buckets de rareté 60/25/10/4/1 %

🪝
5 hooks Claude Code

UserPromptSubmit, PostToolUse, Stop, SessionStart, SessionEnd — sub-50ms, jamais bloquant

📊
Collecteur OTel custom

OTLP/HTTP/JSON daemon (port 7879, bind 127.0.0.1) — ingest cumulative-delta, fan-out Datadog/Honeycomb

📱
Web view PWA mobile

`petforge serve` + SSE + manifest + icône 512×512 — installable depuis Safari/Chrome mobile

🔒
100% local

État ~/.petforge/state.json file-locké, atomic writes, retry EPERM Windows, recovery silencieuse

🎨
Buddy integration consensuelle

`petforge buddy import` parse une carte ASCII Anthropic — visuel local, zéro redistribution, zéro scraping

Stack technique

Runtime
Node 20+TypeScript 5.9 stricttsup 8.5
CLI / TUI
Ink 7 (React 19.2)figlet 1chalk 5
État
proper-lockfile 4.1JSON atomiqueZod 4.4
Observabilité
OTLP/HTTP/JSON customCumulative-delta aggFan-out forward
Tests / CI
Vitest 4.1 (313 tests)Biome 2.4GitHub Actions
Distribution
npm public@mindvisionstudio/petforgeApache 2.0