@vitest-agent/ui 4.1.0 → 5.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (37) hide show
  1. package/README.md +3 -3
  2. package/dispatcher/cells/single-file-fail.js +1 -5
  3. package/dispatcher/cells/single-file-pass.js +1 -5
  4. package/dispatcher/cells/single-file-threshold.js +1 -5
  5. package/dispatcher/cells/single-project-fail.js +1 -5
  6. package/dispatcher/cells/single-project-pass.js +1 -5
  7. package/dispatcher/cells/single-project-threshold.js +1 -5
  8. package/dispatcher/cells/single-test-fail.js +1 -5
  9. package/dispatcher/cells/single-test-pass.js +1 -5
  10. package/dispatcher/cells/workspace-fail.js +1 -5
  11. package/dispatcher/cells/workspace-pass.js +1 -5
  12. package/dispatcher/cells/workspace-threshold.js +1 -5
  13. package/dispatcher/dispatch.js +20 -25
  14. package/index.d.ts +45 -316
  15. package/index.js +4 -17
  16. package/{render-ink → ink}/CountColumns.js +2 -2
  17. package/{render-ink → ink}/CoverageBlock.js +2 -2
  18. package/{render-ink → ink}/FailureSection.js +2 -2
  19. package/{render-ink → ink}/FailuresSection.js +2 -2
  20. package/{render-ink → ink}/ModuleHeader.js +1 -1
  21. package/{render-ink → ink}/ProjectRow.js +1 -1
  22. package/{render-ink → ink}/StatusIcon.js +2 -2
  23. package/{render-ink → ink}/StreamApp.js +14 -5
  24. package/{render-ink → ink}/SuggestedActions.js +2 -2
  25. package/{render-ink → ink}/TagColumns.js +1 -1
  26. package/{render-ink → ink}/TestRow.js +1 -1
  27. package/{render-ink → ink}/TrendLine.js +2 -2
  28. package/ink/dispatch-ink.js +61 -0
  29. package/{dispatcher → ink}/ink-helpers.js +1 -1
  30. package/ink.d.ts +789 -0
  31. package/ink.js +15 -0
  32. package/package.json +12 -7
  33. package/reducer.js +2 -1
  34. package/render-agent.js +2 -0
  35. package/{render-ink/spinner.js → spinner.js} +1 -1
  36. package/synthesize.js +2 -1
  37. package/render-ink/index.js +0 -15
package/index.d.ts CHANGED
@@ -1,5 +1,4 @@
1
1
  import { Schema } from "effect";
2
- import { FC, ReactElement } from "react";
3
2
  import { CoreStatusName, GlyphSet, Status, Style, TokenName } from "@effected/cli";
4
3
  //#region ../sdk/dist/dev/pkg/index.d.ts
5
4
  //#region src/schemas/Coverage.d.ts
@@ -381,6 +380,21 @@ export declare const RenderState: Schema.Struct<{
381
380
  readonly expected: Schema.optional<Schema.String>;
382
381
  readonly received: Schema.optional<Schema.String>;
383
382
  }>>;
383
+ /**
384
+ * What the run wrote straight to the terminal, past Vitest's console
385
+ * capture, folded from `RunFinished.strayOutput`. Absent when the run
386
+ * wrote nothing stray.
387
+ */
388
+ readonly strayOutput: Schema.optional<Schema.Struct<{
389
+ readonly total: Schema.Number;
390
+ readonly stdout: Schema.Number;
391
+ readonly stderr: Schema.Number;
392
+ readonly bytes: Schema.Number;
393
+ readonly samples: Schema.$Array<Schema.Struct<{
394
+ readonly stream: Schema.Literals<readonly ["stdout", "stderr"]>;
395
+ readonly text: Schema.String;
396
+ }>>;
397
+ }>>;
384
398
  }>;
385
399
  /** @public */
386
400
  export type RenderState = typeof RenderState.Type;
@@ -701,6 +715,16 @@ declare const AgentReport: Schema.Struct<{
701
715
  readonly files: Schema.Number;
702
716
  }>>;
703
717
  }>>;
718
+ readonly strayOutput: Schema.optional<Schema.Struct<{
719
+ readonly total: Schema.Number;
720
+ readonly stdout: Schema.Number;
721
+ readonly stderr: Schema.Number;
722
+ readonly bytes: Schema.Number;
723
+ readonly samples: Schema.$Array<Schema.Struct<{
724
+ readonly stream: Schema.Literals<readonly ["stdout", "stderr"]>;
725
+ readonly text: Schema.String;
726
+ }>>;
727
+ }>>;
704
728
  }>;
