From 98e75fce1724b5b22ce7c8159f575b560a59c937 Mon Sep 17 00:00:00 2001 From: Peter Steinberger Date: Mon, 12 Jan 2026 08:45:47 +0000 Subject: [PATCH] test: align group policy defaults --- docs/gateway/security.md | 1 + src/discord/monitor.tool-result.test.ts | 4 ++ .../gateway-models.profiles.live.test.ts | 36 +++++++++----- src/imessage/monitor.test.ts | 10 +++- src/slack/monitor.tool-result.test.ts | 5 +- src/telegram/bot.test.ts | 49 +++++++++++++++---- src/web/monitor-inbox.test.ts | 2 + 7 files changed, 83 insertions(+), 24 deletions(-) diff --git a/docs/gateway/security.md b/docs/gateway/security.md index 84558571b..84e380741 100644 --- a/docs/gateway/security.md +++ b/docs/gateway/security.md @@ -72,6 +72,7 @@ Clawdbot has two separate “who can trigger me?” layers: - `whatsapp.groups`, `telegram.groups`, `imessage.groups`: per-group defaults like `requireMention`; when set, it also acts as a group allowlist (include `"*"` to keep allow-all behavior). - `groupPolicy="allowlist"` + `groupAllowFrom`: restrict who can trigger the bot *inside* a group session (WhatsApp/Telegram/Signal/iMessage/Microsoft Teams). - `discord.guilds` / `slack.channels`: per-surface allowlists + mention defaults. + - **Security note:** treat `dmPolicy="open"` and `groupPolicy="open"` as last-resort settings. They should be barely used; prefer pairing + allowlists unless you fully trust every member of the room. Details: [Configuration](/gateway/configuration) and [Groups](/concepts/groups) diff --git a/src/discord/monitor.tool-result.test.ts b/src/discord/monitor.tool-result.test.ts index 584f62336..ba00cfb0a 100644 --- a/src/discord/monitor.tool-result.test.ts +++ b/src/discord/monitor.tool-result.test.ts @@ -458,6 +458,7 @@ describe("discord tool result dispatch", () => { session: { store: "/tmp/clawdbot-sessions.json" }, discord: { dm: { enabled: true, policy: "open" }, + groupPolicy: "open", guilds: { "*": { requireMention: true } }, }, messages: { @@ -550,6 +551,7 @@ describe("discord tool result dispatch", () => { messages: { responsePrefix: "PFX" }, discord: { dm: { enabled: true, policy: "open" }, + groupPolicy: "open", guilds: { "*": { requireMention: false } }, }, } as ReturnType; @@ -655,6 +657,7 @@ describe("discord tool result dispatch", () => { session: { store: "/tmp/clawdbot-sessions.json" }, discord: { dm: { enabled: true, policy: "open" }, + groupPolicy: "open", guilds: { "*": { requireMention: false } }, }, routing: { allowFrom: [] }, @@ -764,6 +767,7 @@ describe("discord tool result dispatch", () => { messages: { responsePrefix: "PFX" }, discord: { dm: { enabled: true, policy: "open" }, + groupPolicy: "open", guilds: { "*": { requireMention: false } }, }, bindings: [ diff --git a/src/gateway/gateway-models.profiles.live.test.ts b/src/gateway/gateway-models.profiles.live.test.ts index 949d6db60..c40dde12e 100644 --- a/src/gateway/gateway-models.profiles.live.test.ts +++ b/src/gateway/gateway-models.profiles.live.test.ts @@ -240,18 +240,30 @@ function buildLiveGatewayConfig(params: { }): ClawdbotConfig { const lmstudioProvider = params.cfg.models?.providers?.lmstudio; const baseProviders = params.cfg.models?.providers ?? {}; - const nextProviders = { - ...baseProviders, - ...(lmstudioProvider - ? { - lmstudio: { - ...lmstudioProvider, - api: "openai-completions", - }, - } - : {}), - ...(params.providerOverrides ?? {}), - }; + const nextProviders = params.providerOverrides + ? { + ...baseProviders, + ...(lmstudioProvider + ? { + lmstudio: { + ...lmstudioProvider, + api: "openai-completions", + }, + } + : {}), + ...params.providerOverrides, + } + : { + ...baseProviders, + ...(lmstudioProvider + ? { + lmstudio: { + ...lmstudioProvider, + api: "openai-completions", + }, + } + : {}), + }; const providers = Object.keys(nextProviders).length > 0 ? nextProviders : baseProviders; return { diff --git a/src/imessage/monitor.test.ts b/src/imessage/monitor.test.ts index fe9237bb4..649f43a8e 100644 --- a/src/imessage/monitor.test.ts +++ b/src/imessage/monitor.test.ts @@ -129,7 +129,10 @@ describe("monitorIMessageProvider", () => { it("allows group messages when imessage groups default disables mention gating", async () => { config = { ...config, - imessage: { groups: { "*": { requireMention: false } } }, + imessage: { + groupPolicy: "open", + groups: { "*": { requireMention: false } }, + }, }; const run = monitorIMessageProvider(); await waitForSubscribe(); @@ -159,7 +162,10 @@ describe("monitorIMessageProvider", () => { config = { ...config, messages: { groupChat: { mentionPatterns: [] } }, - imessage: { groups: { "*": { requireMention: true } } }, + imessage: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, }; const run = monitorIMessageProvider(); await waitForSubscribe(); diff --git a/src/slack/monitor.tool-result.test.ts b/src/slack/monitor.tool-result.test.ts index 52d201d92..784c71ca3 100644 --- a/src/slack/monitor.tool-result.test.ts +++ b/src/slack/monitor.tool-result.test.ts @@ -108,7 +108,10 @@ beforeEach(() => { ackReaction: "👀", ackReactionScope: "group-mentions", }, - slack: { dm: { enabled: true, policy: "open", allowFrom: ["*"] } }, + slack: { + dm: { enabled: true, policy: "open", allowFrom: ["*"] }, + groupPolicy: "open", + }, }; sendMock.mockReset().mockResolvedValue(undefined); replyMock.mockReset(); diff --git a/src/telegram/bot.test.ts b/src/telegram/bot.test.ts index 3e5c7de03..829ef1bf2 100644 --- a/src/telegram/bot.test.ts +++ b/src/telegram/bot.test.ts @@ -407,7 +407,10 @@ describe("createTelegramBot", () => { loadConfig.mockReturnValue({ identity: { name: "Bert" }, messages: { groupChat: { mentionPatterns: ["\\bbert\\b"] } }, - telegram: { groups: { "*": { requireMention: true } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, }); createTelegramBot({ token: "tok" }); @@ -443,7 +446,10 @@ describe("createTelegramBot", () => { replySpy.mockReset(); loadConfig.mockReturnValue({ - telegram: { groups: { "*": { requireMention: false } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: false } }, + }, }); createTelegramBot({ token: "tok" }); @@ -489,7 +495,10 @@ describe("createTelegramBot", () => { ackReactionScope: "group-mentions", groupChat: { mentionPatterns: ["\\bbert\\b"] }, }, - telegram: { groups: { "*": { requireMention: true } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, }); createTelegramBot({ token: "tok" }); @@ -533,7 +542,10 @@ describe("createTelegramBot", () => { loadConfig.mockReturnValue({ messages: { groupChat: { mentionPatterns: ["\\bbert\\b"] } }, - telegram: { groups: { "*": { requireMention: true } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, }); createTelegramBot({ token: "tok" }); @@ -565,7 +577,10 @@ describe("createTelegramBot", () => { loadConfig.mockReturnValue({ messages: { groupChat: { mentionPatterns: [] } }, - telegram: { groups: { "*": { requireMention: true } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, }); createTelegramBot({ token: "tok" }); @@ -838,7 +853,10 @@ describe("createTelegramBot", () => { "utf-8", ); loadConfig.mockReturnValue({ - telegram: { groups: { "*": { requireMention: true } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, bindings: [ { agentId: "ops", @@ -877,6 +895,7 @@ describe("createTelegramBot", () => { replySpy.mockReset(); loadConfig.mockReturnValue({ telegram: { + groupPolicy: "open", groups: { "*": { requireMention: true }, "123": { requireMention: false }, @@ -910,6 +929,7 @@ describe("createTelegramBot", () => { replySpy.mockReset(); loadConfig.mockReturnValue({ telegram: { + groupPolicy: "open", groups: { "*": { requireMention: true }, "-1001234567890": { @@ -954,6 +974,7 @@ describe("createTelegramBot", () => { replySpy.mockReset(); loadConfig.mockReturnValue({ telegram: { + groupPolicy: "open", groups: { "*": { requireMention: false } }, }, }); @@ -983,7 +1004,10 @@ describe("createTelegramBot", () => { >; replySpy.mockReset(); loadConfig.mockReturnValue({ - telegram: { groups: { "*": { requireMention: true } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: true } }, + }, }); createTelegramBot({ token: "tok" }); @@ -1610,7 +1634,10 @@ describe("createTelegramBot", () => { replySpy.mockReset(); loadConfig.mockReturnValue({ - telegram: { groups: { "*": { requireMention: false } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: false } }, + }, }); createTelegramBot({ token: "tok" }); @@ -1658,6 +1685,7 @@ describe("createTelegramBot", () => { loadConfig.mockReturnValue({ telegram: { + groupPolicy: "open", groups: { "-1001234567890": { requireMention: false, @@ -1715,7 +1743,10 @@ describe("createTelegramBot", () => { replySpy.mockResolvedValue({ text: "response" }); loadConfig.mockReturnValue({ - telegram: { groups: { "*": { requireMention: false } } }, + telegram: { + groupPolicy: "open", + groups: { "*": { requireMention: false } }, + }, }); createTelegramBot({ token: "tok" }); diff --git a/src/web/monitor-inbox.test.ts b/src/web/monitor-inbox.test.ts index 6a48e4dd4..6e43c8afe 100644 --- a/src/web/monitor-inbox.test.ts +++ b/src/web/monitor-inbox.test.ts @@ -682,6 +682,7 @@ describe("web monitor inbox", () => { mockLoadConfig.mockReturnValue({ whatsapp: { allowFrom: ["+111"], // does not include +777 + groupPolicy: "open", }, messages: { messagePrefix: undefined, @@ -847,6 +848,7 @@ describe("web monitor inbox", () => { mockLoadConfig.mockReturnValue({ whatsapp: { allowFrom: ["+1234"], + groupPolicy: "open", }, messages: { messagePrefix: undefined,