Un dev squad Claude Code à 5 personas.
DevSwarm est un serveur FastMCP qui orchestre cinq sessions persistantes de personas Claude Code (Architect, Researcher, Frontend, Backend, Reviewer-Deployer) pour transformer un prompt en une pull request. Fire-and-forget : lancez-le d'un seul appel MCP, fermez le portable, réveillez-vous devant une PR. Pas de Docker, pas de daemon, pas de port ; juste des fichiers sur disque et MCP en stdio. Construit de bout en bout sur un serveur Fedora en une seule après-midi.
Une idée à 23 h. Une pull request au matin.
Une session Claude Code unique est déjà un ingénieur capable. Mais elle travaille une chose à la fois (lire, planifier, coder, relire) dans la même fenêtre de contexte, avec les mêmes priorités, sur la même horloge que l'humain qui tape devant elle. DevSwarm est une petite expérimentation pour partager ce travail entre des agents spécialisés persistants qui s'échangent des fichiers sur disque, tournent dans leurs propres sessions et n'ont besoin de personne pour regarder.
L'état final que je voulais : vous avez une idée tard le soir, vous la dites une fois, et vous vous réveillez devant une pull request à lire, accepter ou renvoyer. Pas de babysitting. Pas de « le swarm s'est coincé trois étapes plus loin ». L'orchestrateur se détache de l'appelant ; l'état vit dans un fichier JSON sur disque ; vous pouvez fermer le terminal et revenir le lendemain matin.
Des fichiers purs sur disque, plus MCP en stdio.
Le serveur MCP est un seul fichier Python. Chaque persona est une vraie session claude épinglée à un UUID et reprise par sous-processus. Le runner est un processus détaché (start_new_session=True) qui parcourt cinq étapes, sérialisant l'état dans .swarm_state.json après chacune. Frontend et Backend tournent en threads parallèles. Pas de daemon, pas de port, pas de conteneur.
Vous (terminal, lunettes, partout où Claude Code tourne)
↓ appel MCP : devswarm.start_project(idea, repo_url)
┌────────────────────────────────────┐
│ devswarm_mcp.py (FastMCP, stdio) │ ← lancé à la demande
└─────────────┬──────────────────────┘
↓ subprocess.Popen(start_new_session=True)
┌────────────────────────────────────┐
│ runner.py (détaché, PPID=1) │ ← survit à la mort du MCP
└─────────────┬──────────────────────┘
↓ pour chaque étape : claude --resume <uuid> -p ...
┌──────┴──────┬──────────┬──────────┬──────────────┐
↓ ↓ ↓ ↓ ↓
Architect Researcher Frontend Backend Reviewer-
→ PLAN.md → RESEARCH → code → code Deployer
.md dans fe/ dans be/ → REVIEW.md
→ gh pr create
↓
l'état vit dans workspace/<id>/.swarm_state.json
vérifiable à tout moment via get_project_status(id) Cinq sessions, cinq jeux d'outils.
Chaque persona est une session Claude Code distincte vivant dans son propre répertoire de travail, avec son propre system prompt CLAUDE.md et sa propre allow-list d'outils settings.json. L'isolation d'outils est appliquée durement au niveau des settings, pas seulement promise dans le prompt.
devswarm/<id>, committe, pousse et ouvre une PR via gh pr create. La seule persona avec accès en écriture sur GitHub.4 minutes 42 secondes, un prompt vers une PR.
Premier test live de bout en bout, sans édition humaine : un CV d'une page avec bascule mode sombre, fondu au défilement et respect de prefers-reduced-motion. Chaque étape a réussi du premier coup.
Ci-dessous : l'index.html exact que le swarm a écrit, rendu en direct. Essayez le commutateur de thème en haut à droite du cadre, faites défiler pour voir l'animation de fondu se déclencher sur chaque section.
/projects/cv-onepager-artifact.html, mot pour mot depuis la sortie de l'espace de travail du swarm. Voir la PR ↗
Honnête sur ce qu'il y a dans la boîte.
- Langage
- Python 3.14, serveur FastMCP écrit à la main en ~260 lignes (
devswarm_mcp.py) plus le runner (runner.py) plus les utilitaires d'état partagé (swarm_state.py). - Modèle d'agent
claude-opus-4-7sur les cinq personas. Sessions persistées en JSONL sous~/.claude/projects/<encoded>/<uuid>.jsonl, reprises viaclaude --resume <uuid> -p ....- Isolation d'outils
- Un
.claude/settings.jsonpar persona avec des motifs allow/deny explicites. Frontend/Backend durement bloqués degit push,gh pr, toutes les écrituresmcp__github__*. Écritures Notion refusées pour chaque persona. - Concurrence
- Python
threadingpour l'étape parallèle Frontend + Backend. Les écritures d'état utilisent des noms de fichiers tmp uniques et un verrou à l'échelle du processus, pour que le read-modify-write dansupdate_stagene perde aucune mise à jour. - Déploiement
- Reviewer-Deployer utilise la CLI
ghavec l'auth existante de l'utilisateur. L'URL de la PR est écrite dans.pr_urldans l'espace de travail ; le runner la récupère et la fait apparaître dansget_project_status. - Source
- Pas encore sur un repo public ; gardé local pendant que l'API se stabilise. Atterrira probablement sur
github.com/tomscholtes93-collab/devswarmune fois que quelques capstones supplémentaires passeront proprement.