Template programs
Give a template a main, and every sandbox from it boots with your program already serving HTTP. Alchemy bundles it, copies it into the template, and E2B snapshots the template once the program answers.
An Effect program
Section titled “An Effect program”import * as E2B from "@alchemy.run/e2b";import * as Effect from "effect/Effect";import * as HttpServerResponse from "effect/http/HttpServerResponse";
export default class Program extends E2B.Template<Program>()( "Program", { main: import.meta.url, port: 3000 }, Effect.gen(function* () { return { fetch: Effect.succeed(HttpServerResponse.text("hello from a sandbox")), }; }),) {}The program runs with Bun from /app, on oven/bun:1 by default. Set image or dockerfile for your own environment; it needs Bun.
Call it
Section titled “Call it”const sandboxes = yield* E2B.CreateSandbox(Program);const sandbox = yield* sandboxes.create({ timeout: 300 });const port = yield* sandbox.getTcpPort(3000);const res = yield* port.fetch(HttpClientRequest.get("/"));Serve it from one sandbox
Section titled “Serve it from one sandbox”import * as E2B from "@alchemy.run/e2b";import * as Alchemy from "alchemy";import * as Output from "alchemy/Output";import * as Effect from "effect/Effect";import Program from "./src/Program.ts";
export default Alchemy.Stack( "Program", { providers: E2B.providers(), state: Alchemy.localState() }, Effect.gen(function* () { const sandbox = yield* E2B.Sandbox("ProgramSandbox", { template: Program, network: { allowPublicTraffic: true }, }); return { url: Output.interpolate`https://3000-${sandbox.sandboxId}.${sandbox.domain}` }; }),);An E2B.Sandbox gives the program a stable URL. The sandbox pauses when it is idle and the next request resumes it, memory included. A new build of the program replaces the sandbox.
Bindings inside the sandbox
Section titled “Bindings inside the sandbox”export default class Program extends E2B.Template<Program>()( "Program", { main: import.meta.url }, Effect.gen(function* () { const reports = yield* E2B.ReadVolume(Reports); return { fetch: Effect.gen(function* () { const report = yield* reports.readText("/latest.json"); return HttpServerResponse.text(report); }).pipe(Effect.orDie), }; }).pipe(Effect.provide(E2B.ReadVolumeHttp)),) {}Any binding works in a template program, from E2B or another provider.
A plain JavaScript program
Section titled “A plain JavaScript program”export const Server = E2B.Template("Server", { main: "./src/server.mjs", env: { GREETING: "hi" },});export type ServerEnv = E2B.InferEnv<typeof Server>;import { createServer } from "node:http";
createServer((_request, response) => { response.end(`${process.env.GREETING} from a sandbox`);}).listen(Number(process.env.PORT ?? 3000), "0.0.0.0");A main without an Effect is bundled and run as-is. It must listen on PORT.
Deploys
Section titled “Deploys”A deploy rebuilds the template when the program’s bundle changes. Sandboxes already running keep the old build, except an E2B.Sandbox declared from the template, which is replaced by one on the new build.