705
729
  /** @public */
706
730
  type AgentReport = typeof AgentReport.Type;
@@ -956,6 +980,21 @@ export declare const RunEvent: Schema.Union<readonly [Schema.TaggedStruct<"RunSt
956
980
  readonly expected: Schema.optional<Schema.String>;
957
981
  readonly received: Schema.optional<Schema.String>;
958
982
  }>>>;
983
+ /**
984
+ * What the run wrote straight to the terminal, past Vitest's console
985
+ * capture (`AgentReport.strayOutput`). Optional: absent when the run
986
+ * wrote nothing stray, and in older replay data.
987
+ */
988
+ readonly strayOutput: Schema.optional<Schema.Struct<{
989
+ readonly total: Schema.Number;
990
+ readonly stdout: Schema.Number;
991
+ readonly stderr: Schema.Number;
992
+ readonly bytes: Schema.Number;
993
+ readonly samples: Schema.$Array<Schema.Struct<{
994
+ readonly stream: Schema.Literals<readonly ["stdout", "stderr"]>;
995
+ readonly text: Schema.String;
996
+ }>>;
997
+ }>>;
959
998
  }>]>;
960
999
  /** @public */
961
1000
  export type RunEvent = typeof RunEvent.Type;
@@ -1135,23 +1174,15 @@ interface VitestTestModule {
1135
1174
  */
1136
1175
  type AgentCellFn = (inputs: DispatchInputs, opts: CellOptions) => string;
1137
1176
  /**
1138
- * A cell's Ink half: pure function from dispatch inputs to a React
1139
- * element rendered live to the terminal.
1140
- *
1141
- * @public
1142
- */
1143
- type InkCellFn = (inputs: DispatchInputs, opts: CellOptions) => ReactElement;
1144
- /**
1145
- * One entry in the dispatcher matrix: an agent-string renderer and an
1146
- * optional Ink-tree renderer for the same `(RunShape, RunOutcome)` pair.
1177
+ * One entry in the dispatcher matrix: the agent-string renderer for a
1178
+ * `(RunShape, RunOutcome)` pair. The Ink half of the same pair is the
1179
+ * matching entry of `inkDispatcherTable` in `@vitest-agent/ui/ink`.
1147
1180
  *
1148
1181
  * @public
1149
1182
  */
1150
1183
  interface Cell {
1151
1184
  /** Agent-string half — always present. */
1152
1185
  readonly agent: AgentCellFn;
1153
- /** Ink-tree half — omitted for cells where agent output is sufficient. */
1154
- readonly ink?: InkCellFn;
1155
1186
  }
1156
1187
  //#endregion
1157
1188
  //#region src/dispatcher/classify.d.ts
@@ -1216,18 +1247,6 @@ export declare const dispatcherTable: Readonly<Record<RunShape, Readonly<Record<
1216
1247
  * @public
1217
1248
  */
1218
1249
  export declare const dispatch: (inputs: DispatchInputs, opts: CellOptions) => string;
1219
- /**
1220
- * Dispatch to the cell that matches `(inputs.shape, inputs.outcome)`
1221
- * and return its Ink-half React tree. Returns `null` when the matched
1222
- * cell does not expose an `ink` half — callers should fall back to
1223
- * the agent string in that case.
1224
- *
1225
- * @param inputs - the classified dispatch inputs
1226
- * @param opts - cell rendering options
1227
- * @returns the Ink React element, or `null` when the cell has no Ink half
1228
- * @public
1229
- */
1230
- export declare const dispatchInk: (inputs: DispatchInputs, opts: CellOptions) => ReactElement | null;
1231
1250
  //#endregion
1232
1251
  //#region src/dispatcher/footer.d.ts
1233
1252
  /**
@@ -1358,229 +1377,7 @@ interface RenderAgentOptions {
1358
1377
  */
1359
1378
  export declare const renderAgent: (state: RenderState, options?: RenderAgentOptions) => string;
1360
1379
  //#endregion
1361
- //#region src/render-ink/CountColumns.d.ts
1362
- /**
1363
- * Props for the `CountColumns` component.
1364
- *
1365
- * @public
1366
- */
1367
- interface CountColumnsProps {
1368
- /** Number of passing tests. */
1369
- readonly passCount: number;
1370
- /** Number of failing tests. */
1371
- readonly failCount: number;
1372
- /** Number of skipped tests. */
1373
- readonly skipCount: number;
1374
- /** Number of timed-out tests. */
1375
- readonly timeoutCount: number;
1376
- }
1377
- /**
1378
- * Fixed width of the duration cell that follows the count columns on an
1379
- * aggregate row — sized for the formatter's widest common output
1380
- * (`59m 59s`). Longer values overflow their row rather than truncate.
1381
- *
1382
- * @public
1383
- */
1384
- export declare const DURATION_CELL_WIDTH = 7;
1385
- /**
1386
- * Renders four colored count columns (pass ✓, fail ✗, skip ↷, timeout ⧖)
1387
- * for an aggregate row. Counts render right-aligned in fixed 4-digit cells so
1388
- * columns align across rows; counts of 10,000+ overflow their row without
1389
- * truncation. Zeros are greyed; all four columns always appear. Glyphs and
1390
- * colours come from `VitestAgentStatus` (skip is `muted`).
1391
- *
1392
- * @public
1393
- */
1394
- export declare const CountColumns: FC<CountColumnsProps>;
1395
- //#endregion
1396
- //#region src/render-ink/CoverageBlock.d.ts
1397
- /**
1398
- * Props for the `CoverageBlock` component.
1399
- *
1400
- * @public
1401
- */
1402
- interface CoverageBlockProps {
1403
- /** The coverage render state to display. */
1404
- readonly coverage: CoverageRenderState;
1405
- /** Maximum number of gap entries to list; defaults to 3. */
1406
- readonly maxGaps?: number;
1407
- }
1408
- /**
1409
- * Renders the coverage section: per-metric percentages, threshold
1410
- * violations, and top-N gap entries sorted by missing line count.
1411
- *
1412
- * @public
1413
- */
1414
- export declare const CoverageBlock: FC<CoverageBlockProps>;
1415
- //#endregion
1416
- //#region src/render-ink/FailureSection.d.ts
1417
- /**
1418
- * Props for the `FailureSection` component.
1419
- *
1420
- * @public
1421
- */
1422
- interface FailureSectionProps {
1423
- /** The list of failure records to display. */
1424
- readonly failures: ReadonlyArray<FailureRecord>;
1425
- /** When `true`, renders the full stack trace under each failure. */
1426
- readonly includeStack?: boolean;
1427
- }
1428
- /**
1429
- * Renders one block per failed test: glyph, path, classification tag,
1430
- * error message, diff lines, and optionally the stack trace.
1431
- *
1432
- * @public
1433
- */
1434
- export declare const FailureSection: FC<FailureSectionProps>;
1435
- //#endregion
1436
- //#region src/render-ink/FailuresSection.d.ts
1437
- /**
1438
- * Props for the `FailuresSection` component.
1439
- *
1440
- * @public
1441
- */
1442
- interface FailuresSectionProps {
1443
- /** The list of failure records to display. */
1444
- readonly failures: ReadonlyArray<FailureRecord>;
1445
- /** Maximum entries to list before collapsing the rest into an overflow line. */
1446
- readonly limit: number;
1447
- }
1448
- /**
1449
- * Renders the capped failures block for aggregate-row shapes.
1450
- * Entries beyond `limit` collapse into an overflow line.
1451
- *
1452
- * @public
1453
- */
1454
- export declare const FailuresSection: FC<FailuresSectionProps>;
1455
- //#endregion
1456
- //#region src/render-ink/ModuleHeader.d.ts
1457
- /**
1458
- * Props for the `ModuleHeader` component.
1459
- *
1460
- * @public
1461
- */
1462
- interface ModuleHeaderProps {
1463
- /** The module record to display. */
1464
- readonly module: ModuleRecord;
1465
- }
1466
- /**
1467
- * Renders the per-module title line: a status glyph, the module path,
1468
- * and a dimmed inline summary of pass/fail/skip counts and duration.
1469
- *
1470
- * @public
1471
- */
1472
- export declare const ModuleHeader: FC<ModuleHeaderProps>;
1473
- //#endregion
1474
- //#region src/render-ink/ProjectRow.d.ts
1475
- /**
1476
- * Props for the `ProjectRow` component.
1477
- *
1478
- * @public
1479
- */
1480
- interface ProjectRowProps {
1481
- /** The per-project rollup. */
1482
- readonly project: ProjectSummary;
1483
- /** Pass/fail/skip/timeout counts for the project. */
1484
- readonly counts: {
1485
- passCount: number;
1486
- failCount: number;
1487
- skipCount: number;
1488
- timeoutCount: number;
1489
- };
1490
- /** True while the project still has a running or queued module. */
1491
- readonly running: boolean;
1492
- /**
1493
- * True when the run has been timed out — running rows resolve to the
1494
- * `⧖` glyph instead of continuing to animate the spinner.
1495
- */
1496
- readonly timedOut?: boolean;
1497
- /** Elapsed milliseconds — wall-clock while running, summed duration once finished. */
1498
- readonly elapsedMs: number;
1499
- /** Current spinner glyph; rendered in place of the status icon while running. */
1500
- readonly frame: string;
1501
- /** Name-column width so the count columns align across rows. */
1502
- readonly nameWidth: number;
1503
- /** Per-tag test counts for the project, merged across its modules; feeds the TagColumns cells. */
1504
- readonly tagCounts?: Record<string, number> | undefined;
1505
- /**
1506
- * The view-level tag union. Every row renders every tag in it so the
1507
- * tag columns align; empty (the default) renders no tag cells.
1508
- */
1509
- readonly tagUnion?: ReadonlyArray<string>;
1510
- }
1511
- /**
1512
- * Renders one per-project row in the `workspace`-shape live view: status
1513
- * glyph (animated spinner while running), project name, count columns,
1514
- * elapsed duration, and optional tag counts.
1515
- *
1516
- * @public
1517
- */
1518
- export declare const ProjectRow: FC<ProjectRowProps>;
1519
- //#endregion
1520
- //#region src/render-ink/StatusIcon.d.ts
1521
- /**
1522
- * The set of named statuses a `StatusIcon` can render.
1523
- *
1524
- * @public
1525
- */
1526
- type StatusIconKind = "passed" | "failed" | "skipped" | "pending" | "running" | "queued" | "finished" | "threshold" | "timed-out";
1527
- /**
1528
- * Props for the `StatusIcon` component.
1529
- *
1530
- * @public
1531
- */
1532
- interface StatusIconProps {
1533
- /** The status to render as a colored glyph. */
1534
- readonly status: StatusIconKind;
1535
- }
1536
- /**
1537
- * Renders a single colored status glyph for a test, module, or run.
1538
- *
1539
- * @public
1540
- */
1541
- export declare const StatusIcon: FC<StatusIconProps>;
1542
- //#endregion
1543
- //#region src/render-ink/StreamApp.d.ts
1544
- /**
1545
- * Props for the `StreamApp` component.
1546
- *
1547
- * @public
1548
- */
1549
- interface StreamAppProps {
1550
- /** The current reduced render state to display. */
1551
- readonly state: RenderState;
1552
- /** Current spinner frame index (the live view's `frame`: wall-clock ticks of `SPINNER_FRAME_MS`). */
1553
- readonly frameIndex: number;
1554
- /** Current wall-clock time in milliseconds; defaults to `Date.now()`. */
1555
- readonly nowMs?: number;
1556
- }
1557
- /**
1558
- * Root Ink component for the `stream` live renderer. Classifies the run
1559
- * shape and renders the appropriate per-shape live region.
1560
- *
1561
- * @public
1562
- */
1563
- export declare const StreamApp: FC<StreamAppProps>;
1564
- //#endregion
1565
- //#region src/render-ink/SuggestedActions.d.ts
1566
- /**
1567
- * Props for the `SuggestedActions` component.
1568
- *
1569
- * @public
1570
- */
1571
- interface SuggestedActionsProps {
1572
- /** The list of suggested actions to display. */
1573
- readonly actions: ReadonlyArray<SuggestedActionRecord>;
1574
- }
1575
- /**
1576
- * Renders the suggested-actions queue as severity-prefixed rows with
1577
- * optional tool hints. Returns `null` when the actions list is empty.
1578
- *
1579
- * @public
1580
- */
1581
- export declare const SuggestedActions: FC<SuggestedActionsProps>;
1582
- //#endregion
1583
- //#region src/render-ink/spinner.d.ts
1380
+ //#region src/spinner.d.ts
1584
1381
  /**
1585
1382
  * The Unicode spinner frames, in animation order (`Glyphs.unicode.spinner`).
1586
1383
  *
@@ -1606,74 +1403,6 @@ export declare const SPINNER_FRAME_MS: number;
1606
1403
  */
1607
1404
  export declare const spinnerFrame: (index: number, glyphs?: GlyphSet) => string;
1608
1405
  //#endregion
1609
- //#region src/render-ink/TagColumns.d.ts
1610
- /**
1611
- * Compute the view-level tag union: the alphabetically sorted set of tag
1612
- * names across every row's tag counts. A union of a single tag carries no
1613
- * signal (the whole view is one kind), so it collapses to empty and the
1614
- * view renders no tag columns at all.
1615
- *
1616
- * @public
1617
- */
1618
- export declare const tagUnion: (rows: ReadonlyArray<Record<string, number> | undefined>) => ReadonlyArray<string>;
1619
- /**
1620
- * Props for the `TagColumns` component.
1621
- *
1622
- * @public
1623
- */
1624
- interface TagColumnsProps {
1625
- /** The view-level tag union — every row renders every tag in it. */
1626
- readonly tags: ReadonlyArray<string>;
1627
- /** This row's per-tag test counts; tags absent here render a dimmed 0. */
1628
- readonly counts?: Record<string, number> | undefined;
1629
- }
1630
- /**
1631
- * Renders one row's fixed-width tag cells for the given tag union.
1632
- * Renders nothing when the union is empty.
1633
- *
1634
- * @public
1635
- */
1636
- export declare const TagColumns: FC<TagColumnsProps>;
1637
- //#endregion
1638
- //#region src/render-ink/TestRow.d.ts
1639
- /**
1640
- * Props for the `TestRow` component.
1641
- *
1642
- * @public
1643
- */
1644
- interface TestRowProps {
1645
- /** The test record to display. */
1646
- readonly test: TestRecord;
1647
- /** Leading indentation in spaces; defaults to 2. */
1648
- readonly indent?: number;
1649
- }
1650
- /**
1651
- * Renders one test row: status glyph, optional suite prefix, test name, and duration.
1652
- *
1653
- * @public
1654
- */
1655
- export declare const TestRow: FC<TestRowProps>;
1656
- //#endregion
1657
- //#region src/render-ink/TrendLine.d.ts
1658
- /**
1659
- * Props for the `TrendLine` component.
1660
- *
1661
- * @public
1662
- */
1663
- interface TrendLineProps {
1664
- /** The trend summary to display. */
1665
- readonly trend: {
1666
- readonly direction: "improving" | "regressing" | "stable";
1667
- readonly runCount: number;
1668
- };
1669
- }
1670
- /**
1671
- * Renders the one-line trend signal: direction (colored) and run count.
1672
- *
1673
- * @public
1674
- */
1675
- export declare const TrendLine: FC<TrendLineProps>;
1676
- //#endregion
1677
1406
  //#region src/synthesize.d.ts
1678
1407
  /**
1679
1408
  * Synthetic test name used to surface a suite-level (collection/load)
@@ -1871,5 +1600,5 @@ export declare const statusInkStyle: (name: VitestAgentStatusName) => InkTextSty
1871
1600
  */
1872
1601
  export declare const CURRENT_UI_VERSION: string;
1873
1602
  //#endregion
1874
- export { type AgentCellFn, type AgentReport, type Cell, type CellOptions, type CountColumnsProps, type CoverageBlockProps, FileCoverageReport as CoverageFile, type CoverageTotals, type DispatchInputs, type FailureSectionProps, type FailuresSectionProps, type GlobShortfall, type InkCellFn, type InkTextStyle, type MetricThresholds, type ModuleHeaderProps, type ProjectRowProps, type ProjectSummary, type RenderAgentOptions, type RunEventByTag, type RunOutcome, type RunShape, type StatusIconKind, type StatusIconProps, type StreamAppProps, type SuggestedActionsProps, type SynthesizeFromAgentReportOptions, type SynthesizeOptions, type SynthesizedCoverage, type TagColumnsProps, type TestClassification, type TestRowProps, type TrendLineProps, type TrendSummary, type VitestAgentStatusName, type VitestModuleDiagnostic, type VitestModuleError, type VitestParsedStack, type VitestTestCase, type VitestTestDiagnostic, type VitestTestError, type VitestTestModule, type VitestTestResult, type VitestTestSuite };
1603
+ export { type AgentCellFn, type AgentReport, type Cell, type CellOptions, FileCoverageReport as CoverageFile, type CoverageTotals, type DispatchInputs, type GlobShortfall, type InkTextStyle, type MetricThresholds, type ProjectSummary, type RenderAgentOptions, type RunEventByTag, type RunOutcome, type RunShape, type SynthesizeFromAgentReportOptions, type SynthesizeOptions, type SynthesizedCoverage, type TestClassification, type TrendSummary, type VitestAgentStatusName, type VitestModuleDiagnostic, type VitestModuleError, type VitestParsedStack, type VitestTestCase, type VitestTestDiagnostic, type VitestTestError, type VitestTestModule, type VitestTestResult, type VitestTestSuite };
1875
1604
  //# sourceMappingURL=index.d.ts.map
package/index.js CHANGED
@@ -2,23 +2,10 @@ import { classifyOutcome, classifyRunShape } from "./dispatcher/classify.js";
2
2
  import { buildFooter, dominantClassification } from "./dispatcher/footer.js";
3
3
  import { VitestAgentStatus, VitestAgentTokens, inkStyle, statusGlyph, statusInkStyle } from "./theme.js";
4
4
  import { formatDisplayDuration } from "./format-duration.js";
5
- import { dispatch, dispatchInk, dispatcherTable } from "./dispatcher/dispatch.js";
5
+ import { dispatch, dispatcherTable } from "./dispatcher/dispatch.js";
6
6
  import { reduceRenderState, reduceRenderStateAll } from "./reducer.js";
7
7
  import { renderAgent } from "./render-agent.js";
8
- import { CountColumns, DURATION_CELL_WIDTH } from "./render-ink/CountColumns.js";
9
- import { CoverageBlock } from "./render-ink/CoverageBlock.js";
10
- import { FailureSection } from "./render-ink/FailureSection.js";
11
- import { FailuresSection } from "./render-ink/FailuresSection.js";
12
- import { StatusIcon } from "./render-ink/StatusIcon.js";
13
- import { ModuleHeader } from "./render-ink/ModuleHeader.js";
14
- import { TagColumns, tagUnion } from "./render-ink/TagColumns.js";
15
- import { ProjectRow } from "./render-ink/ProjectRow.js";
16
- import { SPINNER_FRAMES, SPINNER_FRAME_MS, spinnerFrame } from "./render-ink/spinner.js";
17
- import { TestRow } from "./render-ink/TestRow.js";
18
- import { TrendLine } from "./render-ink/TrendLine.js";
19
- import { StreamApp } from "./render-ink/StreamApp.js";
20
- import { SuggestedActions } from "./render-ink/SuggestedActions.js";
21
- import "./render-ink/index.js";
8
+ import { SPINNER_FRAMES, SPINNER_FRAME_MS, spinnerFrame } from "./spinner.js";
22
9
  import { SUITE_FAILURE_LABEL, SUITE_LOAD_FAILURE_LABEL, synthesizeFromAgentReport, synthesizeRunEvents } from "./synthesize.js";
23
10
  import { ActionSeverity, CoverageFile, CoverageGap, CoverageMetric, CoverageRenderState, FailureRecord, ModuleRecord, RenderState, RenderTotals, RunEvent, SuggestedActionRecord, TestRecord, initialRenderState } from "@vitest-agent/sdk";
24
11
 
@@ -30,7 +17,7 @@ import { ActionSeverity, CoverageFile, CoverageGap, CoverageMetric, CoverageRend
30
17
  *
31
18
  * @public
32
19
  */
33
- const CURRENT_UI_VERSION = "4.1.0";
20
+ const CURRENT_UI_VERSION = "5.0.0";
34
21
 
35
22
  //#endregion
36
- export { ActionSeverity, CURRENT_UI_VERSION, CountColumns, CoverageBlock, CoverageFile, CoverageGap, CoverageMetric, CoverageRenderState, DURATION_CELL_WIDTH, FailureRecord, FailureSection, FailuresSection, ModuleHeader, ModuleRecord, ProjectRow, RenderState, RenderTotals, RunEvent, SPINNER_FRAMES, SPINNER_FRAME_MS, SUITE_FAILURE_LABEL, SUITE_LOAD_FAILURE_LABEL, StatusIcon, StreamApp, SuggestedActionRecord, SuggestedActions, TagColumns, TestRecord, TestRow, TrendLine, VitestAgentStatus, VitestAgentTokens, buildFooter, classifyOutcome, classifyRunShape, dispatch, dispatchInk, dispatcherTable, dominantClassification, formatDisplayDuration, initialRenderState, inkStyle, reduceRenderState, reduceRenderStateAll, renderAgent, spinnerFrame, statusGlyph, statusInkStyle, synthesizeFromAgentReport, synthesizeRunEvents, tagUnion };
23
+ export { ActionSeverity, CURRENT_UI_VERSION, CoverageFile, CoverageGap, CoverageMetric, CoverageRenderState, FailureRecord, ModuleRecord, RenderState, RenderTotals, RunEvent, SPINNER_FRAMES, SPINNER_FRAME_MS, SUITE_FAILURE_LABEL, SUITE_LOAD_FAILURE_LABEL, SuggestedActionRecord, TestRecord, VitestAgentStatus, VitestAgentTokens, buildFooter, classifyOutcome, classifyRunShape, dispatch, dispatcherTable, dominantClassification, formatDisplayDuration, initialRenderState, inkStyle, reduceRenderState, reduceRenderStateAll, renderAgent, spinnerFrame, statusGlyph, statusInkStyle, synthesizeFromAgentReport, synthesizeRunEvents };
@@ -1,9 +1,9 @@
1
1
  import { VitestAgentTokens, inkStyle, statusGlyph, statusInkStyle } from "../theme.js";
2
- import { Text } from "ink";
3
2
  import { useGlyphs } from "@effected/cli/ui";
3
+ import { Text } from "ink";
4
4
  import { jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/CountColumns.tsx
6
+ //#region src/ink/CountColumns.tsx
7
7
  /**
8
8
  * Fixed width of the duration cell that follows the count columns on an
9
9
  * aggregate row — sized for the formatter's widest common output
@@ -1,9 +1,9 @@
1
1
  import { inkStyle } from "../theme.js";
2
- import { Box, Text } from "ink";
3
2
  import { Fmt } from "@effected/cli";
3
+ import { Box, Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/CoverageBlock.tsx
6
+ //#region src/ink/CoverageBlock.tsx
7
7
  /**
8
8
  * Coverage section: per-metric percentage, threshold violations, top-N gaps.
9
9
  */
@@ -1,9 +1,9 @@
1
1
  import { inkStyle, statusGlyph, statusInkStyle } from "../theme.js";
2
- import { Box, Text } from "ink";
3
2
  import { useGlyphs } from "@effected/cli/ui";
3
+ import { Box, Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/FailureSection.tsx
6
+ //#region src/ink/FailureSection.tsx
7
7
  /**
8
8
  * Failure list: one block per failed test with classification, message,
9
9
  * diff, and optionally stack trace.
@@ -1,9 +1,9 @@
1
1
  import { VitestAgentTokens, inkStyle, statusGlyph, statusInkStyle } from "../theme.js";
2
- import { Box, Text } from "ink";
3
2
  import { useGlyphs } from "@effected/cli/ui";
3
+ import { Box, Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/FailuresSection.tsx
6
+ //#region src/ink/FailuresSection.tsx
7
7
  /**
8
8
  * The capped failures block for aggregate-row shapes (workspace,
9
9
  * single-project) — the rows there are projects or modules and cannot
@@ -3,7 +3,7 @@ import { StatusIcon } from "./StatusIcon.js";
3
3
  import { Box, Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/ModuleHeader.tsx
6
+ //#region src/ink/ModuleHeader.tsx
7
7
  const moduleGlyph = (m) => {
8
8
  if (m.status === "queued") return "queued";
9
9
  if (m.status === "running") return "running";
@@ -6,7 +6,7 @@ import { TagColumns } from "./TagColumns.js";
6
6
  import { Box, Text } from "ink";
7
7
  import { Fragment, jsx, jsxs } from "react/jsx-runtime";
8
8
 
9
- //#region src/render-ink/ProjectRow.tsx
9
+ //#region src/ink/ProjectRow.tsx
10
10
  /**
11
11
  * Pick the glyph element for the project row using the spec's severity
12
12
  * precedence (`✗ > ⧖ > ⚠ > ↷ > ✓`). Skip-only projects (no passes, no
@@ -1,9 +1,9 @@
1
1
  import { statusGlyph, statusInkStyle } from "../theme.js";
2
- import { Text } from "ink";
3
2
  import { useGlyphs } from "@effected/cli/ui";
3
+ import { Text } from "ink";
4
4
  import { jsx } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/StatusIcon.tsx
6
+ //#region src/ink/StatusIcon.tsx
7
7
  /**
8
8
  * Single-character status glyph for tests, modules, and the run itself.
9
9
  *
@@ -1,19 +1,20 @@
1
1
  import { classifyRunShape } from "../dispatcher/classify.js";
2
2
  import { VitestAgentTokens, inkStyle, statusGlyph, statusInkStyle } from "../theme.js";
3
3
  import { formatDisplayDuration } from "../format-duration.js";
4
+ import { spinnerFrame } from "../spinner.js";
4
5
  import { CountColumns, DURATION_CELL_WIDTH } from "./CountColumns.js";
5
6
  import { StatusIcon } from "./StatusIcon.js";
6
7
  import { TagColumns, tagUnion } from "./TagColumns.js";
7
8
  import { ProjectRow } from "./ProjectRow.js";
8
- import { spinnerFrame } from "./spinner.js";
9
9
  import { TestRow } from "./TestRow.js";
10
10
  import { TrendLine } from "./TrendLine.js";
11
- import { Box, Text } from "ink";
11
+ import { formatStrayOutputNote } from "@vitest-agent/sdk";
12
12
  import { Fmt } from "@effected/cli";
13
13
  import { useGlyphs } from "@effected/cli/ui";
14
+ import { Box, Text } from "ink";
14
15
  import { Fragment, jsx, jsxs } from "react/jsx-runtime";
15
16
 
16
- //#region src/render-ink/StreamApp.tsx
17
+ //#region src/ink/StreamApp.tsx
17
18
  const ANONYMOUS_PROJECT = "default";
18
19
  /** Maximum number of running rows displayed in the Live region. Beyond this,
19
20
  * excess running units collapse into a single "… and N more running" line. */
@@ -508,9 +509,17 @@ const StreamApp = ({ state, frameIndex, nowMs }) => {
508
509
  const projects = groupByProject(state).map((g) => buildProjectSummary(g.name, sumCounts(g.modules)));
509
510
  const shape = classifyRunShape(state, projects);
510
511
  const liveContent = liveRegion(state, shape, now, frame, glyphs);
511
- return /* @__PURE__ */ jsx(Box, {
512
+ const stray = state.strayOutput !== void 0 ? formatStrayOutputNote(state.strayOutput) : null;
513
+ return /* @__PURE__ */ jsxs(Box, {
512
514
  flexDirection: "column",
513
- children: liveContent
515
+ children: [liveContent, stray !== null ? /* @__PURE__ */ jsx(Box, {
516
+ flexDirection: "column",
517
+ marginTop: 1,
518
+ children: stray.map((line, i) => /* @__PURE__ */ jsx(Text, {
519
+ ...i === 0 ? statusInkStyle("warning") : {},
520
+ children: line
521
+ }, `stray:${i}`))
522
+ }) : null]
514
523
  });
515
524
  };
516
525
 
@@ -1,9 +1,9 @@
1
1
  import { inkStyle } from "../theme.js";
2
- import { Box, Text } from "ink";
3
2
  import { Token } from "@effected/cli";
3
+ import { Box, Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/SuggestedActions.tsx
6
+ //#region src/ink/SuggestedActions.tsx
7
7
  const SEVERITY_TOKEN = {
8
8
  info: Token.named("blue"),
9
9
  warn: "warning",
@@ -2,7 +2,7 @@ import { VitestAgentTokens, inkStyle } from "../theme.js";
2
2
  import { Text } from "ink";
3
3
  import { jsx, jsxs } from "react/jsx-runtime";
4
4
 
5
- //#region src/render-ink/TagColumns.tsx
5
+ //#region src/ink/TagColumns.tsx
6
6
  /**
7
7
  * Fixed-width tag-count columns for aggregate rows in the `stream` view.
8
8
  * Every row renders every tag in the view's union so the columns align
@@ -3,7 +3,7 @@ import { StatusIcon } from "./StatusIcon.js";
3
3
  import { Box, Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/TestRow.tsx
6
+ //#region src/ink/TestRow.tsx
7
7
  const testGlyph = (status) => status;
8
8
  /**
9
9
  * Renders one test row: status glyph, optional suite prefix, test name, and duration.
@@ -1,9 +1,9 @@
1
1
  import { VitestAgentTokens, inkStyle } from "../theme.js";
2
- import { Text } from "ink";
3
2
  import { Fmt } from "@effected/cli";
3
+ import { Text } from "ink";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
5
 
6
- //#region src/render-ink/TrendLine.tsx
6
+ //#region src/ink/TrendLine.tsx
7
7
  /** A regressing trend is a `warning`, not a failure (the kit's drift decision). */
8
8
  const TOKEN = {
9
9
  improving: "success",