"use client"
/**
* KeyMetricsProvider — host-app injection point for the design-system
* `KeyMetrics` component.
*
* `KeyMetrics` itself ships as a pure primitive: it knows how to render
* a KPI strip, an insight rail, and a default insight CTA, but it does
* NOT know anything about the host app's AI assistant, command palette,
* or keyboard-shortcut registry.
*
* Consumers (e.g. `apps/web`) mount a `KeyMetricsProvider` near the root
* of the app and supply two optional injection points:
*
* - `defaultInsightAction` — fired when the user clicks the default
* "Ask Leo about these metrics" button in the card-variant header,
* and the default insight CTA when an individual `MetricInsight` did
* not supply its own `onAction`. When omitted, the default button is
* hidden entirely so the primitive stays useful in apps without an
* AI assistant.
*
* - `shortcutHint` — inline React node rendered inside the tooltip
* alongside the action label (typically a keyboard chord such as
* `⌘⌥K`). When omitted, the tooltip simply shows the
* label.
*
* - `defaultActionLabel` — visible label + accessible name for the
* default action button. Defaults to "Ask Leo" so the existing
* Exxat-DS layout reads identically without any consumer changes.
*
* This is the SAME injection shape used by Adobe Spectrum
* (`Provider`-based service injection) and Material UI (`Theme`
* context). It lets the design-system package ship product patterns
* without taking on a hard dependency on the host app's AI surface.
*/
import * as React from "react"
export interface KeyMetricsContextValue {
/** Click handler for the default "Ask Leo about these metrics" CTA. */
defaultInsightAction?: () => void
/** Inline kbd chord (or any node) rendered next to the action label inside the tooltip. */
shortcutHint?: React.ReactNode
/** Label + aria-label for the default insight action button. Defaults to "Ask Leo". */
defaultActionLabel?: string
}
const KeyMetricsContext = React.createContext({})
/** Read the active `KeyMetricsProvider` value. Returns an empty object if no provider is mounted. */
export function useKeyMetricsContext(): KeyMetricsContextValue {
return React.useContext(KeyMetricsContext)
}
export function KeyMetricsProvider({
value,
children,
}: {
value: KeyMetricsContextValue
children: React.ReactNode
}) {
// Memoize the wrapper so consumers passing fresh object identities
// (common in client components) do not invalidate every descendant
// that reads the context.
const memo = React.useMemo(
() => ({
defaultInsightAction: value.defaultInsightAction,
shortcutHint: value.shortcutHint,
defaultActionLabel: value.defaultActionLabel,
}),
[value.defaultInsightAction, value.shortcutHint, value.defaultActionLabel],
)
return (
{children}
)
}