Summary
In OpenClaw 2026.5.2, optional plugin tools can appear in tools.catalog but remain unavailable to the live agent/tool execution paths (tools.effective, tools.invoke, and native agent tool surface). This affected @openclaw/lobster and the bundled llm-task plugin.
Observed result before hotfix:
openclaw plugins list shows both plugins loaded/enabled.
openclaw gateway call tools.catalog --params '{"agentId":"main","includePlugins":true}' lists llm-task and lobster as optional plugin tools.
openclaw gateway call tools.effective ... does not include them.
openclaw gateway call tools.invoke --params '{"name":"llm-task",...}' returns Tool not available: llm-task.
- Native agent tool surface does not include either tool.
Environment
- OpenClaw:
2026.5.2 (8b2a6e5)
- macOS: 26.4.1
- Plugins:
llm-task: bundled, enabled, version 2026.5.2
lobster: installed from npm as @openclaw/lobster@2026.5.2, enabled
Root cause found locally
There are two related issues:
1. Optional plugin runtime registry is preloaded for tools.catalog, but not for execution/effective paths
tools.catalog explicitly calls ensureStandalonePluginToolRegistryLoaded(...) before resolvePluginTools(...).
But createOpenClawTools(...) / resolveGatewayScopedTools(...) / tools.effective ultimately call plugin tool resolution without that preload. In local reproduction:
resolvePluginTools({ toolAllowlist: ['lobster', 'llm-task'], ... }) // []
ensureStandalonePluginToolRegistryLoaded({ toolAllowlist: ['lobster', 'llm-task'], ... })
resolvePluginTools({ toolAllowlist: ['lobster', 'llm-task'], ... }) // ['llm-task', 'lobster']
This explains why catalog can see the tools while effective/invoke/agent cannot.
2. Docs/config semantics are confusing for optional plugin tools
docs/tools/lobster.md recommends:
{ "tools": { "alsoAllow": ["lobster"] } }
But source behavior in 2026.5.2 is:
collectExplicitAllowlist() reads only allow, not alsoAllow, for plugin discovery.
mergeAlsoAllowPolicy() only merges alsoAllow when there is already a policy.allow list.
tools.profile="full" resolves to {} / no allow list, so alsoAllow alone does not widen the full profile.
- Config validation rejects setting
allow and alsoAllow in the same scope.
So the documented tools.alsoAllow path is insufficient for tools.profile="full" and optional plugin discovery.
Local hotfix that worked
Patch dist/openclaw-tools-*.js so createOpenClawTools(...) preloads the standalone plugin tool registry before calling resolveOpenClawPluginToolsForOptions(...), mirroring tools.catalog.
Conceptual diff:
-import { resolvePluginTools, ... } from "./tools-*.js";
+import { resolvePluginTools, ensureStandalonePluginToolRegistryLoaded, ... } from "./tools-*.js";
if (options?.disablePluginTools) return tools;
+ensureStandalonePluginToolRegistryLoaded({
+ ...resolveOpenClawPluginToolInputs({
+ options,
+ resolvedConfig,
+ runtimeConfig: availabilityConfig,
+ getRuntimeConfig: ...
+ }),
+ toolAllowlist: options?.pluginToolAllowlist,
+ allowGatewaySubagentBinding: options?.allowGatewaySubagentBinding,
+});
const wrappedPluginTools = resolveOpenClawPluginToolsForOptions({ ... });
After patch, I also used a valid per-agent allowlist for main:
{
"agents": {
"list": [
{
"id": "main",
"tools": {
"allow": [
"agents_list", "apply_patch", "canvas", "edit", "exec", "image_generate",
"message", "music_generate", "process", "read", "sessions_history",
"sessions_send", "session_status", "sessions_list", "sessions_spawn",
"subagents", "tts", "update_plan", "video_generate", "web_fetch",
"write", "sessions_yield", "lobster", "llm-task"
]
}
}
]
}
}
Verification after hotfix
openclaw config validate: valid
tools.effective for main includes both llm-task and lobster.
tools.invoke llm-task works and returns schema-validated JSON:
{
"ok": true,
"toolName": "llm-task",
"details": { "json": { "ok": true, "value": 1 } }
}
tools.invoke lobster works for a no-side-effect smoke:
{
"ok": true,
"toolName": "lobster",
"details": {
"ok": true,
"status": "ok",
"output": ["hello"]
}
}
and JSON smoke:
{
"ok": true,
"status": "ok",
"output": [{ "ok": true }]
}
Suggested fixes
- Preload optional plugin tool runtime registry in
createOpenClawTools(...) or in a shared plugin-tool resolution helper used by tools.effective, tools.invoke, and native agent tool assembly.
- Align docs/config behavior for optional plugin tools:
- Either make
alsoAllow participate in optional plugin discovery, or
- update Lobster/llm-task docs to say optional plugins require an explicit
allow entry in a scope where alsoAllow is not also present.
- Consider making
tools.profile="full" + tools.alsoAllow meaningful, or document that full has no allowlist to merge into.
Summary
In OpenClaw 2026.5.2, optional plugin tools can appear in
tools.catalogbut remain unavailable to the live agent/tool execution paths (tools.effective,tools.invoke, and native agent tool surface). This affected@openclaw/lobsterand the bundledllm-taskplugin.Observed result before hotfix:
openclaw plugins listshows both plugins loaded/enabled.openclaw gateway call tools.catalog --params '{"agentId":"main","includePlugins":true}'listsllm-taskandlobsteras optional plugin tools.openclaw gateway call tools.effective ...does not include them.openclaw gateway call tools.invoke --params '{"name":"llm-task",...}'returnsTool not available: llm-task.Environment
2026.5.2 (8b2a6e5)llm-task: bundled, enabled, version2026.5.2lobster: installed from npm as@openclaw/lobster@2026.5.2, enabledRoot cause found locally
There are two related issues:
1. Optional plugin runtime registry is preloaded for
tools.catalog, but not for execution/effective pathstools.catalogexplicitly callsensureStandalonePluginToolRegistryLoaded(...)beforeresolvePluginTools(...).But
createOpenClawTools(...)/resolveGatewayScopedTools(...)/tools.effectiveultimately call plugin tool resolution without that preload. In local reproduction:This explains why catalog can see the tools while effective/invoke/agent cannot.
2. Docs/config semantics are confusing for optional plugin tools
docs/tools/lobster.mdrecommends:{ "tools": { "alsoAllow": ["lobster"] } }But source behavior in 2026.5.2 is:
collectExplicitAllowlist()reads onlyallow, notalsoAllow, for plugin discovery.mergeAlsoAllowPolicy()only mergesalsoAllowwhen there is already apolicy.allowlist.tools.profile="full"resolves to{}/ no allow list, soalsoAllowalone does not widen the full profile.allowandalsoAllowin the same scope.So the documented
tools.alsoAllowpath is insufficient fortools.profile="full"and optional plugin discovery.Local hotfix that worked
Patch
dist/openclaw-tools-*.jssocreateOpenClawTools(...)preloads the standalone plugin tool registry before callingresolveOpenClawPluginToolsForOptions(...), mirroringtools.catalog.Conceptual diff:
After patch, I also used a valid per-agent allowlist for main:
{ "agents": { "list": [ { "id": "main", "tools": { "allow": [ "agents_list", "apply_patch", "canvas", "edit", "exec", "image_generate", "message", "music_generate", "process", "read", "sessions_history", "sessions_send", "session_status", "sessions_list", "sessions_spawn", "subagents", "tts", "update_plan", "video_generate", "web_fetch", "write", "sessions_yield", "lobster", "llm-task" ] } } ] } }Verification after hotfix
openclaw config validate: validtools.effectivefor main includes bothllm-taskandlobster.tools.invokellm-taskworks and returns schema-validated JSON:{ "ok": true, "toolName": "llm-task", "details": { "json": { "ok": true, "value": 1 } } }tools.invokelobsterworks for a no-side-effect smoke:{ "ok": true, "toolName": "lobster", "details": { "ok": true, "status": "ok", "output": ["hello"] } }and JSON smoke:
{ "ok": true, "status": "ok", "output": [{ "ok": true }] }Suggested fixes
createOpenClawTools(...)or in a shared plugin-tool resolution helper used bytools.effective,tools.invoke, and native agent tool assembly.alsoAllowparticipate in optional plugin discovery, orallowentry in a scope wherealsoAllowis not also present.tools.profile="full"+tools.alsoAllowmeaningful, or document thatfullhas no allowlist to merge into.