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

@illuma-ai/code-sandbox

v1.34.0

Published

Browser-native code sandbox with file tree, editor, terminal, and live preview powered by Nodepod

Readme

@illuma-ai/code-sandbox

A browser-native code sandbox with file tree, Monaco editor, terminal, and live preview — powered by Nodepod.

Run Express + React applications entirely in the browser. No server-side containers required.

Features

  • Full IDE workbench: file tree, code editor, terminal, live preview
  • Runs Node.js in the browser via Nodepod (SharedArrayBuffer + Service Worker)
  • Monaco editor with syntax highlighting, diff viewer, and file tabs
  • Structured error reporting with file path, line number, and source context
  • Hot reload for CSS/HTML/static asset changes (no server restart)
  • Imperative API for programmatic control (designed for AI agent integration)
  • Built-in project templates (Express + React full-stack apps)
  • Customizable via CSS custom properties
  • Dark theme by default, with shadcn-compatible theme variable bridge

Installation

npm install @illuma-ai/code-sandbox

Peer Dependencies

These must be installed by the consuming application:

npm install react react-dom @monaco-editor/react monaco-editor allotment framer-motion

| Peer Dependency | Version | | ---------------------- | ----------------------------------- | | react | ^18.0.0 \|\| ^19.0.0 | | react-dom | ^18.0.0 \|\| ^19.0.0 | | @monaco-editor/react | ^4.6.0 | | monaco-editor | >=0.40.0 | | allotment | ^1.20.0 | | framer-motion | ^10.0.0 \|\| ^11.0.0 \|\| ^12.0.0 |

Prerequisites

COOP/COEP Headers

Nodepod requires SharedArrayBuffer, which is only available in cross-origin isolated contexts. Your dev server must send these headers:

Cross-Origin-Opener-Policy: same-origin
Cross-Origin-Embedder-Policy: credentialless

Vite example:

// vite.config.ts
export default defineConfig({
  server: {
    headers: {
      "Cross-Origin-Opener-Policy": "same-origin",
      "Cross-Origin-Embedder-Policy": "credentialless",
    },
  },
});

Service Worker

Copy the Nodepod service worker file to your public/ directory so it's served at /__sw__.js:

cp node_modules/@illuma-ai/nodepod/dist/sw.js public/__sw__.js

Quick Start

import { useRef } from "react";
import { CodeSandbox } from "@illuma-ai/code-sandbox";
import type { CodeSandboxHandle } from "@illuma-ai/code-sandbox";
import "@illuma-ai/code-sandbox/styles.css";

function App() {
  const ref = useRef<CodeSandboxHandle>(null);

  return (
    <CodeSandbox
      ref={ref}
      template="fullstack-starter"
      height="100vh"
      onServerReady={(port, url) => console.log(`Ready on port ${port}`)}
      onSandboxError={(err) => console.error(err.category, err.message)}
    />
  );
}

With Custom Files

const files = {
  "package.json": JSON.stringify(
    {
      name: "my-app",
      dependencies: { express: "^4.18.0" },
    },
    null,
    2,
  ),
  "server.js": `
    const express = require("express");
    const app = express();
    app.get("/", (req, res) => res.send("<h1>Hello World</h1>"));
    app.listen(3000, () => console.log("Running on port 3000"));
  `,
};

<CodeSandbox
  ref={ref}
  files={files}
  entryCommand="node server.js"
  port={3000}
  height="100vh"
/>;

AI Agent Integration

The sandbox is designed as a "dumb renderer" — the host application pushes files in and reads state out. The user does not edit code in the sandbox; an AI agent writes code, and the host pushes it via the imperative API.

const ref = useRef<CodeSandboxHandle>(null);

// Agent starts editing — enable diff view + lock editor
ref.current.setDiffMode(true);

// Agent generates new files → push them into the sandbox
await ref.current.updateFiles(agentGeneratedFiles);

// Agent modifies a single file (surgical — no server restart)
await ref.current.updateFile("server.js", newServerCode);

// Agent deletes a file
await ref.current.deleteFile("old-route.js");

