Skip to content

vercel-labs/wterm

Repository files navigation

wterm

A terminal emulator for the web.

wterm ("dub-term") renders to the DOM — native text selection, copy/paste, find, and accessibility come for free. The core is written in Zig and compiled to WASM for near-native performance.

Packages

Package Description
@wterm/core Headless WASM bridge + WebSocket transport
@wterm/dom DOM renderer, input handler — vanilla JS terminal
@wterm/react React component + useTerminal hook (TypeScript)
@wterm/just-bash In-browser Bash shell powered by just-bash
@wterm/markdown Render Markdown in the terminal

Features

  • Zig + WASM core — VT100/VT220/xterm escape sequence parser compiled to a ~12 KB .wasm binary (release build)
  • DOM rendering — native text selection, clipboard, browser find, and screen reader support
  • Dirty-row tracking — only touched rows are re-rendered each frame via requestAnimationFrame
  • Themes — CSS custom properties with built-in Default, Solarized Dark, Monokai, and Light themes
  • Alternate screen buffervim, less, htop, and similar apps work correctly
  • Scrollback history — configurable ring buffer
  • 24-bit color — full RGB SGR support
  • Auto-resizeResizeObserver-based terminal resizing
  • WebSocket transport — connect to a PTY backend with binary framing and reconnection

Development

Prerequisites

Setup

pnpm install

Build the WASM binary

zig build

For a release build:

zig build -Doptimize=ReleaseSmall

Build all packages

pnpm build

Run the vanilla demo

Serve the web/ directory with any static file server:

cd web && python3 -m http.server 8000

Run the Next.js example

All dev servers use portless to avoid hardcoded ports. Each app is served at a .localhost URL (e.g. nextjs-example.wterm.localhost).

cp web/wterm.wasm examples/nextjs/public/
pnpm --filter nextjs dev

Run Zig tests

zig build test

License

Apache-2.0