niceeval 0.6.0 → 0.6.2
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.
- package/dist/agents/types.d.ts +72 -6
- package/dist/context/types.d.ts +32 -12
- package/dist/i18n/en.d.ts +54 -0
- package/dist/i18n/zh-CN.d.ts +55 -1
- package/dist/o11y/types.d.ts +16 -2
- package/dist/report/aggregate.d.ts +5 -3
- package/dist/report/aggregate.js +32 -5
- package/dist/report/built-ins/experiment-comparison.d.ts +39 -0
- package/dist/report/built-ins/experiment-comparison.js +119 -0
- package/dist/report/built-ins/index.d.ts +2 -1
- package/dist/report/built-ins/index.js +2 -2
- package/dist/report/components.d.ts +10 -2
- package/dist/report/components.js +3 -3
- package/dist/report/compute.d.ts +11 -18
- package/dist/report/compute.js +68 -66
- package/dist/report/flag.d.ts +16 -1
- package/dist/report/flag.js +19 -1
- package/dist/report/format.d.ts +16 -14
- package/dist/report/format.js +28 -30
- package/dist/report/index.d.ts +5 -4
- package/dist/report/index.js +6 -5
- package/dist/report/locale.d.ts +23 -3
- package/dist/report/locale.js +47 -6
- package/dist/report/metrics.d.ts +13 -1
- package/dist/report/metrics.js +66 -15
- package/dist/report/primitives.d.ts +6 -0
- package/dist/report/react/AttemptList.d.ts +4 -4
- package/dist/report/react/AttemptList.js +8 -10
- package/dist/report/react/EvalList.d.ts +1 -1
- package/dist/report/react/EvalList.js +0 -0
- package/dist/report/react/ExperimentComparison.d.ts +8 -0
- package/dist/report/react/ExperimentComparison.js +11 -0
- package/dist/report/react/ExperimentList.d.ts +4 -2
- package/dist/report/react/ExperimentList.js +57 -7
- package/dist/report/react/MetricScatter.js +6 -16
- package/dist/report/react/chart-math.d.ts +23 -6
- package/dist/report/react/chart-math.js +71 -19
- package/dist/report/react/fixtures.d.ts +3 -3
- package/dist/report/react/fixtures.js +30 -18
- package/dist/report/react/format.d.ts +1 -1
- package/dist/report/react/format.js +1 -1
- package/dist/report/react/index.d.ts +1 -1
- package/dist/report/report.d.ts +5 -1
- package/dist/report/report.js +6 -2
- package/dist/report/text/faces.d.ts +1 -1
- package/dist/report/text/faces.js +100 -61
- package/dist/report/text/table.js +36 -5
- package/dist/report/types.d.ts +40 -34
- package/dist/results/types.d.ts +11 -0
- package/dist/runner/feedback/sink.d.ts +110 -0
- package/dist/runner/types.d.ts +513 -22
- package/dist/sandbox/docker.d.ts +23 -2
- package/dist/sandbox/e2b.d.ts +15 -1
- package/dist/sandbox/errors.d.ts +30 -3
- package/dist/sandbox/io-retry.d.ts +17 -0
- package/dist/sandbox/registry.d.ts +2 -0
- package/dist/sandbox/resolve.d.ts +18 -5
- package/dist/sandbox/retry.d.ts +11 -1
- package/dist/sandbox/types.d.ts +39 -5
- package/dist/sandbox/vercel.d.ts +7 -1
- package/dist/scoring/coverage.d.ts +30 -0
- package/dist/scoring/display.d.ts +21 -0
- package/dist/scoring/display.js +120 -0
- package/dist/scoring/types.d.ts +103 -20
- package/dist/shared/aggregate.d.ts +1 -0
- package/dist/shared/aggregate.js +3 -3
- package/dist/shared/types.d.ts +28 -0
- package/dist/tty-line.d.ts +0 -4
- package/dist/util.d.ts +23 -0
- package/docs-site/zh/concepts/adapter.mdx +24 -6
- package/docs-site/zh/concepts/assert.mdx +11 -10
- package/docs-site/zh/concepts/evals.mdx +7 -6
- package/docs-site/zh/concepts/experiment.mdx +1 -1
- package/docs-site/zh/concepts/overview.mdx +7 -7
- package/docs-site/zh/guides/agent-feedback-loop.mdx +35 -31
- package/docs-site/zh/guides/authoring.mdx +33 -0
- package/docs-site/zh/guides/ci-integration.mdx +23 -12
- package/docs-site/zh/guides/connect-your-agent.mdx +29 -3
- package/docs-site/zh/guides/custom-reports.mdx +29 -34
- package/docs-site/zh/guides/dataset-fanout.mdx +25 -3
- package/docs-site/zh/guides/debug-sandbox.mdx +57 -0
- package/docs-site/zh/guides/debugging.mdx +210 -0
- package/docs-site/zh/guides/experiments.mdx +10 -3
- package/docs-site/zh/guides/fixtures.mdx +3 -1
- package/docs-site/zh/guides/official-adapters.mdx +27 -3
- package/docs-site/zh/guides/publish-report.mdx +30 -16
- package/docs-site/zh/guides/report-components.mdx +49 -37
- package/docs-site/zh/guides/reporters.mdx +2 -2
- package/docs-site/zh/guides/results-data.mdx +42 -8
- package/docs-site/zh/guides/runner.mdx +17 -7
- package/docs-site/zh/guides/sandbox-agent.mdx +57 -7
- package/docs-site/zh/guides/sandbox-providers.mdx +258 -10
- package/docs-site/zh/guides/scoring-guide.mdx +4 -4
- package/docs-site/zh/guides/viewing-results.mdx +85 -41
- package/docs-site/zh/guides/write-experiment.mdx +5 -3
- package/docs-site/zh/guides/write-send.mdx +19 -2
- package/docs-site/zh/index.mdx +1 -1
- package/docs-site/zh/reference/builtin-agents.mdx +27 -0
- package/docs-site/zh/reference/capabilities.mdx +2 -2
- package/docs-site/zh/reference/cli.mdx +35 -9
- package/docs-site/zh/reference/define-agent.mdx +60 -5
- package/docs-site/zh/reference/define-config.mdx +1 -1
- package/docs-site/zh/reference/define-eval.mdx +42 -9
- package/docs-site/zh/reference/events.mdx +2 -2
- package/docs-site/zh/reference/expect.mdx +36 -6
- package/package.json +5 -1
- package/src/agents/ai-sdk-otel.test.ts +1 -0
- package/src/agents/ai-sdk.test.ts +3 -0
- package/src/agents/ai-sdk.ts +3 -0
- package/src/agents/bub-install-spec.test.ts +34 -0
- package/src/agents/bub-install-spec.ts +32 -0
- package/src/agents/bub.ts +31 -32
- package/src/agents/claude-code.test.ts +130 -9
- package/src/agents/claude-code.ts +76 -4
- package/src/agents/codex.test.ts +189 -40
- package/src/agents/codex.ts +155 -14
- package/src/agents/coding-cli-versions.test.ts +15 -0
- package/src/agents/coding-cli-versions.ts +3 -0
- package/src/agents/index.ts +11 -0
- package/src/agents/langgraph.test.ts +204 -0
- package/src/agents/langgraph.ts +495 -0
- package/src/agents/marketplace.ts +85 -0
- package/src/agents/native-config.test.ts +179 -0
- package/src/agents/native-config.ts +267 -0
- package/src/agents/openai-compat.test.ts +1 -0
- package/src/agents/openclaw.test.ts +31 -0
- package/src/agents/openclaw.ts +171 -0
- package/src/agents/plugin-config.test.ts +1 -0
- package/src/agents/sdk-streams.test.ts +79 -0
- package/src/agents/sdk-streams.ts +55 -10
- package/src/agents/skills.test.ts +1 -0
- package/src/agents/streaming.test.ts +3 -9
- package/src/agents/types.ts +73 -6
- package/src/agents/ui-message-stream.test.ts +3 -0
- package/src/cli.ts +411 -108
- package/src/context/context.test.ts +51 -12
- package/src/context/context.ts +161 -29
- package/src/context/session.test.ts +1 -0
- package/src/context/session.ts +114 -6
- package/src/context/types.ts +30 -12
- package/src/define.test.ts +13 -8
- package/src/define.ts +25 -4
- package/src/expect/index.ts +53 -23
- package/src/i18n/en.ts +65 -4
- package/src/i18n/zh-CN.ts +66 -4
- package/src/o11y/cost.test.ts +1 -0
- package/src/o11y/execution-tree.test.ts +1 -20
- package/src/o11y/otlp/mappers/claude-code.test.ts +1 -0
- package/src/o11y/otlp/parse.test.ts +1 -0
- package/src/o11y/otlp/turn-otel.test.ts +1 -0
- package/src/o11y/parsers/bub.test.ts +1 -0
- package/src/o11y/parsers/claude-code.test.ts +1 -34
- package/src/o11y/parsers/openclaw.test.ts +154 -0
- package/src/o11y/parsers/openclaw.ts +310 -0
- package/src/o11y/prices.json +746 -311
- package/src/o11y/tool-names.test.ts +1 -0
- package/src/o11y/types.ts +16 -2
- package/src/report/aggregate.ts +34 -5
- package/src/report/built-in-user-parity.test.tsx +127 -173
- package/src/report/built-ins/experiment-comparison.tsx +179 -0
- package/src/report/built-ins/index.ts +7 -2
- package/src/report/components.tsx +11 -3
- package/src/report/compute.ts +80 -74
- package/src/report/dual-render.test.tsx +222 -91
- package/src/report/flag.ts +30 -2
- package/src/report/format.ts +36 -27
- package/src/report/index.ts +23 -6
- package/src/report/locale.ts +49 -6
- package/src/report/metrics.ts +68 -15
- package/src/report/primitives.tsx +6 -0
- package/src/report/react/AttemptList.tsx +9 -36
- package/src/report/react/EvalList.tsx +0 -0
- package/src/report/react/ExperimentComparison.tsx +68 -0
- package/src/report/react/ExperimentList.tsx +173 -55
- package/src/report/react/MetricScatter.tsx +13 -25
- package/src/report/react/chart-math.test.ts +85 -0
- package/src/report/react/chart-math.ts +101 -22
- package/src/report/react/enhance.js +72 -1
- package/src/report/react/fixtures.ts +34 -21
- package/src/report/react/format.ts +1 -1
- package/src/report/react/index.tsx +0 -1
- package/src/report/react/render.test.tsx +30 -69
- package/src/report/react/styles.css +112 -14
- package/src/report/report.test.ts +308 -105
- package/src/report/report.ts +6 -2
- package/src/report/text/faces.ts +111 -67
- package/src/report/text/table.ts +42 -5
- package/src/report/types.ts +42 -34
- package/src/results/annotated-source.test.ts +62 -9
- package/src/results/annotated-source.ts +64 -6
- package/src/results/attempt-evidence.test.ts +9 -7
- package/src/results/attempt-evidence.ts +15 -8
- package/src/results/attempt-source.ts +6 -3
- package/src/results/copy.ts +145 -55
- package/src/results/host-equivalence.test.ts +11 -9
- package/src/results/index.ts +2 -0
- package/src/results/locator.test.ts +1 -22
- package/src/results/open.ts +7 -1
- package/src/results/publish.ts +149 -0
- package/src/results/results.test.ts +85 -51
- package/src/results/truncate.ts +90 -0
- package/src/results/types.ts +7 -0
- package/src/results/writer.ts +31 -13
- package/src/runner/attempt.test.ts +138 -7
- package/src/runner/attempt.ts +603 -104
- package/src/runner/discover.test.ts +47 -0
- package/src/runner/discover.ts +36 -2
- package/src/runner/eval-source.test.ts +1 -27
- package/src/runner/feedback/agent.test.ts +504 -0
- package/src/runner/feedback/agent.ts +409 -0
- package/src/runner/feedback/ci.test.ts +562 -0
- package/src/runner/feedback/ci.ts +401 -0
- package/src/runner/feedback/coordinator.test.ts +317 -0
- package/src/runner/feedback/coordinator.ts +397 -0
- package/src/runner/feedback/failure.ts +40 -0
- package/src/runner/feedback/human.test.ts +616 -0
- package/src/runner/feedback/human.ts +535 -0
- package/src/runner/feedback/index.ts +66 -0
- package/src/runner/feedback/io.ts +78 -0
- package/src/runner/feedback/profile.test.ts +50 -0
- package/src/runner/feedback/profile.ts +58 -0
- package/src/runner/feedback/reducer.test.ts +395 -0
- package/src/runner/feedback/reducer.ts +260 -0
- package/src/runner/feedback/renderer.ts +82 -0
- package/src/runner/feedback/sink.ts +203 -0
- package/src/runner/feedback/testing.ts +106 -0
- package/src/runner/ledger.test.ts +230 -0
- package/src/runner/ledger.ts +329 -0
- package/src/runner/report.test.ts +128 -3
- package/src/runner/report.ts +33 -9
- package/src/runner/reporters/artifacts.ts +8 -2
- package/src/runner/reporters/braintrust.test.ts +8 -7
- package/src/runner/reporters/braintrust.ts +9 -2
- package/src/runner/reporters/index.ts +2 -2
- package/src/runner/reporters/json.test.ts +162 -0
- package/src/runner/reporters/json.ts +35 -8
- package/src/runner/reporters/shared.ts +1 -5
- package/src/runner/run.test.ts +760 -3
- package/src/runner/run.ts +242 -36
- package/src/runner/sandbox-prep.ts +3 -42
- package/src/runner/timing.ts +158 -0
- package/src/runner/types.ts +518 -22
- package/src/sandbox/checkpoint.test.ts +55 -0
- package/src/sandbox/checkpoint.ts +29 -8
- package/src/sandbox/cli-commands.ts +407 -0
- package/src/sandbox/docker.ts +115 -16
- package/src/sandbox/e2b-agent-template.test.ts +56 -0
- package/src/sandbox/e2b-agent-template.ts +94 -0
- package/src/sandbox/e2b.ts +74 -9
- package/src/sandbox/errors.ts +111 -4
- package/src/sandbox/index.ts +2 -0
- package/src/sandbox/io-retry.test.ts +58 -0
- package/src/sandbox/io-retry.ts +45 -0
- package/src/sandbox/keep-registry.test.ts +86 -0
- package/src/sandbox/keep-registry.ts +142 -0
- package/src/sandbox/keep.ts +178 -0
- package/src/sandbox/paths.test.ts +1 -0
- package/src/sandbox/paths.ts +19 -8
- package/src/sandbox/registry.ts +20 -3
- package/src/sandbox/resolve.ts +76 -11
- package/src/sandbox/retry.test.ts +70 -0
- package/src/sandbox/retry.ts +46 -4
- package/src/sandbox/types.ts +44 -6
- package/src/sandbox/vercel.ts +43 -20
- package/src/scoring/collector.ts +60 -17
- package/src/scoring/coverage.ts +95 -0
- package/src/scoring/diff.ts +81 -0
- package/src/scoring/display.test.ts +121 -0
- package/src/scoring/display.ts +133 -0
- package/src/scoring/evidence.test.ts +189 -0
- package/src/scoring/judge.test.ts +142 -0
- package/src/scoring/judge.ts +15 -18
- package/src/scoring/scoped.ts +217 -50
- package/src/scoring/types.ts +117 -20
- package/src/scoring/verdict.ts +16 -4
- package/src/shared/aggregate.ts +3 -2
- package/src/shared/types.ts +31 -0
- package/src/show/compose.ts +2 -2
- package/src/show/index.ts +29 -16
- package/src/show/render.ts +626 -308
- package/src/show/show.test.ts +251 -36
- package/src/tty-line.ts +8 -26
- package/src/util.test.ts +1 -0
- package/src/util.ts +41 -0
- package/src/view/app/components/AttemptModal.tsx +153 -2
- package/src/view/app/components/CodeView.tsx +32 -11
- package/src/view/app/components/CopyControls.tsx +2 -2
- package/src/view/app/i18n.ts +6 -0
- package/src/view/app/lib/attempt-route.test.ts +1 -0
- package/src/view/app/lib/verdict.ts +7 -9
- package/src/view/artifact-serving.test.ts +2 -1
- package/src/view/client-dist/app.css +1 -1
- package/src/view/client-dist/app.js +17 -17
- package/src/view/data.test.ts +2 -1
- package/src/view/data.ts +17 -7
- package/src/view/index.ts +12 -1
- package/src/view/server.ts +2 -0
- package/src/view/shared/types.ts +1 -1
- package/src/view/styles.css +3 -0
- package/src/view/view-report.test.ts +11 -10
- package/dist/o11y/execution-tree.d.ts +0 -103
- package/dist/o11y/otlp/select.d.ts +0 -22
- package/dist/report/built-ins/cost-pass-rate-comparison.d.ts +0 -1
- package/dist/report/built-ins/cost-pass-rate-comparison.js +0 -17
- package/dist/results/annotated-source.d.ts +0 -61
- package/dist/results/attempt-evidence.d.ts +0 -69
- package/dist/results/attempt-source.d.ts +0 -15
- package/src/report/built-ins/cost-pass-rate-comparison.tsx +0 -23
- package/src/runner/reporters/console.ts +0 -70
- package/src/runner/reporters/live.test.ts +0 -56
- package/src/runner/reporters/live.ts +0 -247
- package/src/runner/reporters/quiet.test.ts +0 -66
- package/src/runner/reporters/quiet.ts +0 -49
- package/src/runner/reporters/table.ts +0 -277
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { formatMetricValue } from "../format.js";
|
|
3
3
|
import { DEFAULT_REPORT_LOCALE, countText, localeText, resolveMetricLabel } from "../locale.js";
|
|
4
|
-
import {
|
|
4
|
+
import { niceTicks, placePointLabels } from "./chart-math.js";
|
|
5
5
|
import { colorClassForKey, seriesClassForKey } from "./colors.js";
|
|
6
6
|
import { cx } from "./format.js";
|
|
7
7
|
const WIDTH = 640;
|
|
@@ -40,10 +40,6 @@ export function MetricScatter({ data, pointHref, className, locale = DEFAULT_REP
|
|
|
40
40
|
if (drawableRows.length === 0) {
|
|
41
41
|
return (_jsxs("figure", { className: cx("nre", "nre-metric-scatter", className), children: [_jsx("p", { className: "nre-scatter-empty nre-missing", children: localeText(locale, "scatter.noData", { x: xLabel, y: yLabel }) }), missingNote] }));
|
|
42
42
|
}
|
|
43
|
-
// 恰好 1 个可画点:成本 × 通过率的对比至少要两个实验,单点不成图 —— 显式说清而不是画个孤点。
|
|
44
|
-
if (drawableRows.length === 1) {
|
|
45
|
-
return (_jsxs("figure", { className: cx("nre", "nre-metric-scatter", className), children: [_jsx("p", { className: "nre-scatter-empty", children: localeText(locale, "scatter.needTwo", { x: xLabel, y: yLabel }) }), missingNote] }));
|
|
46
|
-
}
|
|
47
43
|
const axisLabel = (label, col) => `${label}${col.unit ? `(${col.unit})` : ""}`;
|
|
48
44
|
const xScale = axisScale(drawableRows.map((r) => r.x.value), data.x.better, MARGIN.left, MARGIN.left + PLOT_W);
|
|
49
45
|
// y 像素轴向下增长:better:"higher" 高值在上 → 映射到 [bottom, top];"lower" 由 axisScale 反向后同样落到上方
|
|
@@ -57,7 +53,7 @@ export function MetricScatter({ data, pointHref, className, locale = DEFAULT_REP
|
|
|
57
53
|
label: pointLabel(r.key),
|
|
58
54
|
xValue,
|
|
59
55
|
yValue,
|
|
60
|
-
// hover 内容:experiment(点键)+ 系列(series,
|
|
56
|
+
// hover 内容:experiment(点键)+ 系列(series,ExperimentComparison 传的是 agent 维度,
|
|
61
57
|
// 有则加一行;无系列的散点没有这行)+ 两轴 display 与 samples/total(docs/feature/reports/library.md「MetricScatter」行为清单)
|
|
62
58
|
title: `${r.key}${r.series !== undefined ? `\n${r.series}` : ""}\n${xLabel}: ${r.x.display}(${r.x.samples}/${r.x.total})\n${yLabel}: ${r.y.display}(${r.y.samples}/${r.y.total})`,
|
|
63
59
|
px: xScale.scale(xValue),
|
|
@@ -78,22 +74,16 @@ export function MetricScatter({ data, pointHref, className, locale = DEFAULT_REP
|
|
|
78
74
|
}
|
|
79
75
|
for (const list of bySeries.values())
|
|
80
76
|
list.sort((a, b) => a.xValue - b.xValue);
|
|
81
|
-
//
|
|
82
|
-
const
|
|
83
|
-
const anchorLeft = p.px >= MARGIN.left + PLOT_W * 0.72;
|
|
84
|
-
return { cx: p.px, cy: p.py, anchorLeft, width: p.label.length * 6.4 + 10 };
|
|
85
|
-
});
|
|
86
|
-
const labelOffsets = layoutLabelOffsets(positions);
|
|
77
|
+
// 直接标签的候选位择优布局:锚向、避让方向都由布局按空间决定,画布边界含边距
|
|
78
|
+
const labels = placePointLabels(points.map((p) => ({ cx: p.px, cy: p.py, width: p.label.length * 6.4 + 10 })), { x0: 2, y0: 2, x1: WIDTH - 2, y1: HEIGHT - 2 });
|
|
87
79
|
return (_jsxs("figure", { className: cx("nre", "nre-metric-scatter", className), children: [_jsxs("svg", { className: "nre-scatter-svg", viewBox: `0 0 ${WIDTH} ${HEIGHT}`, role: "img", "aria-label": `${axisLabel(xLabel, data.x)} × ${axisLabel(yLabel, data.y)}`, children: [_jsxs("g", { className: "nre-scatter-grid", children: [yScale.ticks.map((tick) => (_jsx("line", { x1: MARGIN.left, x2: MARGIN.left + PLOT_W, y1: yScale.scale(tick), y2: yScale.scale(tick) }, `gy${tick}`))), xScale.ticks.map((tick) => (_jsx("line", { y1: MARGIN.top, y2: MARGIN.top + PLOT_H, x1: xScale.scale(tick), x2: xScale.scale(tick) }, `gx${tick}`)))] }), _jsx("text", { className: "nre-scatter-better-hint", x: MARGIN.left + PLOT_W - 6, y: MARGIN.top + 14, textAnchor: "end", children: localeText(locale, "scatter.betterHint") }), _jsx("g", { className: "nre-scatter-axis nre-scatter-axis-y", children: yScale.ticks.map((tick) => (_jsx("text", { className: "nre-scatter-tick", x: MARGIN.left - 8, y: yScale.scale(tick) + 3, textAnchor: "end", children: formatMetricValue(tick, data.y.unit) }, `ay${tick}`))) }), _jsx("g", { className: "nre-scatter-axis nre-scatter-axis-x", children: xScale.ticks.map((tick) => (_jsx("text", { className: "nre-scatter-tick", x: xScale.scale(tick), y: MARGIN.top + PLOT_H + 16, textAnchor: "middle", children: formatMetricValue(tick, data.x.unit) }, `ax${tick}`))) }), _jsx("text", { className: "nre-scatter-xlabel", x: MARGIN.left + PLOT_W / 2, y: HEIGHT - 8, textAnchor: "middle", children: axisLabel(xLabel, data.x) }), _jsx("text", { className: "nre-scatter-ylabel", x: 14, y: MARGIN.top + PLOT_H / 2, textAnchor: "middle", transform: `rotate(-90 14 ${MARGIN.top + PLOT_H / 2})`, children: axisLabel(yLabel, data.y) }), seriesOrder.map((series) => {
|
|
88
80
|
const list = bySeries.get(series);
|
|
89
81
|
if (list.length < 2)
|
|
90
82
|
return null;
|
|
91
83
|
return (_jsx("polyline", { className: cx("nre-scatter-line", seriesClassForKey(series)), "data-series": series, points: list.map((p) => `${p.px},${p.py}`).join(" "), fill: "none" }, series));
|
|
92
84
|
}), points.map((p, i) => {
|
|
93
|
-
const
|
|
94
|
-
const
|
|
95
|
-
const labelY = p.py + 4 + labelOffsets[i];
|
|
96
|
-
const group = (_jsxs("g", { className: cx("nre-scatter-point", p.series !== undefined ? seriesClassForKey(p.series) : "nre-series-none"), "data-key": p.key, children: [_jsx("title", { children: p.title }), labelOffsets[i] !== 0 && _jsx("line", { className: "nre-leader", x1: p.px, y1: p.py, x2: labelX, y2: labelY - 4 }), _jsx("circle", { className: "nre-scatter-hit", cx: p.px, cy: p.py, r: 12 }), _jsx("circle", { className: "nre-scatter-dot", cx: p.px, cy: p.py, r: 4.5 }), _jsx("text", { className: "nre-scatter-point-label", x: labelX, y: labelY, textAnchor: anchorLeft ? "end" : "start", children: p.label })] }));
|
|
85
|
+
const label = labels[i];
|
|
86
|
+
const group = (_jsxs("g", { className: cx("nre-scatter-point", p.series !== undefined ? seriesClassForKey(p.series) : "nre-series-none"), "data-key": p.key, children: [_jsx("title", { children: p.title }), label.leader && _jsx("line", { className: "nre-leader", x1: p.px, y1: p.py, x2: label.x, y2: label.y - 4 }), _jsx("circle", { className: "nre-scatter-hit", cx: p.px, cy: p.py, r: 12 }), _jsx("circle", { className: "nre-scatter-dot", cx: p.px, cy: p.py, r: 4.5 }), _jsx("text", { className: "nre-scatter-point-label", x: label.x, y: label.y, textAnchor: label.anchor, children: p.label })] }));
|
|
97
87
|
const row = drawableRows[i];
|
|
98
88
|
return pointHref ? (_jsx("a", { className: "nre-scatter-point-link", href: pointHref(row), children: group }, p.key)) : (_jsx("g", { children: group }, p.key));
|
|
99
89
|
})] }), seriesOrder.length > 0 && (_jsx("figcaption", { className: "nre-scatter-legend", children: seriesOrder.map((series) => (_jsx("span", { className: cx("nre-legend-key", "nre-key", colorClassForKey(series)), children: series }, series))) })), missingNote] }));
|
|
@@ -1,14 +1,31 @@
|
|
|
1
1
|
/** [min, max] 区间上生成 count 个左右的“整齐”刻度(Heckbert nice-numbers)。 */
|
|
2
2
|
export declare function niceTicks(min: number, max: number, count?: number): number[];
|
|
3
|
-
export interface
|
|
3
|
+
export interface PointLabelInput {
|
|
4
4
|
cx: number;
|
|
5
5
|
cy: number;
|
|
6
|
+
/** 标签文本的估算宽度(px)。 */
|
|
6
7
|
width: number;
|
|
7
|
-
|
|
8
|
-
|
|
8
|
+
}
|
|
9
|
+
/** 标签允许占用的画布范围(含坐标轴边距,标签可以借用空白边距)。 */
|
|
10
|
+
export interface LabelBounds {
|
|
11
|
+
x0: number;
|
|
12
|
+
y0: number;
|
|
13
|
+
x1: number;
|
|
14
|
+
y1: number;
|
|
15
|
+
}
|
|
16
|
+
export interface PlacedPointLabel {
|
|
17
|
+
/** <text> 的锚点坐标(y 为文字基线)。 */
|
|
18
|
+
x: number;
|
|
19
|
+
y: number;
|
|
20
|
+
anchor: "start" | "end" | "middle";
|
|
21
|
+
/** 标签不在点左右紧邻位:渲染层补 leader line 连回原点。 */
|
|
22
|
+
leader: boolean;
|
|
9
23
|
}
|
|
10
24
|
/**
|
|
11
|
-
*
|
|
12
|
-
*
|
|
25
|
+
* 散点直接标签的候选位择优布局(docs/feature/reports/library.md「MetricScatter」):
|
|
26
|
+
* 每个标签在点四周由近及远的候选环上打分——与已放置标签的重叠、与任何数据点的重叠、
|
|
27
|
+
* 越出画布的面积、离点距离逐项累加,取代价最小的候选。存在无冲突候选时标签必不遮点、
|
|
28
|
+
* 不叠标签、不越界;全候选冲突时取重叠最小者,绝不丢标签。重合点簇因此向不同方向散开,
|
|
29
|
+
* 而不是单向堆叠压到下方的数据点上。
|
|
13
30
|
*/
|
|
14
|
-
export declare function
|
|
31
|
+
export declare function placePointLabels(points: PointLabelInput[], bounds: LabelBounds): PlacedPointLabel[];
|
|
@@ -1,5 +1,4 @@
|
|
|
1
|
-
// 通用图表数值工具:round-number
|
|
2
|
-
// 从 src/view/app/lib/chart.ts 迁来(view 侧从这里 re-export),报告组件与 view 共用同一份。
|
|
1
|
+
// 通用图表数值工具:round-number 刻度生成与点标签布局,零依赖纯函数。
|
|
3
2
|
function niceNumber(range, round) {
|
|
4
3
|
if (range <= 0)
|
|
5
4
|
return 1;
|
|
@@ -43,26 +42,79 @@ export function niceTicks(min, max, count = 5) {
|
|
|
43
42
|
ticks.push(Number(v.toFixed(10)));
|
|
44
43
|
return ticks;
|
|
45
44
|
}
|
|
45
|
+
/** 标签框高度(基线上方 10px、下方 2px,对应 11px 字号)。 */
|
|
46
|
+
const LABEL_ASCENT = 10;
|
|
47
|
+
const LABEL_DESCENT = 2;
|
|
48
|
+
/** 数据点视为边长 2×DOT_R 的方形障碍(点半径 4.5 + 命中余量)。 */
|
|
49
|
+
const DOT_R = 6;
|
|
50
|
+
/** 紧邻位与点的水平间距;候选环按它逐环外扩。 */
|
|
51
|
+
const NEAR = 10;
|
|
52
|
+
const RINGS = [NEAR, NEAR + 12, NEAR + 26];
|
|
53
|
+
function labelBoxAt(x, y, anchor, width) {
|
|
54
|
+
const x0 = anchor === "start" ? x : anchor === "end" ? x - width : x - width / 2;
|
|
55
|
+
return { x0, y0: y - LABEL_ASCENT, x1: x0 + width, y1: y + LABEL_DESCENT };
|
|
56
|
+
}
|
|
57
|
+
function overlapArea(a, b) {
|
|
58
|
+
const w = Math.min(a.x1, b.x1) - Math.max(a.x0, b.x0);
|
|
59
|
+
const h = Math.min(a.y1, b.y1) - Math.max(a.y0, b.y0);
|
|
60
|
+
return w > 0 && h > 0 ? w * h : 0;
|
|
61
|
+
}
|
|
62
|
+
function outOfBoundsArea(box, bounds) {
|
|
63
|
+
const total = (box.x1 - box.x0) * (box.y1 - box.y0);
|
|
64
|
+
const w = Math.min(box.x1, bounds.x1) - Math.max(box.x0, bounds.x0);
|
|
65
|
+
const h = Math.min(box.y1, bounds.y1) - Math.max(box.y0, bounds.y0);
|
|
66
|
+
const inside = w > 0 && h > 0 ? w * h : 0;
|
|
67
|
+
return total - inside;
|
|
68
|
+
}
|
|
69
|
+
/** 一个点在距离 d 的候选环:左右紧邻、四个斜角、正上正下。顺序即同代价时的偏好序。 */
|
|
70
|
+
function ringCandidates(p, d) {
|
|
71
|
+
const diag = d * 0.75;
|
|
72
|
+
return [
|
|
73
|
+
{ x: p.cx + d, y: p.cy + 4, anchor: "start" },
|
|
74
|
+
{ x: p.cx - d, y: p.cy + 4, anchor: "end" },
|
|
75
|
+
{ x: p.cx + diag, y: p.cy - diag - 2, anchor: "start" },
|
|
76
|
+
{ x: p.cx - diag, y: p.cy - diag - 2, anchor: "end" },
|
|
77
|
+
{ x: p.cx, y: p.cy - d - LABEL_DESCENT - 2, anchor: "middle" },
|
|
78
|
+
{ x: p.cx + diag, y: p.cy + diag + LABEL_ASCENT, anchor: "start" },
|
|
79
|
+
{ x: p.cx - diag, y: p.cy + diag + LABEL_ASCENT, anchor: "end" },
|
|
80
|
+
{ x: p.cx, y: p.cy + d + LABEL_ASCENT + 2, anchor: "middle" },
|
|
81
|
+
];
|
|
82
|
+
}
|
|
46
83
|
/**
|
|
47
|
-
*
|
|
48
|
-
*
|
|
84
|
+
* 散点直接标签的候选位择优布局(docs/feature/reports/library.md「MetricScatter」):
|
|
85
|
+
* 每个标签在点四周由近及远的候选环上打分——与已放置标签的重叠、与任何数据点的重叠、
|
|
86
|
+
* 越出画布的面积、离点距离逐项累加,取代价最小的候选。存在无冲突候选时标签必不遮点、
|
|
87
|
+
* 不叠标签、不越界;全候选冲突时取重叠最小者,绝不丢标签。重合点簇因此向不同方向散开,
|
|
88
|
+
* 而不是单向堆叠压到下方的数据点上。
|
|
49
89
|
*/
|
|
50
|
-
export function
|
|
51
|
-
const
|
|
52
|
-
const
|
|
53
|
-
const
|
|
90
|
+
export function placePointLabels(points, bounds) {
|
|
91
|
+
const dots = points.map((p) => ({ x0: p.cx - DOT_R, y0: p.cy - DOT_R, x1: p.cx + DOT_R, y1: p.cy + DOT_R }));
|
|
92
|
+
const placedBoxes = [];
|
|
93
|
+
const result = new Array(points.length);
|
|
94
|
+
// 由上到下、由左到右逐个放置,布局确定可复现
|
|
95
|
+
const order = [...points.keys()].sort((a, b) => points[a].cy - points[b].cy || points[a].cx - points[b].cx);
|
|
54
96
|
for (const i of order) {
|
|
55
|
-
const
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
97
|
+
const p = points[i];
|
|
98
|
+
let best = null;
|
|
99
|
+
for (let ring = 0; ring < RINGS.length; ring++) {
|
|
100
|
+
const candidates = ringCandidates(p, RINGS[ring]);
|
|
101
|
+
for (let c = 0; c < candidates.length; c++) {
|
|
102
|
+
const candidate = candidates[c];
|
|
103
|
+
const box = labelBoxAt(candidate.x, candidate.y, candidate.anchor, p.width);
|
|
104
|
+
let cost = 0;
|
|
105
|
+
for (const placed of placedBoxes)
|
|
106
|
+
cost += overlapArea(box, placed) * 4;
|
|
107
|
+
for (const dot of dots)
|
|
108
|
+
cost += overlapArea(box, dot) * 3;
|
|
109
|
+
cost += outOfBoundsArea(box, bounds) * 6;
|
|
110
|
+
cost += ring * 8 + c * 0.5; // 近环、偏好序靠前者优先,只作同冲突程度下的排序
|
|
111
|
+
if (best === null || cost < best.cost) {
|
|
112
|
+
best = { candidate, box, cost, leader: !(ring === 0 && c <= 1) };
|
|
113
|
+
}
|
|
114
|
+
}
|
|
63
115
|
}
|
|
64
|
-
|
|
65
|
-
|
|
116
|
+
placedBoxes.push(best.box);
|
|
117
|
+
result[i] = { ...best.candidate, leader: best.leader };
|
|
66
118
|
}
|
|
67
|
-
return
|
|
119
|
+
return result;
|
|
68
120
|
}
|
|
@@ -6,14 +6,14 @@ export declare const overviewData: OverviewData;
|
|
|
6
6
|
export declare const overviewWithCost: OverviewData;
|
|
7
7
|
/** GroupSummary.data 的产物形态:eval 级折叠计票 + 旧 GroupSelector 口径的通过率(包成 MetricCell)。 */
|
|
8
8
|
export declare const groupSummaryData: GroupSummaryData;
|
|
9
|
-
export declare const tableData: TableData<"pass-rate" | "code-lines">;
|
|
9
|
+
export declare const tableData: TableData<"task-pass-rate" | "code-lines">;
|
|
10
10
|
/** rows: "experiment" 的榜单形态:行携带 agent/model 元信息与 eval 级折叠计票。 */
|
|
11
|
-
export declare const tableDataWithMeta: TableData<"pass-rate">;
|
|
11
|
+
export declare const tableDataWithMeta: TableData<"task-pass-rate">;
|
|
12
12
|
export declare const matrixData: MatrixData;
|
|
13
13
|
export declare const scoreboardData: ScoreboardData;
|
|
14
14
|
export declare const scatterData: ScatterData;
|
|
15
15
|
export declare const lineData: LineData;
|
|
16
|
-
export declare const deltaData: DeltaData<"pass-rate" | "cost">;
|
|
16
|
+
export declare const deltaData: DeltaData<"task-pass-rate" | "cost">;
|
|
17
17
|
export declare const attemptListItems: AttemptListItem[];
|
|
18
18
|
export declare const evalListItems: EvalListItem[];
|
|
19
19
|
export declare const experimentListItems: ExperimentListItem[];
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
// 数字刻意覆盖诚实细节:coverage 角标(samples<total)、全 null 格子、
|
|
4
4
|
// 稀疏矩阵、缺数据的散点、delta 的 null 不硬算、truncated 计数。
|
|
5
5
|
const locator = (s) => s;
|
|
6
|
-
export const passRateColumn = { key: "pass-rate", label: "pass rate", unit: "%", better: "higher" };
|
|
6
|
+
export const passRateColumn = { key: "task-pass-rate", label: "pass rate", unit: "%", better: "higher" };
|
|
7
7
|
export const codeLinesColumn = { key: "code-lines", label: "code lines", unit: "lines", better: "lower" };
|
|
8
8
|
export const costColumn = { key: "cost", label: "cost", unit: "$", better: "lower" };
|
|
9
9
|
export const overviewData = {
|
|
@@ -59,7 +59,7 @@ export const tableData = {
|
|
|
59
59
|
{
|
|
60
60
|
key: "codex",
|
|
61
61
|
cells: {
|
|
62
|
-
"pass-rate": { value: 0.5, display: "50%", samples: 6, total: 6, refs: [] },
|
|
62
|
+
"task-pass-rate": { value: 0.5, display: "50%", samples: 6, total: 6, refs: [] },
|
|
63
63
|
// 全 null:一个有效样本都没有 → 缺数据文案,绝不画 0
|
|
64
64
|
"code-lines": { value: null, display: "—", samples: 0, total: 6, refs: [] },
|
|
65
65
|
},
|
|
@@ -67,7 +67,7 @@ export const tableData = {
|
|
|
67
67
|
{
|
|
68
68
|
key: "bub",
|
|
69
69
|
cells: {
|
|
70
|
-
"pass-rate": {
|
|
70
|
+
"task-pass-rate": {
|
|
71
71
|
value: 0.87,
|
|
72
72
|
display: "87%",
|
|
73
73
|
samples: 6,
|
|
@@ -87,7 +87,7 @@ export const tableDataWithMeta = {
|
|
|
87
87
|
rows: [
|
|
88
88
|
{
|
|
89
89
|
key: "compare/bub",
|
|
90
|
-
cells: { "pass-rate": { value: 0.5, display: "50%", samples: 2, total: 2, refs: [] } },
|
|
90
|
+
cells: { "task-pass-rate": { value: 0.5, display: "50%", samples: 2, total: 2, refs: [] } },
|
|
91
91
|
meta: {
|
|
92
92
|
agent: "bub",
|
|
93
93
|
model: "gpt-5.4",
|
|
@@ -96,7 +96,7 @@ export const tableDataWithMeta = {
|
|
|
96
96
|
},
|
|
97
97
|
{
|
|
98
98
|
key: "compare/codex",
|
|
99
|
-
cells: { "pass-rate": { value: 1, display: "100%", samples: 2, total: 2, refs: [] } },
|
|
99
|
+
cells: { "task-pass-rate": { value: 1, display: "100%", samples: 2, total: 2, refs: [] } },
|
|
100
100
|
meta: {
|
|
101
101
|
agent: "codex",
|
|
102
102
|
verdicts: { passed: 2, failed: 0, errored: 0, skipped: 0 },
|
|
@@ -242,7 +242,7 @@ export const deltaData = {
|
|
|
242
242
|
b: { experimentId: "compare/bub--agents-md" },
|
|
243
243
|
cells: {
|
|
244
244
|
// 通过率 +12pp:better higher → 好(绿)
|
|
245
|
-
"pass-rate": {
|
|
245
|
+
"task-pass-rate": {
|
|
246
246
|
a: { value: 0.5, display: "50%", samples: 6, total: 6, refs: [] },
|
|
247
247
|
b: { value: 0.62, display: "62%", samples: 6, total: 6, refs: [] },
|
|
248
248
|
delta: 0.12,
|
|
@@ -262,7 +262,7 @@ export const deltaData = {
|
|
|
262
262
|
a: { experimentId: "compare/codex" },
|
|
263
263
|
b: { experimentId: "compare/codex--agents-md" },
|
|
264
264
|
cells: {
|
|
265
|
-
"pass-rate": {
|
|
265
|
+
"task-pass-rate": {
|
|
266
266
|
a: { value: 0.4, display: "40%", samples: 6, total: 6, refs: [] },
|
|
267
267
|
b: { value: 0.4, display: "40%", samples: 6, total: 6, refs: [] },
|
|
268
268
|
delta: 0,
|
|
@@ -292,15 +292,15 @@ const failedAttempt = {
|
|
|
292
292
|
name: "roots-correct",
|
|
293
293
|
severity: "gate",
|
|
294
294
|
score: 0,
|
|
295
|
-
|
|
296
|
-
|
|
295
|
+
outcome: "failed",
|
|
296
|
+
expected: "x=2",
|
|
297
|
+
received: "x=3",
|
|
297
298
|
evidence: "judge: sign flipped when substituting into the quadratic formula",
|
|
298
299
|
},
|
|
299
300
|
],
|
|
300
301
|
durationMs: 32_000,
|
|
301
302
|
costUSD: 0.12,
|
|
302
303
|
locator: locator("@1a4a4a4"),
|
|
303
|
-
capabilities: { eval: true, execution: true, timing: true, diff: false },
|
|
304
304
|
};
|
|
305
305
|
const erroredAttempt = {
|
|
306
306
|
evalId: "geometry/angles",
|
|
@@ -308,11 +308,26 @@ const erroredAttempt = {
|
|
|
308
308
|
attempt: 0,
|
|
309
309
|
agent: "codex",
|
|
310
310
|
verdict: "errored",
|
|
311
|
-
|
|
311
|
+
// 结构化 error:列表只渲染 message 一层摘要;cause/stack 与 diagnostics 是下钻详情,随数据携带
|
|
312
|
+
error: {
|
|
313
|
+
code: "unexpected-error",
|
|
314
|
+
message: "TypeError: cannot read properties of undefined (reading 'foo')",
|
|
315
|
+
phase: "eval.run",
|
|
316
|
+
stack: "TypeError: cannot read properties of undefined (reading 'foo')\n at run (adapter.ts:42:7)",
|
|
317
|
+
cause: { name: "TypeError", message: "cannot read properties of undefined (reading 'foo')" },
|
|
318
|
+
},
|
|
319
|
+
diagnostics: [
|
|
320
|
+
{ code: "sandbox-teardown-failed", level: "warning", message: "sandbox teardown timed out", phase: "sandbox.teardown" },
|
|
321
|
+
],
|
|
312
322
|
assertions: [],
|
|
313
323
|
durationMs: 4_500,
|
|
314
324
|
locator: locator("@1c1c1c1"),
|
|
315
|
-
|
|
325
|
+
};
|
|
326
|
+
const failedRetryAttempt = {
|
|
327
|
+
...failedAttempt,
|
|
328
|
+
attempt: 4,
|
|
329
|
+
durationMs: 35_000,
|
|
330
|
+
locator: locator("@1b5b5b5"),
|
|
316
331
|
};
|
|
317
332
|
export const attemptListItems = [failedAttempt, erroredAttempt];
|
|
318
333
|
export const evalListItems = [
|
|
@@ -320,7 +335,6 @@ export const evalListItems = [
|
|
|
320
335
|
evalId: "algebra/quadratic",
|
|
321
336
|
experimentId: "compare/bub",
|
|
322
337
|
verdict: "failed",
|
|
323
|
-
reason: "roots-correct: expected x=2, got x=3",
|
|
324
338
|
score: { value: 0, display: "0%", samples: 1, total: 1, refs: [failedAttempt.locator] },
|
|
325
339
|
duration: { value: 32_000, display: "32.0s", samples: 1, total: 1, refs: [failedAttempt.locator] },
|
|
326
340
|
cost: { value: 0.12, display: "$0.12", samples: 1, total: 1, refs: [failedAttempt.locator] },
|
|
@@ -330,7 +344,6 @@ export const evalListItems = [
|
|
|
330
344
|
evalId: "geometry/angles",
|
|
331
345
|
experimentId: "compare/codex",
|
|
332
346
|
verdict: "errored",
|
|
333
|
-
reason: erroredAttempt.error,
|
|
334
347
|
score: { value: 0, display: "0%", samples: 1, total: 1, refs: [erroredAttempt.locator] },
|
|
335
348
|
duration: { value: 4_500, display: "4.5s", samples: 1, total: 1, refs: [erroredAttempt.locator] },
|
|
336
349
|
cost: { value: null, display: "—", samples: 0, total: 1, refs: [] },
|
|
@@ -342,22 +355,22 @@ export const experimentListItems = [
|
|
|
342
355
|
experimentId: "compare/bub",
|
|
343
356
|
agent: "bub",
|
|
344
357
|
model: "gpt-5.4",
|
|
358
|
+
flags: { memory: true },
|
|
345
359
|
verdicts: { passed: 1, failed: 1, errored: 0, skipped: 0 },
|
|
346
360
|
passRate: { value: 0.5, display: "50%", samples: 2, total: 2, refs: [] },
|
|
347
361
|
cost: { value: 0.12, display: "$0.12", samples: 1, total: 2, refs: [failedAttempt.locator] },
|
|
348
362
|
duration: { value: 32_000, display: "32.0s", samples: 2, total: 2, refs: [] },
|
|
349
363
|
tokens: { value: null, display: "—", samples: 0, total: 2, refs: [] },
|
|
350
364
|
evals: 2,
|
|
351
|
-
attempts:
|
|
365
|
+
attempts: 3,
|
|
352
366
|
lastRunAt: "2026-07-01T10:00:00Z",
|
|
353
367
|
evalRows: [
|
|
354
368
|
{
|
|
355
369
|
evalId: "algebra/quadratic",
|
|
356
370
|
verdict: "failed",
|
|
357
|
-
reason: "roots-correct: expected x=2, got x=3",
|
|
358
371
|
duration: { value: 32_000, display: "32.0s", samples: 1, total: 1, refs: [failedAttempt.locator] },
|
|
359
372
|
cost: { value: 0.12, display: "$0.12", samples: 1, total: 1, refs: [failedAttempt.locator] },
|
|
360
|
-
attempts: [failedAttempt],
|
|
373
|
+
attempts: [failedAttempt, failedRetryAttempt],
|
|
361
374
|
},
|
|
362
375
|
{
|
|
363
376
|
evalId: "algebra/simple",
|
|
@@ -383,7 +396,6 @@ export const experimentListItems = [
|
|
|
383
396
|
{
|
|
384
397
|
evalId: "geometry/angles",
|
|
385
398
|
verdict: "errored",
|
|
386
|
-
reason: erroredAttempt.error,
|
|
387
399
|
duration: { value: 4_500, display: "4.5s", samples: 1, total: 1, refs: [erroredAttempt.locator] },
|
|
388
400
|
cost: { value: null, display: "—", samples: 0, total: 1, refs: [] },
|
|
389
401
|
attempts: [erroredAttempt],
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
export { MISSING_TEXT,
|
|
1
|
+
export { MISSING_TEXT, formatDurationMs, formatPercent, formatUSD, verdictMark } from "../format.ts";
|
|
2
2
|
/** 拼 class 名:过滤空值,末尾接使用者透传的 className。 */
|
|
3
3
|
export declare function cx(...parts: (string | undefined | false)[]): string;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
// web 面的小工具:展示格式化统一住在计算侧的 ../format.ts(两个渲染面同一份),
|
|
2
2
|
// 这里 re-export 并补 class 名拼接。MetricCell 一律自带 display,组件不重算。
|
|
3
|
-
export { MISSING_TEXT,
|
|
3
|
+
export { MISSING_TEXT, formatDurationMs, formatPercent, formatUSD, verdictMark } from "../format.js";
|
|
4
4
|
/** 拼 class 名:过滤空值,末尾接使用者透传的 className。 */
|
|
5
5
|
export function cx(...parts) {
|
|
6
6
|
return parts.filter(Boolean).join(" ");
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
export { AttemptList, DeltaTable, EvalList, ExperimentList, GroupSummary, MetricBars, MetricLine, MetricMatrix, MetricScatter, MetricTable, RunOverview, Scoreboard, } from "../components.tsx";
|
|
2
2
|
export type { AttemptListProps, DeltaTableProps, EvalListProps, ExperimentListProps, GroupSummaryProps, MetricLineProps, MetricMatrixProps, MetricScatterProps, MetricTableProps, RunOverviewProps, ScoreboardProps, } from "../components.tsx";
|
|
3
|
-
export type {
|
|
3
|
+
export type { AttemptListItem, AttemptLocator, DeltaData, EvalListItem, ExperimentListEvalRow, ExperimentListItem, GroupSummaryData, LineAxis, LineData, MatrixData, MetricCell, MetricColumn, OverviewData, ScatterData, ScoreboardData, SelectionWarning, TableData, TableRowMeta, } from "../types.ts";
|
|
4
4
|
export { DEFAULT_REPORT_LOCALE, resolveMetricLabel } from "../locale.ts";
|
|
5
5
|
export type { LocalizedLabel, ReportLocale } from "../locale.ts";
|
|
6
6
|
export { NRE_PALETTE, colorClassForKey, colorHexForKey, colorIndexForKey, seriesClassForKey } from "./colors.ts";
|
package/dist/report/report.d.ts
CHANGED
|
@@ -13,7 +13,11 @@ export interface ReportDefinition {
|
|
|
13
13
|
[REPORT_DEFINITION]: true;
|
|
14
14
|
}
|
|
15
15
|
export declare function defineReport(build: (ctx: ReportContext) => ReportNode | Promise<ReportNode>): ReportDefinition;
|
|
16
|
-
/**
|
|
16
|
+
/**
|
|
17
|
+
* 宿主装载报告文件时用:默认导出是不是 ReportDefinition。defineReport 的产物是普通对象;
|
|
18
|
+
* 「组件兼报告」(把 defineReport 产物 Object.assign 到双面组件上)是挂了 build 面的
|
|
19
|
+
* 可调用函数,同样算数——判据只看 build 面与标记,不看宿主形态。
|
|
20
|
+
*/
|
|
17
21
|
export declare function isReportDefinition(value: unknown): value is ReportDefinition;
|
|
18
22
|
/**
|
|
19
23
|
* text 宿主的装载语义:build → 渲染前解析数据组件(唯一的 await 边界)→ 树校验 → 遍历渲染
|
package/dist/report/report.js
CHANGED
|
@@ -14,9 +14,13 @@ export function defineReport(build) {
|
|
|
14
14
|
}
|
|
15
15
|
return { build, [REPORT_DEFINITION]: true };
|
|
16
16
|
}
|
|
17
|
-
/**
|
|
17
|
+
/**
|
|
18
|
+
* 宿主装载报告文件时用:默认导出是不是 ReportDefinition。defineReport 的产物是普通对象;
|
|
19
|
+
* 「组件兼报告」(把 defineReport 产物 Object.assign 到双面组件上)是挂了 build 面的
|
|
20
|
+
* 可调用函数,同样算数——判据只看 build 面与标记,不看宿主形态。
|
|
21
|
+
*/
|
|
18
22
|
export function isReportDefinition(value) {
|
|
19
|
-
return (typeof value === "object" &&
|
|
23
|
+
return ((typeof value === "object" || typeof value === "function") &&
|
|
20
24
|
value !== null &&
|
|
21
25
|
value[REPORT_DEFINITION] === true &&
|
|
22
26
|
typeof value.build === "function");
|
|
@@ -24,6 +24,6 @@ export declare function scoreboardText(data: ScoreboardData, ctx: TextContext):
|
|
|
24
24
|
export declare function scatterText(data: ScatterData, ctx: TextContext): string;
|
|
25
25
|
export declare function lineText(data: LineData, ctx: TextContext): string;
|
|
26
26
|
export declare function deltaText(data: DeltaData, ctx: TextContext): string;
|
|
27
|
-
export declare function experimentListText(items: ExperimentListItem[], ctx: TextContext): string;
|
|
27
|
+
export declare function experimentListText(items: ExperimentListItem[], ctx: TextContext, relativeTo?: string): string;
|
|
28
28
|
export declare function evalListText(items: EvalListItem[], ctx: TextContext): string;
|
|
29
29
|
export declare function attemptListText(items: AttemptListItem[], total: number | undefined, ctx: TextContext): string;
|