// Read errors for the agent to self-correct
const errors = ref.current.getErrors();
// errors[0] → { category: "process-stderr", message: "...", filePath: "server.js", line: 42, sourceContext: "..." }

// Agent done — disable diff view + unlock editor
ref.current.setDiffMode(false);

API Reference

<CodeSandbox> Component

The main component. Renders the full workbench (file tree, editor, terminal, preview). Uses React.forwardRef to expose the imperative handle.

<CodeSandbox
  ref={sandboxRef}
  files={fileMap} // OR template="fullstack-starter"
  entryCommand="node server.js"
  port={3000}
  env={{ NODE_ENV: "development" }}
  height="100vh"
  className="my-sandbox"
  onFileChange={(path, content) => {}}
  onServerReady={(port, url) => {}}
  onProgress={(progress) => {}}
  onError={(message) => {}}
  onSandboxError={(error) => {}}
  onFilesUpdated={(changes) => {}}
/>

Props (CodeSandboxProps)

| Prop | Type | Default | Description | | -------------- | ------------------------ | -------------------------------------------------- | --------------------------------------------------------------------------------------------- | | files | FileMap | — | Initial file set. Pass a flat Record<string, string> mapping file paths to contents. | | template | string | — | Use a built-in template instead of files. One of: "express-react", "fullstack-starter". | | entryCommand | string | Inferred from package.json or "node server.js" | Shell command to start the dev server. | | port | number | 3000 | Port the server listens on. | | env | Record<string, string> | — | Environment variables passed to Node.js processes. | | height | string | "100vh" | CSS height of the sandbox root element. | | className | string | — | CSS class name for the root element. | | diffMode | boolean | — | Externally controlled diff mode. When true, the editor shows Monaco's side-by-side DiffEditor for files that have changes. When undefined, the user controls diff via the built-in Diff button. | | readOnly | boolean | false | Make the editor read-only. When true, only the agent can modify files via the imperative handle. Typical pattern: set both readOnly and diffMode to true while the agent is editing, then flip both off when done. |

Callback Props

| Callback | Signature | Description | | ---------------- | ----------------------------------------------------- | ---------------------------------------------------------------------------------------------- | | onFileChange | (path: string, content: string) => void | Fires when a file is modified in the editor. | | onServerReady | (port: number, url: string) => void | Fires when the dev server is ready (initial boot or after restart). | | onProgress | (progress: BootProgress) => void | Fires on boot progress changes. | | onError | (message: string) => void | Fires on errors (legacy string format). | | onSandboxError | (error: SandboxError) => void | Fires when a structured error is detected. Primary error channel for AI agent integration. | | onFilesUpdated | (changes: Record<string, FileChangeStatus>) => void | Fires after updateFiles() completes (files written + server restarted). |


CodeSandboxHandle (Imperative API)

Access via a React ref. This is the primary API for host applications to control the sandbox programmatically.

const ref = useRef<CodeSandboxHandle>(null);
<CodeSandbox ref={ref} ... />

Methods

updateFiles(files, options?)

Replace the entire file set. Diffs against current files, writes only changed files to the virtual FS, and restarts the server if anything changed.

By default, the previous file set becomes originalFiles for diff tracking. Use keepBaseline to preserve the original baseline during incremental updates (e.g., streaming AI agent edits).

// Standard update — resets diff baseline
await ref.current.updateFiles(newFileMap);

// Skip server restart
await ref.current.updateFiles(newFileMap, { restartServer: false });

// Incremental update — preserves diff baseline for accumulated diffs
await ref.current.updateFiles(newFileMap, { keepBaseline: true, restartServer: false });

| Param | Type | Default | Description | | ----------------------- | --------- | ------- | ------------------------------------------------------------- | | files | FileMap | — | Complete new file set. | | options.restartServer | boolean | true | Whether to restart the server after writing. | | options.keepBaseline | boolean | false | When true, preserves originalFiles so diffs accumulate against the initial state rather than resetting on each update. Ideal for streaming AI edits where you want to show total changes. |

Hot reload vs cold restart: If ALL changed files are hot-reloadable (CSS, HTML, images, fonts), the sandbox refreshes the preview iframe without restarting the Node.js server. If ANY changed file is JS/TS/JSON, the server process is killed and re-run.

