Skip to content
| Marketplace
Sign in
Visual Studio Code>Debuggers>super-logNew to Visual Studio Code? Get it now.
super-log

super-log

Basseterre LLC

| (0) | Free
Bench viewer in the editor, plus automatic capture of cmake build and debug output to the super-log hub.
Installation
Launch VS Code Quick Open (Ctrl+P), paste the following command, and press enter.
Copied to clipboard
More Info

super-log for VS Code

Bring the super-log bench into the editor, and forward what the editor already knows — build output and debug output — to the hub as bench events, with no wrapper scripts and no copy-paste.

  • Auto-capture builds. CMake / Make / Ninja (and anything else you point it at) are teed to the hub as vscode.build.<task> events, level-classified the way a compiler talks: error: → ERROR, warning: → WARN, everything else INFO. Ninja/CMake progress rides as a build.progress_pct metric.
  • Auto-capture debug. Every debug session's console output becomes vscode.debug.<session> events (DAP output, classified by category — stderr is error-ish), and session start/stop bookend it.
  • The viewer, in a tab. super-log: Open Bench Viewer opens a theme-aware panel that subscribes to the hub's firehose and renders the log stream and an alarms strip, light/dark-correct.
  • Ergonomics. A status-bar indicator (connected / events sent / hub down), a one-click "run a build and capture it", and a "start the hub" command for when superlogd is not answering.

Zero runtime dependencies. The extension host speaks to the hub over plain node:http; the viewer uses the webview's own WebSocket. The only build tool is esbuild.


Design note

Capturing build output — why a task wrapper

VS Code's stable API has no way to read the text an arbitrary task writes to its terminal. onDidStartTask / onDidEndTaskProcess give you the task, the command line and the exit code — never the body. window.onDidWriteTerminalData would give the bytes, but it is a proposed API a published extension may not ship against. So capture is done in two honest layers:

  1. Full capture — the superlog task type. The extension contributes a task type whose CustomExecution returns a pseudoterminal. The pseudoterminal spawns the build command itself, so the extension owns the child's stdout/stderr: each line is written to the terminal (the task looks and feels normal) and teed to the hub, classified by level. This is the "spawn the build through a wrapper that tees to the hub" approach, exposed as a first-class task so it can be a preLaunchTask, the default build task, or run from the Tasks menu. A workspace with a CMakeLists.txt, Makefile or build.ninja gets these tasks auto-provided.

    Add one to tasks.json:

    {
      "type": "superlog",
      "label": "cmake build",
      "command": "cmake --build build",
      "group": "build"
    }
    

    or just run super-log: Run Build and Capture to Hub and type a command (prefilled from superlog.defaultBuildCommand).

  2. Lifecycle capture — every other task. For a build run by ms-vscode.cmake-tools or any other extension, whose output we cannot read, the task-process listeners still emit a start event and an edge-triggered verdict (INFO on exit 0, ERROR otherwise) on the same vscode.build.<task> topic. Partial but truthful: you always see on the bench that a build ran and how it ended, and if you want the per-line diagnostics too, route that build through a superlog task.

    By default this layer fires for tasks in the Build group or whose command looks like a compiler/build invocation (cmake, make, ninja, msbuild, xcodebuild, cargo build, go build, tsc, gradle, clang/gcc/…). Set superlog.capture.allTasks to widen it to every task.

A start and its verdict share a trace, so "show me everything from that build" is one filter in any viewer.

Capturing debug output — the DAP tracker

vscode.debug.registerDebugAdapterTrackerFactory('*', …) sits between VS Code and every debug adapter and sees the raw Debug Adapter Protocol traffic. The output event is the debug console, so each one is forwarded to vscode.debug.<session>, classified by DAP category (stderr → ERROR, important → WARN, stdout/console → INFO unless the text itself is a compiler-shaped error/warning). Session start/stop ride the session lifecycle events (so a silent session still bookends), and an adapter that errors or exits non-zero surfaces as an ERROR rather than vanishing. All events in one session share the session id as their trace.

The viewer — native webview, with an opt-in React path

