Beacon is a local dashboard for long-running AI coding agents. It watches the session files already on your machine, writes normalized events to ClickHouse, and gives you a live view of active work, searchable history, tool usage, token volume, and past transcripts.
Dashboard overview. Active sessions with compact live stat trackers, a Sessions-first completed-run table, scoped search filters, selectable Token Analytics metrics, and a live Activity Bar in one view.
Session transcript. A single run with session metrics, token charts, tool usage, and the replayable conversation below.
- See active and completed agent runs in one place, including project paths, models, duration, turns, tool calls, subagents, and errors.
- Watch active sessions appear in the live board while scoped dashboard panels refresh without disturbing the rest of the page.
- Catch expensive or noisy work quickly with Token Analytics metrics for total, input, output, cache-read tokens, tool calls, errors, and error rate.
- Search sessions first, then switch the same table to events, tool calls, or error-focused searches when you need detail.
- Replay a session as a readable transcript with expandable tool payloads and timeline context.
- Let agents query prior work through MCP tools instead of asking you to remember which session contained the answer.
Beacon currently understands session data from Claude Code, OpenAI Codex, Hermes Agent, OpenCode, and Pi coding-agent runs.
Beacon is distributed through GitHub Releases and the install script below. The installer supports macOS and Linux on amd64 and arm64 when the selected release includes the matching archive.
curl -sSfL https://johnnygreco.dev/beacon/install.sh | shIt installs beacon to ~/.local/bin. If ClickHouse is not already available on PATH, it also installs a managed ClickHouse binary to ~/.beacon/bin.
Beacon release archives are verified against the release checksums.txt before
installation. Managed ClickHouse downloads use the pinned ClickHouse release
documented in docs/release.md.
If your shell cannot find beacon, add the install directory to PATH:
export PATH="$HOME/.local/bin:$PATH"Common variants:
curl -sSfL https://johnnygreco.dev/beacon/install.sh | INSTALL_DIR=/usr/local/bin sh
curl -sSfL https://johnnygreco.dev/beacon/install.sh | VERSION=x.y.z sh
curl -sSfL https://johnnygreco.dev/beacon/install.sh | INCLUDE_PRERELEASE=1 sh
curl -sSfL https://johnnygreco.dev/beacon/install.sh | INSTALL_CLICKHOUSE=0 sh
curl -sSfL https://johnnygreco.dev/beacon/install.sh | VERIFY_CHECKSUMS=0 sh
curl -sSfL https://johnnygreco.dev/beacon/install.sh | UNINSTALL=1 shUse INSTALL_CLICKHOUSE=0 only when you already run ClickHouse yourself.
Use VERIFY_CHECKSUMS=0 only for local installer debugging or emergency
workarounds. UNINSTALL=1 removes the installed beacon binary and ~/.beacon,
including Beacon-managed ClickHouse data.
Homebrew packaging is not currently a supported distribution channel.
beacon upOpen http://localhost:4600. On startup, Beacon loads ~/.beacon/beacon.toml if it exists, starts local ClickHouse when the configured ClickHouse address is local, migrates the schema, backfills existing sessions, and then watches for new events.
Useful commands:
beacon status # server, ClickHouse, session, and search-index health
beacon down # stop the running Beacon web server
beacon db down # stop Beacon-managed local ClickHouse
beacon --version # show the Beacon CLI versionThe top-left header shows the Beacon mark, live connection indicator, and editable dashboard name. The active-session board updates through SSE as sessions start or change. Completed sessions load immediately for the selected time range; no search is required to populate the table.
The completed table defaults to Sessions because that is the primary review workflow. Use the table controls to filter by range, search text, session ID, result type, sort order, and pagination. The table refresh button reloads only the completed/search table. Sessions search uses Beacon's indexed session content, including event text, session metadata, tool names, payload previews, and bounded payload JSON.
Token Analytics has its own range controls, log-scale toggle, model filter,
metric dropdown, and refresh button. The metric dropdown supports total tokens,
input tokens, output tokens, cache-read tokens, tool calls, errors, and error
rate. The selected metric is stored in the dashboard URL as chart_metric, so
shared links and reloads keep the chart state.
These sources are enabled by default:
| Source | Runtime | Default path |
|---|---|---|
| Claude Code | claude-code |
~/.claude/projects/**/*.jsonl |
| OpenAI Codex | codex |
~/.codex/sessions/**/*.jsonl |
| Hermes Agent | hermes-agent |
~/.hermes/state.db |
| OpenCode | opencode |
~/.local/share/opencode/opencode*.db |
| Pi coding agent | pi-coding-agent |
~/.pi/agent/sessions/**/*.jsonl |
Backfill runs on startup by default, then the watcher keeps configured paths up to date.
Beacon reads ~/.beacon/beacon.toml by default. Pass --config <path> to use another file:
beacon --config ./beacon.toml upStart from the example in beacon.toml. The settings most people change are the web port, ClickHouse address, and capture sources:
[server]
host = "0.0.0.0"
port = 4600
[database]
addrs = ["127.0.0.1:9000"]
database = "beacon"
username = "default"
password = ""
secure = false
[dashboard]
name = "Workstation A"
[[capture.sources]]
name = "codex"
runtime = "codex"
provider = "openai"
glob = "~/.codex/sessions/**/*.jsonl"
watch_root = "~/.codex/sessions"
format = "jsonl"Ports must be in 1..65535, ClickHouse addresses must include a host and port,
and each capture source must set name, runtime, provider, format,
watch_root, and either glob or globs. Supported runtime/format pairs are
claude-code/jsonl, codex/jsonl, hermes-agent/sqlite, opencode/sqlite,
and pi-coding-agent/jsonl.
Set [dashboard].name when you run Beacon dashboards for multiple machines or
workspaces. The configured name becomes the dashboard heading and browser tab
title; the heading can also be renamed locally from the dashboard without
editing the config file.
If [database].addrs points to a remote ClickHouse host, Beacon will not start ClickHouse for you. Start the database yourself and run beacon db migrate.
- Architecture and data flow
- Privacy, retention, and local data boundaries
- Pricing estimate data and fallback behavior
- Performance baselines and query-plan review
- ClickHouse schema, migration, and reset policy
- Errors and observability
- Toolchain and dependency updates
- Installer and release process
For local addresses such as 127.0.0.1:9000, localhost:9000, or 0.0.0.0:9000, beacon up and beacon watch try to start ClickHouse when it is not already reachable.
Auto-start prefers:
- a
clickhousebinary fromBEACON_CLICKHOUSE_BIN,PATH, or~/.beacon/bin/clickhouse - an existing Docker container named
beacon-clickhouse - a new Docker container using
clickhouse/clickhouse-server:24.12
Manual database commands:
beacon db up # start local ClickHouse and migrate tables
beacon db down # stop Beacon-managed local ClickHouse
beacon db migrate # migrate an already-running ClickHouse
beacon db refresh-projections # rebuild derived projections and search index
beacon db reset --force # destructive: drop and recreate Beacon tablesBy default, beacon db up uses the managed ClickHouse binary when available and falls back to Docker.
Native ClickHouse data lives under ~/.beacon/clickhouse. Docker mode uses the beacon-clickhouse-data volume.
For schema ownership, migration behavior, reset policy, and local data locations, see docs/clickhouse.md.
Run beacon db up first so ClickHouse is available and migrated, then add Beacon to your MCP client:
{
"mcpServers": {
"beacon": {
"command": "beacon",
"args": ["mcp"]
}
}
}If your MCP client cannot use Beacon's config file, pass ClickHouse directly:
{
"mcpServers": {
"beacon": {
"command": "beacon",
"args": ["mcp", "--clickhouse", "127.0.0.1:9000"]
}
}
}Available tools:
search_sessionssearches the precomputed activity index and returns session/event IDs.openretrieves one event plus nearby context from the same session.list_sessionslists recent sessions with summary stats.
| Command | Use it for |
|---|---|
beacon up |
Start the dashboard and capture service |
beacon down |
Stop the running Beacon web server |
beacon watch |
Capture sessions without the web dashboard |
beacon mcp |
Start the MCP server over stdin/stdout JSON-RPC |
beacon status |
Show server, database, session, and search-index status |
beacon --version |
Show the Beacon CLI version |
beacon db up |
Start local ClickHouse and migrate tables |
beacon db down |
Stop Beacon-managed local ClickHouse |
beacon db migrate |
Create or update ClickHouse tables |
beacon db refresh-projections |
Rebuild derived projections and search index |
beacon db reset --force |
Delete Beacon data and recreate tables |
Source builds require Go 1.24.1 or newer. Node/npm are only needed for Playwright tests and vendoring browser assets.
git clone https://github.com/johnnygreco/beacon.git
cd beacon
make build
./bin/beacon upDevelopment commands:
make generate # regenerate templ output
make generate-check # verify generated templ output is current
make fmt # gofmt tracked Go files
make fmt-check # verify tracked Go files are gofmt formatted
make test # generate templates and run Go tests
make test-race # run Go tests with the race detector
make test-cover # run Go tests with race, coverage, and coverage floors
make perf-bench # run perf benchmarks; set PERF_SIZE=small|medium|large
make clean # remove build/test outputs such as bin, dist, coverage, and reports
make clean-local # also remove ignored repo-local scratch/agent dirs and local DB files
make clean-deps # remove node_modules
npm install # install Playwright and asset-vendoring dependencies
npm run vendor # refresh vendored frontend assets
npm run vendor:check # verify vendored frontend assets and notices are current
npm run test:frontend # JS lint and unit tests
npm run test:e2e # dashboard and integrated search Playwright tests
npm run test:e2e:search # focused dashboard search Playwright tests
npm run test:a11y # accessibility tests
npm run test:visual # visual regression testspackage.json is private development metadata for vendored browser assets,
linting, and Playwright tests. Beacon release versions come from Git tags and
are injected into the Go binary by GoReleaser.
Cleanup targets only remove files inside the repository checkout. They do not
delete Beacon user data under ~/.beacon; use beacon db reset --force or the
installer's UNINSTALL=1 path when you intentionally want destructive Beacon
data cleanup.
Beacon tracks both .templ source files and generated _templ.go files. After
editing any template source under internal/views, run make generate and
commit the generated Go diff with the source change. make test, make build,
and related local targets run generation first, but they do not replace the
explicit generated-file review before a PR.
Run make generate-check when you want the same stale-generated-output gate CI
uses. It reruns templ generation and fails if generation changes the worktree.
Template tests should render public components, pages, and partials and assert
the resulting HTML behavior, escaping, and helper output instead of targeting
generated _templ.go implementation lines.
Release commands:
make publish VERSION=x.y.zmake publish expects a clean, up-to-date main branch, a working gh authentication or GITHUB_TOKEN, zig for Linux CGO cross-builds, and goreleaser on PATH. It creates tag vx.y.z, runs a local GoReleaser build before pushing the tag, uploads the release artifacts to GitHub Releases, and attempts to roll back the release/tag if publishing fails after the tag push. See Installer and release process for artifact names, verification behavior, and rollback commands.
Most Go tests do not need a live ClickHouse server. Live ClickHouse integration and perf tests are opt-in and require a reachable ClickHouse TCP endpoint:
beacon db up
BEACON_TEST_CLICKHOUSE=127.0.0.1:9000 go test ./internal/store ./internal/search ./internal/web
BEACON_TEST_CLICKHOUSE=127.0.0.1:9000 go test ./internal/perf -bench . -run '^$'Playwright tests require Node dependencies from npm install and a Chromium
browser installed by Playwright. They start their own e2e server by default. To
test against an already running Beacon-compatible server, set
BEACON_E2E_BASE_URL.
Visual regression tests are intentionally local-only for now. The checked-in
snapshots are Chromium baselines captured on Darwin, and
tests/e2e/visual.spec.ts skips on other platforms so Linux CI does not compare
against incompatible raster output. Run them from macOS with:
npm run test:visual
npm run test:visual -- --update-snapshotsOnly update visual snapshots after reviewing the rendered dashboard and transcript states represented by the changed PNG files. Moving this suite into CI should include a stable Linux baseline set or a hosted macOS runner, plus the corresponding removal of the platform skip.
CI enforces conservative Go coverage regression floors from coverage.thresholds.
The current gates are a total statement floor plus selected runtime packages
that should not regress without an intentional threshold update. Generated templ
packages, benchmark/perf helpers, simulator/perfseed binaries, and browser test
coverage are intentionally excluded from package floors.
Update coverage.thresholds in the same PR as any deliberate coverage target
change. make test-cover and CI both run scripts/check-coverage.sh against
the generated coverage profile.
beacon is not found after install. Add the install directory to PATH, usually export PATH="$HOME/.local/bin:$PATH".
ClickHouse does not start. Run beacon db up. Set BEACON_CLICKHOUSE_BIN=/path/to/clickhouse when Beacon should use a specific local binary.
Beacon connects to the wrong database. Check [database].addrs in ~/.beacon/beacon.toml or pass --config <path>.
No sessions appear. Confirm the agent has written session files in one of the configured source paths, then run beacon status and restart with backfill_on_start = true.
Port 4600 is already in use. Change [server].port in the config file or stop the existing process with beacon down.
This project was inspired by Wes McKinney's agentsview, Eric Tramel's moraine, and Simon Willison's claude-code-transcripts.
Third-party browser asset notices are tracked in THIRD_PARTY_NOTICES.md.