Skip to content

perf(runtime): stop sandbox pump loop idle-spinning while awaiting a host call (#3233)#3242

Merged
os-zhuang merged 1 commit into
mainfrom
claude/sandbox-pump-idle-spin-3233
Jul 19, 2026
Merged

perf(runtime): stop sandbox pump loop idle-spinning while awaiting a host call (#3233)#3242
os-zhuang merged 1 commit into
mainfrom
claude/sandbox-pump-idle-spin-3233

Conversation

@os-zhuang

Copy link
Copy Markdown
Contributor

Closes #3233.

问题

hook/action 沙箱的 pump 循环每轮 setImmediate 让出后排空 VM 任务队列。当 body 只是在等待一个在途的宿主调用(慢的 ctx.api 读写,或一次要跨很多 event-loop turn 才 settle 的调用)时,队列每轮都是空的,于是循环以 ~20 万次/秒空转——250ms 的等待里约 5 万次(可从超时信息的 pump 计数看到)。

改动

packages/runtime/src/sandbox/quickjs-runner.ts 的 pump 循环让出改为自适应:

  • 脚本在推进时(某轮执行了 >0 个 VM 任务)保持 setImmediate,近零延迟;
  • 一旦某轮执行 0 个任务(纯等待宿主 promise),让出退避到一个带上限的 setTimeout(1→2→4→8ms,封顶 8ms);
  • 任何被执行的任务(宿主调用 settle、续体恢复)都把状态重置回快路径——所以顺序宿主调用、多 turn 工作都保持低延迟,只有真正空闲的等待才退避,且最多退避到上限。

deadline 兜底与既有的所有 pump-budget / 超时 / 事务语义不变

测试(quickjs-runner.test.ts 新增 2 例)

  • 一个永不 settle 的宿主调用:300ms 等待的 pump 计数现在 < 1000(此前约 5 万);
  • 一个在 ~120ms settle 的调用(正落在退避区间)仍能及时 resolve(远早于超时)。

其余 pump-budget(>1000 顺序调用、>1000-turn 单次调用、永不 settle 超时)、超时解析、事务、嵌套重入等既有用例全部通过(34/34)。附 changeset(patch)。

备注

这是 #3233 里列的「退一步的最小改动:自适应退避」——相对「宿主 settle 时信号唤醒」的完整重写,退避对沙箱这个关键热路径风险更低、控制流不变,同样把空转从 ~20 万/秒降到 ~百余/秒。

🤖 Generated with Claude Code


Generated by Claude Code

…host call (#3233)

The hook/action runner's pump loop yielded via setImmediate every iteration and
drained the VM job queue. While the body only *waits* on an in-flight host
promise the queue is empty each pass, so the loop woke ~200k×/s doing nothing
(~50k iterations for a 250ms wait — surfaced in the timeout message's pump
count).

Make the yield adaptive: stay on setImmediate while the script is progressing;
once a pump executes zero VM jobs, ramp up to a small capped setTimeout (≤8ms).
Any executed job (a settled host call, a resumed continuation) resets the fast
path, so sequential host calls and multi-turn work keep their low latency —
only a genuinely idle wait backs off, by at most the cap. Deadline enforcement
and every existing pump-budget/timeout/transaction guarantee are unchanged.

Tests: a never-settling host call now reports a bounded pump count (<1000 for a
300ms wait, vs ~50k before); a call that settles at ~120ms — squarely in the
backoff regime — still resolves promptly.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01BZguyAaQbyUpwMZ2gMLaAP
@vercel

vercel Bot commented Jul 18, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
spec Error Error Jul 18, 2026 5:21pm

Request Review

@github-actions github-actions Bot added documentation Improvements or additions to documentation tests tooling size/s labels Jul 18, 2026
@github-actions

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

This PR changes 1 package(s): @objectstack/runtime.

16 hand-written doc(s) reference the affected code and may need an implementation-accuracy re-verification:

  • content/docs/api/index.mdx (via @objectstack/runtime)
  • content/docs/api/wire-format.mdx (via @objectstack/runtime)
  • content/docs/automation/hook-bodies.mdx (via @objectstack/runtime)
  • content/docs/concepts/north-star.mdx (via packages/runtime)
  • content/docs/data-modeling/drivers.mdx (via @objectstack/runtime)
  • content/docs/deployment/index.mdx (via @objectstack/runtime)
  • content/docs/deployment/production-readiness.mdx (via @objectstack/runtime)
  • content/docs/deployment/single-project-mode.mdx (via @objectstack/runtime)
  • content/docs/deployment/vercel.mdx (via @objectstack/runtime)
  • content/docs/getting-started/your-first-project.mdx (via @objectstack/runtime)
  • content/docs/permissions/authentication.mdx (via @objectstack/runtime)
  • content/docs/plugins/packages.mdx (via @objectstack/runtime)
  • content/docs/protocol/kernel/http-protocol.mdx (via @objectstack/runtime)
  • content/docs/protocol/kernel/index.mdx (via @objectstack/runtime)
  • content/docs/protocol/kernel/lifecycle.mdx (via @objectstack/runtime)
  • content/docs/releases/implementation-status.mdx (via @objectstack/runtime)

Advisory only. To re-verify, run the docs-accuracy-audit workflow scoped to these files:
node scripts/docs-audit/affected-docs.mjs origin/main → pass the list as args.docs.

@os-zhuang
os-zhuang marked this pull request as ready for review July 19, 2026 12:35
@os-zhuang
os-zhuang merged commit 3a6310c into main Jul 19, 2026
15 of 16 checks passed
@os-zhuang
os-zhuang deleted the claude/sandbox-pump-idle-spin-3233 branch July 19, 2026 12:35
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentation Improvements or additions to documentation size/s tests tooling

Projects

None yet

Development

Successfully merging this pull request may close these issues.

perf(runtime): sandbox pump loop idle-spins ~200k setImmediate wake-ups/sec while awaiting a host call

2 participants