14 KiB
14 KiB
issueRef, version, updatedBy, updatedAt
| issueRef | version | updatedBy | updatedAt | ||||
|---|---|---|---|---|---|---|---|
| #302 | 5 |
|
1788990131498 |
Carnet #302 - MCP tools plugin non visibles par l'agent cible
Signalement
- Date: 2026-09-09.
- Projet utilisateur mentionné:
UnitySOundTool. - Plugin mentionné: Unity fait par
UnityPlugin. - Agent cible:
Maindu projet UnitySOundTool. - Tool attendu:
unity_detect_project.
Observation capture
- L'agent répond qu'il voit des workflows Unity côté IdeA (
unity-test-runner,unity-project-diagnostics, etc.). - Il ne voit pas de tool MCP Unity direct.
- Une recherche explicite de
unity_detect_projectdans les tools disponibles/différés retourne0 tools. - Les tools disponibles visibles dans la session concernent surtout IdeA, Sites, document control et hotline, pas Unity Editor.
Hypothèses initiales à vérifier
- Le plugin expose bien des skills/workflows mais pas de serveur MCP/tool dans son manifeste effectif.
- Les MCP tools du plugin sont installés mais non ajoutés aux permissions MCP de l'agent ou non propagés à la session lancée.
- Les tools ont été ajoutés après démarrage et nécessitent restart/reload de l'agent ou du plugin.
- La source de deferred tools consommée par
tool_searchne fusionne pas les MCP tools issus de plugins personnels/projet. - Le contexte/capability summary liste les skills Unity mais pas les MCP tools, ce qui suggère une divergence entre capabilities manifestées et tools réellement exposés.
Cadrage Architect
Architect a confirmé que les skills plugin et les MCP tools plugin sont deux flux distincts. Les workflows Unity visibles prouvent seulement que les contributions skills du plugin sont résolues et injectées.
Flux à vérifier:
- Manifeste plugin:
contributes.mcpServers[],autoStart: true,server.id,command,toolsincluantunity_detect_project.crates/domain/src/plugin.rscrates/application/src/plugin/mod.rs
- Reconciliation serveur MCP plugin:
active_mcp_specsne démarre que les pluginsruntime_activeet serveursauto_start, puis passe les specs auPluginMcpSupervisor.crates/application/src/plugin/mod.rscrates/infrastructure/src/plugin/mod.rs
- Affectation agent: l'UI persiste un
PluginToolRef { pluginId, serverId, toolName }viaplugin_assign_agent_tooldansProjectPluginSettings, pas dans.ideai/mcp-tool-permissions.json.crates/application/src/project_plugin.rscrates/backend/src/dto.rsfrontend/src/features/permissions/McpToolPermissionsPanel.tsx
- Session runtime agent: point suspect principal. Le lancement semble matérialiser surtout le serveur MCP
ideadans la config runtime ([mcp_servers.idea]/.mcp.json) sans consommerassignments.toolsplugin pour ajouter les serveurs MCP Unity au run dir de l'agent.crates/application/src/agent/lifecycle.rscrates/backend/src/lib.rs
- Catalogue
tool_search/ deferred tools: pour OpenAI/direct,tools_for_contextsemble renvoyer seulement le catalogue MCP IdeA natif filtré par policy, pas les tools métier plugin.crates/backend/src/openai_tools.rscrates/infrastructure/src/orchestrator/mcp/tools.rs
Contrat attendu:
- Une affectation
PluginToolRefà un agent doit avoir un effet runtime vérifiable au prochain démarrage/restart de cet agent. - Pour les profils via client MCP (Codex/Claude/OpenCode), matérialiser les serveurs MCP plugin assignés dans la config de session agent avec un nom stable.
- Pour OpenAI/direct/deferred tools, étendre
ToolInvoker::tools_for_contextetcallou introduire un provider dédié, sinontool_searchrestera aveugle. - Ne pas ajouter naïvement ces tools au catalogue MCP IdeA natif tant qu'IdeA n'est pas proxy MCP dynamique.
Responsables
- DevBackend en premier: propagation affectation plugin -> session runtime / catalogue provider.
- DevFrontend seulement si l'UI affiche une affectation comme effective alors qu'un restart est requis, permet de cocher un tool dont le plugin/server n'est pas actif, ou mélange catalogue manifeste et disponibilité runtime.
- QA: reproduction avec plugin MCP minimal ou Unity, vérifier visibilité et appelabilité du tool.
Critères QA proposés
- Installer/activer un plugin test avec serveur MCP stdio
autoStart: trueexposantunity_detect_project. - Assigner le tool à
Main. - Redémarrer l'agent si le contrat reste prise en compte au lancement.
- Chercher explicitement
unity_detect_projectdans la session Main via tools disponibles/différés. - Vérifier tool visible et appelable.
- Agent sans affectation ne voit pas le tool.
- Plugin désactivé/serveur en erreur: tool absent ou état clair, pas de faux positif.
- Permissions MCP natives IdeA continuent de filtrer
idea_*sans pollution parPluginToolRef.
Implémentation DevBackend — 2026-09-09
Cause confirmée:
ProjectPluginSettings.assignments.toolsétait correctement persisté dans.ideai/project-plugins.jsonparMutateAgentPluginTool.- Le launcher partageait le resolver des skills plugin, mais ne consommait jamais les
PluginToolRef; les configs de session ne contenaient donc que le serveur MCP natifidea.
Correctif:
ProjectPluginResolver::assigned_mcp_serversprojette les affectations de l'agent en specs stdio uniquement lorsque le plugin est activé pour le projet, runtime-active, installé, et que le serveur assigné estautoStart.- Les variables
${pluginRoot}et${appDataDir}sont résolues comme dans la réconciliation globale des serveurs plugin; les serveurs sont dédupliqués par(pluginId, serverId). - Nom de session stable et sans collision:
idea_plugin__<plugin-id encodé>__<server-id encodé>. - Au lancement/restart, le launcher matérialise les serveurs pertinents dans:
- Claude:
.mcp.json, puisenabledMcpjsonServersdans.claude/settings.local.json; - Codex:
.codex/config.tomlsousmcp_servers; - OpenCode local/cloud: bloc
mcpdansopencode.json.
- Claude:
- Un restart interne sans
McpRuntimeconserve le wiring réelideadéjà écrit et ne réconcilie que les entrées plugin gérées. Les entrées plugin devenues obsolètes sont retirées. - Les racines
cwd/commande des serveurs assignés sont ajoutées en lecture au plan Landlock quand un plan existe, pour que le processus plugin puisse réellement lire son package. - Aucun changement dans
.ideai/mcp-tool-permissions.jsonni dans le catalogue natifidea_*.
Fichiers modifiés:
crates/domain/src/plugin.rscrates/application/src/project_plugin.rscrates/application/src/agent/lifecycle.rscrates/backend/src/lib.rs.ideai/tickets/302/carnet.md
Chemin OpenAI/direct/deferred:
- Le symptôme Main/Codex n'utilise pas
AppOpenAiToolInvoker::tools_for_context: Codex consomme son client MCP natif et sontool_searchdécouvre les serveurs déclarés dans leCODEX_HOMEisolé. OpenAiCompatibleSession, en revanche, continue à ne recevoir que les tools locauxidea_*. Le superviseur plugin actuel ne possède pas de client JSON-RPC (tools/list/tools/call), seulement des handles de processus; rendre les tools métier plugin appelables par ce chemin nécessite un provider/client MCP dédié. Ce gap ne bloque pas la correction du cas signalé et n'a pas été contourné en polluant le catalogue natif.
Tests et vérifications exécutés:
cargo test -p application --lib— 178 passés.cargo test -p application --test agent_lifecycle— 111 passés.cargo test -p domain plugin --lib— 7 passés.cargo check -p backend— OK.cargo check -p app-tauri— OK.cargo fmt --allpuisgit diff --check— OK.
Tests ciblés ajoutés:
- matérialisation d'un serveur assigné dans les trois formats Claude/Codex/OpenCode;
- conservation du wiring
idearéel lors d'un restart interne et suppression des entrées plugin obsolètes; - stabilité et absence de collision du nom MCP client;
- conservation des clés/tables Codex non gérées lors de la réconciliation.
Validation QA — 2026-09-09
Verdict: VERT.
Inspection:
- Diff relu sur
crates/application/src/project_plugin.rs,crates/application/src/agent/lifecycle.rs,crates/domain/src/plugin.rs,crates/backend/src/lib.rs. - Le correctif ne modifie pas
.ideai/mcp-tool-permissions.jsonet ne projette pas les tools plugin dans le catalogue natifidea_*; il matérialise des serveurs MCP plugin assignés dans les configs de session Claude/Codex/OpenCode. - Gap
OpenAiCompatibleSession: confirmé comme non bloquant pour le symptôme utilisateur décrit, car le cas Main/Codex passe par client MCP natif etCODEX_HOMEisolé. À suivre séparément si un profil OpenAI/direct doit appeler directement les MCP tools plugin.
Couverture QA ajoutée:
project_plugin::tests::assigned_mcp_servers_project_assigned_active_autostart_server_only- vérifie qu'un
PluginToolRefassigné produit unPluginMcpServerSpecunique, avec nom stableidea_plugin__..., substitution${pluginRoot}/${appDataDir}, commande relative résolue sous le package plugin, env/cwd corrects.
- vérifie qu'un
project_plugin::tests::assigned_mcp_servers_omits_unassigned_disabled_and_non_autostart_servers- vérifie l'absence quand le serveur n'est pas assigné, quand le plugin est désactivé au niveau projet, quand il est désactivé globalement, ou quand le serveur assigné n'est pas
autoStart.
- vérifie l'absence quand le serveur n'est pas assigné, quand le plugin est désactivé au niveau projet, quand il est désactivé globalement, ou quand le serveur assigné n'est pas
Commandes exécutées et résultats:
cargo test -p application --lib assigned_mcp_servers- OK: 2 passed; 0 failed; 178 filtered out.
cargo test -p application --lib plugin_server- OK: 5 passed; 0 failed; 175 filtered out.
cargo test -p application --lib- OK: 180 passed; 0 failed.
cargo test -p application --test agent_lifecycle- OK: 111 passed; 0 failed.
cargo test -p domain plugin --lib- OK: 7 passed; 0 failed.
cargo check -p backend- OK:
Finished dev profile.
- OK:
cargo check -p app-tauri- OK:
Finished dev profile.
- OK:
cargo fmt --all -- --check- OK après formatage des tests QA ajoutés.
git diff --check- OK.
Tentatives remplacées:
- Deux commandes
cargo testavec plusieurs filtres positionnels ont échoué sur erreur d'usage Cargo (unexpected argument ...). Elles ont été remplacées parcargo test -p application --lib,cargo test -p application --lib plugin_serveretcargo test -p application --test agent_lifecycle, toutes vertes.
Conclusion:
- Serveur MCP plugin assigné: injecté au lancement/restart dans les formats client visés avec un nom stable et sans collision.
- Serveur non assigné/désactivé/non-autoStart: non injecté.
- Serveur MCP natif
idea: conservé, y compris au restart interne sans runtime, et non pollué par les entrées plugin. - Aucun finding bloquant.
Topologie Git — 2026-09-09
QA reconfirmée par Git avant commit (exécution réelle):
rustup run stable cargo fmt --all -- --check— OK.git diff --check— OK.cargo test -p application --lib— 180/180.cargo test -p application --test agent_lifecycle— 111/111.cargo test -p domain plugin --lib— 7/7.cargo check -p backend— OK.cargo check -p app-tauri— OK.
Commit du correctif (4 fichiers uniquement, bookkeeping exclu):
- Branche:
fix/302-plugin-mcp-tools-not-visible. - Commit:
78b379a—fix(application,domain,backend): les serveurs MCP des plugins assignés atteignent la session de l'agent — #302. - Fichiers:
crates/domain/src/plugin.rs,crates/application/src/project_plugin.rs,crates/application/src/agent/lifecycle.rs,crates/backend/src/lib.rs. - Exclus (hors périmètre, restés en worktree):
.ideai/tickets/296/*,.ideai/tickets/299-302/*,counter.json,index.json,.ideai/attachments/,scripts/.
Merge local:
develop← merge--no-ffdefix/302-plugin-mcp-tools-not-visible→ commit9e9498b.- develop n'avait pas divergé depuis la création de la branche (fast-path, contenu identique à
78b379a). - Branche
fix/302-plugin-mcp-tools-not-visibleconservée (convention du dépôt, pas de suppression). - Aucune action distante (aucun push; develop reste en avance locale sur
origin/develop).
Restants hors topologie:
- Gap
OpenAiCompatibleSession/tools_for_context(tools plugin non appelables en direct) — ticket séparé à ouvrir si besoin. - Validation live du symptôme UnitySOundTool depuis l'app installée: nécessite un rebuild AppImage (commit dédié + tag
vx.y.zselon convention, incrémentysur develop).
Rebuild AppImage — 2026-09-09
Rebuild exécuté par Main depuis develop @ 9e9498b (incluant le merge #302):
- Commandes:
npm --prefix frontend run buildOK, puis depuiscrates/app-tauri:mkdir -p /tmp/idea-cargo-home && CARGO_HOME=/tmp/idea-cargo-home APPIMAGE_EXTRACT_AND_RUN=1 NO_STRIP=1 ../../frontend/node_modules/.bin/tauri build --bundles appimageOK. - Artefact:
target/release/bundle/appimage/IdeA_0.3.0_amd64.AppImage, 119699960 octets, sha256d016aab3b643bab61a1ab864a4b5f5e5ab57ff1c493f12d1002918efa5c08c33(vérifié par Git).
Traçabilité Git:
- Commit dédié
--allow-empty(l'artefact vit soustarget/gitignoré):3911ce1surdevelop—chore(appimage): rebuild AppImage develop — commit dédié v0.44.0 #302. - Tag annoté
v0.44.0posé sur3911ce1(convention respectée:yincrémenté pour un rebuild committé sur develop, v0.43.0 -> v0.44.0). - Bookkeeping carnet/index/counter et fichiers hors périmètre exclus, restés en worktree. Aucun push.
Restant après rebuild:
- Validation live UnitySOundTool depuis l'app installée (v0.44.0):
unity_detect_projectvisible et appelable par Main après restart de l'agent, agent sans affectation ne voit pas le tool.