test: keep inbound group policy tests hermetic

This commit is contained in:
Gustavo Madeira Santana
2026-04-17 15:48:32 -04:00
parent 8b76bcba90
commit 50e71daaa0
2 changed files with 125 additions and 9 deletions

View File

@@ -0,0 +1,118 @@
import type { OpenClawConfig } from "../config/config.js";
import { setActivePluginRegistry } from "../plugins/runtime.js";
import { createChannelTestPluginBase, createTestRegistry } from "../test-utils/channel-plugins.js";
type TestChannelGroupContext = {
cfg: OpenClawConfig;
groupId?: string | null;
groupChannel?: string | null;
groupSpace?: string | null;
accountId?: string | null;
};
function normalizeTestSlug(raw?: string | null): string {
return raw?.trim().replace(/^#/, "").toLowerCase() ?? "";
}
function resolveDiscordRequireMentionForTest(params: TestChannelGroupContext): boolean {
const discordCfg = params.cfg.channels?.discord as
| {
guilds?: Record<
string,
{
requireMention?: boolean;
slug?: string;
channels?: Record<string, { requireMention?: boolean }>;
}
>;
}
| undefined;
const guilds = discordCfg?.guilds;
if (!guilds) {
return true;
}
const space = params.groupSpace?.trim() ?? "";
const spaceSlug = normalizeTestSlug(space);
const guild =
(space ? guilds[space] : undefined) ??
(spaceSlug ? guilds[spaceSlug] : undefined) ??
Object.values(guilds).find((entry) => normalizeTestSlug(entry?.slug) === spaceSlug) ??
guilds["*"];
const channelSlug = normalizeTestSlug(params.groupChannel);
const channel =
(params.groupId ? guild?.channels?.[params.groupId] : undefined) ??
(channelSlug ? guild?.channels?.[channelSlug] : undefined) ??
(channelSlug ? guild?.channels?.[`#${channelSlug}`] : undefined);
return channel?.requireMention ?? guild?.requireMention ?? true;
}
function resolveSlackRequireMentionForTest(params: TestChannelGroupContext): boolean {
const slackCfg = params.cfg.channels?.slack as
| {
defaultAccount?: string;
channels?: Record<string, { requireMention?: boolean }>;
accounts?: Record<string, { channels?: Record<string, { requireMention?: boolean }> }>;
}
| undefined;
if (!slackCfg) {
return true;
}
const accountId = params.accountId ?? slackCfg.defaultAccount;
const channels =
(accountId ? slackCfg.accounts?.[accountId]?.channels : undefined) ?? slackCfg.channels;
if (!channels) {
return true;
}
const channelName = params.groupChannel?.trim().replace(/^#/, "");
const channelSlug = normalizeTestSlug(channelName);
const candidates = [
params.groupId?.trim(),
channelName ? `#${channelName}` : undefined,
channelName,
channelSlug,
"*",
];
for (const candidate of candidates) {
if (!candidate) {
continue;
}
const entry = channels[candidate];
if (typeof entry?.requireMention === "boolean") {
return entry.requireMention;
}
}
return true;
}
export function installGroupRequireMentionTestPlugins() {
setActivePluginRegistry(
createTestRegistry([
{
pluginId: "discord",
plugin: {
...createChannelTestPluginBase({ id: "discord" }),
groups: { resolveRequireMention: resolveDiscordRequireMentionForTest },
},
source: "test",
},
{
pluginId: "slack",
plugin: {
...createChannelTestPluginBase({ id: "slack" }),
groups: { resolveRequireMention: resolveSlackRequireMentionForTest },
},
source: "test",
},
{
pluginId: "line",
plugin: createChannelTestPluginBase({ id: "line" }),
source: "test",
},
{
pluginId: "bluebubbles",
plugin: createChannelTestPluginBase({ id: "bluebubbles" }),
source: "test",
},
]),
);
}

View File

@@ -1,11 +1,12 @@
import fs from "node:fs/promises";
import os from "node:os";
import path from "node:path";
import { describe, expect, it, vi } from "vitest";
import { beforeEach, describe, expect, it, vi } from "vitest";
import type { OpenClawConfig } from "../config/config.js";
import type { GroupKeyResolution } from "../config/sessions.js";
import { resetPluginRuntimeStateForTest } from "../plugins/runtime.js";
import { createInboundDebouncer } from "./inbound-debounce.js";
import { installGroupRequireMentionTestPlugins } from "./inbound.group-require-mention-test-plugins.js";
import { resolveGroupRequireMention } from "./reply/groups.js";
import { finalizeInboundContext } from "./reply/inbound-context.js";
import {
@@ -809,8 +810,12 @@ describe("mention helpers", () => {
});
describe("resolveGroupRequireMention", () => {
it("respects Discord guild/channel requireMention settings", async () => {
beforeEach(() => {
resetPluginRuntimeStateForTest();
installGroupRequireMentionTestPlugins();
});
it("respects Discord guild/channel requireMention settings", async () => {
const cfg: OpenClawConfig = {
channels: {
discord: {
@@ -841,7 +846,6 @@ describe("resolveGroupRequireMention", () => {
});
it("respects Slack channel requireMention settings", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
slack: {
@@ -867,7 +871,6 @@ describe("resolveGroupRequireMention", () => {
});
it("uses Slack fallback resolver semantics for default-account wildcard channels", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
slack: {
@@ -898,7 +901,6 @@ describe("resolveGroupRequireMention", () => {
});
it("keeps core reply-stage resolution aligned for Slack default-account wildcard fallbacks", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
slack: {
@@ -929,7 +931,6 @@ describe("resolveGroupRequireMention", () => {
});
it("uses Discord fallback resolver semantics for guild slug matches", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
discord: {
@@ -959,7 +960,6 @@ describe("resolveGroupRequireMention", () => {
});
it("keeps core reply-stage resolution aligned for Discord slug + wildcard guild fallbacks", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
discord: {
@@ -991,7 +991,6 @@ describe("resolveGroupRequireMention", () => {
});
it("respects LINE prefixed group keys in reply-stage requireMention resolution", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
line: {
@@ -1016,7 +1015,6 @@ describe("resolveGroupRequireMention", () => {
});
it("preserves plugin-backed channel requireMention resolution", async () => {
resetPluginRuntimeStateForTest();
const cfg: OpenClawConfig = {
channels: {
bluebubbles: {