You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Part of #280 (Dashboard as a first-class module). Phase 4 of 6, after Phase 3. Normative spec in #280.
Folds in and closes:#235 (refresh serializes the Filter wave before every Panel tile), the drag-reorder half of #153, and the baseline filter-bar usability items from #188 (clear one/all, active count, never-hide-blocking — see scope below; #188's impact hints and overflow are dropped as deferred-until-demonstrated-need).
Goal
A standalone read-only DashboardViewerSession plus the normative flow@1 layout (viewer + editor behavior), constructible and testable without Workbench, editors, full App, or global AppState.
Scope (from #280 "Phase 4: viewer and flow layout")
DashboardViewerSession: immutable document snapshot, resolved queries/presentations, filter values, execution queue with bounded concurrency, per-tile cancellation, stale-wave protection, results/errors/progress, layout controller, destroy() cleanup. Depends only on narrow interfaces (query execution, connection session, resolvers, layout registry) — builds directly on Refactor app.ts into explicit application services and route sessions #276 phase 3b (DashboardSession).
Accessible authoring controls: moveTileEarlier/Later, setTileSpan/Height, keyboard-focusable handle, focus retention, ARIA live announcements — pointer drag (Dashboard: drag-reorder, open panel in window. #153) is an equivalent alternative, never the only mechanism.
Layout registry with lazy-loadable, compile-time-registered modules and the flow@1 fallback contract.
Clear one filter: keyboard-accessible affordance per active filter; deactivates without discarding the last value (reactivation restores it), one affected-panel wave.
Clear all filters: one toolbar action resetting every filter of the current document to its defaultActive/defaultValue; all changes coalesce into one preparation + rerun wave; hidden/disabled when nothing is active.
Active count: a compact "N active" indicator counting active filter definitions (not non-empty stored values), updated on every activation change, readable by assistive technology without per-repaint announcements.
Never silently hide a blocking filter: a filter whose state blocks a target panel (invalid value, required-and-unset, source-query error) must stay visible or carry a visible badge — the user can always see why a panel is waiting.
Explicitly not in scope (dropped from Dashboard filter bar: clear actions, active count, impact hints, and overflow #188, refile only against a real dashboard that needs them): per-filter impact hints ("used by N panels" — trivially derivable from DashboardFilterDefinitionV1.targets if ever wanted) and More filters (N) overflow collapse.
Dependencies
#276 phase 3b (DashboardSession extraction) should land first — this phase replaces/absorbs that runtime. Phases 1–3 of #280.
Tests
Per #280 "Flow layout" test list, plus dependency-boundary tests (check:arch rules: dashboard model/application must not import Workbench UI, full App, AppState, or editor modules), plus a #235 regression pair: unaffected panel starts before the filter wave completes; affected panel still sees correct first-pass values.
Acceptance
Viewer session runs a dashboard document end-to-end in unit tests with no Workbench construction.
Filter bar ships with per-filter clear, coalesced clear-all, accurate active count, and no silently hidden blocking state (tests for each, including the single-wave guarantee on clear-all).
Part of #280 (Dashboard as a first-class module). Phase 4 of 6, after Phase 3. Normative spec in #280.
Folds in and closes: #235 (refresh serializes the Filter wave before every Panel tile), the drag-reorder half of #153, and the baseline filter-bar usability items from #188 (clear one/all, active count, never-hide-blocking — see scope below; #188's impact hints and overflow are dropped as deferred-until-demonstrated-need).
Goal
A standalone read-only
DashboardViewerSessionplus the normativeflow@1layout (viewer + editor behavior), constructible and testable without Workbench, editors, fullApp, or globalAppState.Scope (from #280 "Phase 4: viewer and flow layout")
DashboardViewerSession: immutable document snapshot, resolved queries/presentations, filter values, execution queue with bounded concurrency, per-tile cancellation, stale-wave protection, results/errors/progress, layout controller,destroy()cleanup. Depends only on narrow interfaces (query execution, connection session, resolvers, layout registry) — builds directly on Refactor app.ts into explicit application services and route sessions #276 phase 3b (DashboardSession).prepareBatchguarantees today). The explicitDashboardFilterDefinitionV1.parameter/targetscontract supplies the overlap knowledge Dashboard Refresh serializes the Filter wave before the Panel wave for every tile, even unaffected ones #235 said was missing.flow@1per the normative contract: presets,DEFAULT_FLOW_PLACEMENT, effective-span clamping, deterministic row-major packing, semantic = DOM = visual = keyboard = print order, mobile one-column normalization without persistence mutation.moveTileEarlier/Later,setTileSpan/Height, keyboard-focusable handle, focus retention, ARIA live announcements — pointer drag (Dashboard: drag-reorder, open panel in window. #153) is an equivalent alternative, never the only mechanism.flow@1fallback contract.defaultActive/defaultValue; all changes coalesce into one preparation + rerun wave; hidden/disabled when nothing is active.DashboardFilterDefinitionV1.targetsif ever wanted) andMore filters (N)overflow collapse.Dependencies
#276 phase 3b (
DashboardSessionextraction) should land first — this phase replaces/absorbs that runtime. Phases 1–3 of #280.Tests
Per #280 "Flow layout" test list, plus dependency-boundary tests (
check:archrules: dashboard model/application must not import Workbench UI, fullApp,AppState, or editor modules), plus a #235 regression pair: unaffected panel starts before the filter wave completes; affected panel still sees correct first-pass values.Acceptance