Repository navigation
Evaluate adopting dynamic-worker engine for host-cloudflare (Worker Loaders now open beta) #12
Description
Summary
Cloudflare Worker Loaders (Dynamic Workers) moved to open beta on
2026-03-24, available to all paid Workers users. apps/host-cloudflare
currently runs the interim QuickJS-WASM substrate specifically because Worker
Loaders was in closed beta. That constraint is now lifted, so we can evaluate
switching host-cloudflare's engine seam from QuickJS to the
dynamic-worker executor (the same one apps/cloud uses), and the stale
"closed beta" comments/docs should be updated regardless.
Background
The code documents QuickJS as a temporary accommodation, not a preference:
// apps/host-cloudflare/src/execution.ts:21-26
// QuickJS-wasm is the default code substrate because it runs in a single Worker
// with no extra binding. When Cloudflare's dynamic Worker Loader leaves closed
// beta, swap CodeExecutorProvider for the dynamic-worker executor (cloud's) —
// it's a one-Layer change behind this same seam.host-cloudflare/README.md:87-89 and notes/research/product-model.md:89
echo the same: dynamic-worker is the intended cloud runtime.
Latest status (now open beta):
- Dynamic Workers, now in open beta (changelog, 2026-03-24)
- Sandboxing AI agents, 100x faster (blog)
- Worker Loader binding docs
What switching would gain (capability, not just speed)
QuickJS has hard limitations the dynamic-worker runtime does not:
- Binary values: QuickJS cannot represent
Blob/File/Uint8Arrayat the
tool boundary at all; dynamic-worker passes them via structured clone + a
tagged-ArrayBuffer codec. - Serialization fidelity: QuickJS forces JSON round-trips, losing
Date/
Map/Set; dynamic-worker uses Workers RPC structured clone. - Node APIs / network: QuickJS blocks
fetchand has nonodejs_compat
inside the WASM context; dynamic-worker hasnodejs_compatand configurable
globalOutbound. - Isolation: separate workerd isolate vs WASM memory space inside the same
isolate.
Performance is workload-dependent and unmeasured in this repo (the "100x"
figure is isolates-vs-containers, not vs QuickJS). Isolate boot is a few ms, and
warm-cache reuse via get(id) can remove most of the per-call cost (tracked
separately as the warm-cache key fix).
Scope
- Swap
CloudflareCodeExecutorProviderin
apps/host-cloudflare/src/execution.tsfrommakeQuickJsExecutor()to
makeDynamicWorkerExecutor({ loader: env.LOADER })behind the existing
CodeExecutorseam (the "one-Layer change" the comment describes). - Add the
worker_loadersbinding (LOADER) to
apps/host-cloudflare/wrangler.jsonc. - Confirm the deployment's Workers plan is paid (open-beta requirement).
- Decide whether QuickJS stays as a fallback or is removed for host-cloudflare.
- Update the stale "closed beta" comments and
README.mdseam table
(the README already lags reality on R2 blobs + the MCP-session Durable
Object — refresh those while here). - e2e coverage proving code execution + binary/tool I/O works on the new
runtime; gate withformat:check/lint/typecheck/test.
Relationship to other work
- Depends on / benefits from the warm-cache
get(id)key fix in
runtime-dynamic-worker(separate issue) for latency. - Independent of the
github_appauth work (separate issue).
Decision needed
Whether to actually adopt dynamic-worker for host-cloudflare now, or only
update the stale docs/comments and keep QuickJS until a benchmark justifies the
switch. This issue tracks the evaluation; the doc/comment refresh is worth doing
either way.
- To see the specific tasks where the Asana app for GitHub is being used, see below:
Activity