|
| 1 | +// Copyright (c) 2025 ObjectStack. Licensed under the Apache-2.0 license. |
| 2 | + |
| 3 | +import type { ChartConfig, ChartType, Dashboard } from '@objectstack/spec/ui'; |
| 4 | + |
| 5 | +const taskDs = 'showcase_task_metrics'; |
| 6 | +const projectDs = 'showcase_project_metrics'; |
| 7 | + |
| 8 | +const cfg = (type: ChartType, dimension: string, measure: string): ChartConfig => ({ |
| 9 | + type, |
| 10 | + xAxis: { field: dimension, showGridLines: true, logarithmic: false }, |
| 11 | + yAxis: [{ field: measure, showGridLines: true, logarithmic: false }], |
| 12 | + showLegend: true, |
| 13 | + showDataLabels: false, |
| 14 | +}); |
| 15 | + |
| 16 | +/** |
| 17 | + * Delivery Operations — a *believable business* dashboard (vs the Chart Gallery, |
| 18 | + * which is one-of-every-chart). It composes the patterns a real ops landing page |
| 19 | + * needs: |
| 20 | + * • a KPI hero row of `metric` tiles, each scoped by a per-widget `filter` |
| 21 | + * (active projects, at-risk projects, awaiting-review tasks) — the same |
| 22 | + * dataset, sliced different ways; |
| 23 | + * • comparison / distribution / trend charts underneath; |
| 24 | + * • a global `dateRange` (created_at) and a global status filter so the whole |
| 25 | + * board re-scopes from the header. |
| 26 | + * |
| 27 | + * Everything binds the semantic datasets by name (ADR-0021), so a metric is |
| 28 | + * defined once and reused. |
| 29 | + */ |
| 30 | +export const OpsDashboard: Dashboard = { |
| 31 | + name: 'showcase_ops_dashboard', |
| 32 | + label: 'Delivery Operations', |
| 33 | + description: 'Operations landing page — KPI hero row, project health, and task throughput.', |
| 34 | + columns: 12, |
| 35 | + dateRange: { field: 'created_at', defaultRange: 'last_90_days', allowCustomRange: true }, |
| 36 | + globalFilters: [ |
| 37 | + { |
| 38 | + field: 'status', |
| 39 | + label: 'Task Status', |
| 40 | + type: 'select', |
| 41 | + options: [ |
| 42 | + { value: 'backlog', label: 'Backlog' }, |
| 43 | + { value: 'todo', label: 'To Do' }, |
| 44 | + { value: 'in_progress', label: 'In Progress' }, |
| 45 | + { value: 'in_review', label: 'In Review' }, |
| 46 | + { value: 'done', label: 'Done' }, |
| 47 | + ], |
| 48 | + scope: 'dashboard', |
| 49 | + }, |
| 50 | + ], |
| 51 | + widgets: [ |
| 52 | + // ── KPI hero row — same project dataset, sliced by per-widget filter ── |
| 53 | + { id: 'kpi_active_projects', type: 'metric', title: 'Active Projects', dataset: projectDs, values: ['project_count'], filter: { status: 'active' }, colorVariant: 'blue', layout: { x: 0, y: 0, w: 3, h: 2 } }, |
| 54 | + { id: 'kpi_at_risk', type: 'metric', title: 'At-Risk (Red)', dataset: projectDs, values: ['project_count'], filter: { health: 'red' }, colorVariant: 'danger', layout: { x: 3, y: 0, w: 3, h: 2 } }, |
| 55 | + { id: 'kpi_awaiting_review', type: 'metric', title: 'Awaiting Review', dataset: taskDs, values: ['task_count'], filter: { status: 'in_review' }, colorVariant: 'warning', layout: { x: 6, y: 0, w: 3, h: 2 } }, |
| 56 | + { id: 'kpi_total_budget', type: 'metric', title: 'Total Budget', dataset: projectDs, values: ['budget_sum'], colorVariant: 'success', layout: { x: 9, y: 0, w: 3, h: 2 } }, |
| 57 | + |
| 58 | + // ── Health + throughput ────────────────────────────────────────────── |
| 59 | + { id: 'col_health', type: 'column', title: 'Projects by Health', dataset: projectDs, dimensions: ['health'], values: ['project_count'], chartConfig: cfg('column', 'health', 'project_count'), layout: { x: 0, y: 2, w: 4, h: 4 } }, |
| 60 | + { id: 'bar_status', type: 'bar', title: 'Tasks by Status', dataset: taskDs, dimensions: ['status'], values: ['task_count'], chartConfig: cfg('bar', 'status', 'task_count'), layout: { x: 4, y: 2, w: 4, h: 4 } }, |
| 61 | + { id: 'donut_priority', type: 'donut', title: 'Priority Mix', dataset: taskDs, dimensions: ['priority'], values: ['task_count'], chartConfig: cfg('donut', 'priority', 'task_count'), layout: { x: 8, y: 2, w: 4, h: 4 } }, |
| 62 | + |
| 63 | + // ── Trend + account spend ──────────────────────────────────────────── |
| 64 | + { id: 'line_created', type: 'line', title: 'Task Throughput (monthly)', dataset: taskDs, dimensions: ['created_at'], values: ['task_count'], chartConfig: cfg('line', 'created_at', 'task_count'), layout: { x: 0, y: 6, w: 6, h: 4 } }, |
| 65 | + { id: 'table_spend', type: 'table', title: 'Budget vs Spent by Account', dataset: projectDs, dimensions: ['account'], values: ['project_count', 'budget_sum', 'spent_sum'], layout: { x: 6, y: 6, w: 6, h: 4 } }, |
| 66 | + ], |
| 67 | +}; |
0 commit comments