feat(core): Increase Cron observability (#17626)

This commit is contained in:
Iván Ovejero
2025-07-28 11:54:33 +02:00
committed by GitHub
parent 921cdb6fd0
commit 08c38a76f3
12 changed files with 175 additions and 40 deletions

View File

@@ -56,7 +56,7 @@ export class Cron implements INodeType {
};
// Get all the trigger times
const cronTimes = (triggerTimes.item || []).map(toCronExpression);
const expressions = (triggerTimes.item || []).map(toCronExpression);
// The trigger function to execute when the cron-time got reached
// or when manually triggered
@@ -65,7 +65,7 @@ export class Cron implements INodeType {
};
// Register the cron-jobs
cronTimes.forEach((cronTime) => this.helpers.registerCron(cronTime, executeTrigger));
expressions.forEach((expression) => this.helpers.registerCron({ expression }, executeTrigger));
return {
manualTriggerFunction: async () => executeTrigger(),

View File

@@ -451,7 +451,8 @@ export class ScheduleTrigger implements INodeType {
if (this.getMode() !== 'manual') {
for (const { interval, cronExpression, recurrence } of rules) {
try {
this.helpers.registerCron(cronExpression, () => executeTrigger(recurrence));
const cron = { expression: cronExpression, recurrence };
this.helpers.registerCron(cron, () => executeTrigger(recurrence));
} catch (error) {
if (interval.field === 'cronExpression') {
throw new NodeOperationError(this.getNode(), 'Invalid cron expression', {

View File

@@ -24,6 +24,17 @@ import {
type Workflow,
} from 'n8n-workflow';
const logger = mock({
scoped: jest.fn().mockReturnValue(
mock({
debug: jest.fn(),
info: jest.fn(),
warn: jest.fn(),
error: jest.fn(),
}),
),
});
type MockDeepPartial<T> = Parameters<typeof mock<T>>[0];
type TestTriggerNodeOptions = {
@@ -70,7 +81,11 @@ export async function testTriggerNode(
) as INode;
const workflow = mock<Workflow>({ timezone: options.timezone ?? 'Europe/Berlin' });
const scheduledTaskManager = new ScheduledTaskManager(mock<InstanceSettings>());
const scheduledTaskManager = new ScheduledTaskManager(
mock<InstanceSettings>(),
logger as any,
mock(),
);
const helpers = mock<ITriggerFunctions['helpers']>({
createDeferredPromise,
returnJsonArray,
@@ -130,7 +145,11 @@ export async function testWebhookTriggerNode(
) as INode;
const workflow = mock<Workflow>({ timezone: options.timezone ?? 'Europe/Berlin' });
const scheduledTaskManager = new ScheduledTaskManager(mock<InstanceSettings>());
const scheduledTaskManager = new ScheduledTaskManager(
mock<InstanceSettings>(),
logger as any,
mock(),
);
const helpers = mock<ITriggerFunctions['helpers']>({
returnJsonArray,
registerCron: (cronExpression, onTick) =>