A VS Code webview runs in its own origin (vscode-webview://…), so it cannot reach ws://127.0.0.1:7333 unless the page's Content-Security-Policy names that origin in connect-src. The extension sets connect-src from the configured hub URL (plus loopback fallbacks), and from there the webview's own WebSocket talks straight to the hub — nothing is proxied through the extension host.

The shipped viewer is a native panel (media/viewer.js), a faithful, small reimplementation of the viewer half of the wire protocol — parse the /ws envelope, split the NDJSON payload, apply the tolerant-reader rule, seed from /recent?snapshot=1 — themed entirely with VS Code's own --vscode-* CSS variables, so it is light/dark-correct and looks native. Log content reaches the DOM only through textContent, never innerHTML: a log line is data, never markup, and can never inject into the panel.

Why not drop in viewer/react directly? It cannot be embedded unmodified: it derives the hub from window.location (which, inside a webview, is the vscode-webview origin — no :7333 there), it ships absolute /assets/… paths that a webview will not serve, and its optional panels reach services (the alarm gateway, the paid interpreter) that need not be running. Rebuilding it here would also mean either running its Vite toolchain (its node_modules is empty in a fresh clone) or modifying viewer/react — both out of scope for this extension, which stays entirely within editors/vscode/.

So the React app is an opt-in path instead of the default. Set superlog.viewer.useReactBundle: true and populate media/react/ with a build of the viewer, and the panel will load it — the loader rewrites its absolute asset paths to webview URIs and injects the hub via ?hub= (a bootstrap that runs before the app's deferred module reads window.location.search). To produce that build without touching the upstream tree:

# from a super-log clone, with the React viewer's deps installed once:
npm --prefix viewer/react install
npm --prefix viewer/react exec -- vite build --base ./ \
  --outDir "$PWD/editors/vscode/media/react" --emptyOutDir

If media/react/ is absent, the panel falls back to the native viewer with a notice. The tradeoff is deliberate: the native panel always works and always compiles; the React path gives the full board (servers, devices, topology, versions, agents, PRs, RPC, webhooks) at the cost of a manual build step.


Commands

Command What
super-log: Open Bench Viewer Open the viewer panel (also the status-bar click)
super-log: Run Build and Capture to Hub Run a command through the tee wrapper
super-log: Start Hub (superlogd) Launch superlogd if /healthz does not answer
super-log: Toggle Auto-Capture (build + debug) Flip both auto-capture switches
super-log: Show Extension Log Open the extension's output channel

Settings

Setting Default Meaning
superlog.hubUrl http://127.0.0.1:7333 Hub base URL (ingest + /ws + /recent)
superlog.autoCapture.build true Forward build output and verdicts
superlog.autoCapture.debug true Forward debug console and session lifecycle
superlog.capture.allTasks false Lifecycle events for every task, not just builds
superlog.topics.buildPrefix vscode.build Topic prefix for build events
superlog.topics.debugPrefix vscode.debug Topic prefix for debug events
superlog.defaultBuildCommand cmake --build build Prefilled for the capture command
superlog.hubPath "" Path to superlogd; empty auto-detects build/hub/superlogd
superlog.maxQueue 5000 Bounded event queue; oldest dropped under burst
superlog.viewer.useReactBundle false Load the opt-in React bundle from media/react/

Under a burst the queue drops the oldest events rather than stalling the editor — a logger that can stall what it observes is worse than no logger, the same bounded-queue rule every SDK on the bench follows.

Topics on the wire

Events are the v1 schema from docs/PROTOCOL.md, origin.runtime = vscode:

  • vscode.build.<task> — one event per build line (tag stdout/stderr), plus a build.progress_pct metric where the toolchain prints progress, plus a start event and a verdict.
  • vscode.debug.<session> — one event per DAP output line, plus session start/stop and adapter error/exit.

Build and run

cd editors/vscode
npm install
npm run compile        # -> dist/extension.js (esbuild)
# then press F5 in VS Code (Extension Development Host), or:
npm run package        # -> a .vsix (needs @vscode/vsce)

npm run watch rebuilds on change; npm run typecheck runs tsc --noEmit.

License

MIT © Saxon Herschel Nicholls. Part of super-log.

  • Contact us
  • Jobs
  • Privacy
  • Manage cookies
  • Terms of use
  • Trademarks
  • Your Privacy Choices
  • Consumer Health Privacy
© 2026 Microsoft