Skip to the content.

Developing Bun Console

Prerequisites

Build and test

$env:JAVA_HOME = "$env:LOCALAPPDATA\Programs\WebStorm\jbr"
.\gradlew.bat -PwebstormPath="$env:LOCALAPPDATA\Programs\WebStorm" test buildPlugin verifyPlugin
bun test .\tests\runtime\bootstrap.test.mjs

Without -PwebstormPath, Gradle downloads WebStorm 2026.2.3. The plugin archive is written to build/distributions/bun-console-<version>.zip.

Sandbox IDE

.\gradlew.bat -PwebstormPath="$env:LOCALAPPDATA\Programs\WebStorm" runIde

runIde starts WebStorm with the plugin in a separate profile under build/isolated-ide; your own WebStorm settings and windows are not touched. Open tests/runtime/fixtures as the project: it contains manual test files (see its README) that follow the acceptance checks.

In the sandbox IDE the plugin writes a development trace to build/bun-console-trace.log: every input, output fragment, status and tab change, editor switch and message exchanged with Bun. It is enabled only by the bun.console.trace system property that runIde sets.

Layout

Path Contents
src/main/resources/runtime/bootstrap.mjs The Bun side: REPL, context bindings, lazy modules, socket protocol
src/main/kotlin/dev/bunconsole/runtime Bun process, input preparation (ConsoleImports), declarations, trace
src/main/kotlin/dev/bunconsole/service BunConsoleProjectService: lifecycle, contexts, reloads, status
src/main/kotlin/dev/bunconsole/debug Debugger attachment and paused-frame evaluation
src/main/kotlin/dev/bunconsole/ui Tool window, input, tabs, actions, completion
tests/runtime Runtime tests and the manual-test fixtures
docs/ Acceptance checks, debugger notes, publishing guide, investigation notes

Runtime protocol

The IDE listens on a loopback port and starts Bun with the port and a one-time token in its environment; the bootstrap connects back and sends {"event":"ready","token":…}. Requests are JSON lines {id, op, …} answered by {id, ok, …}; console output travels as {event: "output", text, level} on the same socket, so it stays in order with results.

Operation Purpose
eval Run console input (code, imports, declarations); replies with text and the user’s globals
load Make a file the editor context (path, declared, dependencies) without running it
add_file / remove_file Add or remove a pinned/added context file
add_symbol Bind one top-level declaration of a file
reload_file Re-read a changed context file; it runs again on next use
cached_files Loaded module paths, to detect changed dependencies
ping Answered outside the command queue; a late answer means the JavaScript thread is busy

Further notes