AI Agent entity form should reject machine names that collide with existing code-plugin IDs
Project: AI Agents\
Component: Code\
Version: 1.4.x\
Issue type: Bug
**Problem/Motivation**
AiAgentManager merges two types of plugin definitions under a single ID namespace:
1. Code-defined AiAgent plugins discovered via parent::findDefinitions().
2. ai_agent config entities, merged in by AiAgentManager::findDefinitions() at src/PluginManager/AiAgentManager.php:196.
When an admin saves an ai_agent config entity with a machine name that matches an existing code-plugin ID, two failure modes occur:
1. The config entity is silently dropped from plugin discovery — the merge in findDefinitions() uses if (!isset(definitions\[id\])), so code plugins always win the collision. The config entity is invisible to createInstance() and unreachable from any code path that resolves agents through the plugin manager.
2. Downstream consumers fatal. Notably the ai_assistant_api runner expects ConfigAiAgentInterface from createInstance() and crashes when it instead receives the code-plugin instance. Filed separately at #3586449.
The entity form does nothing to prevent this: at src/Form/AiAgentForm.php:126, the machine_name exists callback only checks for another AiAgent config entity (\[AiAgent::class, 'load'\]), not for code-plugin IDs in the same\
namespace.
Steps to reproduce
1. Install ai_agents with ai_assistant_api and any provider.
2. At /admin/config/ai/ai_agents, create a new agent with the machine name taxonomy_agent (or any other shipped code-plugin ID).
3. The form saves the entity successfully.
4. The entity is invisible to \\Drupal::service('plugin.manager.ai_agents')-\>createInstance('taxonomy_agent'), which returns the code-plugin instance instead.
Expected
The entity form rejects machine names that match an existing code-plugin ID at save time, with an inline validation error pointing the admin at a non-colliding name. The collision can never be created in the first place.
Proposed resolution
1. Extend the #machine_name exists callback in AiAgentForm (or add a #machine_name source / dedicated validator) so it checks both:\\
- existing ai_agent config entities (current behavior), and - existing code-plugin definitions returned by AiAgentManager::getDefinitions() whose custom_type is not config.
2. Add a \\Drupal::logger('ai_agents')-\>warning() inside the dropped-on-collision branch of AiAgentManager::findDefinitions() so admins debugging an unreachable config entity see something in watchdog without needing to dive\
into the discovery code.
The second change is purely defensive instrumentation — no behavior change.
Related
- [#3586449](https://git.drupalcode.org/project/ai/-/work_items/3586449) (project: ai) — the runtime fatal that this collision causes in ai_assistant_api. The runner-side fix lands there.
issue