import { createRequire as __cr } from 'node:module'; const require = __cr(import.meta.url);

// src/daemon/logger.ts
import fs from "fs";
import path from "path";

// src/daemon/log-buffer.ts
var LOG_RING_BUFFER_CAPACITY = 1e3;
var LOG_QUERY_DEFAULT_LIMIT = 100;
var LogRingBuffer = class {
  buffer;
  head = 0;
  count = 0;
  sequence = 0;
  startSequence = 0;
  capacity;
  constructor(capacity = LOG_RING_BUFFER_CAPACITY) {
    this.capacity = capacity;
    this.buffer = new Array(capacity);
  }
  push(entry) {
    this.buffer[this.head] = entry;
    this.head = (this.head + 1) % this.capacity;
    if (this.count < this.capacity) {
      this.count++;
    } else {
      this.startSequence++;
    }
    this.sequence++;
  }
  since(cursor, options) {
    const limit = options?.limit ?? LOG_QUERY_DEFAULT_LIMIT;
    const minLevel = options?.level ? LEVEL_ORDER[options.level] : 0;
    let startIdx = 0;
    let cursorReset = false;
    if (cursor !== null) {
      const seq = parseInt(cursor, 10);
      if (isNaN(seq) || seq < this.startSequence) {
        cursorReset = true;
        startIdx = 0;
      } else {
        startIdx = seq - this.startSequence;
      }
    } else {
      startIdx = Math.max(0, this.count - limit);
    }
    const entries = [];
    for (let i = startIdx; i < this.count && entries.length < limit; i++) {
      const bufIdx = (this.head - this.count + i + this.capacity) % this.capacity;
      const entry = this.buffer[bufIdx];
      if (entry && LEVEL_ORDER[entry.level] >= minLevel) {
        entries.push(entry);
      }
    }
    const result = {
      entries,
      cursor: String(this.sequence)
    };
    if (cursorReset) result.cursor_reset = true;
    return result;
  }
};

// src/daemon/logger.ts
var LEVEL_ORDER = {
  debug: 0,
  info: 1,
  warn: 2,
  error: 3
};
var DaemonLogger = class {
  logPath;
  fd = null;
  currentSize = 0;
  level;
  maxSize;
  maxFiles;
  logDir;
  ringBuffer;
  constructor(logDir, options = {}) {
    this.logDir = logDir;
    this.logPath = path.join(logDir, "daemon.log");
    this.level = options.level ?? "info";
    this.maxSize = options.maxSize ?? 5242880;
    this.maxFiles = options.maxFiles ?? 3;
    this.ringBuffer = new LogRingBuffer();
    fs.mkdirSync(logDir, { recursive: true });
    this.fd = fs.openSync(this.logPath, "a");
    try {
      this.currentSize = fs.fstatSync(this.fd).size;
    } catch {
      this.currentSize = 0;
    }
  }
  debug(component, message, data) {
    this.write("debug", component, message, data);
  }
  info(component, message, data) {
    this.write("info", component, message, data);
  }
  warn(component, message, data) {
    this.write("warn", component, message, data);
  }
  error(component, message, data) {
    this.write("error", component, message, data);
  }
  close() {
    if (this.fd !== null) {
      fs.closeSync(this.fd);
      this.fd = null;
    }
  }
  getRingBuffer() {
    return this.ringBuffer;
  }
  write(level, component, message, data) {
    if (LEVEL_ORDER[level] < LEVEL_ORDER[this.level]) return;
    const entry = {
      timestamp: (/* @__PURE__ */ new Date()).toISOString(),
      level,
      component,
      message,
      ...data
    };
    this.ringBuffer.push(entry);
    const line = JSON.stringify(entry) + "\n";
    const bytes = Buffer.byteLength(line);
    if (this.currentSize + bytes > this.maxSize) {
      this.rotate();
    }
    if (this.fd !== null) {
      fs.writeSync(this.fd, line);
      this.currentSize += bytes;
    }
  }
  rotate() {
    this.close();
    for (let i = this.maxFiles - 1; i >= 1; i--) {
      const from = path.join(this.logDir, `daemon.${i}.log`);
      const to = path.join(this.logDir, `daemon.${i + 1}.log`);
      if (fs.existsSync(from)) {
        if (i + 1 > this.maxFiles) {
          fs.unlinkSync(from);
        } else {
          fs.renameSync(from, to);
        }
      }
    }
    if (fs.existsSync(this.logPath)) {
      fs.renameSync(this.logPath, path.join(this.logDir, "daemon.1.log"));
    }
    this.fd = fs.openSync(this.logPath, "a");
    this.currentSize = 0;
  }
};

export {
  LEVEL_ORDER,
  DaemonLogger
};
//# sourceMappingURL=chunk-QLUE3BUL.js.map