mirror of
https://github.com/whyour/qinglong.git
synced 2026-09-21 00:36:13 +08:00
141 lines
3.5 KiB
JavaScript
141 lines
3.5 KiB
JavaScript
require('ts-node/register/transpile-only');
|
|
|
|
const assert = require('node:assert/strict');
|
|
const { test } = require('node:test');
|
|
const {
|
|
PrimaryTimeoutSupervisor,
|
|
} = require('../../back/runtime/application/primaryTimeoutSupervisor');
|
|
|
|
function summary(overrides = {}) {
|
|
return {
|
|
scanned: 1,
|
|
accepted: 1,
|
|
alreadyRequested: 0,
|
|
alreadyTerminal: 0,
|
|
failed: 0,
|
|
truncated: false,
|
|
...overrides,
|
|
};
|
|
}
|
|
|
|
test('aggregates bounded timeout pages with one fixed observation time', async () => {
|
|
const calls = [];
|
|
const responses = [
|
|
summary({
|
|
truncated: true,
|
|
nextCursor: { deadlineAtMs: 10, attemptId: 'attempt-1' },
|
|
}),
|
|
summary({ accepted: 0, alreadyTerminal: 1 }),
|
|
];
|
|
const supervisor = new PrimaryTimeoutSupervisor({
|
|
async requestBatch(options) {
|
|
calls.push(options);
|
|
return responses.shift();
|
|
},
|
|
});
|
|
|
|
const result = await supervisor.run({ nowMs: 100, pageSize: 8, maxPages: 4 });
|
|
assert.deepEqual(calls, [
|
|
{ nowMs: 100, limit: 8 },
|
|
{
|
|
nowMs: 100,
|
|
cursor: { deadlineAtMs: 10, attemptId: 'attempt-1' },
|
|
limit: 8,
|
|
},
|
|
]);
|
|
assert.deepEqual(result, {
|
|
pages: 2,
|
|
scanned: 2,
|
|
accepted: 1,
|
|
alreadyRequested: 0,
|
|
alreadyTerminal: 1,
|
|
failed: 0,
|
|
stopReason: 'complete',
|
|
remaining: false,
|
|
});
|
|
});
|
|
|
|
test('samples its clock once when the caller omits an observation time', async () => {
|
|
const calls = [];
|
|
let clockCalls = 0;
|
|
const responses = [
|
|
summary({
|
|
truncated: true,
|
|
nextCursor: { deadlineAtMs: 10, attemptId: 'attempt-1' },
|
|
}),
|
|
summary(),
|
|
];
|
|
const supervisor = new PrimaryTimeoutSupervisor(
|
|
{
|
|
async requestBatch(options) {
|
|
calls.push(options);
|
|
return responses.shift();
|
|
},
|
|
},
|
|
{
|
|
now() {
|
|
clockCalls += 1;
|
|
return 123;
|
|
},
|
|
},
|
|
);
|
|
|
|
await supervisor.run({ pageSize: 8 });
|
|
assert.equal(clockCalls, 1);
|
|
assert.equal(calls.length, 2);
|
|
assert.equal(calls[0].nowMs, 123);
|
|
assert.equal(calls[1].nowMs, 123);
|
|
});
|
|
|
|
test('fails closed for a stalled cursor and bounded page exhaustion', async () => {
|
|
const stalledCursor = { deadlineAtMs: 10, attemptId: 'attempt-1' };
|
|
const stalled = new PrimaryTimeoutSupervisor({
|
|
async requestBatch() {
|
|
return summary({ truncated: true, nextCursor: stalledCursor });
|
|
},
|
|
});
|
|
assert.deepEqual(await stalled.run({ cursor: stalledCursor }), {
|
|
pages: 1,
|
|
scanned: 1,
|
|
accepted: 1,
|
|
alreadyRequested: 0,
|
|
alreadyTerminal: 0,
|
|
failed: 0,
|
|
stopReason: 'cursor_stalled',
|
|
remaining: true,
|
|
nextCursor: stalledCursor,
|
|
});
|
|
|
|
let sequence = 0;
|
|
const limited = new PrimaryTimeoutSupervisor({
|
|
async requestBatch() {
|
|
sequence += 1;
|
|
return summary({
|
|
truncated: true,
|
|
nextCursor: {
|
|
deadlineAtMs: sequence,
|
|
attemptId: `attempt-${sequence}`,
|
|
},
|
|
});
|
|
},
|
|
});
|
|
const limitedResult = await limited.run({ maxPages: 2 });
|
|
assert.equal(limitedResult.stopReason, 'page_limit');
|
|
assert.equal(limitedResult.remaining, true);
|
|
assert.deepEqual(limitedResult.nextCursor, {
|
|
deadlineAtMs: 2,
|
|
attemptId: 'attempt-2',
|
|
});
|
|
});
|
|
|
|
test('rejects unbounded timeout supervisor settings', async () => {
|
|
const supervisor = new PrimaryTimeoutSupervisor({
|
|
async requestBatch() {
|
|
return summary();
|
|
},
|
|
});
|
|
await assert.rejects(supervisor.run({ pageSize: 0 }), /pageSize/);
|
|
await assert.rejects(supervisor.run({ maxPages: 65 }), /maxPages/);
|
|
await assert.rejects(supervisor.run({ nowMs: -1 }), /nowMs/);
|
|
});
|