claude-overnight 1.25.12 → 1.25.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- export declare const VERSION = "1.25.12";
1
+ export declare const VERSION = "1.25.13";
package/dist/_version.js CHANGED
@@ -1,2 +1,2 @@
1
1
  // Auto-generated by build — do not edit manually.
2
- export const VERSION = "1.25.12";
2
+ export const VERSION = "1.25.13";
package/dist/index.js CHANGED
@@ -806,32 +806,19 @@ async function main() {
806
806
  }
807
807
  }
808
808
  process.stdout.write(` ${chalk.dim(`◆ Pinging ${pending.map(([r, p]) => `${r} (${p.displayName})`).join(", ")}…`)}\n`);
809
- // Cursor proxy: each saved model is a distinct provider id (`cursor-composer-2`, etc.), so
810
- // planner + executor + fast can schedule multiple preflights. The bundled proxy typically
811
- // handles one agent query at a time parallel preflights starve each other and hit the
812
- // 20s timeout. Run non-proxy checks in parallel, then cursor proxy checks one at a time
813
- // (preserve original `pending` order for messages).
809
+ // All preflights run in parallel. Cursor proxy preflights now go through a
810
+ // plain HTTP POST /v1/messages (see preflightCursorProxyViaHttp) instead of
811
+ // spawning the claude CLI, and the bundled proxy has no internal queue
812
+ // each request spawns its own cursor-agent subprocess (request-listener.js
813
+ // handleAnthropicMessages runAgentStream).
814
814
  const progress = (msg) => process.stdout.write(chalk.dim(` ${msg}\n`));
815
- /** Cursor agent cold start + model variance can exceed 20s; API providers stay tight. */
815
+ /** Cursor agent cold start + thinking-variant model latency can exceed 20s; API providers stay tight. */
816
816
  const preflightMs = (p) => isCursorProxyProvider(p) ? 60_000 : 20_000;
