Pont CLI Claude
L'app spawn le binaire claude en sous-processus et communique avec lui en stream-json bidirectionnel. Zéro appel à l'API Anthropic — la session Claude Max de Yann sert d'identité.
Les agents disponibles
Définis dans appsettings.json sous Elynav.Agents. Chaque agent correspond à un fichier .claude/agents/<name>.md qui contient son system prompt et ses outils autorisés.
| Agent | Rôle | Outils principaux |
|---|---|---|
| elynav-orchestrator | Chef d'orchestre — plan du jour, arbitrage priorités, rapports consolidés | Read, Write, MCP CRM |
| elynav-sdr | Sales Development — sourcing ICP, enrichissement, séquences outbound | WebSearch, WebFetch, MCP CRM |
| elynav-cmo | CMO — stratégie messaging, calendrier éditorial, validation | Read, Write, MCP CRM |
| elynav-content | Content Producer — articles, posts, newsletters à partir des briefs CMO | Read, Write, MCP CRM |
| elynav-dev-proposer | Dev senior reviewer — audite code, propose des fix sous forme de diff (read-only sur prod) | Read, Grep, Glob, Write (proposals only) |
| elynav-dev-executor | Dev senior — applique diffs validés (pair-programming, branche dédiée, validation avant push) | Tous outils (mode bypassPermissions en local) |
Cycle de vie d'un ClaudeCliRunner
Le runner persiste entre les messages d'une même conversation. Le sous-processus claude tient l'état conversationnel en mémoire jusqu'à StopAsync().
Arguments CLI assemblés
Construits par ClaudeCliRunner.StartAsync() à partir de la AgentDefinition :
claude
--print
--agent <name>
--input-format stream-json
--output-format stream-json
--verbose
[--mcp-config /path/.mcp.json] # si fichier détecté dans le cwd
[--permission-mode bypassPermissions] # si défini sur l'agent
Modes de permission
default
Confirmations interactives. En --print non-interactif, bloque les Write/Bash non allowlistés. Mode utilisé par tous les agents en prod containerisée.
acceptEdits
Auto-accept des Write/Edit. Bash reste sous allow-list. Compromis raisonnable pour des agents qui ne font que de l'édition de fichiers.
bypassPermissions
Aucune vérification. Refusé en root par le CLI — donc inutilisable dans le conteneur Docker actuel (qui tourne en root). Réservé au pair-programming local.
plan
Read-only. L'agent peut proposer des changements mais pas les appliquer. Utile pour audit.
Parsing du flux stream-json
PumpStdoutAsync lit ligne par ligne, parse chaque ligne en JSON, dispatche en AgentEvent typé selon le champ type :
Les events sont écrits dans un Channel<AgentEvent> unbounded, et lus par les hubs SignalR qui les relaient au client Blazor pour rendu progressif.
MCP servers — accès CRM
Les agents lisent et écrivent dans la base SQLite via les MCP servers Node du dossier Salesforce/mcp-servers/, déclarés dans .mcp.json. L'app .NET n'expose pas de wrapper — elle laisse le CLI parler aux MCP servers en son nom.
Pourquoi ? Cela évite de dupliquer la logique d'accès CRM en C#. Les MCP servers Node sont la source de vérité unique pour search_accounts, create_contact, log_activity, etc.