fix(schedule): close fixed-rate delivery review gaps

This commit is contained in:
pku-xht
2026-08-08 02:54:36 +08:00
committed by Tianyi Cui
parent d2be9a634f
commit 9a0bfc143b
3 changed files with 29 additions and 21 deletions

View File

@@ -28,11 +28,9 @@ import {
ScheduleId,
createAfterScheduleRecord,
foldScheduleEvents,
scheduleReminderPresentation,
} from '@deepseek-ai/dsh-tool-schedule'
import {
createEveryScheduleRecord,
resolveEveryOccurrence,
} from '../../../packages/schedule/tool-schedule/src/domain.ts'
import type { EveryScheduleRecord } from '@deepseek-ai/dsh-tool-schedule'
const MODE = webSnapshotMode()
const OVERLAY = fileURLToPath(new URL('../../../examples/web-schedule/cordis.yml', import.meta.url))
@@ -394,22 +392,23 @@ describe.skipIf(MODE === 'record')('web e2e: fixed-rate restart and batch receip
title: 'Every restart session', messageSeqs: [], source: { kind: 'user' },
})
const seededAt = Date.now()
const records = [
createEveryScheduleRecord(
ScheduleId('schedule-every-primary'),
EVERY_PROMPTS[0],
300,
seededAt - 1_200_000,
),
createEveryScheduleRecord(
ScheduleId('schedule-every-secondary'),
EVERY_PROMPTS[1],
300,
seededAt - 1_140_000,
),
const records: readonly [EveryScheduleRecord, EveryScheduleRecord] = [
{
id: ScheduleId('schedule-every-primary'),
kind: 'every',
prompt: EVERY_PROMPTS[0],
everySeconds: 300,
scheduledAt: new Date(seededAt - 900_000).toISOString(),
},
{
id: ScheduleId('schedule-every-secondary'),
kind: 'every',
prompt: EVERY_PROMPTS[1],
everySeconds: 300,
scheduledAt: new Date(seededAt - 840_000).toISOString(),
},
]
const [primary, secondary] = records
if (primary === undefined || secondary === undefined) throw new Error('missing every fixtures')
const recordIds = new Set(records.map(record => record.id))
for (const record of records) {
seeded.append('schedule/change', { version: 1, operation: 'create', schedule: record })
@@ -470,7 +469,16 @@ describe.skipIf(MODE === 'record')('web e2e: fixed-rate restart and batch receip
let batchSnapshot = batchBlock.text
const occurrencePlaceholders = ['{{primaryOccurrenceAt}}', '{{secondaryOccurrenceAt}}'] as const
for (const [index, record] of records.entries()) {
const occurrenceAt = resolveEveryOccurrence(record, Date.parse(acceptedAt)).occurrenceAt
const dispatch = dispatches.find(event => event.type === 'schedule/change'
&& event.data.operation === 'dispatch'
&& event.data.id === record.id)
if (dispatch?.type !== 'schedule/change') throw new Error(`missing dispatch for ${record.id}`)
const occurrenceAt = scheduleReminderPresentation(
agent.session.events,
dispatch.seq,
agent.session.header.seedLength ?? 0,
)?.occurrenceAt
if (occurrenceAt === undefined) throw new Error(`missing receipt occurrence for ${record.id}`)
batchSnapshot = batchSnapshot.split(occurrenceAt).join(occurrencePlaceholders[index])
}
await compareOrRefreshGolden(EVERY_BATCH_EXPECTED, batchSnapshot, MODE)

View File

@@ -471,7 +471,7 @@ export function registerScheduleTools(
&& isRecurringGateExhausted(folded.lastRecurringAcceptedAt)) {
return {
code: 'time_out_of_range',
message: 'The scheduled time must be representable as a four-digit-year RFC 3339 UTC instant.',
message: 'No compliant recurring delivery time remains representable within the four-digit-year range.',
}
}
const id = allocateScheduleId(folded)

View File

@@ -327,7 +327,7 @@ describe('Schedule tool protocol', () => {
prompt: 'rolled back', every_seconds: 300,
}))).toEqual({
code: 'time_out_of_range',
message: 'The scheduled time must be representable as a four-digit-year RFC 3339 UTC instant.',
message: 'No compliant recurring delivery time remains representable within the four-digit-year range.',
})
expect(test.agent.session.events.filter(event => event.type === 'schedule/change')).toHaveLength(2)
expect(value(await execute(test, 'schedule_list', {}))).toEqual([])