Use this file to discover all available pages before exploring further.
Example on GitHub
Full working example with a sandboxed Hono dev server.
Let users run their own dev servers inside a sandboxed isolate. Secure Exec can host long-lived Node servers from untrusted code, not just one-shot scripts. The host starts the user’s server inside the isolate, verifies it’s ready, proxies requests to it, and tears it down when done.
Start a user-provided Hono server inside the isolate, wait for its health endpoint, fetch a response from the host, then terminate.
Hono Dev Server
import { createServer } from "node:net";import { NodeRuntime, allowAllNetwork, createNodeDriver, createNodeRuntimeDriverFactory,} from "secure-exec";const host = "127.0.0.1";const port = await findOpenPort();const logs: string[] = [];const runtime = new NodeRuntime({ systemDriver: createNodeDriver({ useDefaultNetwork: true, permissions: { ...allowAllNetwork }, }), runtimeDriverFactory: createNodeRuntimeDriverFactory(), memoryLimit: 128, cpuTimeLimitMs: 60_000,});const execPromise = runtime.exec(` import { Hono } from "hono"; import { serve } from "@hono/node-server"; const app = new Hono(); app.get("/", (c) => c.text("hello from sandboxed hono")); app.get("/health", (c) => c.json({ ok: true })); serve({ fetch: app.fetch, port: ${port}, hostname: "${host}", }); console.log("server:listening:${port}"); await new Promise(() => {});`, { filePath: "/app/server.mjs", onStdio: (event) => logs.push(`[${event.channel}] ${event.message}`),});try { await waitForServer(runtime, `http://${host}:${port}/health`); const response = await runtime.network.fetch(`http://${host}:${port}/`, { method: "GET", }); console.log(response.status); // 200 console.log(response.body); // "hello from sandboxed hono"} finally { await runtime.terminate(); await execPromise.catch(() => undefined);}async function findOpenPort(): Promise<number> { return new Promise((resolve, reject) => { const server = createServer(); server.once("error", reject); server.listen(0, host, () => { const address = server.address(); if (!address || typeof address !== "object") { reject(new Error("Failed to allocate a port")); server.close(); return; } const allocatedPort = address.port; server.close((error) => { if (error) { reject(error); return; } resolve(allocatedPort); }); }); });}async function waitForServer(runtime: NodeRuntime, url: string): Promise<void> { for (let attempt = 0; attempt < 50; attempt += 1) { try { const response = await runtime.network.fetch(url, { method: "GET" }); if (response.status === 200) { return; } } catch { // Retry until the server is ready. } await new Promise((resolve) => setTimeout(resolve, 100)); } throw new Error(`Timed out waiting for ${url}`);}
Your platform stays in control of the lifecycle while the user’s code runs isolated:
The isolate owns the user’s server process and application code
The host verifies readiness through the network adapter
The host proxies traffic to the sandboxed server
The host terminates the runtime when the session ends
This is useful for platforms that let users write and preview server-side code (live coding environments, serverless playgrounds, educational tools) without giving them access to the host machine.For a simpler request-only model without a bound TCP port, Hono also works with direct app.fetch(...) handlers. See Quickstart.