mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-06 05:40:44 +00:00
fix(config): tolerate missing channel metadata during auto-enable
This commit is contained in:
@@ -36,6 +36,7 @@ Docs: https://docs.openclaw.ai
|
||||
- Agents/MCP: keep `mcp.servers` and bundle MCP tools available in Pi embedded
|
||||
`coding` and `messaging` sessions while preserving `minimal` profile and
|
||||
`tools.deny: ["bundle-mcp"]` opt-out behavior. Fixes #68875 and #68818.
|
||||
- Plugins/startup: tolerate transient bundled-channel catalog/metadata drift while auto-enabling configured plugins, so CLI and gateway startup no longer crash when a channel id is known but its display metadata is unavailable.
|
||||
- CLI/Claude: report CLI-backed reply runs as streaming while Claude/Codex CLI turns are still in flight, so WebChat keeps visible response state until the backend finishes. Fixes #70125.
|
||||
- Codex harness: rotate the shared app-server websocket client when the configured bearer token changes, so auth-token refreshes reconnect with the new `Authorization` header instead of reusing a stale socket. (#70328) Thanks @Lucenx9.
|
||||
- Telegram/sandbox: keep Telegram bot DMs on per-account sender session keys even when `session.dmScope=main`, so sandbox/tool policy can distinguish Telegram-originated direct chats from the agent main session.
|
||||
|
||||
89
src/config/plugin-auto-enable.prefer-over.test.ts
Normal file
89
src/config/plugin-auto-enable.prefer-over.test.ts
Normal file
@@ -0,0 +1,89 @@
|
||||
import fs from "node:fs";
|
||||
import os from "node:os";
|
||||
import path from "node:path";
|
||||
import { afterEach, describe, expect, it, vi } from "vitest";
|
||||
import type { PluginManifestRegistry } from "../plugins/manifest-registry.js";
|
||||
import { cleanupTrackedTempDirs } from "../plugins/test-helpers/fs-fixtures.js";
|
||||
|
||||
const tempDirs: string[] = [];
|
||||
|
||||
function makeTempDir(): string {
|
||||
const dir = fs.mkdtempSync(path.join(os.tmpdir(), "openclaw-plugin-prefer-over-"));
|
||||
tempDirs.push(dir);
|
||||
return dir;
|
||||
}
|
||||
|
||||
function writeBundledChannelPackage(rootDir: string, channelId: string): void {
|
||||
const pluginDir = path.join(rootDir, channelId);
|
||||
fs.mkdirSync(pluginDir, { recursive: true });
|
||||
fs.writeFileSync(
|
||||
path.join(pluginDir, "package.json"),
|
||||
JSON.stringify({
|
||||
openclaw: {
|
||||
channel: {
|
||||
id: channelId,
|
||||
label: "Cache Drift",
|
||||
selectionLabel: "Cache Drift",
|
||||
docsPath: `/channels/${channelId}`,
|
||||
blurb: "Cache drift fixture",
|
||||
},
|
||||
},
|
||||
}),
|
||||
"utf-8",
|
||||
);
|
||||
}
|
||||
|
||||
const EMPTY_MANIFEST_REGISTRY: PluginManifestRegistry = {
|
||||
plugins: [],
|
||||
diagnostics: [],
|
||||
};
|
||||
|
||||
afterEach(() => {
|
||||
vi.unstubAllEnvs();
|
||||
vi.resetModules();
|
||||
cleanupTrackedTempDirs(tempDirs);
|
||||
});
|
||||
|
||||
describe("plugin auto-enable preferOver", () => {
|
||||
it("tolerates bundled channel id metadata drift during auto-enable", async () => {
|
||||
vi.resetModules();
|
||||
const rootDir = makeTempDir();
|
||||
const channelId = "cache-drift-channel";
|
||||
writeBundledChannelPackage(rootDir, channelId);
|
||||
|
||||
vi.stubEnv("OPENCLAW_BUNDLED_PLUGINS_DIR", rootDir);
|
||||
const { normalizeChatChannelId } = await import("../channels/ids.js");
|
||||
expect(normalizeChatChannelId(channelId)).toBe(channelId);
|
||||
|
||||
vi.stubEnv("OPENCLAW_BUNDLED_PLUGINS_DIR", path.join(rootDir, "missing"));
|
||||
const { materializePluginAutoEnableCandidates } = await import("./plugin-auto-enable.js");
|
||||
|
||||
const result = materializePluginAutoEnableCandidates({
|
||||
config: {
|
||||
channels: {
|
||||
[channelId]: { token: "configured" },
|
||||
fallback: { token: "configured" },
|
||||
},
|
||||
},
|
||||
candidates: [
|
||||
{
|
||||
pluginId: channelId,
|
||||
kind: "channel-configured",
|
||||
channelId,
|
||||
},
|
||||
{
|
||||
pluginId: "fallback",
|
||||
kind: "channel-configured",
|
||||
channelId: "fallback",
|
||||
},
|
||||
],
|
||||
env: {
|
||||
OPENCLAW_STATE_DIR: path.join(rootDir, "state"),
|
||||
OPENCLAW_BUNDLED_PLUGINS_DIR: path.join(rootDir, "missing"),
|
||||
},
|
||||
manifestRegistry: EMPTY_MANIFEST_REGISTRY,
|
||||
});
|
||||
|
||||
expect(result.config.channels?.[channelId]?.enabled).toBe(true);
|
||||
});
|
||||
});
|
||||
@@ -96,7 +96,7 @@ function resolveBuiltInChannelPreferOver(channelId: string): readonly string[] {
|
||||
if (!builtInChannelId) {
|
||||
return [];
|
||||
}
|
||||
return getChatChannelMeta(builtInChannelId).preferOver ?? [];
|
||||
return getChatChannelMeta(builtInChannelId)?.preferOver ?? [];
|
||||
}
|
||||
|
||||
function resolvePreferredOverIds(
|
||||
|
||||
@@ -684,7 +684,7 @@ function resolveChannelAutoEnableDisplayLabel(
|
||||
): string | undefined {
|
||||
const builtInChannelId = normalizeChatChannelId(entry.channelId);
|
||||
if (builtInChannelId) {
|
||||
return getChatChannelMeta(builtInChannelId).label;
|
||||
return getChatChannelMeta(builtInChannelId)?.label;
|
||||
}
|
||||
const plugin = manifestRegistry.plugins.find((record) => record.id === entry.pluginId);
|
||||
return plugin?.channelConfigs?.[entry.channelId]?.label ?? plugin?.channelCatalogMeta?.label;
|
||||
|
||||
Reference in New Issue
Block a user