817
- const nonCursorIdx = [];
818
- const cursorIdx = [];
819
- for (let i = 0; i < pending.length; i++) {
820
- if (isCursorProxyProvider(pending[i][1]))
821
- cursorIdx.push(i);
822
- else
823
- nonCursorIdx.push(i);
824
- }
825
- const slot = Array.from({ length: pending.length });
826
- await Promise.all(nonCursorIdx.map(async (i) => {
827
- const [role, p] = pending[i];
828
- slot[i] = { role, provider: p, result: await preflightProvider(p, cwd, preflightMs(p), { onProgress: progress }) };
829
- }));
830
- for (const i of cursorIdx) {
831
- const [role, p] = pending[i];
832
- slot[i] = { role, provider: p, result: await preflightProvider(p, cwd, preflightMs(p), { onProgress: progress }) };
833
- }
834
- const results = slot;
817
+ const results = await Promise.all(pending.map(async ([role, p]) => ({
818
+ role,
819
+ provider: p,
820
+ result: await preflightProvider(p, cwd, preflightMs(p), { onProgress: progress }),
821
+ })));
835
822
  for (const { role, provider, result } of results) {
836
823
  if (!result.ok) {
837
824
  console.error(chalk.red(` ✗ ${role} preflight failed: ${chalk.dim(result.error)}`));
package/dist/providers.js CHANGED
@@ -256,6 +256,12 @@ function normalizeBaseURL(raw) {
256
256
  * so misconfig doesn't delay the main run.
257
257
  */
258
258
  export async function preflightProvider(p, cwd, timeoutMs = 20_000, opts) {
259
+ // Cursor proxy path: direct HTTP POST /v1/messages instead of spawning a
260
+ // full `claude` CLI subprocess. Same end-to-end validation (proxy + auth +
261
+ // cursor-agent + model) without per-check 1-3s of CLI spawn overhead.
262
+ if (isCursorProxyProvider(p)) {
263
+ return preflightCursorProxyViaHttp(p, timeoutMs, opts);
264
+ }
259
265
  let env;
260
266
  try {
261
267
  env = envFor(p);
@@ -264,11 +270,7 @@ export async function preflightProvider(p, cwd, timeoutMs = 20_000, opts) {
264
270
  return { ok: false, error: err.message };
265
271
  }
266
272
  // Show what we're checking
267
- const keyInfo = p.cursorProxy
268
- ? `proxy auth`
269
- : p.keyEnv
270
- ? `env ${p.keyEnv}`
271
- : "stored key";
273
+ const keyInfo = p.keyEnv ? `env ${p.keyEnv}` : "stored key";
272
274
  opts?.onProgress?.(`checking ${p.model} (${keyInfo})…`);
273
275
  let pq;
274
276
  try {
@@ -327,6 +329,57 @@ export async function preflightProvider(p, cwd, timeoutMs = 20_000, opts) {
327
329
  catch { }
328
330
  }
329
331
  }
332
+ /**
333
+ * Cursor-proxy-only preflight: HTTP POST /v1/messages instead of spawning the
334
+ * `claude` CLI. The proxy spawns its own cursor-agent subprocess per request
335
+ * (see cursor-composer-in-claude agent-runner.js) with no internal queue —
336
+ * callers can safely run these in parallel.
337
+ */
338
+ async function preflightCursorProxyViaHttp(p, timeoutMs, opts) {
339
+ opts?.onProgress?.(`checking ${p.model} (proxy auth)…`);
340
+ const baseURL = (p.baseURL || PROXY_DEFAULT_URL).replace(/\/$/, "");
341
+ const key = resolveCursorProxyKey();
342
+ const headers = { "content-type": "application/json" };
343
+ if (key)
344
+ headers["authorization"] = `Bearer ${key}`;
345
+ const controller = new AbortController();
346
+ let elapsed = 0;
347
+ const PROGRESS_INTERVAL_MS = 3_000;
348
+ const progressTimer = setInterval(() => {
349
+ elapsed += PROGRESS_INTERVAL_MS;
350
+ opts?.onProgress?.(`still waiting… (${(elapsed / 1000).toFixed(1)}s)`);
351
+ }, PROGRESS_INTERVAL_MS);
352
+ const deadline = setTimeout(() => controller.abort(), timeoutMs);
353
+ try {
354
+ const res = await fetch(`${baseURL}/v1/messages`, {
355
+ method: "POST",
356
+ headers,
357
+ body: JSON.stringify({
358
+ model: p.model,
359
+ max_tokens: 1,
360
+ messages: [{ role: "user", content: "ok" }],
361
+ }),
362
+ signal: controller.signal,
363
+ });
364
+ if (!res.ok) {
365
+ const text = await res.text().catch(() => "");
366
+ return { ok: false, error: `HTTP ${res.status}: ${text.slice(0, 200)}` };
367
+ }
368
+ // Drain body so the connection closes cleanly; we don't care about content.
369
+ await res.text().catch(() => "");
370
+ return { ok: true };
371
+ }
372
+ catch (err) {
373
+ if (err?.name === "AbortError") {
374
+ return { ok: false, error: `timeout after ${Math.round(timeoutMs / 1000)}s` };
375
+ }
376
+ return { ok: false, error: String(err?.message || err).slice(0, 200) };
377
+ }
378
+ finally {
379
+ clearTimeout(deadline);
380
+ clearInterval(progressTimer);
381
+ }
382
+ }
330
383
  // ── Cursor API Proxy ──
331
384
  export const PROXY_DEFAULT_URL = "http://127.0.0.1:8765";
332
385
  /** Check if a provider routes through cursor-composer-in-claude. */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "claude-overnight",
3
- "version": "1.25.12",
3
+ "version": "1.25.13",
4
4
  "description": "Parallel Claude agents in git worktrees with a usage cap that reserves headroom for your interactive Claude Code. Crash-safe resume. Provider-agnostic model catalog (Anthropic, Cursor, OpenAI, Gemini, DeepSeek, Llama, Qwen) with capability-based task scoping.",
5
5
  "type": "module",
6
6
  "bin": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "claude-overnight",
3
- "version": "1.25.12",
3
+ "version": "1.25.13",
4
4
  "description": "Claude Code skill for understanding, installing, and inspecting claude-overnight runs -- parallel Claude agents in git worktrees with thinking waves, multi-wave steering, and crash-safe resume. Supports Cursor API Proxy, Qwen, OpenRouter.",
5
5
  "author": {
6
6
  "name": "Francesco Fornace"