"use strict"; var __create = Object.create; var __defProp = Object.defineProperty; var __getOwnPropDesc = Object.getOwnPropertyDescriptor; var __getOwnPropNames = Object.getOwnPropertyNames; var __getProtoOf = Object.getPrototypeOf; var __hasOwnProp = Object.prototype.hasOwnProperty; var __export = (target, all) => { for (var name in all) __defProp(target, name, { get: all[name], enumerable: true }); }; var __copyProps = (to, from, except, desc) => { if (from && typeof from === "object" || typeof from === "function") { for (let key of __getOwnPropNames(from)) if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable }); } return to; }; var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps( // If the importer is in node compatibility mode or this is not an ESM // file that has been converted to a CommonJS file using a Babel- // compatible transform (i.e. "__esModule" has not been set), then set // "default" to the CommonJS "module.exports" for node compatibility. isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target, mod )); var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod); // src/index.ts var src_exports = {}; __export(src_exports, { WriterEffect: () => WriterEffect }); module.exports = __toCommonJS(src_exports); // src/writer.ts var import_mono_logger2 = require("@zodyac/mono-logger"); var import_node_fs2 = __toESM(require("fs"), 1); var import_node_path2 = __toESM(require("path"), 1); // src/defaults.ts var import_mono_logger = require("@zodyac/mono-logger"); var DEFAULT_FILENAME = (d, i) => { const ts = `${d.getFullYear()}${d.getMonth()}${d.getDate()}`; return `mono-logger-${ts}-${i}.log`; }; var DEFAULT_TRANSFORMER = (ts, lvl, topics, ...args) => { const topics_str = topics.join(":"); const content = args.map((c) => { if (c instanceof Error) return c.stack; if (typeof c === "object") return JSON.stringify(c); return c; }).join(" "); return `${ts.toISOString()} [${import_mono_logger.CODES[lvl]}] ${topics_str} ${content}`; }; // src/utils.ts var import_node_fs = __toESM(require("fs"), 1); var import_node_path = __toESM(require("path"), 1); var META_FILE = ".writer-meta"; function writeMetaFile(dir, iter = 0) { const meta_path = import_node_path.default.resolve(dir, META_FILE); const ts = (/* @__PURE__ */ new Date()).toISOString(); import_node_fs.default.writeFileSync(meta_path, `${ts} ${iter}`); } function readMetaFile(dir) { try { const meta_path = import_node_path.default.resolve(dir, META_FILE); const meta = import_node_fs.default.readFileSync(meta_path, "utf-8"); if (!meta) throw new Error("Empty meta file"); const lines = meta.split("\n"); if (lines.length < 2) throw new Error("Incorrect number of lines"); const [raw_date, raw_iter] = lines; if (!raw_date) throw new Error("Empty date line"); const date = new Date(raw_date); const iter = Number.parseInt(raw_iter); if (Number.isNaN(iter)) return [date, 0]; return [date, iter]; } catch (e) { return [/* @__PURE__ */ new Date(), 0]; } } // src/writer.ts var WriterEffect = class extends import_mono_logger2.MonoEffect { dir_path; filename_gen; max_file_size; transformer; daily_rotate; current_stream; current_output_path; current_file_size = 0; next_iter = 0; _last_used_topics = []; constructor(config) { super( (ts, lvl, topics, ...args) => this.executor.bind(this)(ts, lvl, topics, ...args), config?.level ); this.dir_path = config?.path ?? "logs"; this.transformer = config?.transform ?? DEFAULT_TRANSFORMER; this.max_file_size = (config?.max_file_size ?? 5 * 1024) * 1024; this.filename_gen = config?.filename ?? DEFAULT_FILENAME; this.daily_rotate = config?.daily_rotation ?? false; this.setupFolder(); process.on("exit", () => this._emergency_close()); process.on("uncaughtException", (e) => this._emergency_close(e)); process.on("unhandledRejection", (e) => this._emergency_close(e)); process.on("error", (e) => this._emergency_close(e)); } _emergency_close(e, reason) { if (e) { console.error(e); this.executor(/* @__PURE__ */ new Date(), "error", this._last_used_topics, e); } return new Promise((resolve) => { if (!this.current_stream) return resolve(0); this.current_stream?.close(resolve); }); } // Daily rotation rotation_needed = false; currentTimer; setupDailyRotation() { const now = /* @__PURE__ */ new Date(); const next = new Date( now.getFullYear(), now.getMonth(), now.getDate() + 1, 0, 0, 0, 0 ); const diff = next.getTime() - now.getTime(); this.currentTimer = setTimeout(() => { this.rotation_needed = true; this.currentTimer = void 0; }, diff); } // Files and folders setupFolder() { if (import_node_fs2.default.existsSync(this.dir_path)) { import_node_fs2.default.accessSync(this.dir_path, import_node_fs2.default.constants.W_OK); const meta = readMetaFile(this.dir_path); this.next_iter = meta[1] + 1; return; } import_node_fs2.default.mkdirSync(this.dir_path, { recursive: true }); writeMetaFile(this.dir_path, this.next_iter); } output_path() { const ts = /* @__PURE__ */ new Date(); const filename = this.filename_gen(ts, this.next_iter); return import_node_path2.default.resolve(this.dir_path, filename); } // Streams closeCurrentStream() { if (!this.current_stream) return; if (!this.current_stream.closed) this.current_stream.close(); else this.current_stream.close(); this.current_output_path = void 0; this.current_file_size = 0; } createStream() { if (this.current_stream) this.closeCurrentStream(); if (this.daily_rotate) { if (this.currentTimer) clearTimeout(this.currentTimer); this.setupDailyRotation(); this.current_output_path = this.output_path(); } else { while (true) { const path = this.output_path(); try { const stats = import_node_fs2.default.statSync(path); if (stats.size > this.max_file_size) { this.next_iter++; continue; } } catch (e) { } this.current_output_path = path; break; } } this.current_stream = import_node_fs2.default.createWriteStream(this.current_output_path, { autoClose: true }); writeMetaFile(this.dir_path, this.next_iter); this.next_iter++; return this.current_stream; } selectStream(record) { if (!this.current_stream) return this.createStream(); if (this.daily_rotate) { if (this.rotation_needed) { this.rotation_needed = false; this.createStream(); } } else { const out_size = this.current_file_size + Buffer.byteLength(record, "utf-8"); if (out_size > this.max_file_size) return this.createStream(); } return this.current_stream; } // Effect executor(ts, level, topics, ...args) { this._last_used_topics = topics; const record = this.transformer(ts, level, topics, ...args); const content = `${record} `; const stream = this.selectStream(content); stream.write(content); this.current_file_size += Buffer.byteLength(content, "utf-8"); } }; // Annotate the CommonJS export names for ESM import in node: 0 && (module.exports = { WriterEffect }); //# sourceMappingURL=index.cjs.map