n8n
Version:
n8n Workflow Automation Tool
307 lines • 14.4 kB
JavaScript
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
__setModuleDefault(result, mod);
return result;
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.MessageEventBusLogWriter = void 0;
const AbstractEventMessage_1 = require("../EventMessageClasses/AbstractEventMessage");
const n8n_core_1 = require("n8n-core");
const path_1 = __importStar(require("path"));
const worker_threads_1 = require("worker_threads");
const fs_1 = require("fs");
const readline_1 = __importDefault(require("readline"));
const remove_1 = __importDefault(require("lodash/remove"));
const EventMessageGeneric_1 = require("../EventMessageClasses/EventMessageGeneric");
const EventMessageWorkflow_1 = require("../EventMessageClasses/EventMessageWorkflow");
const n8n_workflow_1 = require("n8n-workflow");
const EventMessageAudit_1 = require("../EventMessageClasses/EventMessageAudit");
const EventMessageNode_1 = require("../EventMessageClasses/EventMessageNode");
const EventMessageConfirm_1 = require("../EventMessageClasses/EventMessageConfirm");
const events_1 = require("events");
const constants_1 = require("../../constants");
const Logger_1 = require("../../Logger");
const typedi_1 = __importDefault(require("typedi"));
const config_1 = require("@n8n/config");
class MessageEventBusLogWriter {
constructor() {
this.logger = typedi_1.default.get(Logger_1.Logger);
this.globalConfig = typedi_1.default.get(config_1.GlobalConfig);
}
get worker() {
return this._worker;
}
static async getInstance(options) {
var _a, _b, _c, _d;
if (!MessageEventBusLogWriter.instance) {
MessageEventBusLogWriter.instance = new MessageEventBusLogWriter();
MessageEventBusLogWriter.options = {
logFullBasePath: path_1.default.join((_a = options === null || options === void 0 ? void 0 : options.logBasePath) !== null && _a !== void 0 ? _a : typedi_1.default.get(n8n_core_1.InstanceSettings).n8nFolder, (_b = options === null || options === void 0 ? void 0 : options.logBaseName) !== null && _b !== void 0 ? _b : typedi_1.default.get(config_1.GlobalConfig).eventBus.logWriter.logBaseName),
keepNumberOfFiles: (_c = options === null || options === void 0 ? void 0 : options.keepNumberOfFiles) !== null && _c !== void 0 ? _c : typedi_1.default.get(config_1.GlobalConfig).eventBus.logWriter.keepLogCount,
maxFileSizeInKB: (_d = options === null || options === void 0 ? void 0 : options.maxFileSizeInKB) !== null && _d !== void 0 ? _d : typedi_1.default.get(config_1.GlobalConfig).eventBus.logWriter.maxFileSizeInKB,
};
await MessageEventBusLogWriter.instance.startThread();
}
return MessageEventBusLogWriter.instance;
}
startLogging() {
if (this.worker) {
this.worker.postMessage({ command: 'startLogging', data: {} });
}
}
startRecoveryProcess() {
if (this.worker) {
this.worker.postMessage({ command: 'startRecoveryProcess', data: {} });
}
}
isRecoveryProcessRunning() {
return (0, fs_1.existsSync)(this.getRecoveryInProgressFileName());
}
endRecoveryProcess() {
if (this.worker) {
this.worker.postMessage({ command: 'endRecoveryProcess', data: {} });
}
}
async startThread() {
if (this.worker) {
await this.close();
}
await MessageEventBusLogWriter.instance.spawnThread();
if (this.worker) {
this.worker.postMessage({ command: 'initialize', data: MessageEventBusLogWriter.options });
}
}
async spawnThread() {
const parsedName = (0, path_1.parse)(__filename);
let workerFileName;
if (constants_1.inTest) {
workerFileName = './dist/eventbus/MessageEventBusWriter/MessageEventBusLogWriterWorker.js';
}
else {
workerFileName = path_1.default.join(parsedName.dir, `${parsedName.name}Worker${parsedName.ext}`);
}
this._worker = new worker_threads_1.Worker(workerFileName);
if (this.worker) {
this.worker.on('messageerror', async (error) => {
this.logger.error('Event Bus Log Writer thread error, attempting to restart...', error);
await MessageEventBusLogWriter.instance.startThread();
});
return true;
}
return false;
}
async close() {
if (this.worker) {
await this.worker.terminate();
this._worker = undefined;
}
}
putMessage(msg) {
if (this.worker) {
this.worker.postMessage({ command: 'appendMessageToLog', data: msg.serialize() });
}
}
confirmMessageSent(msgId, source) {
if (this.worker) {
this.worker.postMessage({
command: 'confirmMessageSent',
data: new EventMessageConfirm_1.EventMessageConfirm(msgId, source).serialize(),
});
}
}
async getMessages(mode = 'all', logHistory = 1) {
const results = {
loggedMessages: [],
sentMessages: [],
unfinishedExecutions: {},
};
const configLogCount = this.globalConfig.eventBus.logWriter.keepLogCount;
const logCount = logHistory ? Math.min(configLogCount, logHistory) : configLogCount;
for (let i = logCount; i >= 0; i--) {
const logFileName = this.getLogFileName(i);
if (logFileName) {
await this.readLoggedMessagesFromFile(results, mode, logFileName);
}
}
return results;
}
async readLoggedMessagesFromFile(results, mode, logFileName) {
if (logFileName && (0, fs_1.existsSync)(logFileName)) {
try {
const rl = readline_1.default.createInterface({
input: (0, fs_1.createReadStream)(logFileName),
crlfDelay: Infinity,
});
rl.on('line', (line) => {
var _a;
try {
const json = (0, n8n_workflow_1.jsonParse)(line);
if ((0, AbstractEventMessage_1.isEventMessageOptions)(json) && json.__type !== undefined) {
const msg = this.getEventMessageObjectByType(json);
if (msg !== null)
results.loggedMessages.push(msg);
if ((msg === null || msg === void 0 ? void 0 : msg.eventName) && ((_a = msg.payload) === null || _a === void 0 ? void 0 : _a.executionId)) {
const executionId = msg.payload.executionId;
switch (msg.eventName) {
case 'n8n.workflow.started':
if (!Object.keys(results.unfinishedExecutions).includes(executionId)) {
results.unfinishedExecutions[executionId] = [];
}
results.unfinishedExecutions[executionId] = [msg];
break;
case 'n8n.workflow.success':
case 'n8n.workflow.failed':
case 'n8n.workflow.crashed':
case 'n8n.execution.throttled':
case 'n8n.execution.started-during-bootup':
delete results.unfinishedExecutions[executionId];
break;
case 'n8n.node.started':
case 'n8n.node.finished':
if (!Object.keys(results.unfinishedExecutions).includes(executionId)) {
results.unfinishedExecutions[executionId] = [];
}
results.unfinishedExecutions[executionId].push(msg);
break;
}
}
}
if ((0, EventMessageConfirm_1.isEventMessageConfirm)(json) && mode !== 'all') {
const removedMessage = (0, remove_1.default)(results.loggedMessages, (e) => e.id === json.confirm);
if (mode === 'sent') {
results.sentMessages.push(...removedMessage);
}
}
}
catch (error) {
this.logger.error(`Error reading line messages from file: ${logFileName}, line: ${line}, ${error.message}}`);
}
});
await (0, events_1.once)(rl, 'close');
}
catch {
this.logger.error(`Error reading logged messages from file: ${logFileName}`);
}
}
return results;
}
getLogFileName(counter) {
if (counter) {
return `${MessageEventBusLogWriter.options.logFullBasePath}-${counter}.log`;
}
else {
return `${MessageEventBusLogWriter.options.logFullBasePath}.log`;
}
}
getRecoveryInProgressFileName() {
return `${MessageEventBusLogWriter.options.logFullBasePath}.recoveryInProgress`;
}
cleanAllLogs() {
for (let i = 0; i <= MessageEventBusLogWriter.options.keepNumberOfFiles; i++) {
if ((0, fs_1.existsSync)(this.getLogFileName(i))) {
(0, fs_1.rmSync)(this.getLogFileName(i));
}
}
}
async getMessagesByExecutionId(executionId, logHistory) {
const result = [];
const configLogCount = this.globalConfig.eventBus.logWriter.keepLogCount;
const logCount = logHistory ? Math.min(configLogCount, logHistory) : configLogCount;
for (let i = 0; i < logCount; i++) {
const logFileName = this.getLogFileName(i);
if (logFileName) {
result.push(...(await this.readFromFileByExecutionId(executionId, logFileName)));
}
}
return result.sort((a, b) => a.ts.diff(b.ts).toMillis());
}
async readFromFileByExecutionId(executionId, logFileName) {
const messages = [];
if (logFileName && (0, fs_1.existsSync)(logFileName)) {
try {
const rl = readline_1.default.createInterface({
input: (0, fs_1.createReadStream)(logFileName),
crlfDelay: Infinity,
});
rl.on('line', (line) => {
var _a;
try {
const json = (0, n8n_workflow_1.jsonParse)(line);
if ((0, AbstractEventMessage_1.isEventMessageOptions)(json) &&
json.__type !== undefined &&
((_a = json.payload) === null || _a === void 0 ? void 0 : _a.executionId) === executionId) {
const msg = this.getEventMessageObjectByType(json);
if (msg !== null)
messages.push(msg);
}
}
catch {
this.logger.error(`Error reading line messages from file: ${logFileName}, line: ${line}`);
}
});
await (0, events_1.once)(rl, 'close');
}
catch {
this.logger.error(`Error reading logged messages from file: ${logFileName}`);
}
}
return messages;
}
async getMessagesAll() {
return (await this.getMessages('all')).loggedMessages;
}
async getMessagesSent() {
return (await this.getMessages('sent')).sentMessages;
}
async getMessagesUnsent() {
return (await this.getMessages('unsent')).loggedMessages;
}
async getUnfinishedExecutions() {
return (await this.getMessages('unfinished')).unfinishedExecutions;
}
async getUnsentAndUnfinishedExecutions() {
const result = await this.getMessages('unsent');
return {
unsentMessages: result.loggedMessages,
unfinishedExecutions: result.unfinishedExecutions,
};
}
getEventMessageObjectByType(message) {
switch (message.__type) {
case "$$EventMessage":
return new EventMessageGeneric_1.EventMessageGeneric(message);
case "$$EventMessageWorkflow":
return new EventMessageWorkflow_1.EventMessageWorkflow(message);
case "$$EventMessageAudit":
return new EventMessageAudit_1.EventMessageAudit(message);
case "$$EventMessageNode":
return new EventMessageNode_1.EventMessageNode(message);
default:
return null;
}
}
}
exports.MessageEventBusLogWriter = MessageEventBusLogWriter;
//# sourceMappingURL=MessageEventBusLogWriter.js.map
;