feat: machine-wide intelligence discovery and a selectable project view - #119
Merged
Conversation
The dashboard's Intelligence panel previously showed exactly one project's
learning telemetry, implicitly tied to whichever directory the dashboard
process happened to launch from -- with no way to see or compare any other
project on the machine. This was a deliberate clean-break redesign (the
project is still pre-release, 4.0.0-alpha line, so no backward-compatibility
constraint applied): the panel now shows a machine-wide rollup across every
ruflo-initialized project plus an explicitly selected, explicitly labeled
detail project, defaulting to whichever was most recently active.
Source
- Add src/lib/dashboard/project-discovery.mjs: discoverRuvfloProjects()
unions three sources into one deduplicated, most-recently-active-first
catalog -- ruflo's own daemon workspace registry (registryWorkspaces(),
reused verbatim from daemons.mjs, now exported), a cross-reference against
Observability's persisted workspace snapshots, and real cwd values read
directly out of Claude/Codex transcript content via the same
discoverJsonl()/bootstrapRecords() functions Observability already trusts.
The third source exists because the first two turned out to be
insufficient in practice: this machine's ruflo 3.34.0 install never wrote
the central registry files daemons.mjs's own header comment assumed
ruflo 3.28+ would, and Observability's snapshot store is deliberately
privacy-sanitized and structurally never carries a resolvable path. The
transcript source is what actually finds real projects on a real machine,
verified against this repo's own 4 ruflo-initialized projects.
- Add readMachineWideIntel(projects) to intel-history.mjs, folding
readIntelHistory() across every discovered project into one
{ totals, perProject } rollup, keeping the lifetime patterns-learned
counter and the pattern-store's current size as two distinct,
never-conflated sums at machine scope, exactly as at single-project scope.
A project whose data is missing or malformed degrades to nulls/zeros
rather than aborting the whole scan.
- Redesign dashboard-server.mjs's /api/status intel payload and
/api/live/intelligence route around a shared ?project=<key> parameter,
resolved identically by both endpoints and defaulting to the
most-recently-active discovered project (never the server's own cwd,
which no longer has any special status). Replace the prior server-wide
singleton IntelligenceWatch with a small pool keyed by resolved project
path: a watcher is created lazily on a project's first SSE subscriber and
stopped the moment its last subscriber disconnects.
- Update client.mjs/page.mjs: an always-visible machine-wide stat row and
per-project breakdown table, a project picker driving the existing
5-figure detail strip (now explicitly labeled by selected project, never
implicitly "this project"), and live-stream resubscription whenever the
picker selection changes.
Tests
- tests/kit/project-discovery.test.mjs: dedup/tagging across all three
sources, the .claude-flow/neural filter, most-recently-active sorting,
and direct coverage of the transcript source (flat Claude cwd, nested
Codex payload.cwd, dedup against the registry source, and the neural-state
filter applied consistently).
- tests/kit/intel-history.test.mjs: readMachineWideIntel's multi-project
aggregation, the lifetime-counter-vs-store-entries sum distinction,
graceful per-project degradation, and most-active-project selection.
- tests/kit/dashboard-intel-integration.test.mjs: rewritten for the new
intel payload shape -- default project selection, explicit selection,
fallback on an unresolvable key, machine-wide aggregation, and the
watcher pool's create-on-subscribe/teardown-on-last-disconnect lifecycle.
- tests/dashboard.test.cjs: updated for the new nested intel.health shape.
Docs
- Amend ADR-0024 and docs/ddd/project-intelligence.md in place (no new ADR
number) to describe the three-source discovery model, the corrected
standing of the registry source (no longer "guaranteed-correct" given the
real-machine finding above), the shared ?project= contract, and the
watcher-pool lifecycle.
- Update docs/ddd/ubiquitous-language.md and docs/DASHBOARD.md for the new
shared vocabulary and to correct descriptions of the prior
single-project-only behavior.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
The dashboard's Intelligence panel previously showed exactly one project's learning telemetry, implicitly tied to whichever directory the dashboard process happened to launch from — with no way to see or compare any other project on the machine. This was a deliberate clean-break redesign (the project is still pre-release,
4.0.0-alphaline, so no backward-compatibility constraint applied): the panel now shows a machine-wide rollup across every ruflo-initialized project plus an explicitly selected, explicitly labeled detail project, defaulting to whichever was most recently active.Source
src/lib/dashboard/project-discovery.mjs—discoverRuvfloProjects()unions three sources into one deduplicated, most-recently-active-first catalog: ruflo's own daemon workspace registry (registryWorkspaces(), reused verbatim fromdaemons.mjs, now exported), a cross-reference against Observability's persisted workspace snapshots, and realcwdvalues read directly out of Claude/Codex transcript content via the samediscoverJsonl()/bootstrapRecords()functions Observability already trusts. The third source exists because the first two turned out to be insufficient in practice — this machine's ruflo 3.34.0 install never wrote the central registry filesdaemons.mjs's own header comment assumed ruflo 3.28+ would, and Observability's snapshot store is deliberately privacy-sanitized and structurally never carries a resolvable path. The transcript source is what actually finds real projects on a real machine, verified against this repo's own 4 ruflo-initialized projects.readMachineWideIntel(projects)added tointel-history.mjs, foldingreadIntelHistory()across every discovered project into one{ totals, perProject }rollup, keeping the lifetime patterns-learned counter and the pattern-store's current size as two distinct, never-conflated sums at machine scope. A project whose data is missing/malformed degrades to nulls/zeros rather than aborting the whole scan.dashboard-server.mjs's/api/statusintel payload and/api/live/intelligenceroute redesigned around a shared?project=<key>parameter, resolved identically by both endpoints, defaulting to the most-recently-active discovered project (never the server's own cwd, which no longer has special status). The prior server-wide singletonIntelligenceWatchis replaced by a small pool keyed by resolved project path: created lazily on a project's first SSE subscriber, stopped on last disconnect.client.mjs/page.mjs— an always-visible machine-wide stat row and per-project breakdown table, a project picker driving the existing 5-figure detail strip (now explicitly labeled by selected project), and live-stream resubscription on picker change.Tests
tests/kit/project-discovery.test.mjs— dedup/tagging across all three sources, the.claude-flow/neuralfilter, most-recently-active sorting, and direct coverage of the transcript source (flat Claudecwd, nested Codexpayload.cwd, dedup against the registry source).tests/kit/intel-history.test.mjs—readMachineWideIntel's multi-project aggregation, the lifetime-counter-vs-store-entries distinction, graceful degradation, most-active-project selection.tests/kit/dashboard-intel-integration.test.mjs— rewritten for the new payload shape: default/explicit/fallback project selection, machine-wide aggregation, and the watcher pool's create-on-subscribe/teardown-on-last-disconnect lifecycle.tests/dashboard.test.cjs— updated for the new nestedintel.healthshape.Docs
docs/ddd/project-intelligence.mdamended in place (no new ADR number) to describe the three-source discovery model, the corrected standing of the registry source, the shared?project=contract, and the watcher-pool lifecycle.docs/ddd/ubiquitous-language.mdanddocs/DASHBOARD.mdupdated for the new shared vocabulary.Test plan
pnpm run check(typecheck, lint, markdownlint, build, full test suite) — green locally, 1301 tests.claude-flow/data (finds all 4 real projects)