mirror of
https://github.com/openclaw/openclaw.git
synced 2026-03-27 09:21:35 +07:00
test: stabilize discord monitor ci isolation
This commit is contained in:
@@ -19,19 +19,7 @@ import {
|
||||
resolvePluginConversationBindingApprovalMock,
|
||||
upsertPairingRequestMock,
|
||||
} from "../../../../test/helpers/extensions/discord-component-runtime.js";
|
||||
import {
|
||||
clearDiscordComponentEntries,
|
||||
registerDiscordComponentEntries,
|
||||
resolveDiscordComponentEntry,
|
||||
resolveDiscordModalEntry,
|
||||
} from "../components-registry.js";
|
||||
import type { DiscordComponentEntry, DiscordModalEntry } from "../components.js";
|
||||
import * as sendComponents from "../send.components.js";
|
||||
import {
|
||||
createDiscordComponentButton,
|
||||
createDiscordComponentStringSelect,
|
||||
createDiscordComponentModal,
|
||||
} from "./agent-components.js";
|
||||
import { type DiscordComponentEntry, type DiscordModalEntry } from "../components.js";
|
||||
import type { DiscordChannelConfigResolved } from "./allow-list.js";
|
||||
import {
|
||||
resolveDiscordMemberAllowed,
|
||||
@@ -53,6 +41,22 @@ import {
|
||||
resolveDiscordReplyDeliveryPlan,
|
||||
} from "./threading.js";
|
||||
|
||||
type CreateDiscordComponentButton =
|
||||
typeof import("./agent-components.js").createDiscordComponentButton;
|
||||
type CreateDiscordComponentModal =
|
||||
typeof import("./agent-components.js").createDiscordComponentModal;
|
||||
type CreateDiscordComponentStringSelect =
|
||||
typeof import("./agent-components.js").createDiscordComponentStringSelect;
|
||||
|
||||
let createDiscordComponentButton: CreateDiscordComponentButton;
|
||||
let createDiscordComponentStringSelect: CreateDiscordComponentStringSelect;
|
||||
let createDiscordComponentModal: CreateDiscordComponentModal;
|
||||
let clearDiscordComponentEntries: typeof import("../components-registry.js").clearDiscordComponentEntries;
|
||||
let registerDiscordComponentEntries: typeof import("../components-registry.js").registerDiscordComponentEntries;
|
||||
let resolveDiscordComponentEntry: typeof import("../components-registry.js").resolveDiscordComponentEntry;
|
||||
let resolveDiscordModalEntry: typeof import("../components-registry.js").resolveDiscordModalEntry;
|
||||
let sendComponents: typeof import("../send.components.js");
|
||||
|
||||
const enqueueSystemEventMock = vi.hoisted(() => vi.fn());
|
||||
const dispatchReplyMock = vi.hoisted(() => vi.fn());
|
||||
const readSessionUpdatedAtMock = vi.hoisted(() => vi.fn());
|
||||
@@ -136,9 +140,9 @@ describe("discord component interactions", () => {
|
||||
};
|
||||
};
|
||||
|
||||
const createComponentContext = (
|
||||
overrides?: Partial<Parameters<typeof createDiscordComponentButton>[0]>,
|
||||
) =>
|
||||
type ComponentContext = Parameters<CreateDiscordComponentButton>[0];
|
||||
|
||||
const createComponentContext = (overrides?: Partial<ComponentContext>) =>
|
||||
({
|
||||
cfg: createCfg(),
|
||||
accountId: "default",
|
||||
@@ -147,7 +151,7 @@ describe("discord component interactions", () => {
|
||||
discordConfig: createDiscordConfig(),
|
||||
token: "token",
|
||||
...overrides,
|
||||
}) as Parameters<typeof createDiscordComponentButton>[0];
|
||||
}) as ComponentContext;
|
||||
|
||||
const createComponentButtonInteraction = (overrides: Partial<ButtonInteraction> = {}) => {
|
||||
const reply = vi.fn().mockResolvedValue(undefined);
|
||||
@@ -307,7 +311,20 @@ describe("discord component interactions", () => {
|
||||
expect(dispatchReplyMock).not.toHaveBeenCalled();
|
||||
}
|
||||
|
||||
beforeEach(() => {
|
||||
beforeEach(async () => {
|
||||
vi.resetModules();
|
||||
({
|
||||
createDiscordComponentButton,
|
||||
createDiscordComponentStringSelect,
|
||||
createDiscordComponentModal,
|
||||
} = await import("./agent-components.js"));
|
||||
({
|
||||
clearDiscordComponentEntries,
|
||||
registerDiscordComponentEntries,
|
||||
resolveDiscordComponentEntry,
|
||||
resolveDiscordModalEntry,
|
||||
} = await import("../components-registry.js"));
|
||||
sendComponents = await import("../send.components.js");
|
||||
editDiscordComponentMessageMock = vi
|
||||
.spyOn(sendComponents, "editDiscordComponentMessage")
|
||||
.mockResolvedValue({
|
||||
|
||||
@@ -5,7 +5,7 @@ import * as dispatcherModule from "../../../../src/auto-reply/reply/provider-dis
|
||||
import type { OpenClawConfig } from "../../../../src/config/config.js";
|
||||
import type { DiscordAccountConfig } from "../../../../src/config/types.discord.js";
|
||||
import * as pluginCommandsModule from "../../../../src/plugins/commands.js";
|
||||
import { createDiscordNativeCommand } from "./native-command.js";
|
||||
import { __testing as nativeCommandTesting, createDiscordNativeCommand } from "./native-command.js";
|
||||
import {
|
||||
createMockCommandInteraction,
|
||||
type MockCommandInteraction,
|
||||
@@ -68,13 +68,17 @@ function createCommand(cfg: OpenClawConfig, discordConfig?: DiscordAccountConfig
|
||||
}
|
||||
|
||||
function createDispatchSpy() {
|
||||
return vi.spyOn(dispatcherModule, "dispatchReplyWithDispatcher").mockResolvedValue({
|
||||
const dispatchSpy = vi.spyOn(dispatcherModule, "dispatchReplyWithDispatcher").mockResolvedValue({
|
||||
counts: {
|
||||
final: 1,
|
||||
block: 0,
|
||||
tool: 0,
|
||||
},
|
||||
} as never);
|
||||
nativeCommandTesting.setDispatchReplyWithDispatcher(
|
||||
dispatcherModule.dispatchReplyWithDispatcher as typeof import("openclaw/plugin-sdk/reply-runtime").dispatchReplyWithDispatcher,
|
||||
);
|
||||
return dispatchSpy;
|
||||
}
|
||||
|
||||
async function runGuildSlashCommand(params?: {
|
||||
@@ -110,6 +114,9 @@ function expectUnauthorizedReply(interaction: MockCommandInteraction) {
|
||||
describe("Discord native slash commands with commands.allowFrom", () => {
|
||||
beforeEach(() => {
|
||||
vi.restoreAllMocks();
|
||||
nativeCommandTesting.setDispatchReplyWithDispatcher(
|
||||
dispatcherModule.dispatchReplyWithDispatcher as typeof import("openclaw/plugin-sdk/reply-runtime").dispatchReplyWithDispatcher,
|
||||
);
|
||||
});
|
||||
|
||||
it("authorizes guild slash commands when commands.allowFrom.discord matches the sender", async () => {
|
||||
|
||||
@@ -10,7 +10,6 @@ import {
|
||||
import type { OpenClawConfig, loadConfig } from "../../../../src/config/config.js";
|
||||
import { clearSessionStoreCacheForTest } from "../../../../src/config/sessions/store.js";
|
||||
import { createConfiguredBindingConversationRuntimeModuleMock } from "../../../../test/helpers/extensions/configured-binding-runtime.js";
|
||||
import { resolveDiscordNativeChoiceContext } from "./native-command-ui.js";
|
||||
import { createNoopThreadBindingManager } from "./thread-bindings.js";
|
||||
|
||||
const ensureConfiguredBindingRouteReadyMock = vi.hoisted(() =>
|
||||
@@ -52,9 +51,12 @@ const STORE_PATH = path.join(
|
||||
`openclaw-discord-think-autocomplete-${process.pid}.json`,
|
||||
);
|
||||
const SESSION_KEY = "agent:main:main";
|
||||
let resolveDiscordNativeChoiceContext: typeof import("./native-command-ui.js").resolveDiscordNativeChoiceContext;
|
||||
|
||||
describe("discord native /think autocomplete", () => {
|
||||
beforeEach(() => {
|
||||
beforeEach(async () => {
|
||||
vi.resetModules();
|
||||
({ resolveDiscordNativeChoiceContext } = await import("./native-command-ui.js"));
|
||||
clearSessionStoreCacheForTest();
|
||||
ensureConfiguredBindingRouteReadyMock.mockReset();
|
||||
ensureConfiguredBindingRouteReadyMock.mockResolvedValue({ ok: true });
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { describe, expect, it, vi } from "vitest";
|
||||
import { resolveDiscordRestFetch } from "./rest-fetch.js";
|
||||
import { beforeEach, describe, expect, it, vi } from "vitest";
|
||||
|
||||
const { undiciFetchMock, proxyAgentSpy } = vi.hoisted(() => ({
|
||||
undiciFetchMock: vi.fn(),
|
||||
@@ -23,7 +22,14 @@ vi.mock("undici", () => {
|
||||
};
|
||||
});
|
||||
|
||||
let resolveDiscordRestFetch: typeof import("./rest-fetch.js").resolveDiscordRestFetch;
|
||||
|
||||
describe("resolveDiscordRestFetch", () => {
|
||||
beforeEach(async () => {
|
||||
vi.resetModules();
|
||||
({ resolveDiscordRestFetch } = await import("./rest-fetch.js"));
|
||||
});
|
||||
|
||||
it("uses undici proxy fetch when a proxy URL is configured", async () => {
|
||||
const runtime = {
|
||||
log: vi.fn(),
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import { beforeEach, describe, expect, it, vi } from "vitest";
|
||||
import type { OpenClawConfig } from "../../../../src/config/config.js";
|
||||
import type { RuntimeEnv } from "../../../../src/runtime.js";
|
||||
import { deliverDiscordReply } from "./reply-delivery.js";
|
||||
import {
|
||||
__testing as threadBindingTesting,
|
||||
createThreadBindingManager,
|
||||
@@ -59,6 +58,8 @@ vi.mock("openclaw/plugin-sdk/infra-runtime", async (importOriginal) => {
|
||||
};
|
||||
});
|
||||
|
||||
let deliverDiscordReply: typeof import("./reply-delivery.js").deliverDiscordReply;
|
||||
|
||||
describe("deliverDiscordReply", () => {
|
||||
const runtime = {} as RuntimeEnv;
|
||||
const cfg = {
|
||||
@@ -111,7 +112,9 @@ describe("deliverDiscordReply", () => {
|
||||
return threadBindings;
|
||||
};
|
||||
|
||||
beforeEach(() => {
|
||||
beforeEach(async () => {
|
||||
vi.resetModules();
|
||||
({ deliverDiscordReply } = await import("./reply-delivery.js"));
|
||||
sendMessageDiscordMock.mockClear().mockResolvedValue({
|
||||
messageId: "msg-1",
|
||||
channelId: "channel-1",
|
||||
|
||||
@@ -30,11 +30,9 @@ const MATCHED_KEY = `agent:main:discord:channel:${THREAD_ID}`;
|
||||
const UNMATCHED_KEY = `agent:main:discord:channel:${OTHER_ID}`;
|
||||
|
||||
describe("closeDiscordThreadSessions", () => {
|
||||
beforeAll(async () => {
|
||||
beforeEach(async () => {
|
||||
vi.resetModules();
|
||||
({ closeDiscordThreadSessions } = await import("./thread-session-close.js"));
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
hoisted.updateSessionStore.mockClear();
|
||||
hoisted.resolveStorePath.mockClear();
|
||||
hoisted.resolveStorePath.mockReturnValue("/tmp/openclaw-sessions.json");
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { ChannelType } from "@buape/carbon";
|
||||
import { beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
|
||||
import { beforeEach, describe, expect, it, vi } from "vitest";
|
||||
import type { OpenClawConfig } from "../../../../src/config/config.js";
|
||||
type MaybeCreateDiscordAutoThreadFn = typeof import("./threading.js").maybeCreateDiscordAutoThread;
|
||||
|
||||
@@ -46,7 +46,8 @@ async function flushAsyncWork() {
|
||||
await Promise.resolve();
|
||||
}
|
||||
|
||||
beforeAll(async () => {
|
||||
beforeEach(async () => {
|
||||
vi.resetModules();
|
||||
postMock.mockReset();
|
||||
getMock.mockReset();
|
||||
patchMock.mockReset();
|
||||
@@ -54,13 +55,6 @@ beforeAll(async () => {
|
||||
({ maybeCreateDiscordAutoThread } = await import("./threading.js"));
|
||||
});
|
||||
|
||||
beforeEach(() => {
|
||||
postMock.mockReset();
|
||||
getMock.mockReset();
|
||||
patchMock.mockReset();
|
||||
generateThreadTitleMock.mockReset();
|
||||
});
|
||||
|
||||
describe("maybeCreateDiscordAutoThread", () => {
|
||||
it("skips auto-thread if channelType is GuildForum", async () => {
|
||||
const result = await maybeCreateDiscordAutoThread(
|
||||
|
||||
Reference in New Issue
Block a user