mirror of
https://github.com/moltbot/moltbot.git
synced 2026-05-13 23:56:07 +00:00
test: tighten remaining plugin sdk assertions
This commit is contained in:
@@ -154,12 +154,23 @@ describe("handleStopCommand target fallback", () => {
|
||||
});
|
||||
expect(replyRunAbortMock).toHaveBeenCalledWith("agent:target:telegram:direct:123");
|
||||
expect(abortEmbeddedPiRunMock).not.toHaveBeenCalledWith("wrapper-session-id");
|
||||
const persistAbortTargetParams = persistAbortTargetEntryMock.mock.calls[0]?.[0];
|
||||
const [[persistAbortTargetParams]] = persistAbortTargetEntryMock.mock.calls as unknown as Array<
|
||||
[
|
||||
{
|
||||
key?: string;
|
||||
entry?: unknown;
|
||||
sessionStore?: unknown;
|
||||
storePath?: string;
|
||||
},
|
||||
]
|
||||
>;
|
||||
expect(persistAbortTargetParams?.key).toBe("agent:target:telegram:direct:123");
|
||||
expect(persistAbortTargetParams?.entry).toBeUndefined();
|
||||
expect(persistAbortTargetParams?.sessionStore).toBe(params.sessionStore);
|
||||
expect(persistAbortTargetParams?.storePath).toBe("/tmp/sessions.json");
|
||||
const stopSubagentsParams = stopSubagentsForRequesterMock.mock.calls[0]?.[0];
|
||||
const [[stopSubagentsParams]] = stopSubagentsForRequesterMock.mock.calls as unknown as Array<
|
||||
[{ cfg?: unknown; requesterSessionKey?: string }]
|
||||
>;
|
||||
expect(stopSubagentsParams?.cfg).toBe(params.cfg);
|
||||
expect(stopSubagentsParams?.requesterSessionKey).toBe("agent:target:telegram:direct:123");
|
||||
expect(createInternalHookEventMock).toHaveBeenCalledWith(
|
||||
|
||||
@@ -118,7 +118,18 @@ describe("dispatchReplyFromConfig reply_dispatch hook", () => {
|
||||
|
||||
expect(hookMocks.runner.runReplyDispatch).toHaveBeenCalledOnce();
|
||||
const [replyDispatchEvent, replyDispatchRuntime] =
|
||||
hookMocks.runner.runReplyDispatch.mock.calls[0] ?? [];
|
||||
(hookMocks.runner.runReplyDispatch.mock.calls[0] as
|
||||
| [
|
||||
{
|
||||
sessionKey?: string;
|
||||
sendPolicy?: string;
|
||||
inboundAudio?: boolean;
|
||||
},
|
||||
{
|
||||
cfg?: unknown;
|
||||
},
|
||||
]
|
||||
| undefined) ?? [];
|
||||
expect(replyDispatchEvent?.sessionKey).toBe("agent:test:session");
|
||||
expect(replyDispatchEvent?.sendPolicy).toBe("allow");
|
||||
expect(replyDispatchEvent?.inboundAudio).toBe(false);
|
||||
|
||||
@@ -68,11 +68,15 @@ describe("createChannelRunQueue", () => {
|
||||
|
||||
await flushAsyncWork();
|
||||
|
||||
expect(setStatus).toHaveBeenCalledWith({ activeRuns: 0, busy: false });
|
||||
expect(setStatus).toHaveBeenCalledWith(expect.objectContaining({ activeRuns: 1, busy: true }));
|
||||
expect(setStatus).toHaveBeenLastCalledWith(
|
||||
expect.objectContaining({ activeRuns: 0, busy: false }),
|
||||
);
|
||||
expect(setStatus).toHaveBeenCalledTimes(3);
|
||||
const [initialStatus, busyStatus, finalStatus] = setStatus.mock.calls.map(([status]) => status);
|
||||
expect(initialStatus).toEqual({ activeRuns: 0, busy: false });
|
||||
expect(busyStatus?.activeRuns).toBe(1);
|
||||
expect(busyStatus?.busy).toBe(true);
|
||||
expect(typeof busyStatus?.lastRunActivityAt).toBe("number");
|
||||
expect(finalStatus?.activeRuns).toBe(0);
|
||||
expect(finalStatus?.busy).toBe(false);
|
||||
expect(typeof finalStatus?.lastRunActivityAt).toBe("number");
|
||||
expect(onError).toHaveBeenCalledWith(taskError);
|
||||
});
|
||||
|
||||
|
||||
@@ -279,20 +279,21 @@ describe("channel-streaming", () => {
|
||||
});
|
||||
|
||||
it("formats progress draft lines with shared tool display labels", () => {
|
||||
expect(
|
||||
buildChannelProgressDraftLine({
|
||||
event: "tool",
|
||||
name: "write",
|
||||
args: { path: "/tmp/demo/index.html" },
|
||||
}),
|
||||
).toMatchObject({
|
||||
kind: "tool",
|
||||
icon: "✍️",
|
||||
label: "Write",
|
||||
detail: "to /tmp/demo/index.html",
|
||||
text: "✍️ Write: to /tmp/demo/index.html",
|
||||
toolName: "write",
|
||||
const progressLine = buildChannelProgressDraftLine({
|
||||
event: "tool",
|
||||
name: "write",
|
||||
args: { path: "/tmp/demo/index.html" },
|
||||
});
|
||||
expect(progressLine).toBeDefined();
|
||||
if (!progressLine) {
|
||||
throw new Error("expected tool progress draft line");
|
||||
}
|
||||
expect(progressLine.kind).toBe("tool");
|
||||
expect(progressLine.icon).toBe("✍️");
|
||||
expect(progressLine.label).toBe("Write");
|
||||
expect(progressLine.detail).toBe("to /tmp/demo/index.html");
|
||||
expect(progressLine.text).toBe("✍️ Write: to /tmp/demo/index.html");
|
||||
expect(progressLine.toolName).toBe("write");
|
||||
expect(
|
||||
formatChannelProgressDraftLine({
|
||||
event: "tool",
|
||||
|
||||
@@ -46,11 +46,10 @@ describe("plugin-sdk delivery queue drainPendingDeliveries", () => {
|
||||
selectEntry: () => ({ match: false }),
|
||||
});
|
||||
|
||||
expect(mocks.coreDrainPendingDeliveries).toHaveBeenCalledWith(
|
||||
expect.objectContaining({
|
||||
deliver: mocks.deliverOutboundPayloads,
|
||||
}),
|
||||
);
|
||||
expect(mocks.coreDrainPendingDeliveries).toHaveBeenCalledTimes(1);
|
||||
const [[{ deliver: lazyDeliver }]] = mocks.coreDrainPendingDeliveries.mock
|
||||
.calls as unknown as Array<[{ deliver?: unknown }]>;
|
||||
expect(lazyDeliver).toBe(mocks.deliverOutboundPayloads);
|
||||
});
|
||||
|
||||
it("preserves an explicit deliver fn without loading the lazy runtime", async () => {
|
||||
@@ -65,11 +64,10 @@ describe("plugin-sdk delivery queue drainPendingDeliveries", () => {
|
||||
selectEntry: () => ({ match: false }),
|
||||
});
|
||||
|
||||
expect(mocks.coreDrainPendingDeliveries).toHaveBeenCalledWith(
|
||||
expect.objectContaining({
|
||||
deliver,
|
||||
}),
|
||||
);
|
||||
expect(mocks.coreDrainPendingDeliveries).toHaveBeenCalledTimes(1);
|
||||
const [[{ deliver: explicitDeliver }]] = mocks.coreDrainPendingDeliveries.mock
|
||||
.calls as unknown as Array<[{ deliver?: unknown }]>;
|
||||
expect(explicitDeliver).toBe(deliver);
|
||||
expect(mocks.deliverOutboundPayloads).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -160,19 +160,17 @@ describe("discord plugin-sdk facade", () => {
|
||||
childSessionKey: "child",
|
||||
});
|
||||
|
||||
expect(mocks.runtimeModule.autoBindSpawnedDiscordSubagent).toHaveBeenCalledWith(
|
||||
expect.objectContaining({
|
||||
agentId: "agent",
|
||||
cfg: mocks.runtimeConfig,
|
||||
childSessionKey: "child",
|
||||
}),
|
||||
);
|
||||
expect(binding).toEqual(
|
||||
expect.objectContaining({
|
||||
cfg: mocks.runtimeConfig,
|
||||
targetKind: "subagent",
|
||||
targetSessionKey: "child",
|
||||
}),
|
||||
);
|
||||
expect(mocks.runtimeModule.autoBindSpawnedDiscordSubagent).toHaveBeenCalledTimes(1);
|
||||
const callParams = mocks.runtimeModule.autoBindSpawnedDiscordSubagent.mock.calls[0]?.[0];
|
||||
expect(callParams.agentId).toBe("agent");
|
||||
expect(callParams.cfg).toBe(mocks.runtimeConfig);
|
||||
expect(callParams.childSessionKey).toBe("child");
|
||||
expect(binding).not.toBeNull();
|
||||
if (!binding) {
|
||||
throw new Error("expected Discord subagent binding");
|
||||
}
|
||||
expect(binding.cfg).toBe(mocks.runtimeConfig);
|
||||
expect(binding.targetKind).toBe("subagent");
|
||||
expect(binding.targetSessionKey).toBe("child");
|
||||
});
|
||||
});
|
||||
|
||||
@@ -44,10 +44,9 @@ describe("acquireFileLock", () => {
|
||||
);
|
||||
|
||||
await expect(acquireFileLock(filePath, options)).rejects.toSatisfy((error) => {
|
||||
expect(error).toMatchObject({
|
||||
code: FILE_LOCK_TIMEOUT_ERROR_CODE,
|
||||
});
|
||||
expect((error as { lockPath?: string }).lockPath).toMatch(/oauth-refresh\.lock$/);
|
||||
const lockError = error as { code?: string; lockPath?: string };
|
||||
expect(lockError.code).toBe(FILE_LOCK_TIMEOUT_ERROR_CODE);
|
||||
expect(lockError.lockPath).toMatch(/oauth-refresh\.lock$/);
|
||||
return true;
|
||||
});
|
||||
}, 5_000);
|
||||
|
||||
@@ -196,12 +196,12 @@ describe("buildProviderToolCompatFamilyHooks", () => {
|
||||
});
|
||||
|
||||
expect(normalized[0]?.parameters).toEqual(permissiveParameters);
|
||||
expect(findOpenAIStrictSchemaViolations(permissiveParameters, "cron.parameters")).toEqual(
|
||||
expect.arrayContaining([
|
||||
"cron.parameters.required.schedule",
|
||||
"cron.parameters.additionalProperties",
|
||||
]),
|
||||
const strictSchemaViolations = findOpenAIStrictSchemaViolations(
|
||||
permissiveParameters,
|
||||
"cron.parameters",
|
||||
);
|
||||
expect(strictSchemaViolations).toContain("cron.parameters.required.schedule");
|
||||
expect(strictSchemaViolations).toContain("cron.parameters.additionalProperties");
|
||||
expect(
|
||||
hooks.inspectToolSchemas({
|
||||
provider: "openai",
|
||||
|
||||
@@ -518,14 +518,21 @@ describe("sendMediaWithLeadingCaption", () => {
|
||||
}),
|
||||
).resolves.toBe(true);
|
||||
|
||||
expect(onError).toHaveBeenCalledWith(
|
||||
expect.objectContaining({
|
||||
mediaUrl: "https://example.com/a.png",
|
||||
caption: "hello",
|
||||
index: 0,
|
||||
isFirst: true,
|
||||
}),
|
||||
);
|
||||
expect(onError).toHaveBeenCalledTimes(1);
|
||||
const [[errorPayload]] = onError.mock.calls as unknown as Array<
|
||||
[
|
||||
{
|
||||
mediaUrl?: string;
|
||||
caption?: string;
|
||||
index?: number;
|
||||
isFirst?: boolean;
|
||||
},
|
||||
]
|
||||
>;
|
||||
expect(errorPayload.mediaUrl).toBe("https://example.com/a.png");
|
||||
expect(errorPayload.caption).toBe("hello");
|
||||
expect(errorPayload.index).toBe(0);
|
||||
expect(errorPayload.isFirst).toBe(true);
|
||||
expect(send).toHaveBeenNthCalledWith(2, {
|
||||
mediaUrl: "https://example.com/b.png",
|
||||
caption: undefined,
|
||||
|
||||
@@ -36,11 +36,7 @@ describe("telegram account plugin-sdk compatibility facade", () => {
|
||||
cfg,
|
||||
accountId: "default",
|
||||
});
|
||||
expect(account).toEqual(
|
||||
expect.objectContaining({
|
||||
accountId: "default",
|
||||
token: "token",
|
||||
}),
|
||||
);
|
||||
expect(account.accountId).toBe("default");
|
||||
expect(account.token).toBe("token");
|
||||
});
|
||||
});
|
||||
|
||||
@@ -86,7 +86,10 @@ describe("withTempDownloadPath", () => {
|
||||
expect(capturedPath).toContain(path.join(resolvePreferredOpenClawTmpDir(), "line-media-"));
|
||||
}
|
||||
if (expectCleanup) {
|
||||
await expect(fs.stat(capturedPath)).rejects.toMatchObject({ code: "ENOENT" });
|
||||
await expect(fs.stat(capturedPath)).rejects.toSatisfy((error) => {
|
||||
expect((error as NodeJS.ErrnoException).code).toBe("ENOENT");
|
||||
return true;
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
@@ -85,7 +85,7 @@ describe("registerWebhookTarget", () => {
|
||||
expect(onFirstPathTarget).toHaveBeenCalledTimes(1);
|
||||
expect(onFirstPathTarget).toHaveBeenCalledWith({
|
||||
path: "/hook",
|
||||
target: expect.objectContaining({ id: "A", path: "/hook" }),
|
||||
target: registeredA.target,
|
||||
});
|
||||
|
||||
registeredB.unregister();
|
||||
@@ -147,13 +147,13 @@ describe("registerWebhookTargetWithPluginRoute", () => {
|
||||
});
|
||||
|
||||
expect(registry.httpRoutes).toHaveLength(1);
|
||||
expect(registry.httpRoutes[0]).toEqual(
|
||||
expect.objectContaining({
|
||||
pluginId: "demo",
|
||||
path: "/hook",
|
||||
source: "demo-webhook",
|
||||
}),
|
||||
);
|
||||
const route = registry.httpRoutes[0];
|
||||
if (!route) {
|
||||
throw new Error("expected plugin route to be registered");
|
||||
}
|
||||
expect(route.pluginId).toBe("demo");
|
||||
expect(route.path).toBe("/hook");
|
||||
expect(route.source).toBe("demo-webhook");
|
||||
|
||||
registeredA.unregister();
|
||||
expect(registry.httpRoutes).toHaveLength(1);
|
||||
|
||||
Reference in New Issue
Block a user