LocalMode
DevTools

DevTools

Instrumentation and React hooks for debugging and monitoring local AI applications.

DevTools

Instrumentation and React hooks for inspecting model cache, vector database stats, inference queue metrics, pipeline execution traces, and live event streams in LocalMode applications.

Overview

@localmode/devtools provides headless instrumentation (enableDevTools()) plus React hooks (@localmode/devtools/react) that give you full visibility into your local AI application at runtime — all without any telemetry or data leaving your device. The hooks are the primary integration path: subscribe to any slice of the observability bridge and render it in your own UI, with your own styling.

See it in action

DevTools instrumentation is enabled across the LocalMode blocks gallery — open any block and use the DevTools drawer to inspect live model, VectorDB, and queue state.

What you can observe

  • Models — Cached models, load times, status
  • VectorDB — Collections, document counts, search stats
  • Queue — Live inference queue: pending, active, completed, latency
  • Pipeline — Step execution traces with timings
  • Events — Live event stream with filtering
  • Device — WebGPU, WASM, Chrome AI, WebNN capabilities
  • Storage — Storage quota usage

Installation

pnpm add -D @localmode/devtools

Quick Start

Enable instrumentation once, then subscribe to any data domain with a hook:

import { enableDevTools } from '@localmode/devtools';
import { useDevToolsQueueStats, useDevToolsEvents } from '@localmode/devtools/react';

if (process.env.NODE_ENV === 'development') {
  enableDevTools();
}

function Observability() {
  const queues = useDevToolsQueueStats();
  const events = useDevToolsEvents({ types: ['vectordb'], limit: 50 });

  return (
    <div>
      {Object.entries(queues).map(([name, stats]) => (
        <p key={name}>{name}: {stats.pending} pending, {stats.active} active</p>
      ))}
      {events.map((e) => (
        <p key={e.id}>{e.type}</p>
      ))}
    </div>
  );
}

If you only want instrumentation without any UI, calling enableDevTools() alone is enough — data is written to the bridge and you can inspect window.__LOCALMODE_DEVTOOLS__ directly.

React Hooks

@localmode/devtools/react exports nine hooks — one per bridge data domain — all built on useSyncExternalStore with version-keyed immutable snapshots:

HookReturns
useDevToolsBridgeThe raw bridge object (window.__LOCALMODE_DEVTOOLS__), or null when absent
useDevToolsStatus{ available, enabled } — bridge availability and instrumentation state
useDevToolsQueueStatsLive stats per registered inference queue (Record<string, QueueStats>)
useDevToolsEventsRecent bridge events, filterable by types with a limit
useDevToolsModelCachePer-model load info (Record<string, ModelCacheInfo>)
useDevToolsPipelineRunsPipeline step execution traces (Record<string, PipelineSnapshot>)
useDevToolsVectorDBsPer-collection VectorDB operation stats (Record<string, VectorDBSnapshot>)
useDevToolsStorageStorage quota snapshot, or null before the first sample
useDevToolsCapabilitiesDevice capabilities snapshot, or null before detection

Guarantees shared by all hooks:

  • Subscribe on mount, fully unsubscribe on unmount — no leaks
  • SSR-safe — no window access during server render; inert values on the server
  • Inert when devtools is absent — referentially stable fallback values; no errors in production builds
  • Late-enable attachment — a hook mounted before enableDevTools() attaches once the bridge appears, no remount needed
  • Immutable snapshots — slice hooks return fresh copies per notification; they never alias the bridge's mutable objects

Prebuilt UI: the ui/devtools family + drawer

Prefer copy-owned components to hand-rolling panels? The ui/devtools family ships four theme-aware, zero-dependency primitives (inference-queue-monitor, event-log-viewer, pipeline-run-inspector, model-cache-table) that render these hooks' output, and npx shadcn add @localmode/ui/blocks/devtools-drawer installs a composed six-tab observability drawer (Queue / Events / Pipeline / Models / Device / VectorDB — off by default, zero-overhead when closed). These are the successor UI to the removed widget (see below).

How It Works

enableDevTools() subscribes to existing observability hooks in @localmode/core:

  • globalEventBus for VectorDB and embedding events
  • queue.on('stats') for inference queue metrics
  • onProgress callbacks for pipeline step traces
  • getStorageQuota() for storage usage
  • detectCapabilities() for device features

Data is written to window.__LOCALMODE_DEVTOOLS__. The React hooks read this bridge directly via subscribe() for instant, non-polling updates. Zero core changes needed — DevTools is a pure read-only visualization layer.

DevToolsWidget (removed in v3.0.0)

Removed in v3.0.0

The prebuilt DevToolsWidget overlay and its @localmode/devtools/widget subpath were removed in v3.0.0. Its replacements are the React hooks above (build your own panel with your own styling), the copy-owned ui/devtools family primitives (inference-queue-monitor, event-log-viewer, pipeline-run-inspector, model-cache-table), and the composed six-tab ui/blocks/devtools-drawer (npx shadcn add @localmode/ui/blocks/devtools-drawer). The data layer — enableDevTools(), the window.__LOCALMODE_DEVTOOLS__ bridge, and every collector — is unchanged; only the widget UI was removed.

See Data Domains for the six domains the bridge collects — each maps 1:1 to a /react hook, a ui/devtools primitive, and a tab of the drawer.

Requirements

  • @localmode/core ^1.0.0 (peer dependency)
  • react >=18.0.0 (peer dependency, only for the /react hooks)

Composed Block

BlockDescriptionLinks
DevTools DrawerSix-tab global observability drawer composing the @localmode/devtools bridge and hooks across the /blocks galleryLive · Install: npx shadcn add @localmode/ui/blocks/devtools-drawer

On this page