mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-06 05:30:42 +00:00
fix: keep disabled channel doctor probes lazy
This commit is contained in:
@@ -10,6 +10,12 @@
|
||||
.bun
|
||||
.artifacts
|
||||
**/.artifacts
|
||||
.local
|
||||
**/.local
|
||||
.pi
|
||||
**/.pi
|
||||
__openclaw_vitest__
|
||||
**/__openclaw_vitest__
|
||||
.tmp
|
||||
**/.tmp
|
||||
.DS_Store
|
||||
@@ -40,6 +46,9 @@ docs/.generated
|
||||
*.log
|
||||
tmp
|
||||
**/tmp
|
||||
dist-runtime
|
||||
**/dist-runtime
|
||||
openclaw-path-alias-*
|
||||
|
||||
# build artifacts
|
||||
dist
|
||||
|
||||
@@ -904,9 +904,56 @@ assert_dep_absent_everywhere() {
|
||||
exit 1
|
||||
fi
|
||||
done
|
||||
if find "$OPENCLAW_PLUGIN_STAGE_DIR" -maxdepth 12 -path "*/node_modules/$dep_path/package.json" -type f | grep -q .; then
|
||||
echo "disabled $channel unexpectedly staged $dep_path externally" >&2
|
||||
find "$OPENCLAW_PLUGIN_STAGE_DIR" -maxdepth 12 -type f | sort | head -160 >&2 || true
|
||||
|
||||
if ! node - <<'NODE' "$OPENCLAW_PLUGIN_STAGE_DIR" "$dep_path"
|
||||
const fs = require("node:fs");
|
||||
const path = require("node:path");
|
||||
|
||||
const stageDir = process.argv[2];
|
||||
const depName = process.argv[3];
|
||||
const manifestName = ".openclaw-runtime-deps.json";
|
||||
const matches = [];
|
||||
|
||||
function visit(dir) {
|
||||
let entries;
|
||||
try {
|
||||
entries = fs.readdirSync(dir, { withFileTypes: true });
|
||||
} catch {
|
||||
return;
|
||||
}
|
||||
for (const entry of entries) {
|
||||
const fullPath = path.join(dir, entry.name);
|
||||
if (entry.isDirectory()) {
|
||||
visit(fullPath);
|
||||
continue;
|
||||
}
|
||||
if (entry.name !== manifestName) {
|
||||
continue;
|
||||
}
|
||||
let parsed;
|
||||
try {
|
||||
parsed = JSON.parse(fs.readFileSync(fullPath, "utf8"));
|
||||
} catch {
|
||||
continue;
|
||||
}
|
||||
const specs = Array.isArray(parsed.specs) ? parsed.specs : [];
|
||||
for (const spec of specs) {
|
||||
if (typeof spec === "string" && spec.startsWith(`${depName}@`)) {
|
||||
matches.push(`${fullPath}: ${spec}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
visit(stageDir);
|
||||
if (matches.length > 0) {
|
||||
process.stderr.write(`${matches.join("\n")}\n`);
|
||||
process.exit(1);
|
||||
}
|
||||
NODE
|
||||
then
|
||||
echo "disabled $channel unexpectedly selected $dep_path for external runtime deps" >&2
|
||||
cat /tmp/openclaw-disabled-config-doctor.log >&2
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
@@ -969,7 +1016,7 @@ assert_dep_absent_everywhere telegram grammy "$root"
|
||||
assert_dep_absent_everywhere slack @slack/web-api "$root"
|
||||
assert_dep_absent_everywhere discord discord-api-types "$root"
|
||||
|
||||
if grep -Eq "\\[plugins\\] (telegram|slack|discord) installed bundled runtime deps:" /tmp/openclaw-disabled-config-doctor.log; then
|
||||
if grep -Eq "(used by .*\\b(telegram|slack|discord)\\b|\\[plugins\\] (telegram|slack|discord) installed bundled runtime deps:)" /tmp/openclaw-disabled-config-doctor.log; then
|
||||
echo "doctor installed runtime deps for an explicitly disabled channel/plugin" >&2
|
||||
cat /tmp/openclaw-disabled-config-doctor.log >&2
|
||||
exit 1
|
||||
|
||||
@@ -522,6 +522,13 @@ describe("bundled channel entry shape guards", () => {
|
||||
"./bundled.js?scope=bundled-setup-only-feature",
|
||||
);
|
||||
|
||||
expect(
|
||||
bundled.listBundledChannelLegacyStateMigrationDetectors({
|
||||
config: { channels: { alpha: { enabled: false } } },
|
||||
}),
|
||||
).toEqual([]);
|
||||
expect(testGlobal.__bundledSetupOnlySetupLoaded).toBeUndefined();
|
||||
|
||||
const detectors = bundled.listBundledChannelLegacyStateMigrationDetectors();
|
||||
expect(
|
||||
detectors.map((detector) =>
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import path from "node:path";
|
||||
import type { OpenClawConfig } from "../../config/types.openclaw.js";
|
||||
import { formatErrorMessage } from "../../infra/errors.js";
|
||||
import { createSubsystemLogger } from "../../logging/subsystem.js";
|
||||
import type {
|
||||
@@ -17,6 +18,7 @@ import {
|
||||
} from "../../plugins/bundled-runtime-root.js";
|
||||
import { unwrapDefaultModuleExport } from "../../plugins/module-export.js";
|
||||
import type { PluginRuntime } from "../../plugins/runtime/types.js";
|
||||
import { normalizeOptionalLowercaseString } from "../../shared/string-coerce.js";
|
||||
import { resolveBundledChannelRootScope, type BundledChannelRootScope } from "./bundled-root.js";
|
||||
import { normalizeChannelMeta } from "./meta-normalization.js";
|
||||
import { isJavaScriptModulePath, loadChannelPluginModule } from "./module-loader.js";
|
||||
@@ -44,8 +46,12 @@ type BundledChannelSetupEntryRuntimeContract = {
|
||||
loadSetupSecrets?: (
|
||||
options?: BundledEntryModuleLoadOptions,
|
||||
) => ChannelPlugin["secrets"] | undefined;
|
||||
loadLegacyStateMigrationDetector?: () => BundledChannelLegacyStateMigrationDetector;
|
||||
loadLegacySessionSurface?: () => BundledChannelLegacySessionSurface;
|
||||
loadLegacyStateMigrationDetector?: (
|
||||
options?: BundledEntryModuleLoadOptions,
|
||||
) => BundledChannelLegacyStateMigrationDetector;
|
||||
loadLegacySessionSurface?: (
|
||||
options?: BundledEntryModuleLoadOptions,
|
||||
) => BundledChannelLegacySessionSurface;
|
||||
features?: {
|
||||
legacyStateMigrations?: boolean;
|
||||
legacySessionSurfaces?: boolean;
|
||||
@@ -347,15 +353,74 @@ function listBundledChannelPluginIdsForRoot(
|
||||
.toSorted((left, right) => left.localeCompare(right));
|
||||
}
|
||||
|
||||
function shouldIncludeBundledChannelSetupFeatureForConfig(params: {
|
||||
metadata: BundledChannelPluginMetadata;
|
||||
config?: OpenClawConfig;
|
||||
}): boolean {
|
||||
if (!params.config) {
|
||||
return true;
|
||||
}
|
||||
const plugins = params.config.plugins;
|
||||
if (plugins?.enabled === false) {
|
||||
return false;
|
||||
}
|
||||
const pluginId = params.metadata.manifest.id;
|
||||
if (plugins?.deny?.includes(pluginId)) {
|
||||
return false;
|
||||
}
|
||||
if (plugins?.entries?.[pluginId]?.enabled === false) {
|
||||
return false;
|
||||
}
|
||||
|
||||
let hasExplicitChannelDisable = false;
|
||||
for (const channelId of params.metadata.manifest.channels ?? [pluginId]) {
|
||||
const normalizedChannelId = normalizeOptionalLowercaseString(channelId);
|
||||
if (!normalizedChannelId) {
|
||||
continue;
|
||||
}
|
||||
const channelConfig = (params.config.channels as Record<string, unknown> | undefined)?.[
|
||||
normalizedChannelId
|
||||
];
|
||||
if (!channelConfig || typeof channelConfig !== "object" || Array.isArray(channelConfig)) {
|
||||
continue;
|
||||
}
|
||||
if ((channelConfig as { enabled?: unknown }).enabled === false) {
|
||||
hasExplicitChannelDisable = true;
|
||||
continue;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
return !hasExplicitChannelDisable;
|
||||
}
|
||||
|
||||
function listBundledChannelPluginIdsForSetupFeature(
|
||||
rootScope: BundledChannelRootScope,
|
||||
feature: keyof NonNullable<BundledChannelSetupEntryRuntimeContract["features"]>,
|
||||
options: { config?: OpenClawConfig } = {},
|
||||
): readonly ChannelId[] {
|
||||
const hinted = listBundledChannelMetadata(rootScope)
|
||||
.filter((metadata) => metadata.packageManifest?.setupFeatures?.[feature] === true)
|
||||
.filter(
|
||||
(metadata) =>
|
||||
metadata.packageManifest?.setupFeatures?.[feature] === true &&
|
||||
shouldIncludeBundledChannelSetupFeatureForConfig({
|
||||
metadata,
|
||||
config: options.config,
|
||||
}),
|
||||
)
|
||||
.map((metadata) => metadata.manifest.id)
|
||||
.toSorted((left, right) => left.localeCompare(right));
|
||||
return hinted.length > 0 ? hinted : listBundledChannelPluginIdsForRoot(rootScope);
|
||||
return hinted.length > 0
|
||||
? hinted
|
||||
: listBundledChannelMetadata(rootScope)
|
||||
.filter((metadata) =>
|
||||
shouldIncludeBundledChannelSetupFeatureForConfig({
|
||||
metadata,
|
||||
config: options.config,
|
||||
}),
|
||||
)
|
||||
.map((metadata) => metadata.manifest.id)
|
||||
.toSorted((left, right) => left.localeCompare(right));
|
||||
}
|
||||
|
||||
export function listBundledChannelPluginIds(): readonly ChannelId[] {
|
||||
@@ -626,9 +691,12 @@ export function listBundledChannelSetupPlugins(): readonly ChannelPlugin[] {
|
||||
|
||||
export function listBundledChannelSetupPluginsByFeature(
|
||||
feature: keyof NonNullable<BundledChannelSetupEntryRuntimeContract["features"]>,
|
||||
options: { config?: OpenClawConfig } = {},
|
||||
): readonly ChannelPlugin[] {
|
||||
const { rootScope, cacheContext } = resolveActiveBundledChannelCacheScope();
|
||||
return listBundledChannelPluginIdsForSetupFeature(rootScope, feature).flatMap((id) => {
|
||||
return listBundledChannelPluginIdsForSetupFeature(rootScope, feature, {
|
||||
config: options.config,
|
||||
}).flatMap((id) => {
|
||||
const setupEntry = getLazyGeneratedBundledChannelSetupEntryForRoot(id, rootScope, cacheContext);
|
||||
if (!hasSetupEntryFeature(setupEntry, feature)) {
|
||||
return [];
|
||||
@@ -638,50 +706,50 @@ export function listBundledChannelSetupPluginsByFeature(
|
||||
});
|
||||
}
|
||||
|
||||
export function listBundledChannelLegacySessionSurfaces(): readonly BundledChannelLegacySessionSurface[] {
|
||||
export function listBundledChannelLegacySessionSurfaces(
|
||||
options: {
|
||||
config?: OpenClawConfig;
|
||||
} = {},
|
||||
): readonly BundledChannelLegacySessionSurface[] {
|
||||
const { rootScope, cacheContext } = resolveActiveBundledChannelCacheScope();
|
||||
return listBundledChannelPluginIdsForSetupFeature(rootScope, "legacySessionSurfaces").flatMap(
|
||||
(id) => {
|
||||
const setupEntry = getLazyGeneratedBundledChannelSetupEntryForRoot(
|
||||
id,
|
||||
rootScope,
|
||||
cacheContext,
|
||||
);
|
||||
const surface = setupEntry?.loadLegacySessionSurface?.();
|
||||
if (surface) {
|
||||
return [surface];
|
||||
}
|
||||
if (!hasSetupEntryFeature(setupEntry, "legacySessionSurfaces")) {
|
||||
return [];
|
||||
}
|
||||
const plugin = getBundledChannelSetupPluginForRoot(id, rootScope, cacheContext);
|
||||
return plugin?.messaging ? [plugin.messaging] : [];
|
||||
},
|
||||
);
|
||||
return listBundledChannelPluginIdsForSetupFeature(rootScope, "legacySessionSurfaces", {
|
||||
config: options.config,
|
||||
}).flatMap((id) => {
|
||||
const setupEntry = getLazyGeneratedBundledChannelSetupEntryForRoot(id, rootScope, cacheContext);
|
||||
const surface = setupEntry?.loadLegacySessionSurface?.({ installRuntimeDeps: false });
|
||||
if (surface) {
|
||||
return [surface];
|
||||
}
|
||||
if (!hasSetupEntryFeature(setupEntry, "legacySessionSurfaces")) {
|
||||
return [];
|
||||
}
|
||||
const plugin = getBundledChannelSetupPluginForRoot(id, rootScope, cacheContext);
|
||||
return plugin?.messaging ? [plugin.messaging] : [];
|
||||
});
|
||||
}
|
||||
|
||||
export function listBundledChannelLegacyStateMigrationDetectors(): readonly BundledChannelLegacyStateMigrationDetector[] {
|
||||
export function listBundledChannelLegacyStateMigrationDetectors(
|
||||
options: {
|
||||
config?: OpenClawConfig;
|
||||
} = {},
|
||||
): readonly BundledChannelLegacyStateMigrationDetector[] {
|
||||
const { rootScope, cacheContext } = resolveActiveBundledChannelCacheScope();
|
||||
return listBundledChannelPluginIdsForSetupFeature(rootScope, "legacyStateMigrations").flatMap(
|
||||
(id) => {
|
||||
const setupEntry = getLazyGeneratedBundledChannelSetupEntryForRoot(
|
||||
id,
|
||||
rootScope,
|
||||
cacheContext,
|
||||
);
|
||||
const detector = setupEntry?.loadLegacyStateMigrationDetector?.();
|
||||
if (detector) {
|
||||
return [detector];
|
||||
}
|
||||
if (!hasSetupEntryFeature(setupEntry, "legacyStateMigrations")) {
|
||||
return [];
|
||||
}
|
||||
const plugin = getBundledChannelSetupPluginForRoot(id, rootScope, cacheContext);
|
||||
return plugin?.lifecycle?.detectLegacyStateMigrations
|
||||
? [plugin.lifecycle.detectLegacyStateMigrations]
|
||||
: [];
|
||||
},
|
||||
);
|
||||
return listBundledChannelPluginIdsForSetupFeature(rootScope, "legacyStateMigrations", {
|
||||
config: options.config,
|
||||
}).flatMap((id) => {
|
||||
const setupEntry = getLazyGeneratedBundledChannelSetupEntryForRoot(id, rootScope, cacheContext);
|
||||
const detector = setupEntry?.loadLegacyStateMigrationDetector?.({ installRuntimeDeps: false });
|
||||
if (detector) {
|
||||
return [detector];
|
||||
}
|
||||
if (!hasSetupEntryFeature(setupEntry, "legacyStateMigrations")) {
|
||||
return [];
|
||||
}
|
||||
const plugin = getBundledChannelSetupPluginForRoot(id, rootScope, cacheContext);
|
||||
return plugin?.lifecycle?.detectLegacyStateMigrations
|
||||
? [plugin.lifecycle.detectLegacyStateMigrations]
|
||||
: [];
|
||||
});
|
||||
}
|
||||
|
||||
export function hasBundledChannelEntryFeature(
|
||||
|
||||
@@ -33,4 +33,40 @@ describe("doctor allowlist-policy repair", () => {
|
||||
expect(result.config.channels?.matrix?.allowFrom).toBeUndefined();
|
||||
expect(result.config.channels?.matrix?.dm?.allowFrom).toEqual(["@alice:example.org"]);
|
||||
});
|
||||
|
||||
it("skips disabled channel and account entries", async () => {
|
||||
readChannelAllowFromStoreMock.mockResolvedValue(["alice"]);
|
||||
|
||||
const result = await maybeRepairAllowlistPolicyAllowFrom({
|
||||
channels: {
|
||||
telegram: {
|
||||
enabled: false,
|
||||
dmPolicy: "allowlist",
|
||||
},
|
||||
signal: {
|
||||
accounts: {
|
||||
disabled: { enabled: false, dmPolicy: "allowlist" },
|
||||
},
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
expect(result).toEqual({
|
||||
config: {
|
||||
channels: {
|
||||
telegram: {
|
||||
enabled: false,
|
||||
dmPolicy: "allowlist",
|
||||
},
|
||||
signal: {
|
||||
accounts: {
|
||||
disabled: { enabled: false, dmPolicy: "allowlist" },
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
changes: [],
|
||||
});
|
||||
expect(readChannelAllowFromStoreMock).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -118,6 +118,9 @@ export async function maybeRepairAllowlistPolicyAllowFrom(cfg: OpenClawConfig):
|
||||
if (!channelConfig || typeof channelConfig !== "object") {
|
||||
continue;
|
||||
}
|
||||
if (channelConfig.enabled === false) {
|
||||
continue;
|
||||
}
|
||||
await recoverAllowFromForAccount({
|
||||
channelName,
|
||||
account: channelConfig,
|
||||
@@ -132,6 +135,9 @@ export async function maybeRepairAllowlistPolicyAllowFrom(cfg: OpenClawConfig):
|
||||
if (!accountConfig || typeof accountConfig !== "object") {
|
||||
continue;
|
||||
}
|
||||
if ((accountConfig as { enabled?: unknown }).enabled === false) {
|
||||
continue;
|
||||
}
|
||||
await recoverAllowFromForAccount({
|
||||
channelName,
|
||||
account: accountConfig as Record<string, unknown>,
|
||||
|
||||
@@ -11,6 +11,7 @@ import type {
|
||||
ChannelDoctorSequenceResult,
|
||||
} from "../../../channels/plugins/types.adapters.js";
|
||||
import type { OpenClawConfig } from "../../../config/types.openclaw.js";
|
||||
import { normalizeOptionalLowercaseString } from "../../../shared/string-coerce.js";
|
||||
|
||||
type ChannelDoctorEntry = {
|
||||
doctor: ChannelDoctorAdapter;
|
||||
@@ -59,6 +60,9 @@ export type ChannelDoctorEmptyAllowlistPolicyHooks = {
|
||||
};
|
||||
|
||||
function collectConfiguredChannelIds(cfg: OpenClawConfig): string[] {
|
||||
if (cfg.plugins?.enabled === false) {
|
||||
return [];
|
||||
}
|
||||
const channels =
|
||||
cfg.channels && typeof cfg.channels === "object" && !Array.isArray(cfg.channels)
|
||||
? cfg.channels
|
||||
@@ -72,6 +76,9 @@ function collectConfiguredChannelIds(cfg: OpenClawConfig): string[] {
|
||||
if (channelId === "defaults") {
|
||||
return false;
|
||||
}
|
||||
if (isChannelDoctorBlockedByConfig(channelId, cfg)) {
|
||||
return false;
|
||||
}
|
||||
const entry = channelEntries[channelId];
|
||||
return (
|
||||
!entry ||
|
||||
@@ -83,6 +90,21 @@ function collectConfiguredChannelIds(cfg: OpenClawConfig): string[] {
|
||||
.toSorted();
|
||||
}
|
||||
|
||||
function isChannelDoctorBlockedByConfig(channelId: string, cfg: OpenClawConfig): boolean {
|
||||
if (cfg.plugins?.enabled === false) {
|
||||
return true;
|
||||
}
|
||||
const normalizedChannelId = normalizeOptionalLowercaseString(channelId) ?? channelId;
|
||||
if (cfg.plugins?.entries?.[normalizedChannelId]?.enabled === false) {
|
||||
return true;
|
||||
}
|
||||
const channelEntry = (cfg.channels as Record<string, unknown> | undefined)?.[normalizedChannelId];
|
||||
return (
|
||||
Boolean(channelEntry && typeof channelEntry === "object" && !Array.isArray(channelEntry)) &&
|
||||
(channelEntry as { enabled?: unknown }).enabled === false
|
||||
);
|
||||
}
|
||||
|
||||
function safeGetLoadedChannelPlugin(id: string) {
|
||||
try {
|
||||
return getLoadedChannelPlugin(id);
|
||||
@@ -180,7 +202,12 @@ function listChannelDoctorEntries(
|
||||
if (channelIds.length === 0) {
|
||||
return [];
|
||||
}
|
||||
const selectedIds = new Set(channelIds);
|
||||
const selectedIds = new Set(
|
||||
channelIds.filter((id) => !isChannelDoctorBlockedByConfig(id, context.cfg)),
|
||||
);
|
||||
if (selectedIds.size === 0) {
|
||||
return [];
|
||||
}
|
||||
const readOnlyPluginsById =
|
||||
options.readOnlyPluginsById ?? listReadOnlyChannelPluginsById(context);
|
||||
|
||||
|
||||
@@ -56,4 +56,34 @@ describe("doctor empty allowlist policy scan", () => {
|
||||
|
||||
expect(warnings).toContain("extra:channels.telegram");
|
||||
});
|
||||
|
||||
it("skips disabled channel and account entries", () => {
|
||||
const extraWarningsForAccount = vi.fn(({ prefix }) => [`extra:${prefix}`]);
|
||||
|
||||
const warnings = scanEmptyAllowlistPolicyWarnings(
|
||||
{
|
||||
channels: {
|
||||
telegram: {
|
||||
enabled: false,
|
||||
dmPolicy: "allowlist",
|
||||
accounts: {
|
||||
default: { dmPolicy: "allowlist" },
|
||||
},
|
||||
},
|
||||
signal: {
|
||||
accounts: {
|
||||
disabled: { enabled: false, dmPolicy: "allowlist" },
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{ doctorFixCommand: "openclaw doctor --fix", extraWarningsForAccount },
|
||||
);
|
||||
|
||||
expect(warnings).toEqual(["extra:channels.signal"]);
|
||||
expect(extraWarningsForAccount).toHaveBeenCalledTimes(1);
|
||||
expect(extraWarningsForAccount).toHaveBeenCalledWith(
|
||||
expect.objectContaining({ prefix: "channels.signal" }),
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -12,6 +12,13 @@ type ScanEmptyAllowlistPolicyWarningsParams = {
|
||||
) => boolean;
|
||||
};
|
||||
|
||||
function isDisabledRecord(value: unknown): boolean {
|
||||
return (
|
||||
Boolean(value && typeof value === "object" && !Array.isArray(value)) &&
|
||||
(value as { enabled?: unknown }).enabled === false
|
||||
);
|
||||
}
|
||||
|
||||
export function scanEmptyAllowlistPolicyWarnings(
|
||||
cfg: OpenClawConfig,
|
||||
params: ScanEmptyAllowlistPolicyWarningsParams,
|
||||
@@ -76,6 +83,9 @@ export function scanEmptyAllowlistPolicyWarnings(
|
||||
if (!channelConfig || typeof channelConfig !== "object") {
|
||||
continue;
|
||||
}
|
||||
if (isDisabledRecord(channelConfig)) {
|
||||
continue;
|
||||
}
|
||||
checkAccount(channelConfig, `channels.${channelName}`, channelName);
|
||||
|
||||
const accounts = asObjectRecord(channelConfig.accounts);
|
||||
@@ -86,6 +96,9 @@ export function scanEmptyAllowlistPolicyWarnings(
|
||||
if (!account || typeof account !== "object") {
|
||||
continue;
|
||||
}
|
||||
if (isDisabledRecord(account)) {
|
||||
continue;
|
||||
}
|
||||
checkAccount(
|
||||
account as DoctorAccountRecord,
|
||||
`channels.${channelName}.accounts.${accountId}`,
|
||||
|
||||
@@ -669,7 +669,7 @@ async function collectChannelLegacyStateMigrationPlans(params: {
|
||||
const plans: ChannelLegacyStateMigrationPlan[] = [];
|
||||
// Legacy state detection belongs on a narrow setup-entry surface so doctor
|
||||
// does not cold-load unrelated runtime channel code.
|
||||
const detectors = listBundledChannelLegacyStateMigrationDetectors();
|
||||
const detectors = listBundledChannelLegacyStateMigrationDetectors({ config: params.cfg });
|
||||
for (const detectLegacyStateMigrations of detectors) {
|
||||
const detected = await detectLegacyStateMigrations({
|
||||
cfg: params.cfg,
|
||||
|
||||
@@ -111,8 +111,12 @@ export type BundledChannelSetupEntryContract<TPlugin = ChannelPlugin> = {
|
||||
loadSetupSecrets?: (
|
||||
options?: BundledEntryModuleLoadOptions,
|
||||
) => ChannelPlugin["secrets"] | undefined;
|
||||
loadLegacyStateMigrationDetector?: () => BundledChannelLegacyStateMigrationDetector;
|
||||
loadLegacySessionSurface?: () => BundledChannelLegacySessionSurface;
|
||||
loadLegacyStateMigrationDetector?: (
|
||||
options?: BundledEntryModuleLoadOptions,
|
||||
) => BundledChannelLegacyStateMigrationDetector;
|
||||
loadLegacySessionSurface?: (
|
||||
options?: BundledEntryModuleLoadOptions,
|
||||
) => BundledChannelLegacySessionSurface;
|
||||
setChannelRuntime?: (runtime: PluginRuntime) => void;
|
||||
features?: BundledChannelSetupEntryFeatures;
|
||||
};
|
||||
@@ -519,17 +523,19 @@ export function defineBundledChannelSetupEntry<TPlugin = ChannelPlugin>({
|
||||
}
|
||||
: undefined;
|
||||
const loadLegacyStateMigrationDetector = legacyStateMigrations
|
||||
? () =>
|
||||
? (options?: BundledEntryModuleLoadOptions) =>
|
||||
loadBundledEntryExportSync<BundledChannelLegacyStateMigrationDetector>(
|
||||
importMetaUrl,
|
||||
legacyStateMigrations,
|
||||
options,
|
||||
)
|
||||
: undefined;
|
||||
const loadLegacySessionSurface = legacySessionSurface
|
||||
? () =>
|
||||
? (options?: BundledEntryModuleLoadOptions) =>
|
||||
loadBundledEntryExportSync<BundledChannelLegacySessionSurface>(
|
||||
importMetaUrl,
|
||||
legacySessionSurface,
|
||||
options,
|
||||
)
|
||||
: undefined;
|
||||
return {
|
||||
|
||||
Reference in New Issue
Block a user