import {
  getConfig
} from "./chunk-2MAQ6JFL.js";
import {
  serverBusy
} from "./chunk-EZYKRG4W.js";

// src/queue/index.ts
function state() {
  const g = globalThis;
  if (!g.__caQueue) {
    g.__caQueue = {
      queue: [],
      activeGlobal: 0,
      activeByEnv: /* @__PURE__ */ new Map()
    };
  }
  return g.__caQueue;
}
function enqueueTurn(envId, run) {
  const s = state();
  const cfg = getConfig();
  const maxDepth = 100;
  if (s.queue.length >= maxDepth) {
    throw serverBusy("turn queue is full");
  }
  return new Promise((resolve, reject) => {
    s.queue.push({
      envId,
      run,
      resolve,
      reject
    });
    drain();
  });
  function drain() {
    const st = state();
    const c = getConfig();
    for (let i = 0; i < st.queue.length; i++) {
      if (st.activeGlobal >= c.concurrency) break;
      const job = st.queue[i];
      const envActive = st.activeByEnv.get(job.envId) ?? 0;
      if (envActive >= c.maxSandboxesPerEnv) continue;
      st.queue.splice(i, 1);
      i--;
      st.activeGlobal++;
      st.activeByEnv.set(job.envId, envActive + 1);
      void (async () => {
        try {
          const r = await job.run();
          job.resolve(r);
        } catch (err) {
          job.reject(err);
        } finally {
          const st2 = state();
          st2.activeGlobal--;
          const envAct = st2.activeByEnv.get(job.envId) ?? 1;
          if (envAct <= 1) st2.activeByEnv.delete(job.envId);
          else st2.activeByEnv.set(job.envId, envAct - 1);
          drain();
        }
      })();
    }
  }
}
function queueStats() {
  const s = state();
  return {
    queued: s.queue.length,
    activeGlobal: s.activeGlobal,
    activeByEnv: Array.from(s.activeByEnv.entries())
  };
}

export {
  enqueueTurn,
  queueStats
};