AI agent editing pattern:

// 1. Agent starts editing — switch to code view, enable diff mode
ref.current.setView("code");

// 2. Agent edits files one at a time — push each surgically
//    updateFile() does NOT restart the server, diffs accumulate
await ref.current.updateFile("routes/todos.js", newContent);
ref.current.openFile("routes/todos.js", 42); // scroll to changed line

// 2b. Agent deletes a file
await ref.current.deleteFile("routes/deprecated.js");

// 3. Agent finishes — reconciliation with restart
await ref.current.updateFiles(finalFiles); // resets baseline, restarts server
ref.current.setView("preview"); // switch back to see the running app
updateFile(path, content)

Update a single file. Writes to the virtual FS and updates state. Does not restart the server — call restart() manually if needed, or use updateFiles() for bulk updates with auto-restart.

await ref.current.updateFile("public/styles.css", newCss);
deleteFile(path)

Delete a file from the sandbox. Removes it from the virtual FS and marks it as "deleted" in fileChanges for diff tracking. If the file was open in the editor, it is automatically closed.

await ref.current.deleteFile("routes/old-api.js");
// fileChanges → { "routes/old-api.js": "deleted" }

Files that existed in originalFiles are tracked as "deleted" (shown with red indicator in file tree). Files that were added after boot and then deleted are simply removed from tracking.

restart()

Force restart the server process. Kills the current process and re-runs the entry command.

await ref.current.restart();
getFiles()

Returns the current FileMap (all files including edits).

const files: FileMap = ref.current.getFiles();
getChangedFiles()

Returns a FileMap containing only files that have been modified relative to originalFiles.

const changed: FileMap = ref.current.getChangedFiles();
getFileChanges()

Returns the per-file change status map. Missing keys should be treated as "unchanged".

const changes: Record<string, FileChangeStatus> = ref.current.getFileChanges();
// { "server.js": "modified", "public/new-page.html": "new" }
getErrors()

Returns all structured errors collected during this session. The array grows monotonically — new errors are appended.

const errors: SandboxError[] = ref.current.getErrors();
getState()

Returns the current RuntimeState snapshot.

const state: RuntimeState = ref.current.getState();
// state.status, state.previewUrl, state.terminalOutput, etc.
setDiffMode(enabled)

Enable or disable diff mode in the editor. When enabled, files with changes show Monaco's side-by-side DiffEditor comparing originalFiles (left) with current files (right).

Use this to show diffs in real-time while the AI agent is editing, then disable when the agent finishes.

// Agent starts editing
ref.current.setDiffMode(true);

// Push agent edits — user sees diffs live
await ref.current.updateFiles(agentEditedFiles);

// Agent done — back to normal editor
ref.current.setDiffMode(false);

Tip: Combine with the readOnly prop to lock the editor during agent edits:

<CodeSandbox ref={ref} readOnly={agentEditing} diffMode={agentEditing} ... />
setView(view)

Programmatically switch between "code", "preview", and "swagger" views.

ref.current.setView("code");    // Show editor + file tree
ref.current.setView("preview"); // Show live preview iframe
ref.current.setView("swagger"); // Show auto-generated API documentation

Both views are always mounted (no destroy/recreate). Switching uses opacity + pointer-events for instant toggling without losing state.

openFile(path)

Open a specific file in the editor and switch to code view. Useful for highlighting agent-edited files.

ref.current.openFile("routes/todos.js");
// → File opens in editor, code view activated
getConsoleLogs()

Returns all console log entries captured from the preview iframe (console.log, info, warn, error).

const logs: ConsoleEntry[] = ref.current.getConsoleLogs();
clearConsoleLogs()

Clear all captured console log entries.

ref.current.clearConsoleLogs();

SandboxError

Structured error type designed for AI agent consumption. Includes enough context for the agent to construct a targeted fix prompt.

interface SandboxError {
  id: string; // Unique ID for deduplication
  category: SandboxErrorCategory; // Error type
  message: string; // Human-readable error message
  stack?: string; // Full stack trace
  filePath?: string; // File path (relative to workdir)
  line?: number; // Line number (1-indexed)
  column?: number; // Column number (1-indexed)
  timestamp: string; // ISO 8601 timestamp
  sourceContext?: string; // ~10 surrounding source lines
}

