Files
openclaw/extensions/slack/src/doctor.ts
2026-04-06 19:24:42 +01:00

59 lines
2.0 KiB
TypeScript

import { type ChannelDoctorAdapter } from "openclaw/plugin-sdk/channel-contract";
import { createDangerousNameMatchingMutableAllowlistWarningCollector } from "openclaw/plugin-sdk/channel-policy";
import {
legacyConfigRules as SLACK_LEGACY_CONFIG_RULES,
normalizeCompatibilityConfig as normalizeSlackCompatibilityConfig,
} from "./doctor-contract.js";
import { isSlackMutableAllowEntry } from "./security-doctor.js";
function asObjectRecord(value: unknown): Record<string, unknown> | null {
return value && typeof value === "object" && !Array.isArray(value)
? (value as Record<string, unknown>)
: null;
}
export const collectSlackMutableAllowlistWarnings =
createDangerousNameMatchingMutableAllowlistWarningCollector({
channel: "slack",
detector: isSlackMutableAllowEntry,
collectLists: (scope) => {
const lists = [
{
pathLabel: `${scope.prefix}.allowFrom`,
list: scope.account.allowFrom,
},
];
const dm = asObjectRecord(scope.account.dm);
if (dm) {
lists.push({
pathLabel: `${scope.prefix}.dm.allowFrom`,
list: dm.allowFrom,
});
}
const channels = asObjectRecord(scope.account.channels);
if (channels) {
for (const [channelKey, channelRaw] of Object.entries(channels)) {
const channel = asObjectRecord(channelRaw);
if (!channel) {
continue;
}
lists.push({
pathLabel: `${scope.prefix}.channels.${channelKey}.users`,
list: channel.users,
});
}
}
return lists;
},
});
export const slackDoctor: ChannelDoctorAdapter = {
dmAllowFromMode: "topOrNested",
groupModel: "route",
groupAllowFromFallbackToAllowFrom: false,
warnOnEmptyGroupSenderAllowlist: false,
legacyConfigRules: SLACK_LEGACY_CONFIG_RULES,
normalizeCompatibilityConfig: normalizeSlackCompatibilityConfig,
collectMutableAllowlistWarnings: collectSlackMutableAllowlistWarnings,
};