mirror of
https://github.com/farcasclaudiu/openclaw.git
synced 2026-06-29 05:02:04 +03:00
test(cron): remove flaky real-timer polling
This commit is contained in:
@@ -1,7 +1,6 @@
|
|||||||
import fs from "node:fs/promises";
|
import fs from "node:fs/promises";
|
||||||
import os from "node:os";
|
import os from "node:os";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
import { setTimeout as delay } from "node:timers/promises";
|
|
||||||
import { afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
|
import { afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi } from "vitest";
|
||||||
import type { CronJob } from "./types.js";
|
import type { CronJob } from "./types.js";
|
||||||
import { CronService } from "./service.js";
|
import { CronService } from "./service.js";
|
||||||
@@ -31,6 +30,16 @@ async function makeStorePath() {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function createDeferred<T>() {
|
||||||
|
let resolve!: (value: T) => void;
|
||||||
|
let reject!: (reason?: unknown) => void;
|
||||||
|
const promise = new Promise<T>((res, rej) => {
|
||||||
|
resolve = res;
|
||||||
|
reject = rej;
|
||||||
|
});
|
||||||
|
return { promise, resolve, reject };
|
||||||
|
}
|
||||||
|
|
||||||
function createDueIsolatedJob(params: {
|
function createDueIsolatedJob(params: {
|
||||||
id: string;
|
id: string;
|
||||||
nowMs: number;
|
nowMs: number;
|
||||||
@@ -211,7 +220,6 @@ describe("Cron issue regressions", () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it("skips forced manual runs while a timer-triggered run is in progress", async () => {
|
it("skips forced manual runs while a timer-triggered run is in progress", async () => {
|
||||||
vi.useRealTimers();
|
|
||||||
const store = await makeStorePath();
|
const store = await makeStorePath();
|
||||||
let resolveRun:
|
let resolveRun:
|
||||||
| ((value: { status: "ok" | "error" | "skipped"; summary?: string; error?: string }) => void)
|
| ((value: { status: "ok" | "error" | "skipped"; summary?: string; error?: string }) => void)
|
||||||
@@ -225,6 +233,10 @@ describe("Cron issue regressions", () => {
|
|||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
const started = createDeferred<void>();
|
||||||
|
const finished = createDeferred<void>();
|
||||||
|
let targetJobId = "";
|
||||||
|
|
||||||
const cron = new CronService({
|
const cron = new CronService({
|
||||||
cronEnabled: true,
|
cronEnabled: true,
|
||||||
storePath: store.storePath,
|
storePath: store.storePath,
|
||||||
@@ -232,6 +244,16 @@ describe("Cron issue regressions", () => {
|
|||||||
enqueueSystemEvent: vi.fn(),
|
enqueueSystemEvent: vi.fn(),
|
||||||
requestHeartbeatNow: vi.fn(),
|
requestHeartbeatNow: vi.fn(),
|
||||||
runIsolatedAgentJob,
|
runIsolatedAgentJob,
|
||||||
|
onEvent: (evt: CronEvent) => {
|
||||||
|
if (evt.jobId !== targetJobId) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (evt.action === "started") {
|
||||||
|
started.resolve();
|
||||||
|
} else if (evt.action === "finished" && evt.status === "ok") {
|
||||||
|
finished.resolve();
|
||||||
|
}
|
||||||
|
},
|
||||||
});
|
});
|
||||||
await cron.start();
|
await cron.start();
|
||||||
|
|
||||||
@@ -246,9 +268,9 @@ describe("Cron issue regressions", () => {
|
|||||||
delivery: { mode: "none" },
|
delivery: { mode: "none" },
|
||||||
});
|
});
|
||||||
|
|
||||||
for (let i = 0; i < 20 && runIsolatedAgentJob.mock.calls.length === 0; i++) {
|
targetJobId = job.id;
|
||||||
await delay(1);
|
await vi.advanceTimersByTimeAsync(2);
|
||||||
}
|
await started.promise;
|
||||||
expect(runIsolatedAgentJob).toHaveBeenCalledTimes(1);
|
expect(runIsolatedAgentJob).toHaveBeenCalledTimes(1);
|
||||||
|
|
||||||
const manualResult = await cron.run(job.id, "force");
|
const manualResult = await cron.run(job.id, "force");
|
||||||
@@ -256,13 +278,7 @@ describe("Cron issue regressions", () => {
|
|||||||
expect(runIsolatedAgentJob).toHaveBeenCalledTimes(1);
|
expect(runIsolatedAgentJob).toHaveBeenCalledTimes(1);
|
||||||
|
|
||||||
resolveRun?.({ status: "ok", summary: "done" });
|
resolveRun?.({ status: "ok", summary: "done" });
|
||||||
for (let i = 0; i < 20; i++) {
|
await finished.promise;
|
||||||
const jobs = await cron.list({ includeDisabled: true });
|
|
||||||
if (jobs.some((j) => j.id === job.id && j.state.lastStatus === "ok")) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
await delay(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
cron.stop();
|
cron.stop();
|
||||||
await store.cleanup();
|
await store.cleanup();
|
||||||
|
|||||||
Reference in New Issue
Block a user