mirror of
https://github.com/Abdulazizzn/n8n-enterprise-unlocked.git
synced 2025-12-19 11:01:15 +00:00
feat(core): Add execution runData recovery and status field (#5112)
* adds ExecutionEvents view modal to ExecutionList * fix time rendering and remove wf column * checks for unfinished executions and fails them * prevent re-setting stoppedAt for execution * some cleanup / manually create rundata after crash * quicksave * remove Threads lib, log worker rewrite * cleanup comment * fix sentry destination return value * test for tests... * run tests with single worker * fix tests * remove console log * add endpoint for execution data recovery * lint cleanup and some refactoring * fix accidental recursion * remove cyclic imports * add rundata recovery to Workflowrunner * remove comments * cleanup and refactor * adds a status field to executions * setExecutionStatus on queued worker * fix onWorkflowPostExecute * set waiting from worker * get crashed status into frontend * remove comment * merge fix * cleanup * catch empty rundata in recovery * refactor IExecutionsSummary and inject nodeExecution Errors * reduce default event log size to 10mb from 100mb * add per node execution status * lint fix * merge and lint fix * phrasing change * improve preview rendering and messaging * remove debug * Improve partial rundata recovery * fix labels * fix line through * send manual rundata to ui at crash * some type and msg push fixes * improve recovered item rendering in preview * update workflowStatistics on recover * merge fix * review fixes * merge fix * notify eventbus when ui is back up * add a small timeout to make sure the UI is back up * increase reconnect timeout to 30s * adjust recover timeout and ui connection lost msg * do not stop execution in editor after x reconnects * add executionRecovered push event * fix recovered connection not green * remove reconnect toast and merge existing rundata * merge editor and recovered data for own mode
This commit is contained in:
committed by
GitHub
parent
3a9c257f55
commit
d143f3f2ec
@@ -5,8 +5,13 @@
|
||||
/* eslint-disable @typescript-eslint/no-unsafe-call */
|
||||
/* eslint-disable @typescript-eslint/no-non-null-assertion */
|
||||
/* eslint-disable @typescript-eslint/no-unsafe-assignment */
|
||||
import type { IDeferredPromise, IExecuteResponsePromiseData, IRun } from 'n8n-workflow';
|
||||
import { createDeferredPromise } from 'n8n-workflow';
|
||||
import type {
|
||||
IDeferredPromise,
|
||||
IExecuteResponsePromiseData,
|
||||
IRun,
|
||||
ExecutionStatus,
|
||||
} from 'n8n-workflow';
|
||||
import { createDeferredPromise, LoggerProxy } from 'n8n-workflow';
|
||||
|
||||
import type { ChildProcess } from 'child_process';
|
||||
import { stringify } from 'flatted';
|
||||
@@ -36,6 +41,7 @@ export class ActiveExecutions {
|
||||
process?: ChildProcess,
|
||||
executionId?: string,
|
||||
): Promise<string> {
|
||||
let executionStatus: ExecutionStatus = executionId ? 'running' : 'new';
|
||||
if (executionId === undefined) {
|
||||
// Is a new execution so save in DB
|
||||
|
||||
@@ -45,6 +51,7 @@ export class ActiveExecutions {
|
||||
finished: false,
|
||||
startedAt: new Date(),
|
||||
workflowData: executionData.workflowData,
|
||||
status: executionStatus,
|
||||
};
|
||||
|
||||
if (executionData.retryOf !== undefined) {
|
||||
@@ -59,32 +66,37 @@ export class ActiveExecutions {
|
||||
const execution = ResponseHelper.flattenExecutionData(fullExecutionData);
|
||||
|
||||
const executionResult = await Db.collections.Execution.save(execution as IExecutionFlattedDb);
|
||||
// TODO: what is going on here?
|
||||
executionId =
|
||||
typeof executionResult.id === 'object'
|
||||
? // @ts-ignore
|
||||
executionResult.id!.toString()
|
||||
: executionResult.id + '';
|
||||
if (executionId === undefined) {
|
||||
throw new Error('There was an issue assigning an execution id to the execution');
|
||||
}
|
||||
executionStatus = 'running';
|
||||
} else {
|
||||
// Is an existing execution we want to finish so update in DB
|
||||
|
||||
const execution = {
|
||||
const execution: Pick<IExecutionFlattedDb, 'id' | 'data' | 'waitTill' | 'status'> = {
|
||||
id: executionId,
|
||||
data: stringify(executionData.executionData!),
|
||||
waitTill: null,
|
||||
status: executionStatus,
|
||||
};
|
||||
|
||||
await Db.collections.Execution.update(executionId, execution);
|
||||
}
|
||||
|
||||
// @ts-ignore
|
||||
this.activeExecutions[executionId] = {
|
||||
executionData,
|
||||
process,
|
||||
startedAt: new Date(),
|
||||
postExecutePromises: [],
|
||||
status: executionStatus,
|
||||
};
|
||||
|
||||
// @ts-ignore
|
||||
return executionId;
|
||||
}
|
||||
|
||||
@@ -215,11 +227,31 @@ export class ActiveExecutions {
|
||||
startedAt: data.startedAt,
|
||||
mode: data.executionData.executionMode,
|
||||
workflowId: data.executionData.workflowData.id! as string,
|
||||
status: data.status,
|
||||
});
|
||||
}
|
||||
|
||||
return returnData;
|
||||
}
|
||||
|
||||
async setStatus(executionId: string, status: ExecutionStatus): Promise<void> {
|
||||
if (this.activeExecutions[executionId] === undefined) {
|
||||
LoggerProxy.debug(
|
||||
`There is no active execution with id "${executionId}", can't update status to ${status}.`,
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
this.activeExecutions[executionId].status = status;
|
||||
}
|
||||
|
||||
getStatus(executionId: string): ExecutionStatus {
|
||||
if (this.activeExecutions[executionId] === undefined) {
|
||||
return 'unknown';
|
||||
}
|
||||
|
||||
return this.activeExecutions[executionId].status;
|
||||
}
|
||||
}
|
||||
|
||||
let activeExecutionsInstance: ActiveExecutions | undefined;
|
||||
|
||||
Reference in New Issue
Block a user