Skip to main content

:::warning AUTO-GENERATED — do not edit This page is generated from the MCP server snapshot content/guide-mcp.json. Edit the source MCP server (not this file), then run npm run generate. :::

Add a KPI overview page

When to use: You want a dashboard landing page with headline metrics (KPI cards) and a couple of charts — the typical PowerBI replacement.

Prerequisites

  • Completed discover-api for each metric's source endpoint.

Steps

Step 1: Get the dashboard layout pattern.

Tools: get_layout_patterns

Step 2: Get the KPI card and chart card templates.

Tools: get_component_template

Step 3: Discover + validate each metric endpoint and create typed service functions.

Tools: get_endpoint_details, validate_endpoint

Step 4: Build the page: KPI row from real aggregates, charts from real series.

Step 5: ALWAYS render a <Skeleton> loading state for each KPI card and chart while its query is pending.

Tools: get_shadcn_components

Step 6: Create co-located .test.tsx files next to each KPI/chart component covering loading and data states.

Step 7: Append each new component to the checklist so unchecked items are tracked.

Step 8: Run the quality gate.

Full recipe definition

The complete machine-readable recipe as returned by the MCP server:

{
"id": "add-kpi-page",
"title": "Add a KPI overview page",
"when": "You want a dashboard landing page with headline metrics (KPI cards) and a couple of charts — the typical PowerBI replacement.",
"prerequisites": [
"Completed `discover-api` for each metric's source endpoint."
],
"steps": [
{
"action": "Get the dashboard layout pattern.",
"tools": [
"get_layout_patterns"
],
"note": "name='DashboardGrid' — 4-column KPI row + chart grid."
},
{
"action": "Get the KPI card and chart card templates.",
"tools": [
"get_component_template"
],
"note": "names 'KPICard' and 'ChartCard'."
},
{
"action": "Discover + validate each metric endpoint and create typed service functions.",
"tools": [
"get_endpoint_details",
"validate_endpoint"
],
"files": [
"src/types/{domain}.ts",
"src/lib/{domain}.ts"
]
},
{
"action": "Build the page: KPI row from real aggregates, charts from real series.",
"files": [
"src/routes/_authenticated/index.tsx"
],
"note": "Each KPI value comes from a query — never a literal number. Each chart uses its OWN endpoint (see `add-chart`)."
},
{
"action": "ALWAYS render a `<Skeleton>` loading state for each KPI card and chart while its query is pending.",
"tools": [
"get_shadcn_components"
],
"files": [
"src/components/{feature}/{name}Card.tsx"
],
"note": "npx shadcn@latest add skeleton. Every card/chart shows a <Skeleton> for isLoading and a typed empty/error state otherwise."
},
{
"action": "Create co-located `.test.tsx` files next to each KPI/chart component covering loading and data states.",
"files": [
"src/components/{feature}/{name}Card.test.tsx"
],
"note": "Same folder as the component. Assert the Skeleton renders while loading and real values render once data resolves."
},
{
"action": "Append each new component to the checklist so unchecked items are tracked.",
"files": [
"COMPONENT_CHECKLIST.md"
],
"note": "Add a `- [ ] {name}Card — Skeleton + test` line per component; check off only once the Skeleton and test exist."
},
{
"action": "Run the quality gate.",
"note": "npm run verify"
}
],
"filesToCreate": [
"src/routes/_authenticated/index.tsx",
"src/lib/{domain}.ts",
"src/types/{domain}.ts",
"src/components/{feature}/{name}Card.test.tsx",
"COMPONENT_CHECKLIST.md"
],
"validation": [
"`npm run verify` passes.",
"Every KPI and chart is bound to a query result, not a literal.",
"Each KPI/chart has a `<Skeleton>` loading state and a co-located `.test.tsx`."
],
"doneCriteria": [
"verify green",
"No placeholder/faked metric values remain.",
"Every new KPI/chart component ships with a `<Skeleton>` loading state and a co-located `.test.tsx`, and is listed in COMPONENT_CHECKLIST.md."
],
"commonMistakes": [
"Hardcoding KPI numbers to make the page look finished.",
"Using arbitrary colors for charts instead of the chart token palette.",
"Batching multiple charts into a single endpoint instead of one endpoint per chart.",
"Shipping a card/chart with no Skeleton loading state or no co-located test."
],
"relatedRecipes": [
"add-chart",
"add-data-table",
"add-filters"
]
}