Error Categories (SandboxErrorCategory)

| Category | Description | | ----------------------------- | -------------------------------------------------------------- | | process-stderr | Output written to stderr by the Node.js process | | process-exit | Process exited with a non-zero code | | runtime-exception | Uncaught exception in the Node.js runtime | | browser-error | JavaScript error in the preview iframe (window.onerror) | | browser-unhandled-rejection | Unhandled promise rejection in the iframe | | browser-console-error | console.error() calls in the iframe | | compilation | Syntax/import errors at module load time | | network | Failed HTTP requests from the preview (fetch/XHR) | | boot | Error during Nodepod boot, file writing, or dependency install |

Source Context Format

When available, sourceContext contains lines formatted as "lineNum: content":

38: const express = require("express");
39: const app = express();
40: const PORT = 3000;
41:
42: app.get("/api/data", (req, res) => {
43:   res.json(undefinedVariable);    // ← error here
44: });
45: app.listen(PORT);

RuntimeState

The full reactive state exposed by the runtime.

interface RuntimeState {
  status: BootStage;
  progress: BootProgress;
  previewUrl: string | null;
  terminalOutput: string[];
  files: FileMap;
  originalFiles: FileMap;
  fileChanges: Record<string, FileChangeStatus>;
  previewReloadKey: number;
  error: string | null;
  errors: SandboxError[];
}

| Field | Type | Description | | ------------------ | ---------------------------------- | --------------------------------------------------------------------------- | | status | BootStage | Current lifecycle stage. | | progress | BootProgress | Current boot progress (stage, message, percent). | | previewUrl | string \| null | URL for the preview iframe. null until server is ready. | | terminalOutput | string[] | All terminal output lines (stdout + stderr). | | files | FileMap | Current files in the virtual FS (including edits). | | originalFiles | FileMap | Baseline files before the latest updateFiles(). Used for diffs. | | fileChanges | Record<string, FileChangeStatus> | Per-file change status. Missing keys = "unchanged". | | previewReloadKey | number | Incremented on hot reload — triggers iframe refresh without server restart. | | error | string \| null | Error message if status is "error". | | errors | SandboxError[] | All structured errors (grows monotonically). |

BootStage

type BootStage =
  | "initializing" // Nodepod.boot() in progress
  | "writing-files" // Writing project files to virtual FS
  | "installing" // npm install running
  | "starting" // Entry command executing
  | "ready" // Server is listening, preview iframe can load
  | "error"; // Something failed

BootProgress

interface BootProgress {
  stage: BootStage;
  message: string;
  percent: number; // 0-100, approximate
}

FileChangeStatus

type FileChangeStatus = "new" | "modified" | "deleted" | "unchanged";

Hot Reload

When updateFiles() is called, the sandbox inspects which files changed:

  • Hot-reloadable extensions: .css, .html, .htm, .svg, .png, .jpg, .jpeg, .gif, .webp, .ico, .woff, .woff2, .ttf, .eot
  • If all changed files have hot-reloadable extensions → the preview iframe is soft-reloaded (location.reload()) without restarting the Node.js server process.
  • If any changed file is JS/TS/JSON/etc. → the server process is killed and re-run (cold restart).

This makes CSS-only iterations instant.


Built-in Templates

Use template="name" to bootstrap with a pre-built project.

express-react

A lightweight Express + React app using JSONPlaceholder as a data source. React is loaded from CDN (no build step). Demonstrates posts/users CRUD views.

  • Entry command: node server.js
  • Port: 3000
  • Files: 9 (server.js, public/index.html, styles, 5 React components)

fullstack-starter

A comprehensive full-stack template with authentication, CRUD, charts, and theming.

  • Entry command: node server.js
  • Port: 3000
  • Files: 35 (Express + sql.js + React + React Router + Auth + CRUD + Chart.js + shadcn theme variables)
  • Features: Login/register, todo CRUD with SQLite (sql.js), doughnut chart, light/dark theme, responsive layout

Template API

