diff --git a/package.json b/package.json index d729176943..26eecf6f6e 100644 --- a/package.json +++ b/package.json @@ -93,6 +93,7 @@ "dead-exports:check": "node --experimental-strip-types scripts/check-dead-exports.ts", "publishable-deps:check": "node --experimental-strip-types scripts/check-publishable-deps.ts", "release-commit-parsing:check": "tsx scripts/check-release-commit-parsing.ts", + "releasable-commit-types:check": "tsx scripts/check-releasable-commit-types.ts", "checkers-wired:check": "node --experimental-strip-types scripts/check-checkers-wired.ts", "maintainer-associations:check": "node --experimental-strip-types scripts/check-maintainer-association-copies.ts", "regate-sort-key:check": "node --experimental-strip-types scripts/check-regate-sort-key.ts", @@ -146,7 +147,7 @@ "test:smoke:browser:install": "playwright install chromium", "test:smoke:browser": "node --experimental-strip-types scripts/smoke-ui-browser.ts", "pretest:ci": "npm run check-node-version", - "test:ci": "git diff --check && npm run actionlint && npm run lint:composite-actions && npm run db:migrations:check && npm run db:migrations:immutable:check && npm run turbo-inputs:check && npm run workspace-dep-ranges:check && npm run db:schema-drift:check && npm run selfhost:env-reference:check && npm run miner:env-reference:check && npm run selfhost:validate-observability && npm run cf-typegen:check && npm run build --workspace @loopover/engine && npm run build --workspace @loopover/discovery-index && npm run build:mcp && npm run build:miner && npm run build --workspace @loopover/ui-kit && npm run typecheck && npm run test:coverage && npm run test:engine-parity && npm run test:live-gate-parity && npm run test:driver-parity && npm run validate:mcp && npm run test --workspace @loopover/engine && npm run test:workers && npm run test:mcp-pack && npm run test:contract-pack && npm run test:miner-pack && npm run test:engine-pack && npm run test:ui-kit-pack && npm run test:miner-deployment-docs-audit && npm run rees:test && npm run ui:openapi:check && npm run control-plane:contract:check && npm run control-plane:openapi:check && npm run ui:version-audit && npm run docs:drift-check && npm run coverage-boltons:check && npm run import-specifiers:check && npm run ui-derived-types:check && npm run server-manifest:check && npm run dead-source-files:check && npm run dead-exports:check && npm run publishable-deps:check && npm run fixture-clock-races:check && npm run typecheck-coverage:check && npm run checkers-wired:check && npm run release-commit-parsing:check && npm run regate-sort-key:check && npm run maintainer-associations:check && npm run command-redelivery-guards:check && npm run dispatch-gate-reasons:check && npm run validate:no-hand-written-js && npm run replay-runner-manifest:check && npm run coco-dev-versions:check && npm run branding-drift:check && npm run manifest:drift-check && npm run engine-parity:drift-check && npm run engines-nvmrc:check && npm run release-manifest:sync:check && npm run release-linked-versions:check && npm run command-reference:check && npm run mcp:tool-reference:check && npm run mcp:client-config:check && npm run contract:api-schemas:check && npm run ui:lint && npm run ui:typecheck && npm run ui:test && npm run ui:build", + "test:ci": "git diff --check && npm run actionlint && npm run lint:composite-actions && npm run db:migrations:check && npm run db:migrations:immutable:check && npm run turbo-inputs:check && npm run workspace-dep-ranges:check && npm run db:schema-drift:check && npm run selfhost:env-reference:check && npm run miner:env-reference:check && npm run selfhost:validate-observability && npm run cf-typegen:check && npm run build --workspace @loopover/engine && npm run build --workspace @loopover/discovery-index && npm run build:mcp && npm run build:miner && npm run build --workspace @loopover/ui-kit && npm run typecheck && npm run test:coverage && npm run test:engine-parity && npm run test:live-gate-parity && npm run test:driver-parity && npm run validate:mcp && npm run test --workspace @loopover/engine && npm run test:workers && npm run test:mcp-pack && npm run test:contract-pack && npm run test:miner-pack && npm run test:engine-pack && npm run test:ui-kit-pack && npm run test:miner-deployment-docs-audit && npm run rees:test && npm run ui:openapi:check && npm run control-plane:contract:check && npm run control-plane:openapi:check && npm run ui:version-audit && npm run docs:drift-check && npm run coverage-boltons:check && npm run import-specifiers:check && npm run ui-derived-types:check && npm run server-manifest:check && npm run dead-source-files:check && npm run dead-exports:check && npm run publishable-deps:check && npm run fixture-clock-races:check && npm run typecheck-coverage:check && npm run checkers-wired:check && npm run release-commit-parsing:check && npm run releasable-commit-types:check && npm run regate-sort-key:check && npm run maintainer-associations:check && npm run command-redelivery-guards:check && npm run dispatch-gate-reasons:check && npm run validate:no-hand-written-js && npm run replay-runner-manifest:check && npm run coco-dev-versions:check && npm run branding-drift:check && npm run manifest:drift-check && npm run engine-parity:drift-check && npm run engines-nvmrc:check && npm run release-manifest:sync:check && npm run release-linked-versions:check && npm run command-reference:check && npm run mcp:tool-reference:check && npm run mcp:client-config:check && npm run contract:api-schemas:check && npm run ui:lint && npm run ui:typecheck && npm run ui:test && npm run ui:build", "test:release": "npm run test:ci && npm run changelog:check", "test:release:mcp": "npm run test:ci", "test:watch": "vitest", diff --git a/packages/loopover-ui-kit/src/components/chart.test.tsx b/packages/loopover-ui-kit/src/components/chart.test.tsx new file mode 100644 index 0000000000..15326edf2e --- /dev/null +++ b/packages/loopover-ui-kit/src/components/chart.test.tsx @@ -0,0 +1,135 @@ +import { render } from "@testing-library/react"; +import { describe, expect, it, vi } from "vitest"; + +// ResponsiveContainer measures its parent through a ResizeObserver, and under jsdom that measurement never +// resolves -- it renders NOTHING, discarding its children entirely. Every assertion below would then fail, and +// the "renders nothing" ones would pass for entirely the wrong reason. +// +// Only that one measuring wrapper is replaced, with a plain passthrough; everything else -- including +// ChartContainer, which is the context provider under test -- stays real. Stubbing the whole module would mean +// asserting against a mock rather than against `chart.tsx`. +vi.mock("recharts", async (importOriginal) => ({ + ...(await importOriginal()), + ResponsiveContainer: ({ children }: { children?: React.ReactNode }) =>
{children}
, +})); + +import { + ChartContainer, + ChartLegendContent, + ChartStyle, + ChartTooltipContent, + type ChartConfig, +} from "./chart.js"; + +// #9937: `chart.tsx` is the one file the recharts v3 migration (#8610) rewrote, and it shipped with no tests +// at all -- so the migration's load-bearing behaviours were resting on the type-checker alone. +// +// What v3 actually changed here: `payload` and `label` moved OFF Tooltip's own props and are supplied through +// context, and the render-prop shape is published as `TooltipContentProps`. Everything below drives +// ChartTooltipContent the way recharts now drives it -- as a component receiving that shape -- inside the real +// ChartContainer, so the context wiring the migration touched is exercised rather than assumed. + +const config = { + revenue: { label: "Revenue", color: "#0ea5e9" }, + cost: { label: "Cost", theme: { light: "#111827", dark: "#f9fafb" } }, +} satisfies ChartConfig; + +const payload = [ + { dataKey: "revenue", name: "revenue", value: 120, color: "#0ea5e9", payload: { month: "Jan", revenue: 120 } }, + { dataKey: "cost", name: "cost", value: 80, color: "#111827", payload: { month: "Jan", cost: 80 } }, +]; + +/** ChartTooltipContent calls useChart(), so it must render inside a provider. ChartContainer is that + * provider and is exercised deliberately rather than mocked. Queries are scoped to the slot, never the whole + * container: ChartContainer also emits a