npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@execbox/process

v0.2.0

Published

Child-process executor for the execbox core package.

Downloads

415

Readme

@execbox/process

Child-process executor for @execbox/core, using the shared QuickJS runner behind a Node IPC boundary.

npm version License

Choose execbox-process When

  • you want QuickJS semantics with a stronger lifecycle boundary than worker threads
  • you want to hard-kill the execution process on timeout
  • you want pooled child-process reuse by default, with explicit ephemeral opt-out when needed

If you want the simplest default backend, use @execbox/quickjs instead.

Install

npm install @execbox/core @execbox/process

Usage

import { resolveProvider } from "@execbox/core";
import { ProcessExecutor } from "@execbox/process";

const provider = resolveProvider({
  name: "tools",
  tools: {
    echo: {
      execute: async (input) => input,
    },
  },
});

const executor = new ProcessExecutor();
const result = await executor.execute("await tools.echo({ ok: true })", [
  provider,
]);

Pooling

ProcessExecutor now defaults to pooled child-process reuse. Each execute() call still gets a fresh QuickJS runtime/context inside the child; only the outer child-process shell is reused.

const executor = new ProcessExecutor({
  mode: "pooled",
  pool: {
    idleTimeoutMs: 30_000,
    maxSize: 2,
    prewarm: true,
  },
});

await executor.prewarm?.(2);
await executor.dispose?.();

Use mode: "ephemeral" to keep the previous behavior of creating a fresh child process for every execution, even if a pool config is present:

const executor = new ProcessExecutor({
  mode: "ephemeral",
});

Default pooled settings are:

  • maxSize: 1
  • minSize: 0
  • idleTimeoutMs: 30_000
  • prewarm: false

Call dispose() in long-lived applications and tests when you want deterministic cleanup of pooled child processes.

Pooling Internals

ProcessExecutor does not keep a QuickJS runtime alive between executions. The pooled resource is the outer child-process shell only.

  • the child process starts once and attaches the shared QuickJS protocol endpoint
  • each execute() call sends one execute message to that endpoint, which starts a fresh runQuickJsSession() inside the child
  • the parent acquires one pooled shell lease, runs runHostTransportSession() for that execution, then releases or evicts the lease when the session settles
  • pooled mode uses a borrowed transport wrapper because the host session always disposes its transport at the end of an execution, while the real pooled child must stay alive for reuse
  • if all pooled children are busy and the pool is already at maxSize, new executions wait in an internal FIFO queue until a shell is released or replaced

Shell reuse rules are:

  • success returns the child to the pool
  • normal guest/tool/runtime failures also return it
  • timeout and internal_error evict it
  • idle children are evicted after idleTimeoutMs

The transport wrapper also caches the first unexpected close reason and replays it to late listeners. That prevents pooled executions from hanging if the child exits before the host session has attached its close handler.

Queue wait time is pool backpressure, not execution time. The configured execution timeout starts only after the lease has been acquired and the host transport session begins.

Security Notes

  • This package improves lifecycle isolation by moving the QuickJS runtime to a fresh child process.
  • It is still not documented as a hard hostile-code boundary equivalent to a container or VM.
  • Providers remain the real capability boundary.
  • Internally it is a thin transport adapter over the shared execbox-protocol host session and the shared QuickJS protocol endpoint.

Examples