import { getTemplate, listTemplates } from "@illuma-ai/code-sandbox";

const names = listTemplates();
// ["express-react", "fullstack-starter"]

const tpl = getTemplate("fullstack-starter");
// { files: FileMap, entryCommand: string, port: number }

Theming

Sandbox Chrome (CSS Custom Properties)

The sandbox UI is themed via --sb-* CSS custom properties. Override them in your CSS to match your application:

:root {
  --sb-bg: #1e1e1e;
  --sb-bg-alt: #252526;
  --sb-bg-hover: #2a2d2e;
  --sb-bg-active: #37373d;
  --sb-sidebar: #252526;
  --sb-editor: #1e1e1e;
  --sb-terminal: #0d1117;
  --sb-terminal-header: #161b22;
  --sb-preview: #ffffff;
  --sb-border: #3c3c3c;
  --sb-text: #cccccc;
  --sb-text-muted: #858585;
  --sb-text-active: #ffffff;
  --sb-accent: #007acc;
  --sb-accent-hover: #1a8ad4;
  --sb-success: #3fb950;
  --sb-warning: #d29922;
  --sb-error: #f85149;
  --sb-info: #58a6ff;
  --sb-scrollbar-thumb: rgba(255, 255, 255, 0.12);
  --sb-scrollbar-thumb-hover: rgba(255, 255, 255, 0.25);
  --sb-scrollbar-track: transparent;
  --sb-scrollbar-width: 6px;
}

Theme Variable Bridge

The sandbox CSS also defines shadcn-compatible design tokens (--text-primary, --surface-primary, --border-light, --chart-1 through --chart-5, etc.) in both light and dark variants. These are available inside the preview iframe content for seamless visual integration with your application's UI.

Add the .dark class to an ancestor element to activate dark mode tokens.


Advanced Usage

Individual Components

All sub-components are exported individually for custom layouts:

import {
  FileTree,
  buildFileTree,
  CodeEditor,
  Terminal,
  Preview,
  BootOverlay,
  ViewSlider,
} from "@illuma-ai/code-sandbox";

<FileTree>

Renders a collapsible file tree with per-extension SVG icons (19 distinct types: JS, TS, JSX, TSX, JSON, HTML, CSS, SCSS, MD, PY, RB, GO, RS, YML, ENV, SH, SQL, SVG, Lock) and change status indicators.

import { FileTree, buildFileTree } from "@illuma-ai/code-sandbox";

const tree = buildFileTree(fileMap);
<FileTree
  files={tree}
  selectedFile="server.js"
  onSelectFile={(path) => setSelected(path)}
  fileChanges={{ "server.js": "modified" }}
/>;

<CodeEditor>

Monaco-based code editor with file tabs, diff mode toggle, and change status indicators on tabs.

<CodeEditor
  files={fileMap}
  originalFiles={baselineFiles}
  fileChanges={changes}
  activeFile="server.js"
  openFiles={["server.js", "public/index.html"]}
  onSelectFile={(path) => {}}
  onCloseFile={(path) => {}}
  onFileChange={(path, content) => {}}
  readOnly={false}
  diffMode={false}
/>

<Terminal>

Clean monochrome terminal output display with minimize/expand toggle and line count badge.

<Terminal
  output={terminalLines}
  minimized={false}
  onToggleMinimize={() => setMinimized(!minimized)}
/>

<Preview>

Live preview iframe with JavaScript error capture (injects window.onerror, unhandledrejection, and console.error listeners). URL bar displays friendly localhost:3000/ instead of internal paths.

<Preview
  url={previewUrl}
  onRefresh={() => runtime.restart()}
  onBrowserError={(error) => handleError(error)}
  reloadKey={state.previewReloadKey}
/>

<BootOverlay>

Loading overlay with staged progress animation.

<BootOverlay
  progress={{
    stage: "installing",
    message: "Installing express...",
    percent: 55,
  }}
/>

<ViewSlider>

Icon-based tab toggle for Code, Preview, and API Docs views with Framer Motion animation. Icons expand to show labels on hover.

import type { WorkbenchView } from "@illuma-ai/code-sandbox";
// WorkbenchView = "code" | "preview" | "swagger"

<ViewSlider
  selected={view}
  onSelect={(v: WorkbenchView) => setView(v)}
/>;

NodepodRuntime Service

The framework-agnostic runtime service (no React dependency). Use directly for custom integrations.

import { NodepodRuntime } from "@illuma-ai/code-sandbox";

const runtime = new NodepodRuntime({
  files: myFiles,
  entryCommand: "node server.js",
  port: 3000,
  workdir: "/app",
  env: { NODE_ENV: "production" },
});

runtime.setProgressCallback((progress) => console.log(progress));
runtime.setOutputCallback((line) => console.log(line));
runtime.setServerReadyCallback((port, url) => console.log("Ready:", url));
runtime.setErrorCallback((error) => console.error(error));

await runtime.boot();

// File operations
await runtime.writeFile("server.js", newContent);
await runtime.deleteFile("old-route.js");
const content = await runtime.readFile("server.js");

// State
const files = runtime.getCurrentFiles();
const changed = runtime.getChangedFiles();
const errors = runtime.getErrors();
const status = runtime.getStatus();
const previewUrl = runtime.getPreviewUrl();

// Lifecycle
await runtime.restart();
runtime.teardown();

useRuntime Hook

React hook wrapping NodepodRuntime. Powers the CodeSandbox component internally. Use for fully custom React UIs.

import { useRuntime } from "@illuma-ai/code-sandbox";

const {
  state, // RuntimeState
  selectedFile, // string | null
  openFiles, // string[]
  handleFileChange, // (path, content) => void
  handleSelectFile, // (path) => void
  handleCloseFile, // (path) => void
  handleBrowserError, // (error: SandboxError) => void
  restart, // () => Promise<void>
  updateFiles, // (files, options?) => Promise<void>
  updateFile, // (path, content) => Promise<void>
  deleteFile, // (path) => Promise<void>
  getFiles, // () => FileMap
  getChangedFiles, // () => FileMap
  getFileChanges, // () => Record<string, FileChangeStatus>
  getErrors, // () => SandboxError[]
  getState, // () => RuntimeState
} = useRuntime(props);

Nodepod Constraints

The sandbox runs on Nodepod, a browser-native Node.js runtime. Key constraints:

  • No build tools: Vite, Webpack, Next.js, etc. will not work. Use CDN-loaded libraries instead.
  • express.static() does not work. Serve files manually via fs.readFileSync() + res.send().
  • res.sendFile() does not work. Same — use fs.readFileSync() + res.send().
  • Module wrapper hides browser globals: document, window, location are undefined in server-side code (as expected in Node.js).
  • Preview URL rewriting: Nodepod returns /__virtual__/{port} URLs but the Service Worker expects /__preview__/{port}/. The sandbox handles this transparently.

All Exports

// Main component
export { CodeSandbox } from "@illuma-ai/code-sandbox";

// Individual components
export { FileTree, buildFileTree } from "@illuma-ai/code-sandbox";
export { CodeEditor } from "@illuma-ai/code-sandbox";
export { Terminal } from "@illuma-ai/code-sandbox";
export { Preview } from "@illuma-ai/code-sandbox";
export { BootOverlay } from "@illuma-ai/code-sandbox";
export { ViewSlider } from "@illuma-ai/code-sandbox";

// Services & hooks
export { NodepodRuntime } from "@illuma-ai/code-sandbox";
export { useRuntime } from "@illuma-ai/code-sandbox";

// Templates
export { getTemplate, listTemplates } from "@illuma-ai/code-sandbox";

// Types
export type {
  FileMap,
  FileNode,
  FileChangeStatus,
  SandboxError,
  SandboxErrorCategory,
  SandboxErrorSeverity,
  ConsoleEntry,
  ConsoleLevel,
  BootStage,
  BootProgress,
  RuntimeConfig,
  RuntimeState,
  CodeSandboxProps,
  CodeSandboxHandle,
  FileTreeProps,
  CodeEditorProps,
  TerminalProps,
  PreviewProps,
  BootOverlayProps,
  WorkbenchView,
} from "@illuma-ai/code-sandbox";

License

MIT - See LICENSE for details.