@sanity/ailf-studio 0.1.0 → 0.1.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/index.js CHANGED
@@ -18,9 +18,8 @@ var GraduateToNativeAction = (props) => {
18
18
  const [isConfirming, setIsConfirming] = useState(false);
19
19
  const doc = draft ?? published;
20
20
  const origin = doc?.origin;
21
- if (type !== "ailf.task" || !origin) return null;
22
- const repoDisplay = origin.repo ?? "an external repository";
23
- const repoUrl = origin.repo && origin.path && origin.branch ? `https://github.com/${origin.repo}/blob/${origin.branch}/${origin.path}` : null;
21
+ const repoDisplay = origin?.repo ?? "an external repository";
22
+ const repoUrl = origin?.repo && origin.path && origin.branch ? `https://github.com/${origin.repo}/blob/${origin.branch}/${origin.path}` : null;
24
23
  const handleGraduate = useCallback(async () => {
25
24
  try {
26
25
  const publishedId = id.replace(/^drafts\./, "");
@@ -34,6 +33,7 @@ var GraduateToNativeAction = (props) => {
34
33
  console.error("Failed to graduate task:", err);
35
34
  }
36
35
  }, [client, draft, id, onComplete]);
36
+ if (type !== "ailf.task" || !origin) return null;
37
37
  return {
38
38
  dialog: isConfirming ? {
39
39
  type: "confirm",
@@ -60,19 +60,26 @@ var GraduateToNativeAction = (props) => {
60
60
  onConfirm: handleGraduate
61
61
  } : void 0,
62
62
  icon: EditIcon,
63
- label: "Graduate to Native",
63
+ label: "Graduate to native task",
64
64
  onHandle: () => setIsConfirming(true),
65
+ title: "Disconnect this task from its source repo so it becomes fully editable in Studio. This cannot be undone.",
65
66
  tone: "caution"
66
67
  };
67
68
  };
68
69
  GraduateToNativeAction.displayName = "GraduateToNativeAction";
69
70
 
70
71
  // src/schema/eval-request.ts
71
- import { defineField, defineType } from "sanity";
72
+ import { ALL_FIELDS_GROUP, defineField, defineType } from "sanity";
72
73
  var evalRequestSchema = defineType({
74
+ groups: [
75
+ { name: "main", title: "Main", default: true },
76
+ { name: "optional", title: "Optional" },
77
+ ALL_FIELDS_GROUP
78
+ ],
73
79
  fields: [
74
80
  defineField({
75
81
  description: "Set when the pipeline completes",
82
+ group: ["optional", "all-fields"],
76
83
  name: "completedAt",
77
84
  readOnly: true,
78
85
  title: "Completed At",
@@ -80,6 +87,7 @@ var evalRequestSchema = defineType({
80
87
  }),
81
88
  defineField({
82
89
  description: "Sanity dataset name",
90
+ group: ["main", "all-fields"],
83
91
  name: "dataset",
84
92
  readOnly: true,
85
93
  title: "Dataset",
@@ -88,6 +96,7 @@ var evalRequestSchema = defineType({
88
96
  }),
89
97
  defineField({
90
98
  description: "Set by webhook handler when GitHub dispatch succeeds",
99
+ group: ["optional", "all-fields"],
91
100
  name: "dispatchedAt",
92
101
  readOnly: true,
93
102
  title: "Dispatched At",
@@ -95,6 +104,7 @@ var evalRequestSchema = defineType({
95
104
  }),
96
105
  defineField({
97
106
  description: "Error message if dispatch or pipeline failed",
107
+ group: ["optional", "all-fields"],
98
108
  name: "error",
99
109
  readOnly: true,
100
110
  title: "Error",
@@ -102,6 +112,7 @@ var evalRequestSchema = defineType({
102
112
  }),
103
113
  defineField({
104
114
  description: "Evaluation mode",
115
+ group: ["main", "all-fields"],
105
116
  initialValue: "baseline",
106
117
  name: "mode",
107
118
  options: {
@@ -118,6 +129,7 @@ var evalRequestSchema = defineType({
118
129
  }),
119
130
  defineField({
120
131
  description: "Content release perspective ID",
132
+ group: ["main", "all-fields"],
121
133
  name: "perspective",
122
134
  readOnly: true,
123
135
  title: "Perspective",
@@ -126,6 +138,7 @@ var evalRequestSchema = defineType({
126
138
  }),
127
139
  defineField({
128
140
  description: "Sanity project ID",
141
+ group: ["main", "all-fields"],
129
142
  name: "projectId",
130
143
  readOnly: true,
131
144
  title: "Project ID",
@@ -134,6 +147,7 @@ var evalRequestSchema = defineType({
134
147
  }),
135
148
  defineField({
136
149
  description: "Links to the resulting ailf.report document's reportId",
150
+ group: ["optional", "all-fields"],
137
151
  name: "reportId",
138
152
  readOnly: true,
139
153
  title: "Report ID",
@@ -141,6 +155,7 @@ var evalRequestSchema = defineType({
141
155
  }),
142
156
  defineField({
143
157
  description: "ISO timestamp of when the request was created",
158
+ group: ["main", "all-fields"],
144
159
  name: "requestedAt",
145
160
  readOnly: true,
146
161
  title: "Requested At",
@@ -149,6 +164,7 @@ var evalRequestSchema = defineType({
149
164
  }),
150
165
  defineField({
151
166
  description: "User ID of the person who clicked the button",
167
+ group: ["optional", "all-fields"],
152
168
  name: "requestedBy",
153
169
  readOnly: true,
154
170
  title: "Requested By",
@@ -156,6 +172,7 @@ var evalRequestSchema = defineType({
156
172
  }),
157
173
  defineField({
158
174
  description: "Request lifecycle: pending \u2192 dispatched \u2192 completed \u2192 failed. Only 'pending' is set by Studio; the webhook handler and pipeline callback update subsequent states.",
175
+ group: ["main", "all-fields"],
159
176
  initialValue: "pending",
160
177
  name: "status",
161
178
  options: {
@@ -173,6 +190,7 @@ var evalRequestSchema = defineType({
173
190
  }),
174
191
  defineField({
175
192
  description: 'Publish tag for the report (e.g. "release-my-release-2026-03-16")',
193
+ group: ["optional", "all-fields"],
176
194
  name: "tag",
177
195
  readOnly: true,
178
196
  title: "Tag",
@@ -197,11 +215,17 @@ var evalRequestSchema = defineType({
197
215
  });
198
216
 
199
217
  // src/schema/feature-area.ts
200
- import { defineField as defineField2, defineType as defineType2 } from "sanity";
218
+ import { ALL_FIELDS_GROUP as ALL_FIELDS_GROUP2, defineField as defineField2, defineType as defineType2 } from "sanity";
201
219
  var featureAreaSchema = defineType2({
220
+ groups: [
221
+ { name: "main", title: "Main", default: true },
222
+ { name: "optional", title: "Optional" },
223
+ ALL_FIELDS_GROUP2
224
+ ],
202
225
  fields: [
203
226
  defineField2({
204
227
  description: 'Unique stable identifier (e.g., "groq"). Must be lowercase alphanumeric with hyphens. Used for CLI filtering (--area groq) and score aggregation.',
228
+ group: ["main", "all-fields"],
205
229
  name: "areaId",
206
230
  title: "Area ID",
207
231
  type: "slug",
@@ -214,6 +238,7 @@ var featureAreaSchema = defineType2({
214
238
  }),
215
239
  defineField2({
216
240
  description: 'Human-readable label shown in Studio and reports (e.g., "GROQ Query Language")',
241
+ group: ["main", "all-fields"],
217
242
  name: "description",
218
243
  title: "Description",
219
244
  type: "string",
@@ -221,12 +246,14 @@ var featureAreaSchema = defineType2({
221
246
  }),
222
247
  defineField2({
223
248
  description: "Team or person responsible for this feature area (optional)",
249
+ group: ["optional", "all-fields"],
224
250
  name: "owner",
225
251
  title: "Owner",
226
252
  type: "string"
227
253
  }),
228
254
  defineField2({
229
255
  description: "Additional categorization labels for filtering",
256
+ group: ["optional", "all-fields"],
230
257
  name: "tags",
231
258
  of: [{ type: "string" }],
232
259
  title: "Tags",
@@ -252,31 +279,25 @@ var featureAreaSchema = defineType2({
252
279
  });
253
280
 
254
281
  // src/schema/reference-solution.ts
255
- import { defineField as defineField3, defineType as defineType3 } from "sanity";
282
+ import { ALL_FIELDS_GROUP as ALL_FIELDS_GROUP3, defineField as defineField3, defineType as defineType3 } from "sanity";
256
283
  var referenceSolutionSchema = defineType3({
284
+ groups: [
285
+ { name: "main", title: "Main", default: true },
286
+ { name: "optional", title: "Optional" },
287
+ ALL_FIELDS_GROUP3
288
+ ],
257
289
  fields: [
258
290
  defineField3({
259
291
  description: "Human-readable label for this reference solution",
292
+ group: ["main", "all-fields"],
260
293
  name: "title",
261
294
  title: "Title",
262
295
  type: "string",
263
296
  validation: (rule) => rule.required()
264
297
  }),
265
- defineField3({
266
- description: "Primary programming language of the solution",
267
- initialValue: "typescript",
268
- name: "language",
269
- options: {
270
- list: [
271
- { title: "TypeScript", value: "typescript" },
272
- { title: "JavaScript", value: "javascript" }
273
- ]
274
- },
275
- title: "Language",
276
- type: "string"
277
- }),
278
298
  defineField3({
279
299
  description: "Gold-standard implementation with code blocks and prose explanation. Use code blocks for the implementation and regular text to explain why this is the correct approach.",
300
+ group: ["main", "all-fields"],
280
301
  name: "content",
281
302
  of: [{ type: "block" }, { type: "code" }],
282
303
  title: "Content",
@@ -284,28 +305,23 @@ var referenceSolutionSchema = defineType3({
284
305
  }),
285
306
  defineField3({
286
307
  description: "CDN-uploaded files for multi-file solutions (e.g., a Next.js page + a schema + a config). Each file is uploaded as an asset with its filename preserved.",
308
+ group: ["optional", "all-fields"],
287
309
  name: "files",
288
310
  of: [{ type: "file" }],
289
311
  title: "Files",
290
312
  type: "array"
291
313
  }),
292
314
  defineField3({
293
- description: "Why this is the correct approach \u2014 rationale and design decisions",
315
+ description: "Describe why this is the correct approach, including any rationale and decisions.",
316
+ group: ["optional", "all-fields"],
294
317
  name: "notes",
295
- title: "Notes",
318
+ title: "Author Notes",
296
319
  type: "text"
297
320
  })
298
321
  ],
299
322
  name: "ailf.referenceSolution",
300
323
  preview: {
301
- prepare({ language, title }) {
302
- return {
303
- subtitle: typeof language === "string" ? language : "",
304
- title: typeof title === "string" ? title : "Reference Solution"
305
- };
306
- },
307
324
  select: {
308
- language: "language",
309
325
  title: "title"
310
326
  }
311
327
  },
@@ -314,7 +330,7 @@ var referenceSolutionSchema = defineType3({
314
330
  });
315
331
 
316
332
  // src/schema/report.ts
317
- import { defineField as defineField4, defineType as defineType4 } from "sanity";
333
+ import { ALL_FIELDS_GROUP as ALL_FIELDS_GROUP4, defineField as defineField4, defineType as defineType4 } from "sanity";
318
334
  function documentRefSchema() {
319
335
  return {
320
336
  fields: [
@@ -327,8 +343,14 @@ function documentRefSchema() {
327
343
  };
328
344
  }
329
345
  var reportSchema = defineType4({
346
+ groups: [
347
+ { name: "main", title: "Main", default: true },
348
+ { name: "optional", title: "Optional" },
349
+ ALL_FIELDS_GROUP4
350
+ ],
330
351
  fields: [
331
352
  defineField4({
353
+ group: ["main", "all-fields"],
332
354
  name: "reportId",
333
355
  readOnly: true,
334
356
  title: "Report ID",
@@ -336,6 +358,7 @@ var reportSchema = defineType4({
336
358
  validation: (rule) => rule.required()
337
359
  }),
338
360
  defineField4({
361
+ group: ["main", "all-fields"],
339
362
  name: "completedAt",
340
363
  readOnly: true,
341
364
  title: "Completed At",
@@ -343,12 +366,14 @@ var reportSchema = defineType4({
343
366
  validation: (rule) => rule.required()
344
367
  }),
345
368
  defineField4({
369
+ group: ["optional", "all-fields"],
346
370
  name: "durationMs",
347
371
  readOnly: true,
348
372
  title: "Duration (ms)",
349
373
  type: "number"
350
374
  }),
351
375
  defineField4({
376
+ group: ["optional", "all-fields"],
352
377
  name: "tag",
353
378
  readOnly: true,
354
379
  title: "Tag",
@@ -528,6 +553,7 @@ var reportSchema = defineType4({
528
553
  type: "object"
529
554
  })
530
555
  ],
556
+ group: ["main", "all-fields"],
531
557
  name: "provenance",
532
558
  readOnly: true,
533
559
  title: "Provenance",
@@ -976,6 +1002,7 @@ var reportSchema = defineType4({
976
1002
  type: "array"
977
1003
  })
978
1004
  ],
1005
+ group: ["main", "all-fields"],
979
1006
  name: "summary",
980
1007
  readOnly: true,
981
1008
  title: "Score Summary",
@@ -1047,6 +1074,7 @@ var reportSchema = defineType4({
1047
1074
  type: "string"
1048
1075
  })
1049
1076
  ],
1077
+ group: ["optional", "all-fields"],
1050
1078
  name: "comparison",
1051
1079
  readOnly: true,
1052
1080
  title: "Auto-Comparison",
@@ -1078,18 +1106,306 @@ var reportSchema = defineType4({
1078
1106
  });
1079
1107
 
1080
1108
  // src/schema/task.ts
1081
- import { defineField as defineField5, defineType as defineType5 } from "sanity";
1109
+ import { ALL_FIELDS_GROUP as ALL_FIELDS_GROUP5, defineField as defineField5, defineType as defineType5 } from "sanity";
1110
+
1111
+ // src/components/AssertionInput.tsx
1112
+ import { HelpCircleIcon } from "@sanity/icons";
1113
+ import { Box as Box2, Card, Flex, Stack as Stack2, Text as Text2 } from "@sanity/ui";
1114
+ import { useCallback as useCallback2 } from "react";
1115
+ import { Fragment, jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
1116
+ var TYPE_HELP = {
1117
+ "llm-rubric": {
1118
+ description: "Sends the LLM output to a grader model that scores it against a rubric template. Select a template and add task-specific criteria bullets that describe what the grader should check."
1119
+ },
1120
+ contains: {
1121
+ description: "Passes if the output contains this exact substring. Case-sensitive.",
1122
+ valueHint: "The exact text that must appear in the output.",
1123
+ example: "createClient"
1124
+ },
1125
+ "contains-any": {
1126
+ description: "Passes if the output contains at least one of the given substrings. Case-sensitive. Enter each substring on a separate line.",
1127
+ valueHint: "One substring per line \u2014 passes if any match.",
1128
+ example: "createClient\ngetClient"
1129
+ },
1130
+ "contains-all": {
1131
+ description: "Passes if the output contains all of the given substrings. Case-sensitive. Enter each substring on a separate line.",
1132
+ valueHint: "One substring per line \u2014 all must match.",
1133
+ example: "import\ncreateClient\nclient.fetch"
1134
+ },
1135
+ "not-contains": {
1136
+ description: "Passes if the output does NOT contain this substring. Case-sensitive. Useful for checking that deprecated patterns or incorrect APIs are absent.",
1137
+ valueHint: "Text that must NOT appear in the output.",
1138
+ example: "documentStore"
1139
+ },
1140
+ icontains: {
1141
+ description: "Like contains, but case-insensitive. Passes if the output contains this substring regardless of casing.",
1142
+ valueHint: "The text that must appear (case-insensitive).",
1143
+ example: "groq"
1144
+ },
1145
+ "icontains-any": {
1146
+ description: "Like contains-any, but case-insensitive. Passes if the output contains at least one substring, ignoring case. Enter each on a separate line.",
1147
+ valueHint: "One substring per line \u2014 passes if any match (case-insensitive).",
1148
+ example: "GROQ\ngroq\nGroq"
1149
+ },
1150
+ regex: {
1151
+ description: "Passes if the output matches this regular expression pattern. Uses JavaScript regex syntax (without delimiters).",
1152
+ valueHint: "A JavaScript regular expression pattern.",
1153
+ example: "import\\s+\\{.*createClient.*\\}\\s+from"
1154
+ },
1155
+ javascript: {
1156
+ description: "A JavaScript function body that evaluates the output. Receives the variable 'output' (string) and must return true (pass) or false (fail). Can also return a number 0\u20131 for scored assertions, or an object { pass: boolean, score: number, reason: string }.",
1157
+ valueHint: "JavaScript code \u2014 'output' variable is available.",
1158
+ example: "// Check for correct import pattern\nconst hasImport = output.includes('createClient');\nconst noDeprecated = !output.includes('documentStore');\nreturn hasImport && noDeprecated;"
1159
+ },
1160
+ similar: {
1161
+ description: "Passes if the output is semantically similar to the value text, using embedding-based cosine similarity. Set the threshold between 0 (no similarity required) and 1 (exact match).",
1162
+ valueHint: "Reference text to compare against.",
1163
+ thresholdHint: "Similarity score 0\u20131 (e.g. 0.8 for strong match)."
1164
+ },
1165
+ cost: {
1166
+ description: "Passes if the API call cost is below the threshold. Useful for ensuring tasks stay within budget.",
1167
+ thresholdHint: "Maximum cost in dollars (e.g. 0.05)."
1168
+ },
1169
+ latency: {
1170
+ description: "Passes if the API call latency is below the threshold. Useful for performance-sensitive evaluations.",
1171
+ thresholdHint: "Maximum latency in milliseconds (e.g. 5000)."
1172
+ }
1173
+ };
1174
+ var MONOSPACE_TYPES = /* @__PURE__ */ new Set(["javascript", "regex"]);
1175
+ var MONOSPACE_STYLE = `
1176
+ [data-ailf-monospace="true"] textarea {
1177
+ font-family: "SF Mono", "Fira Code", "Fira Mono", Menlo, Consolas, monospace !important;
1178
+ font-size: 13px !important;
1179
+ line-height: 1.5 !important;
1180
+ tab-size: 2;
1181
+ }
1182
+ `;
1183
+ var TEMPLATE_HELP = {
1184
+ "task-completion": {
1185
+ description: "Scores whether the LLM produced a functional implementation that satisfies the task requirements. This is the most heavily weighted dimension.",
1186
+ weight: "50% of composite score",
1187
+ scaleHint: "0 = couldn't attempt \u2192 50 = major gaps \u2192 100 = fully functional"
1188
+ },
1189
+ "code-correctness": {
1190
+ description: "Scores whether the code follows best practices, uses current APIs, and avoids anti-patterns. Checks for idiomatic implementation and correct API usage.",
1191
+ weight: "25% of composite score",
1192
+ scaleHint: "0 = broken/deprecated \u2192 50 = works but not idiomatic \u2192 100 = best practices"
1193
+ },
1194
+ "doc-coverage": {
1195
+ description: "Scores how much of the implementation could be derived from the provided documentation vs. requiring hallucination or guesswork. Measures doc quality.",
1196
+ weight: "25% of composite score",
1197
+ scaleHint: "0 = had to hallucinate \u2192 50 = inferred from partial info \u2192 100 = fully covered"
1198
+ }
1199
+ };
1200
+ function TypeHelpCard({ help }) {
1201
+ return /* @__PURE__ */ jsx2(Card, { padding: 3, radius: 2, tone: "transparent", border: true, children: /* @__PURE__ */ jsxs2(Stack2, { space: 3, children: [
1202
+ /* @__PURE__ */ jsxs2(Flex, { align: "flex-start", gap: 2, children: [
1203
+ /* @__PURE__ */ jsx2(Box2, { style: { flexShrink: 0, marginTop: 1 }, children: /* @__PURE__ */ jsx2(Text2, { size: 1, muted: true, children: /* @__PURE__ */ jsx2(HelpCircleIcon, {}) }) }),
1204
+ /* @__PURE__ */ jsx2(Text2, { size: 1, muted: true, children: help.description })
1205
+ ] }),
1206
+ (help.valueHint || help.thresholdHint || help.example) && /* @__PURE__ */ jsxs2(Stack2, { space: 2, paddingLeft: 4, children: [
1207
+ help.valueHint && /* @__PURE__ */ jsxs2(Text2, { size: 0, muted: true, children: [
1208
+ /* @__PURE__ */ jsx2("strong", { children: "Value:" }),
1209
+ " ",
1210
+ help.valueHint
1211
+ ] }),
1212
+ help.thresholdHint && /* @__PURE__ */ jsxs2(Text2, { size: 0, muted: true, children: [
1213
+ /* @__PURE__ */ jsx2("strong", { children: "Threshold:" }),
1214
+ " ",
1215
+ help.thresholdHint
1216
+ ] }),
1217
+ help.example && /* @__PURE__ */ jsxs2(Box2, { marginTop: 1, children: [
1218
+ /* @__PURE__ */ jsx2(Text2, { size: 0, muted: true, children: /* @__PURE__ */ jsx2("strong", { children: "Example:" }) }),
1219
+ /* @__PURE__ */ jsx2(
1220
+ Box2,
1221
+ {
1222
+ marginTop: 1,
1223
+ style: {
1224
+ background: "var(--card-code-bg-color, #f5f5f5)",
1225
+ borderRadius: 3,
1226
+ padding: "6px 8px",
1227
+ fontFamily: '"SF Mono", "Fira Code", Menlo, Consolas, monospace',
1228
+ fontSize: 12,
1229
+ lineHeight: 1.5,
1230
+ whiteSpace: "pre-wrap",
1231
+ wordBreak: "break-word"
1232
+ },
1233
+ children: help.example
1234
+ }
1235
+ )
1236
+ ] })
1237
+ ] })
1238
+ ] }) });
1239
+ }
1240
+ function TemplateHelpCard({ help }) {
1241
+ return /* @__PURE__ */ jsx2(Card, { padding: 3, radius: 2, tone: "transparent", border: true, children: /* @__PURE__ */ jsxs2(Stack2, { space: 2, children: [
1242
+ /* @__PURE__ */ jsxs2(Flex, { align: "flex-start", gap: 2, children: [
1243
+ /* @__PURE__ */ jsx2(Box2, { style: { flexShrink: 0, marginTop: 1 }, children: /* @__PURE__ */ jsx2(Text2, { size: 1, muted: true, children: /* @__PURE__ */ jsx2(HelpCircleIcon, {}) }) }),
1244
+ /* @__PURE__ */ jsx2(Text2, { size: 1, muted: true, children: help.description })
1245
+ ] }),
1246
+ /* @__PURE__ */ jsxs2(Stack2, { space: 1, paddingLeft: 4, children: [
1247
+ /* @__PURE__ */ jsxs2(Text2, { size: 0, muted: true, children: [
1248
+ /* @__PURE__ */ jsx2("strong", { children: "Weight:" }),
1249
+ " ",
1250
+ help.weight
1251
+ ] }),
1252
+ /* @__PURE__ */ jsxs2(Text2, { size: 0, muted: true, children: [
1253
+ /* @__PURE__ */ jsx2("strong", { children: "Scale:" }),
1254
+ " ",
1255
+ help.scaleHint
1256
+ ] })
1257
+ ] })
1258
+ ] }) });
1259
+ }
1260
+ function AssertionInput(props) {
1261
+ const value = props.value;
1262
+ const selectedType = typeof value?.type === "string" ? value.type : null;
1263
+ const selectedTemplate = typeof value?.template === "string" ? value.template : null;
1264
+ const typeHelp = selectedType ? TYPE_HELP[selectedType] : null;
1265
+ const templateHelp = selectedTemplate ? TEMPLATE_HELP[selectedTemplate] : null;
1266
+ const isMonospace = selectedType ? MONOSPACE_TYPES.has(selectedType) : false;
1267
+ const { renderField: parentRenderField } = props;
1268
+ const renderField = useCallback2(
1269
+ (fieldProps) => {
1270
+ const rendered = parentRenderField(fieldProps);
1271
+ if (fieldProps.name === "type" && typeHelp) {
1272
+ return /* @__PURE__ */ jsxs2(Stack2, { space: 3, children: [
1273
+ rendered,
1274
+ /* @__PURE__ */ jsx2(TypeHelpCard, { help: typeHelp })
1275
+ ] });
1276
+ }
1277
+ if (fieldProps.name === "template" && templateHelp) {
1278
+ return /* @__PURE__ */ jsxs2(Stack2, { space: 3, children: [
1279
+ rendered,
1280
+ /* @__PURE__ */ jsx2(TemplateHelpCard, { help: templateHelp })
1281
+ ] });
1282
+ }
1283
+ return rendered;
1284
+ },
1285
+ [typeHelp, templateHelp, parentRenderField]
1286
+ );
1287
+ return /* @__PURE__ */ jsxs2(Fragment, { children: [
1288
+ isMonospace && /* @__PURE__ */ jsx2("style", { children: MONOSPACE_STYLE }),
1289
+ /* @__PURE__ */ jsx2("div", { "data-ailf-monospace": isMonospace ? "true" : void 0, children: props.renderDefault({ ...props, renderField }) })
1290
+ ] });
1291
+ }
1292
+
1293
+ // src/components/CanonicalDocInput.tsx
1294
+ import { HelpCircleIcon as HelpCircleIcon2 } from "@sanity/icons";
1295
+ import { Box as Box3, Card as Card2, Flex as Flex2, Stack as Stack3, Text as Text3 } from "@sanity/ui";
1296
+ import { useCallback as useCallback3 } from "react";
1297
+ import { Fragment as Fragment2, jsx as jsx3, jsxs as jsxs3 } from "react/jsx-runtime";
1298
+ var REF_TYPE_HELP = {
1299
+ slug: {
1300
+ description: "References a single article document. Use the document picker below to select the article. The pipeline reads the slug, path, and ID directly from the referenced document.",
1301
+ valueHint: "Select an article document using the picker below."
1302
+ },
1303
+ perspective: {
1304
+ description: "Includes all articles from a content release. Use the release picker below to select a release. The pipeline auto-discovers every article in the release at evaluation time.",
1305
+ valueHint: "Select a content release using the picker below."
1306
+ }
1307
+ };
1308
+ function RefTypeHelpCard({ help }) {
1309
+ return /* @__PURE__ */ jsx3(Card2, { padding: 3, radius: 2, tone: "transparent", border: true, children: /* @__PURE__ */ jsxs3(Flex2, { align: "flex-start", gap: 2, children: [
1310
+ /* @__PURE__ */ jsx3(Box3, { style: { flexShrink: 0, marginTop: 1 }, children: /* @__PURE__ */ jsx3(Text3, { size: 1, muted: true, children: /* @__PURE__ */ jsx3(HelpCircleIcon2, {}) }) }),
1311
+ /* @__PURE__ */ jsx3(Text3, { size: 1, muted: true, children: help.description })
1312
+ ] }) });
1313
+ }
1314
+ function CanonicalDocInput(props) {
1315
+ const value = props.value;
1316
+ const selectedType = typeof value?.refType === "string" ? value.refType : null;
1317
+ const help = selectedType ? REF_TYPE_HELP[selectedType] : null;
1318
+ const { renderField: parentRenderField } = props;
1319
+ const renderField = useCallback3(
1320
+ (fieldProps) => {
1321
+ const rendered = parentRenderField(fieldProps);
1322
+ if (fieldProps.name === "refType" && help) {
1323
+ return /* @__PURE__ */ jsxs3(Stack3, { space: 3, children: [
1324
+ rendered,
1325
+ /* @__PURE__ */ jsx3(RefTypeHelpCard, { help })
1326
+ ] });
1327
+ }
1328
+ return rendered;
1329
+ },
1330
+ [help, parentRenderField]
1331
+ );
1332
+ return /* @__PURE__ */ jsx3(Fragment2, { children: props.renderDefault({ ...props, renderField }) });
1333
+ }
1334
+
1335
+ // src/components/CanonicalDocPreview.tsx
1336
+ import { Flex as Flex3, Text as Text4 } from "@sanity/ui";
1337
+ import { useMemo } from "react";
1338
+ import {
1339
+ getReleaseIdFromReleaseDocumentId,
1340
+ useActiveReleases,
1341
+ useArchivedReleases
1342
+ } from "sanity";
1343
+ import { jsx as jsx4, jsxs as jsxs4 } from "react/jsx-runtime";
1344
+ function CanonicalDocPreview(props) {
1345
+ const { perspective, perspectiveTitle, reason, refType, slug, path } = props;
1346
+ const isPerspective = refType === "perspective";
1347
+ const { data: activeReleases } = useActiveReleases();
1348
+ const { data: archivedReleases } = useArchivedReleases();
1349
+ const resolvedTitle = useMemo(() => {
1350
+ if (!isPerspective) {
1351
+ return typeof props.title === "string" ? props.title : "Document";
1352
+ }
1353
+ if (typeof perspectiveTitle === "string" && perspectiveTitle.length > 0) {
1354
+ return perspectiveTitle;
1355
+ }
1356
+ if (typeof perspective === "string") {
1357
+ const allReleases = [
1358
+ ...activeReleases ?? [],
1359
+ ...archivedReleases ?? []
1360
+ ];
1361
+ const match = allReleases.find(
1362
+ (r) => getReleaseIdFromReleaseDocumentId(r._id) === perspective
1363
+ );
1364
+ if (match?.metadata?.title) {
1365
+ return match.metadata.title;
1366
+ }
1367
+ }
1368
+ return typeof perspective === "string" ? perspective : "Content Release";
1369
+ }, [
1370
+ isPerspective,
1371
+ perspectiveTitle,
1372
+ perspective,
1373
+ activeReleases,
1374
+ archivedReleases,
1375
+ props.title
1376
+ ]);
1377
+ const icon = isPerspective ? "\u{1F4E6}" : "\u{1F4C4}";
1378
+ let subtitle;
1379
+ if (typeof reason === "string" && reason.length > 0) {
1380
+ subtitle = reason;
1381
+ } else if (isPerspective && typeof perspective === "string") {
1382
+ subtitle = perspective;
1383
+ } else if (typeof slug === "string") {
1384
+ subtitle = slug;
1385
+ } else if (typeof path === "string") {
1386
+ subtitle = path;
1387
+ } else {
1388
+ subtitle = "";
1389
+ }
1390
+ return /* @__PURE__ */ jsxs4(Flex3, { align: "center", gap: 2, padding: 2, children: [
1391
+ /* @__PURE__ */ jsx4(Text4, { size: 1, children: icon }),
1392
+ /* @__PURE__ */ jsxs4(Flex3, { direction: "column", gap: 1, flex: 1, children: [
1393
+ /* @__PURE__ */ jsx4(Text4, { size: 1, weight: "semibold", children: resolvedTitle }),
1394
+ subtitle && /* @__PURE__ */ jsx4(Text4, { muted: true, size: 0, children: subtitle })
1395
+ ] })
1396
+ ] });
1397
+ }
1082
1398
 
1083
1399
  // src/components/OriginInput.tsx
1084
- import { Stack as Stack3 } from "@sanity/ui";
1400
+ import { Stack as Stack5 } from "@sanity/ui";
1085
1401
 
1086
1402
  // src/components/MirrorBanner.tsx
1087
1403
  import { LinkIcon } from "@sanity/icons";
1088
- import { Card, Flex, Stack as Stack2, Text as Text3 } from "@sanity/ui";
1404
+ import { Card as Card3, Flex as Flex4, Stack as Stack4, Text as Text6 } from "@sanity/ui";
1089
1405
 
1090
1406
  // src/components/SyncStatusBadge.tsx
1091
- import { Badge, Box as Box2, Text as Text2, Tooltip } from "@sanity/ui";
1092
- import { jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
1407
+ import { Badge, Box as Box4, Text as Text5, Tooltip } from "@sanity/ui";
1408
+ import { jsx as jsx5, jsxs as jsxs5 } from "react/jsx-runtime";
1093
1409
  var MS_PER_DAY = 24 * 60 * 60 * 1e3;
1094
1410
  var FRESH_THRESHOLD_MS = 3 * MS_PER_DAY;
1095
1411
  var STALE_THRESHOLD_MS = 7 * MS_PER_DAY;
@@ -1113,33 +1429,33 @@ function SyncStatusBadge({
1113
1429
  const label = ageMs < FRESH_THRESHOLD_MS ? "Synced" : ageMs < STALE_THRESHOLD_MS ? "Stale" : "Outdated";
1114
1430
  const ageStr = formatAge(ageMs);
1115
1431
  const shaStr = commitSha ? ` \xB7 ${commitSha.slice(0, 7)}` : "";
1116
- return /* @__PURE__ */ jsx2(
1432
+ return /* @__PURE__ */ jsx5(
1117
1433
  Tooltip,
1118
1434
  {
1119
- content: /* @__PURE__ */ jsx2(Box2, { padding: 2, children: /* @__PURE__ */ jsxs2(Text2, { size: 1, children: [
1435
+ content: /* @__PURE__ */ jsx5(Box4, { padding: 2, children: /* @__PURE__ */ jsxs5(Text5, { size: 1, children: [
1120
1436
  "Last synced ",
1121
1437
  ageStr,
1122
1438
  shaStr
1123
1439
  ] }) }),
1124
1440
  portal: true,
1125
- children: /* @__PURE__ */ jsx2(Badge, { fontSize, tone, children: label })
1441
+ children: /* @__PURE__ */ jsx5(Badge, { fontSize, tone, children: label })
1126
1442
  }
1127
1443
  );
1128
1444
  }
1129
1445
 
1130
1446
  // src/components/MirrorBanner.tsx
1131
- import { jsx as jsx3, jsxs as jsxs3 } from "react/jsx-runtime";
1447
+ import { jsx as jsx6, jsxs as jsxs6 } from "react/jsx-runtime";
1132
1448
  function MirrorBanner({ origin }) {
1133
1449
  const { repo, path, branch, commitSha, lastSyncedAt } = origin;
1134
1450
  const repoUrl = repo && path && branch ? `https://github.com/${repo}/blob/${branch}/${path}` : null;
1135
1451
  const repoDisplay = repo ?? "an external repository";
1136
- return /* @__PURE__ */ jsx3(Card, { padding: 3, radius: 2, tone: "transparent", border: true, children: /* @__PURE__ */ jsxs3(Stack2, { space: 3, children: [
1137
- /* @__PURE__ */ jsxs3(Flex, { align: "center", gap: 2, children: [
1138
- /* @__PURE__ */ jsx3(Text3, { size: 1, children: /* @__PURE__ */ jsx3(LinkIcon, {}) }),
1139
- /* @__PURE__ */ jsxs3(Text3, { size: 1, children: [
1452
+ return /* @__PURE__ */ jsx6(Card3, { padding: 3, radius: 2, tone: "transparent", border: true, children: /* @__PURE__ */ jsxs6(Stack4, { space: 3, children: [
1453
+ /* @__PURE__ */ jsxs6(Flex4, { align: "center", gap: 2, children: [
1454
+ /* @__PURE__ */ jsx6(Text6, { size: 1, children: /* @__PURE__ */ jsx6(LinkIcon, {}) }),
1455
+ /* @__PURE__ */ jsxs6(Text6, { size: 1, children: [
1140
1456
  "This task is managed in",
1141
1457
  " ",
1142
- repoUrl ? /* @__PURE__ */ jsx3(
1458
+ repoUrl ? /* @__PURE__ */ jsx6(
1143
1459
  "a",
1144
1460
  {
1145
1461
  href: repoUrl,
@@ -1148,12 +1464,12 @@ function MirrorBanner({ origin }) {
1148
1464
  style: { fontWeight: 600 },
1149
1465
  children: repoDisplay
1150
1466
  }
1151
- ) : /* @__PURE__ */ jsx3("strong", { children: repoDisplay }),
1467
+ ) : /* @__PURE__ */ jsx6("strong", { children: repoDisplay }),
1152
1468
  ". Edit it there to make changes."
1153
1469
  ] })
1154
1470
  ] }),
1155
- /* @__PURE__ */ jsxs3(Flex, { align: "center", gap: 2, wrap: "wrap", children: [
1156
- lastSyncedAt && /* @__PURE__ */ jsx3(
1471
+ /* @__PURE__ */ jsxs6(Flex4, { align: "center", gap: 2, wrap: "wrap", children: [
1472
+ lastSyncedAt && /* @__PURE__ */ jsx6(
1157
1473
  SyncStatusBadge,
1158
1474
  {
1159
1475
  lastSyncedAt,
@@ -1161,17 +1477,17 @@ function MirrorBanner({ origin }) {
1161
1477
  fontSize: 0
1162
1478
  }
1163
1479
  ),
1164
- branch && /* @__PURE__ */ jsxs3(Text3, { size: 0, muted: true, children: [
1480
+ branch && /* @__PURE__ */ jsxs6(Text6, { size: 0, muted: true, children: [
1165
1481
  branch,
1166
1482
  commitSha ? ` @ ${commitSha.slice(0, 7)}` : ""
1167
1483
  ] }),
1168
- path && /* @__PURE__ */ jsx3(Text3, { size: 0, muted: true, children: path })
1484
+ path && /* @__PURE__ */ jsx6(Text6, { size: 0, muted: true, children: path })
1169
1485
  ] })
1170
1486
  ] }) });
1171
1487
  }
1172
1488
 
1173
1489
  // src/components/OriginInput.tsx
1174
- import { jsx as jsx4, jsxs as jsxs4 } from "react/jsx-runtime";
1490
+ import { jsx as jsx7, jsxs as jsxs7 } from "react/jsx-runtime";
1175
1491
  function OriginInput(props) {
1176
1492
  const value = props.value;
1177
1493
  if (!value) return props.renderDefault(props);
@@ -1184,12 +1500,123 @@ function OriginInput(props) {
1184
1500
  commitSha: typeof value.commitSha === "string" ? value.commitSha : void 0,
1185
1501
  lastSyncedAt: typeof value.lastSyncedAt === "string" ? value.lastSyncedAt : void 0
1186
1502
  };
1187
- return /* @__PURE__ */ jsxs4(Stack3, { space: 3, children: [
1188
- /* @__PURE__ */ jsx4(MirrorBanner, { origin }),
1503
+ return /* @__PURE__ */ jsxs7(Stack5, { space: 3, children: [
1504
+ /* @__PURE__ */ jsx7(MirrorBanner, { origin }),
1189
1505
  props.renderDefault(props)
1190
1506
  ] });
1191
1507
  }
1192
1508
 
1509
+ // src/components/ReleasePicker.tsx
1510
+ import { SearchIcon } from "@sanity/icons";
1511
+ import { Autocomplete, Badge as Badge2, Card as Card4, Flex as Flex5, Stack as Stack6, Text as Text7 } from "@sanity/ui";
1512
+ import { useCallback as useCallback4, useEffect, useMemo as useMemo2, useRef } from "react";
1513
+ import {
1514
+ getReleaseIdFromReleaseDocumentId as getReleaseIdFromReleaseDocumentId2,
1515
+ PatchEvent,
1516
+ set,
1517
+ unset,
1518
+ useActiveReleases as useActiveReleases2,
1519
+ useArchivedReleases as useArchivedReleases2,
1520
+ useFormCallbacks
1521
+ } from "sanity";
1522
+ import { jsx as jsx8, jsxs as jsxs8 } from "react/jsx-runtime";
1523
+ function StateBadge({ state }) {
1524
+ const tone = state === "active" ? "positive" : state === "published" ? "primary" : "default";
1525
+ return /* @__PURE__ */ jsx8(Badge2, { fontSize: 0, tone, children: state });
1526
+ }
1527
+ function ReleasePicker(props) {
1528
+ const { onChange, path, value = "" } = props;
1529
+ const { data: activeReleases } = useActiveReleases2();
1530
+ const { data: archivedReleases } = useArchivedReleases2();
1531
+ const { onChange: formOnChange } = useFormCallbacks();
1532
+ const titlePath = useMemo2(
1533
+ () => [...path.slice(0, -1), "perspectiveTitle"],
1534
+ [path]
1535
+ );
1536
+ const options = useMemo2(() => {
1537
+ const releases = [
1538
+ ...(activeReleases ?? []).map((r) => ({ ...r, _state: "active" })),
1539
+ ...(archivedReleases ?? []).map((r) => ({ ...r, _state: "archived" }))
1540
+ ];
1541
+ const result = releases.map((release) => {
1542
+ const releaseId = getReleaseIdFromReleaseDocumentId2(release._id);
1543
+ const title = release.metadata?.title ?? releaseId;
1544
+ const state = release.state ?? release._state ?? "unknown";
1545
+ return {
1546
+ payload: { state: String(state), title },
1547
+ value: releaseId
1548
+ };
1549
+ }).sort((a, b) => {
1550
+ if (a.payload.state === "active" && b.payload.state !== "active")
1551
+ return -1;
1552
+ if (a.payload.state !== "active" && b.payload.state === "active")
1553
+ return 1;
1554
+ return a.payload.title.localeCompare(b.payload.title);
1555
+ });
1556
+ return result;
1557
+ }, [activeReleases, archivedReleases]);
1558
+ const hasSynced = useRef(false);
1559
+ useEffect(() => {
1560
+ if (hasSynced.current || !value || options.length === 0) return;
1561
+ const match = options.find((o) => o.value === value);
1562
+ if (match && match.payload.title !== value) {
1563
+ hasSynced.current = true;
1564
+ formOnChange(PatchEvent.from(set(match.payload.title, titlePath)));
1565
+ }
1566
+ }, [value, options, formOnChange, titlePath]);
1567
+ const handleChange = useCallback4(
1568
+ (newValue) => {
1569
+ if (newValue) {
1570
+ onChange(set(newValue));
1571
+ const option = options.find((o) => o.value === newValue);
1572
+ const title = option?.payload.title ?? newValue;
1573
+ formOnChange(PatchEvent.from(set(title, titlePath)));
1574
+ } else {
1575
+ onChange(unset());
1576
+ formOnChange(PatchEvent.from(unset(titlePath)));
1577
+ }
1578
+ },
1579
+ [onChange, formOnChange, titlePath, options]
1580
+ );
1581
+ return /* @__PURE__ */ jsxs8(Stack6, { space: 2, children: [
1582
+ /* @__PURE__ */ jsx8(
1583
+ Autocomplete,
1584
+ {
1585
+ filterOption: (query, option) => {
1586
+ const q = query.toLowerCase();
1587
+ const opt = option;
1588
+ return opt.value.toLowerCase().includes(q) || (opt.payload?.title ?? "").toLowerCase().includes(q);
1589
+ },
1590
+ icon: SearchIcon,
1591
+ id: "canonical-doc-release-picker",
1592
+ onChange: handleChange,
1593
+ openButton: true,
1594
+ options,
1595
+ placeholder: "Search releases by title or ID\u2026",
1596
+ renderOption: (option) => {
1597
+ const opt = option;
1598
+ return /* @__PURE__ */ jsx8(Card4, { as: "button", padding: 3, children: /* @__PURE__ */ jsxs8(Flex5, { align: "center", gap: 2, children: [
1599
+ /* @__PURE__ */ jsxs8(Stack6, { flex: 1, space: 1, children: [
1600
+ /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: opt.payload.title }),
1601
+ opt.payload.title !== opt.value && /* @__PURE__ */ jsx8(Text7, { muted: true, size: 1, children: opt.value })
1602
+ ] }),
1603
+ /* @__PURE__ */ jsx8(StateBadge, { state: opt.payload.state })
1604
+ ] }) });
1605
+ },
1606
+ renderValue: (_v, option) => {
1607
+ const opt = option;
1608
+ return opt?.payload?.title ?? _v;
1609
+ },
1610
+ value
1611
+ }
1612
+ ),
1613
+ value && /* @__PURE__ */ jsxs8(Text7, { muted: true, size: 0, children: [
1614
+ "Release ID: ",
1615
+ /* @__PURE__ */ jsx8("code", { children: value })
1616
+ ] })
1617
+ ] });
1618
+ }
1619
+
1193
1620
  // src/schema/task.ts
1194
1621
  var ASSERTION_TYPES = [
1195
1622
  { title: "LLM Rubric", value: "llm-rubric" },
@@ -1205,18 +1632,28 @@ var ASSERTION_TYPES = [
1205
1632
  { title: "Cost Constraint", value: "cost" },
1206
1633
  { title: "Latency Constraint", value: "latency" }
1207
1634
  ];
1635
+ var DOC_REF_TYPES = [
1636
+ { title: "Document", value: "id" },
1637
+ { title: "Content Release", value: "perspective" }
1638
+ ];
1208
1639
  var RUBRIC_TEMPLATES = [
1209
1640
  { title: "Task Completion", value: "task-completion" },
1210
1641
  { title: "Code Correctness", value: "code-correctness" },
1211
1642
  { title: "Doc Coverage", value: "doc-coverage" }
1212
1643
  ];
1213
1644
  var taskSchema = defineType5({
1645
+ groups: [
1646
+ { name: "main", title: "Main", default: true },
1647
+ { name: "optional", title: "Optional" },
1648
+ ALL_FIELDS_GROUP5
1649
+ ],
1214
1650
  fields: [
1215
1651
  // -----------------------------------------------------------------------
1216
1652
  // Identity
1217
1653
  // -----------------------------------------------------------------------
1218
1654
  defineField5({
1219
1655
  description: "Unique task identifier (e.g., 'groq-blog-queries'). Used for CLI filtering (--task groq-blog-queries), score aggregation, and report linkage.",
1656
+ group: ["main", "all-fields"],
1220
1657
  name: "id",
1221
1658
  title: "Task ID",
1222
1659
  type: "slug",
@@ -1229,16 +1666,30 @@ var taskSchema = defineType5({
1229
1666
  }),
1230
1667
  defineField5({
1231
1668
  description: "Human-readable label shown in reports and Studio",
1669
+ group: ["main", "all-fields"],
1232
1670
  name: "description",
1233
1671
  title: "Description",
1234
1672
  type: "string",
1235
1673
  validation: (rule) => rule.required()
1236
1674
  }),
1237
1675
  // -----------------------------------------------------------------------
1676
+ // Task prompt
1677
+ // -----------------------------------------------------------------------
1678
+ defineField5({
1679
+ description: "The implementation prompt sent to the evaluated LLM. This is the user-facing request (e.g., 'Write GROQ queries for a blog app...'). Plain text or Markdown.",
1680
+ group: ["main", "all-fields"],
1681
+ name: "taskPrompt",
1682
+ rows: 10,
1683
+ title: "Task Prompt",
1684
+ type: "text",
1685
+ validation: (rule) => rule.required()
1686
+ }),
1687
+ // -----------------------------------------------------------------------
1238
1688
  // Classification
1239
1689
  // -----------------------------------------------------------------------
1240
1690
  defineField5({
1241
1691
  description: "Feature area this task belongs to. Used for score aggregation and --area CLI filtering.",
1692
+ group: ["main", "all-fields"],
1242
1693
  name: "featureArea",
1243
1694
  title: "Feature Area",
1244
1695
  to: [{ type: "ailf.featureArea" }],
@@ -1247,6 +1698,7 @@ var taskSchema = defineType5({
1247
1698
  }),
1248
1699
  defineField5({
1249
1700
  description: "Freeform labels for filtering and organization",
1701
+ group: ["optional", "all-fields"],
1250
1702
  name: "tags",
1251
1703
  of: [{ type: "string" }],
1252
1704
  title: "Tags",
@@ -1256,21 +1708,87 @@ var taskSchema = defineType5({
1256
1708
  // Documentation references
1257
1709
  // -----------------------------------------------------------------------
1258
1710
  defineField5({
1259
- description: "Documentation articles that the LLM should use to complete this task. These become the gold-standard doc context injected in baseline mode. Each entry includes a reference to an article document and an optional reason explaining why the doc is relevant.",
1711
+ description: "Documentation that the LLM should use to complete this task. These become the gold-standard doc context injected in baseline mode. Each entry is either a single article document or a content release (whose articles are all included automatically).",
1712
+ group: ["main", "all-fields"],
1260
1713
  name: "canonicalDocs",
1261
1714
  of: [
1262
1715
  {
1716
+ components: {
1717
+ input: CanonicalDocInput,
1718
+ preview: CanonicalDocPreview
1719
+ },
1263
1720
  fields: [
1721
+ // Resolution type — drives conditional field visibility.
1722
+ // Stored as "slug" (Document) or "perspective" (Content Release).
1723
+ // Mirrored YAML tasks may carry "path" or "id" but those are
1724
+ // read-only in Studio and handled by the adapter.
1264
1725
  defineField5({
1265
- description: "Reference to the documentation article",
1726
+ description: "Document references a single article. Content Release includes all articles from a release.",
1727
+ name: "refType",
1728
+ options: {
1729
+ layout: "radio",
1730
+ direction: "horizontal",
1731
+ list: [...DOC_REF_TYPES]
1732
+ },
1733
+ title: "Resolution Type",
1734
+ type: "string",
1735
+ initialValue: "id",
1736
+ validation: (rule) => rule.required()
1737
+ }),
1738
+ // --- Article reference (Document mode) ---
1739
+ defineField5({
1740
+ description: "The article this canonical doc entry points to. The pipeline resolves the slug, path, and _id from this reference.",
1741
+ hidden: ({ parent }) => parent?.refType === "perspective",
1266
1742
  name: "doc",
1267
1743
  title: "Document",
1268
1744
  to: [{ type: "article" }],
1269
- type: "reference",
1270
- validation: (rule) => rule.required()
1745
+ type: "reference"
1746
+ }),
1747
+ // --- Path (hidden — only populated by mirrored YAML tasks) ---
1748
+ defineField5({
1749
+ description: "Full path after /docs/ (e.g. 'groq/groq-introduction'). Populated automatically for mirrored YAML/repo tasks with refType 'path'. Not shown in Studio \u2014 the pipeline derives the path from the doc reference when needed.",
1750
+ hidden: true,
1751
+ name: "path",
1752
+ title: "Document Path",
1753
+ type: "string"
1754
+ }),
1755
+ // --- Document ID (hidden — only populated by mirrored YAML tasks) ---
1756
+ defineField5({
1757
+ description: "Sanity document _id. Populated automatically for mirrored YAML/repo tasks with refType 'id'. Not shown in Studio \u2014 the pipeline reads the _id from the doc reference.",
1758
+ hidden: true,
1759
+ name: "docId",
1760
+ title: "Document ID",
1761
+ type: "string"
1762
+ }),
1763
+ // --- Perspective resolution ---
1764
+ defineField5({
1765
+ components: {
1766
+ input: ReleasePicker
1767
+ },
1768
+ description: "Content release name (e.g. 'bundle-chatbox-launch'). All articles in this release are included as canonical docs. The pipeline auto-discovers articles at evaluation time.",
1769
+ hidden: ({ parent }) => parent?.refType !== "perspective",
1770
+ name: "perspective",
1771
+ title: "Content Release",
1772
+ type: "string",
1773
+ validation: (rule) => rule.custom((value, context) => {
1774
+ const parent = context.parent;
1775
+ if (parent?.refType === "perspective" && !value) {
1776
+ return "Content release ID is required for perspective resolution";
1777
+ }
1778
+ return true;
1779
+ })
1780
+ }),
1781
+ // --- Perspective title (hidden — populated by ReleasePicker) ---
1782
+ defineField5({
1783
+ description: "Human-readable title of the selected content release. Populated automatically by the release picker \u2014 used for list preview only, not by the pipeline.",
1784
+ hidden: true,
1785
+ name: "perspectiveTitle",
1786
+ title: "Release Title",
1787
+ type: "string"
1271
1788
  }),
1789
+ // --- Reason (always visible) ---
1272
1790
  defineField5({
1273
- description: "Why this document helps with the task",
1791
+ description: "Why this documentation helps with the task",
1274
1792
  name: "reason",
1275
1793
  title: "Reason",
1276
1794
  type: "string"
@@ -1278,14 +1796,13 @@ var taskSchema = defineType5({
1278
1796
  ],
1279
1797
  name: "canonicalDocRef",
1280
1798
  preview: {
1281
- prepare({ reason, title }) {
1282
- return {
1283
- subtitle: typeof reason === "string" ? reason : "",
1284
- title: typeof title === "string" ? title : "Document"
1285
- };
1286
- },
1287
1799
  select: {
1800
+ path: "path",
1801
+ perspective: "perspective",
1802
+ perspectiveTitle: "perspectiveTitle",
1288
1803
  reason: "reason",
1804
+ refType: "refType",
1805
+ slug: "doc.slug.current",
1289
1806
  title: "doc.title"
1290
1807
  }
1291
1808
  },
@@ -1298,34 +1815,26 @@ var taskSchema = defineType5({
1298
1815
  }),
1299
1816
  defineField5({
1300
1817
  description: "Gold-standard implementation that demonstrates the correct approach",
1818
+ group: ["optional", "all-fields"],
1301
1819
  name: "referenceSolution",
1302
1820
  title: "Reference Solution",
1303
1821
  to: [{ type: "ailf.referenceSolution" }],
1304
1822
  type: "reference"
1305
1823
  }),
1306
- // -----------------------------------------------------------------------
1307
- // Task prompt
1308
- // -----------------------------------------------------------------------
1309
1824
  defineField5({
1310
1825
  description: "Auto-generate a doc-coverage rubric assertion. When true, the pipeline adds a doc-coverage assertion that checks whether the LLM's output reflects the content of the canonical documents.",
1826
+ group: ["optional", "all-fields"],
1311
1827
  initialValue: false,
1312
1828
  name: "docCoverage",
1313
1829
  title: "Doc Coverage",
1314
1830
  type: "boolean"
1315
1831
  }),
1316
- defineField5({
1317
- description: "The implementation prompt sent to the evaluated LLM. This is the user-facing request (e.g., 'Write GROQ queries for a blog app...'). Plain text or Markdown \u2014 consumed as a raw string by the evaluation harness, not rendered by Studio.",
1318
- name: "taskPrompt",
1319
- rows: 10,
1320
- title: "Task Prompt",
1321
- type: "text",
1322
- validation: (rule) => rule.required()
1323
- }),
1324
1832
  // -----------------------------------------------------------------------
1325
1833
  // Assertions (grading criteria)
1326
1834
  // -----------------------------------------------------------------------
1327
1835
  defineField5({
1328
1836
  description: "Grading criteria for evaluating the LLM's output. At least one assertion is required. Use llm-rubric with a template for scored evaluation, or value-based assertions for exact checks.",
1837
+ group: ["main", "all-fields"],
1329
1838
  name: "assert",
1330
1839
  of: [
1331
1840
  {
@@ -1386,6 +1895,9 @@ var taskSchema = defineType5({
1386
1895
  type: "number"
1387
1896
  })
1388
1897
  ],
1898
+ components: {
1899
+ input: AssertionInput
1900
+ },
1389
1901
  name: "assertion",
1390
1902
  preview: {
1391
1903
  prepare({
@@ -1423,6 +1935,7 @@ var taskSchema = defineType5({
1423
1935
  // -----------------------------------------------------------------------
1424
1936
  defineField5({
1425
1937
  description: "Advanced: Raw Promptfoo assertion objects that bypass AILF's curated type validation and template resolution. These are appended directly to the expanded Promptfoo test case. Use for edge cases where the curated assertion types are insufficient.",
1938
+ group: ["optional", "all-fields"],
1426
1939
  name: "rawAssert",
1427
1940
  of: [
1428
1941
  {
@@ -1460,6 +1973,7 @@ var taskSchema = defineType5({
1460
1973
  // -----------------------------------------------------------------------
1461
1974
  defineField5({
1462
1975
  description: "Controls baseline variant generation. The baseline measures the LLM's performance without documentation (training data only).",
1976
+ group: ["optional", "all-fields"],
1463
1977
  fields: [
1464
1978
  defineField5({
1465
1979
  description: "Generate a baseline variant (default: true)",
@@ -1496,6 +2010,7 @@ var taskSchema = defineType5({
1496
2010
  // -----------------------------------------------------------------------
1497
2011
  defineField5({
1498
2012
  description: "Controls when and how this task runs in the pipeline. Tasks without execution controls use defaults: enabled, blocking, no filters, no threshold.",
2013
+ group: ["optional", "all-fields"],
1499
2014
  fields: [
1500
2015
  defineField5({
1501
2016
  description: "Skip this task when false (default: true)",
@@ -1594,29 +2109,6 @@ var taskSchema = defineType5({
1594
2109
  },
1595
2110
  title: "Threshold",
1596
2111
  type: "object"
1597
- }),
1598
- defineField5({
1599
- description: "Doc source override \u2014 evaluate this task against a different source than the pipeline default (e.g., a branch deploy URL)",
1600
- fields: [
1601
- defineField5({
1602
- name: "url",
1603
- title: "URL",
1604
- type: "url"
1605
- }),
1606
- defineField5({
1607
- description: "Content release perspective ID",
1608
- name: "perspective",
1609
- title: "Perspective",
1610
- type: "string"
1611
- })
1612
- ],
1613
- name: "source",
1614
- options: {
1615
- collapsible: true,
1616
- collapsed: true
1617
- },
1618
- title: "Source Override",
1619
- type: "object"
1620
2112
  })
1621
2113
  ],
1622
2114
  name: "execution",
@@ -1632,6 +2124,7 @@ var taskSchema = defineType5({
1632
2124
  // -----------------------------------------------------------------------
1633
2125
  defineField5({
1634
2126
  description: "Source repo provenance for mirrored tasks. This field is populated automatically when the pipeline mirrors repo-based tasks into the Content Lake. Read-only \u2014 the source of truth is the repo.",
2127
+ group: ["optional", "all-fields"],
1635
2128
  fields: [
1636
2129
  defineField5({
1637
2130
  name: "type",
@@ -1751,11 +2244,17 @@ var taskSchema = defineType5({
1751
2244
  });
1752
2245
 
1753
2246
  // src/schema/webhook-config.ts
1754
- import { defineField as defineField6, defineType as defineType6 } from "sanity";
2247
+ import { ALL_FIELDS_GROUP as ALL_FIELDS_GROUP6, defineField as defineField6, defineType as defineType6 } from "sanity";
1755
2248
  var webhookConfigSchema = defineType6({
2249
+ groups: [
2250
+ { name: "main", title: "Main", default: true },
2251
+ { name: "optional", title: "Optional" },
2252
+ ALL_FIELDS_GROUP6
2253
+ ],
1756
2254
  fields: [
1757
2255
  defineField6({
1758
2256
  description: "When enabled, publishing articles will automatically trigger AI Literacy evaluations for affected feature areas.",
2257
+ group: ["main", "all-fields"],
1759
2258
  initialValue: false,
1760
2259
  name: "enabled",
1761
2260
  title: "Evaluate on Publish",
@@ -1763,6 +2262,7 @@ var webhookConfigSchema = defineType6({
1763
2262
  }),
1764
2263
  defineField6({
1765
2264
  description: "Which evaluation mode to use for webhook-triggered evaluations.",
2265
+ group: ["main", "all-fields"],
1766
2266
  initialValue: "baseline",
1767
2267
  name: "mode",
1768
2268
  options: {
@@ -1778,6 +2278,7 @@ var webhookConfigSchema = defineType6({
1778
2278
  }),
1779
2279
  defineField6({
1780
2280
  description: "Maximum evaluations per day. Prevents runaway costs from rapid editing.",
2281
+ group: ["main", "all-fields"],
1781
2282
  initialValue: 20,
1782
2283
  name: "dailyBudget",
1783
2284
  title: "Daily Budget",
@@ -1786,6 +2287,7 @@ var webhookConfigSchema = defineType6({
1786
2287
  }),
1787
2288
  defineField6({
1788
2289
  description: "Seconds to wait after the last edit before dispatching. Coalesces rapid edits into a single evaluation.",
2290
+ group: ["optional", "all-fields"],
1789
2291
  initialValue: 300,
1790
2292
  name: "debounceSeconds",
1791
2293
  title: "Debounce Window (seconds)",
@@ -1794,6 +2296,7 @@ var webhookConfigSchema = defineType6({
1794
2296
  }),
1795
2297
  defineField6({
1796
2298
  description: "Specific feature areas to evaluate. Leave empty to evaluate all affected areas automatically.",
2299
+ group: ["optional", "all-fields"],
1797
2300
  name: "areas",
1798
2301
  of: [{ type: "string" }],
1799
2302
  title: "Area Filter",
@@ -1801,6 +2304,7 @@ var webhookConfigSchema = defineType6({
1801
2304
  }),
1802
2305
  defineField6({
1803
2306
  description: "Slack webhook URL for notifications about webhook-triggered evaluations.",
2307
+ group: ["optional", "all-fields"],
1804
2308
  name: "notifySlack",
1805
2309
  title: "Slack Notification URL",
1806
2310
  type: "url"
@@ -1829,15 +2333,15 @@ import { route } from "sanity/router";
1829
2333
  // src/components/Dashboard.tsx
1830
2334
  import {
1831
2335
  Container,
1832
- Flex as Flex20,
2336
+ Flex as Flex24,
1833
2337
  Select as Select3,
1834
- Stack as Stack21,
2338
+ Stack as Stack24,
1835
2339
  Tab,
1836
2340
  TabList,
1837
2341
  TabPanel,
1838
- Text as Text28
2342
+ Text as Text32
1839
2343
  } from "@sanity/ui";
1840
- import { useCallback as useCallback11, useEffect as useEffect8, useState as useState10 } from "react";
2344
+ import { useCallback as useCallback14, useEffect as useEffect9, useState as useState10 } from "react";
1841
2345
  import { useClient as useClient8 } from "sanity";
1842
2346
  import { useRouter } from "sanity/router";
1843
2347
 
@@ -2082,8 +2586,8 @@ function filterSourceClause(param) {
2082
2586
  }
2083
2587
 
2084
2588
  // src/components/ComparisonView.tsx
2085
- import { Badge as Badge2, Box as Box5, Card as Card3, Flex as Flex3, Grid, Select, Stack as Stack5, Text as Text7 } from "@sanity/ui";
2086
- import { useCallback as useCallback2, useEffect, useMemo, useState as useState2 } from "react";
2589
+ import { Badge as Badge3, Box as Box7, Card as Card6, Flex as Flex7, Grid, Select, Stack as Stack8, Text as Text11 } from "@sanity/ui";
2590
+ import { useCallback as useCallback5, useEffect as useEffect2, useMemo as useMemo3, useState as useState2 } from "react";
2087
2591
  import { useClient as useClient2 } from "sanity";
2088
2592
 
2089
2593
  // src/glossary.ts
@@ -2163,11 +2667,11 @@ function scoreMap(summary) {
2163
2667
  return new Map(summary.scores.map((s) => [s.feature, s]));
2164
2668
  }
2165
2669
  function allAreas(baseline, experiment) {
2166
- const set = /* @__PURE__ */ new Set([
2670
+ const set2 = /* @__PURE__ */ new Set([
2167
2671
  ...baseline.scores.map((s) => s.feature),
2168
2672
  ...experiment.scores.map((s) => s.feature)
2169
2673
  ]);
2170
- return [...set].sort();
2674
+ return [...set2].sort();
2171
2675
  }
2172
2676
  function classify(delta) {
2173
2677
  if (delta >= NOISE_THRESHOLD) return "improved";
@@ -2277,16 +2781,16 @@ function formatDuration(ms) {
2277
2781
  }
2278
2782
 
2279
2783
  // src/components/PageBlurb.tsx
2280
- import { Card as Card2, Stack as Stack4, Text as Text4 } from "@sanity/ui";
2281
- import { jsx as jsx5 } from "react/jsx-runtime";
2784
+ import { Card as Card5, Stack as Stack7, Text as Text8 } from "@sanity/ui";
2785
+ import { jsx as jsx9 } from "react/jsx-runtime";
2282
2786
  function PageBlurb({ text }) {
2283
- return /* @__PURE__ */ jsx5(Card2, { padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsx5(Stack4, { space: 2, children: /* @__PURE__ */ jsx5(Text4, { size: 1, children: text }) }) });
2787
+ return /* @__PURE__ */ jsx9(Card5, { padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsx9(Stack7, { space: 2, children: /* @__PURE__ */ jsx9(Text8, { size: 1, children: text }) }) });
2284
2788
  }
2285
2789
 
2286
2790
  // src/components/primitives/ColumnHeader.tsx
2287
- import { HelpCircleIcon } from "@sanity/icons";
2288
- import { Box as Box3, Flex as Flex2, Text as Text5, Tooltip as Tooltip2 } from "@sanity/ui";
2289
- import { jsx as jsx6, jsxs as jsxs5 } from "react/jsx-runtime";
2791
+ import { HelpCircleIcon as HelpCircleIcon3 } from "@sanity/icons";
2792
+ import { Box as Box5, Flex as Flex6, Text as Text9, Tooltip as Tooltip2 } from "@sanity/ui";
2793
+ import { jsx as jsx10, jsxs as jsxs9 } from "react/jsx-runtime";
2290
2794
  function ColumnHeader({
2291
2795
  label,
2292
2796
  tooltip,
@@ -2296,9 +2800,9 @@ function ColumnHeader({
2296
2800
  borderBottom: "1px solid var(--card-border-color)",
2297
2801
  paddingBottom: 6
2298
2802
  } : void 0;
2299
- return /* @__PURE__ */ jsxs5(Flex2, { align: "center", gap: 1, style, children: [
2300
- /* @__PURE__ */ jsx6(
2301
- Text5,
2803
+ return /* @__PURE__ */ jsxs9(Flex6, { align: "center", gap: 1, style, children: [
2804
+ /* @__PURE__ */ jsx10(
2805
+ Text9,
2302
2806
  {
2303
2807
  muted: true,
2304
2808
  size: 1,
@@ -2307,26 +2811,26 @@ function ColumnHeader({
2307
2811
  children: label
2308
2812
  }
2309
2813
  ),
2310
- tooltip && /* @__PURE__ */ jsx6(
2814
+ tooltip && /* @__PURE__ */ jsx10(
2311
2815
  Tooltip2,
2312
2816
  {
2313
- content: /* @__PURE__ */ jsx6(Box3, { padding: 2, children: /* @__PURE__ */ jsx6(Text5, { size: 1, children: tooltip }) }),
2817
+ content: /* @__PURE__ */ jsx10(Box5, { padding: 2, children: /* @__PURE__ */ jsx10(Text9, { size: 1, children: tooltip }) }),
2314
2818
  portal: true,
2315
- children: /* @__PURE__ */ jsx6(Text5, { muted: true, size: 0, children: /* @__PURE__ */ jsx6(HelpCircleIcon, {}) })
2819
+ children: /* @__PURE__ */ jsx10(Text9, { muted: true, size: 0, children: /* @__PURE__ */ jsx10(HelpCircleIcon3, {}) })
2316
2820
  }
2317
2821
  )
2318
2822
  ] });
2319
2823
  }
2320
2824
 
2321
2825
  // src/components/primitives/LoadingState.tsx
2322
- import { Box as Box4, Text as Text6 } from "@sanity/ui";
2323
- import { jsx as jsx7 } from "react/jsx-runtime";
2826
+ import { Box as Box6, Text as Text10 } from "@sanity/ui";
2827
+ import { jsx as jsx11 } from "react/jsx-runtime";
2324
2828
  function LoadingState({ message = "Loading\u2026" }) {
2325
- return /* @__PURE__ */ jsx7(Box4, { padding: 4, children: /* @__PURE__ */ jsx7(Text6, { muted: true, children: message }) });
2829
+ return /* @__PURE__ */ jsx11(Box6, { padding: 4, children: /* @__PURE__ */ jsx11(Text10, { muted: true, children: message }) });
2326
2830
  }
2327
2831
 
2328
2832
  // src/components/ComparisonView.tsx
2329
- import { Fragment, jsx as jsx8, jsxs as jsxs6 } from "react/jsx-runtime";
2833
+ import { Fragment as Fragment3, jsx as jsx12, jsxs as jsxs10 } from "react/jsx-runtime";
2330
2834
  function ComparisonView() {
2331
2835
  const client = useClient2({ apiVersion: API_VERSION });
2332
2836
  const [baselineId, setBaselineId] = useState2(null);
@@ -2337,14 +2841,14 @@ function ComparisonView() {
2337
2841
  const [experimentSummary, setExperimentSummary] = useState2(null);
2338
2842
  const [loading, setLoading] = useState2(false);
2339
2843
  const [reports, setReports] = useState2([]);
2340
- useEffect(() => {
2844
+ useEffect2(() => {
2341
2845
  client.fetch(latestReportsQuery, {
2342
2846
  limit: 50,
2343
2847
  mode: null,
2344
2848
  source: null
2345
2849
  }).then((data) => setReports(data ?? [])).catch(() => setReports([]));
2346
2850
  }, [client]);
2347
- useEffect(() => {
2851
+ useEffect2(() => {
2348
2852
  if (!baselineId || !experimentId) {
2349
2853
  setBaselineSummary(null);
2350
2854
  setExperimentSummary(null);
@@ -2365,75 +2869,75 @@ function ComparisonView() {
2365
2869
  setLoading(false);
2366
2870
  });
2367
2871
  }, [baselineId, client, experimentId]);
2368
- const baselineOptions = useMemo(
2872
+ const baselineOptions = useMemo3(
2369
2873
  () => reports.filter((r) => r.reportId !== experimentId),
2370
2874
  [experimentId, reports]
2371
2875
  );
2372
- const experimentOptions = useMemo(
2876
+ const experimentOptions = useMemo3(
2373
2877
  () => reports.filter((r) => r.reportId !== baselineId),
2374
2878
  [baselineId, reports]
2375
2879
  );
2376
- const areaDeltas = useMemo(
2880
+ const areaDeltas = useMemo3(
2377
2881
  () => baselineSummary && experimentSummary ? computeAreaDeltas(baselineSummary, experimentSummary) : [],
2378
2882
  [baselineSummary, experimentSummary]
2379
2883
  );
2380
- const dimDeltas = useMemo(
2884
+ const dimDeltas = useMemo3(
2381
2885
  () => baselineSummary && experimentSummary ? computeDimensionDeltas(baselineSummary, experimentSummary) : [],
2382
2886
  [baselineSummary, experimentSummary]
2383
2887
  );
2384
- const threeLayerDeltas = useMemo(
2888
+ const threeLayerDeltas = useMemo3(
2385
2889
  () => baselineSummary && experimentSummary ? computeThreeLayerDeltas(baselineSummary, experimentSummary) : [],
2386
2890
  [baselineSummary, experimentSummary]
2387
2891
  );
2388
2892
  const hasThreeLayerData = threeLayerDeltas.some(
2389
2893
  (d) => d.baseActual !== null || d.baseRetGap !== null
2390
2894
  );
2391
- const overallDelta = useMemo(() => {
2895
+ const overallDelta = useMemo3(() => {
2392
2896
  if (!baselineSummary || !experimentSummary) return null;
2393
2897
  const b = baselineSummary.overall.avgScore;
2394
2898
  const e = experimentSummary.overall.avgScore;
2395
2899
  return { baseline: b, delta: e - b, experiment: e };
2396
2900
  }, [baselineSummary, experimentSummary]);
2397
- const onBaseline = useCallback2(
2901
+ const onBaseline = useCallback5(
2398
2902
  (e) => setBaselineId(e.currentTarget.value || null),
2399
2903
  []
2400
2904
  );
2401
- const onExperiment = useCallback2(
2905
+ const onExperiment = useCallback5(
2402
2906
  (e) => setExperimentId(e.currentTarget.value || null),
2403
2907
  []
2404
2908
  );
2405
2909
  const hasBoth = baselineId && experimentId;
2406
2910
  const hasData = baselineSummary && experimentSummary;
2407
- return /* @__PURE__ */ jsxs6(Stack5, { space: 4, children: [
2408
- /* @__PURE__ */ jsx8(PageBlurb, { text: "Select two reports to compare." }),
2409
- /* @__PURE__ */ jsxs6(Flex3, { gap: 3, children: [
2410
- /* @__PURE__ */ jsx8(Box5, { flex: 1, children: /* @__PURE__ */ jsxs6(Stack5, { space: 2, children: [
2411
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: "Baseline (before)" }),
2412
- /* @__PURE__ */ jsxs6(Select, { onChange: onBaseline, value: baselineId ?? "", children: [
2413
- /* @__PURE__ */ jsx8("option", { value: "", children: "Select baseline\u2026" }),
2414
- baselineOptions.map((r) => /* @__PURE__ */ jsx8("option", { value: r.reportId, children: formatOption(r) }, r.reportId))
2911
+ return /* @__PURE__ */ jsxs10(Stack8, { space: 4, children: [
2912
+ /* @__PURE__ */ jsx12(PageBlurb, { text: "Select two reports to compare." }),
2913
+ /* @__PURE__ */ jsxs10(Flex7, { gap: 3, children: [
2914
+ /* @__PURE__ */ jsx12(Box7, { flex: 1, children: /* @__PURE__ */ jsxs10(Stack8, { space: 2, children: [
2915
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: "Baseline (before)" }),
2916
+ /* @__PURE__ */ jsxs10(Select, { onChange: onBaseline, value: baselineId ?? "", children: [
2917
+ /* @__PURE__ */ jsx12("option", { value: "", children: "Select baseline\u2026" }),
2918
+ baselineOptions.map((r) => /* @__PURE__ */ jsx12("option", { value: r.reportId, children: formatOption(r) }, r.reportId))
2415
2919
  ] })
2416
2920
  ] }) }),
2417
- /* @__PURE__ */ jsx8(Box5, { flex: 1, children: /* @__PURE__ */ jsxs6(Stack5, { space: 2, children: [
2418
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: "Experiment (after)" }),
2419
- /* @__PURE__ */ jsxs6(Select, { onChange: onExperiment, value: experimentId ?? "", children: [
2420
- /* @__PURE__ */ jsx8("option", { value: "", children: "Select experiment\u2026" }),
2421
- experimentOptions.map((r) => /* @__PURE__ */ jsx8("option", { value: r.reportId, children: formatOption(r) }, r.reportId))
2921
+ /* @__PURE__ */ jsx12(Box7, { flex: 1, children: /* @__PURE__ */ jsxs10(Stack8, { space: 2, children: [
2922
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: "Experiment (after)" }),
2923
+ /* @__PURE__ */ jsxs10(Select, { onChange: onExperiment, value: experimentId ?? "", children: [
2924
+ /* @__PURE__ */ jsx12("option", { value: "", children: "Select experiment\u2026" }),
2925
+ experimentOptions.map((r) => /* @__PURE__ */ jsx12("option", { value: r.reportId, children: formatOption(r) }, r.reportId))
2422
2926
  ] })
2423
2927
  ] }) })
2424
2928
  ] }),
2425
- hasBoth && loading && /* @__PURE__ */ jsx8(LoadingState, { message: "Loading comparison\u2026" }),
2426
- hasBoth && !loading && !hasData && /* @__PURE__ */ jsx8(Card3, { padding: 4, tone: "caution", children: /* @__PURE__ */ jsx8(Text7, { size: 1, children: "Report not found." }) }),
2427
- hasBoth && !loading && hasData && /* @__PURE__ */ jsxs6(Fragment, { children: [
2428
- /* @__PURE__ */ jsx8(
2929
+ hasBoth && loading && /* @__PURE__ */ jsx12(LoadingState, { message: "Loading comparison\u2026" }),
2930
+ hasBoth && !loading && !hasData && /* @__PURE__ */ jsx12(Card6, { padding: 4, tone: "caution", children: /* @__PURE__ */ jsx12(Text11, { size: 1, children: "Report not found." }) }),
2931
+ hasBoth && !loading && hasData && /* @__PURE__ */ jsxs10(Fragment3, { children: [
2932
+ /* @__PURE__ */ jsx12(
2429
2933
  AreaComparisonTable,
2430
2934
  {
2431
2935
  areaDeltas,
2432
2936
  overallDelta
2433
2937
  }
2434
2938
  ),
2435
- /* @__PURE__ */ jsx8(DimensionDeltasTable, { dimDeltas }),
2436
- hasThreeLayerData && /* @__PURE__ */ jsx8(ThreeLayerDeltasTable, { threeLayerDeltas })
2939
+ /* @__PURE__ */ jsx12(DimensionDeltasTable, { dimDeltas }),
2940
+ hasThreeLayerData && /* @__PURE__ */ jsx12(ThreeLayerDeltasTable, { threeLayerDeltas })
2437
2941
  ] })
2438
2942
  ] });
2439
2943
  }
@@ -2441,23 +2945,23 @@ function AreaComparisonTable({
2441
2945
  areaDeltas,
2442
2946
  overallDelta
2443
2947
  }) {
2444
- return /* @__PURE__ */ jsx8(Card3, { overflow: "auto", padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs6(Stack5, { space: 3, children: [
2445
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: "Per-area comparison" }),
2446
- /* @__PURE__ */ jsxs6(Grid, { columns: 5, gap: 2, children: [
2447
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Area" }),
2448
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Baseline", tooltip: GLOSSARY.baseline }),
2449
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Experiment", tooltip: GLOSSARY.experiment }),
2450
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Delta", tooltip: GLOSSARY.delta }),
2451
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Change", tooltip: GLOSSARY.change })
2948
+ return /* @__PURE__ */ jsx12(Card6, { overflow: "auto", padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs10(Stack8, { space: 3, children: [
2949
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: "Per-area comparison" }),
2950
+ /* @__PURE__ */ jsxs10(Grid, { columns: 5, gap: 2, children: [
2951
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Area" }),
2952
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Baseline", tooltip: GLOSSARY.baseline }),
2953
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Experiment", tooltip: GLOSSARY.experiment }),
2954
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Delta", tooltip: GLOSSARY.delta }),
2955
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Change", tooltip: GLOSSARY.change })
2452
2956
  ] }),
2453
- areaDeltas.map((row) => /* @__PURE__ */ jsxs6(Grid, { columns: 5, gap: 2, children: [
2454
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.area }),
2455
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.baseline.toFixed(1) }),
2456
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.experiment.toFixed(1) }),
2457
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: formatDelta(row.delta) }),
2458
- /* @__PURE__ */ jsx8(Box5, { children: /* @__PURE__ */ jsx8(Badge2, { tone: changeTone(row.change), children: row.change }) })
2957
+ areaDeltas.map((row) => /* @__PURE__ */ jsxs10(Grid, { columns: 5, gap: 2, children: [
2958
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.area }),
2959
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.baseline.toFixed(1) }),
2960
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.experiment.toFixed(1) }),
2961
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: formatDelta(row.delta) }),
2962
+ /* @__PURE__ */ jsx12(Box7, { children: /* @__PURE__ */ jsx12(Badge3, { tone: changeTone(row.change), children: row.change }) })
2459
2963
  ] }, row.area)),
2460
- overallDelta && /* @__PURE__ */ jsxs6(
2964
+ overallDelta && /* @__PURE__ */ jsxs10(
2461
2965
  Grid,
2462
2966
  {
2463
2967
  columns: 5,
@@ -2467,36 +2971,36 @@ function AreaComparisonTable({
2467
2971
  paddingTop: 8
2468
2972
  },
2469
2973
  children: [
2470
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: "Overall" }),
2471
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: overallDelta.baseline.toFixed(1) }),
2472
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: overallDelta.experiment.toFixed(1) }),
2473
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: formatDelta(overallDelta.delta) }),
2474
- /* @__PURE__ */ jsx8(Box5, { children: /* @__PURE__ */ jsx8(Badge2, { tone: changeTone(classify(overallDelta.delta)), children: classify(overallDelta.delta) }) })
2974
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: "Overall" }),
2975
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: overallDelta.baseline.toFixed(1) }),
2976
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: overallDelta.experiment.toFixed(1) }),
2977
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: formatDelta(overallDelta.delta) }),
2978
+ /* @__PURE__ */ jsx12(Box7, { children: /* @__PURE__ */ jsx12(Badge3, { tone: changeTone(classify(overallDelta.delta)), children: classify(overallDelta.delta) }) })
2475
2979
  ]
2476
2980
  }
2477
2981
  )
2478
2982
  ] }) });
2479
2983
  }
2480
2984
  function DimensionDeltasTable({ dimDeltas }) {
2481
- return /* @__PURE__ */ jsx8(Card3, { overflow: "auto", padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs6(Stack5, { space: 3, children: [
2482
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: "Dimension deltas" }),
2483
- /* @__PURE__ */ jsxs6(Grid, { columns: 4, gap: 2, children: [
2484
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Area" }),
2485
- /* @__PURE__ */ jsx8(
2985
+ return /* @__PURE__ */ jsx12(Card6, { overflow: "auto", padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs10(Stack8, { space: 3, children: [
2986
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: "Dimension deltas" }),
2987
+ /* @__PURE__ */ jsxs10(Grid, { columns: 4, gap: 2, children: [
2988
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Area" }),
2989
+ /* @__PURE__ */ jsx12(
2486
2990
  ColumnHeader,
2487
2991
  {
2488
2992
  label: "Task completion",
2489
2993
  tooltip: GLOSSARY.dimTaskCompletion
2490
2994
  }
2491
2995
  ),
2492
- /* @__PURE__ */ jsx8(
2996
+ /* @__PURE__ */ jsx12(
2493
2997
  ColumnHeader,
2494
2998
  {
2495
2999
  label: "Code correctness",
2496
3000
  tooltip: GLOSSARY.dimCodeCorrectness
2497
3001
  }
2498
3002
  ),
2499
- /* @__PURE__ */ jsx8(
3003
+ /* @__PURE__ */ jsx12(
2500
3004
  ColumnHeader,
2501
3005
  {
2502
3006
  label: "Doc coverage",
@@ -2504,11 +3008,11 @@ function DimensionDeltasTable({ dimDeltas }) {
2504
3008
  }
2505
3009
  )
2506
3010
  ] }),
2507
- dimDeltas.map((row) => /* @__PURE__ */ jsxs6(Grid, { columns: 4, gap: 2, children: [
2508
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.area }),
2509
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: formatDelta(row.taskDelta) }),
2510
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: formatDelta(row.codeDelta) }),
2511
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: formatDelta(row.docDelta) })
3011
+ dimDeltas.map((row) => /* @__PURE__ */ jsxs10(Grid, { columns: 4, gap: 2, children: [
3012
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.area }),
3013
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: formatDelta(row.taskDelta) }),
3014
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: formatDelta(row.codeDelta) }),
3015
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: formatDelta(row.docDelta) })
2512
3016
  ] }, row.area))
2513
3017
  ] }) });
2514
3018
  }
@@ -2518,27 +3022,27 @@ function ThreeLayerDeltasTable({
2518
3022
  const filtered = threeLayerDeltas.filter(
2519
3023
  (d) => d.baseActual !== null || d.baseRetGap !== null
2520
3024
  );
2521
- return /* @__PURE__ */ jsx8(Card3, { overflow: "auto", padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs6(Stack5, { space: 3, children: [
2522
- /* @__PURE__ */ jsxs6(Flex3, { align: "center", gap: 2, children: [
2523
- /* @__PURE__ */ jsx8(Text7, { size: 1, weight: "semibold", children: "Three-layer decomposition deltas" }),
2524
- /* @__PURE__ */ jsx8(Badge2, { fontSize: 0, tone: "primary", children: "full mode" })
3025
+ return /* @__PURE__ */ jsx12(Card6, { overflow: "auto", padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs10(Stack8, { space: 3, children: [
3026
+ /* @__PURE__ */ jsxs10(Flex7, { align: "center", gap: 2, children: [
3027
+ /* @__PURE__ */ jsx12(Text11, { size: 1, weight: "semibold", children: "Three-layer decomposition deltas" }),
3028
+ /* @__PURE__ */ jsx12(Badge3, { fontSize: 0, tone: "primary", children: "full mode" })
2525
3029
  ] }),
2526
- /* @__PURE__ */ jsxs6(Grid, { columns: 7, gap: 2, children: [
2527
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Area" }),
2528
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Actual (B)", tooltip: GLOSSARY.actual }),
2529
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Actual (E)", tooltip: GLOSSARY.actual }),
2530
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Actual \u0394", tooltip: GLOSSARY.actualDelta }),
2531
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Ret. Gap \u0394", tooltip: GLOSSARY.retGapDelta }),
2532
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Eff. (B)", tooltip: GLOSSARY.efficiency }),
2533
- /* @__PURE__ */ jsx8(ColumnHeader, { label: "Eff. (E)", tooltip: GLOSSARY.efficiency })
3030
+ /* @__PURE__ */ jsxs10(Grid, { columns: 7, gap: 2, children: [
3031
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Area" }),
3032
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Actual (B)", tooltip: GLOSSARY.actual }),
3033
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Actual (E)", tooltip: GLOSSARY.actual }),
3034
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Actual \u0394", tooltip: GLOSSARY.actualDelta }),
3035
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Ret. Gap \u0394", tooltip: GLOSSARY.retGapDelta }),
3036
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Eff. (B)", tooltip: GLOSSARY.efficiency }),
3037
+ /* @__PURE__ */ jsx12(ColumnHeader, { label: "Eff. (E)", tooltip: GLOSSARY.efficiency })
2534
3038
  ] }),
2535
- filtered.map((row) => /* @__PURE__ */ jsxs6(Grid, { columns: 7, gap: 2, children: [
2536
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.area }),
2537
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.baseActual != null ? row.baseActual.toFixed(1) : "\u2014" }),
2538
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.expActual != null ? row.expActual.toFixed(1) : "\u2014" }),
2539
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: row.actualDelta != null ? formatDelta(row.actualDelta) : "\u2014" }),
2540
- /* @__PURE__ */ jsx8(
2541
- Text7,
3039
+ filtered.map((row) => /* @__PURE__ */ jsxs10(Grid, { columns: 7, gap: 2, children: [
3040
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.area }),
3041
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.baseActual != null ? row.baseActual.toFixed(1) : "\u2014" }),
3042
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.expActual != null ? row.expActual.toFixed(1) : "\u2014" }),
3043
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: row.actualDelta != null ? formatDelta(row.actualDelta) : "\u2014" }),
3044
+ /* @__PURE__ */ jsx12(
3045
+ Text11,
2542
3046
  {
2543
3047
  size: 1,
2544
3048
  style: {
@@ -2547,8 +3051,8 @@ function ThreeLayerDeltasTable({
2547
3051
  children: row.retGapDelta != null ? formatDelta(row.retGapDelta) : "\u2014"
2548
3052
  }
2549
3053
  ),
2550
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: formatPercent(row.baseEfficiency) }),
2551
- /* @__PURE__ */ jsx8(Text7, { size: 1, children: formatPercent(row.expEfficiency) })
3054
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: formatPercent(row.baseEfficiency) }),
3055
+ /* @__PURE__ */ jsx12(Text11, { size: 1, children: formatPercent(row.expEfficiency) })
2552
3056
  ] }, `tl-${row.area}`))
2553
3057
  ] }) });
2554
3058
  }
@@ -2560,26 +3064,26 @@ function formatOption(r) {
2560
3064
  // src/components/LatestReports.tsx
2561
3065
  import { SortIcon } from "@sanity/icons";
2562
3066
  import {
2563
- Badge as Badge11,
2564
- Box as Box6,
3067
+ Badge as Badge12,
3068
+ Box as Box8,
2565
3069
  Button,
2566
- Card as Card9,
2567
- Flex as Flex12,
3070
+ Card as Card12,
3071
+ Flex as Flex16,
2568
3072
  Menu,
2569
3073
  MenuButton,
2570
3074
  MenuItem,
2571
- Stack as Stack10,
2572
- Text as Text16
3075
+ Stack as Stack13,
3076
+ Text as Text20
2573
3077
  } from "@sanity/ui";
2574
- import { useCallback as useCallback8, useEffect as useEffect5, useMemo as useMemo3, useState as useState6 } from "react";
3078
+ import { useCallback as useCallback11, useEffect as useEffect6, useMemo as useMemo5, useState as useState6 } from "react";
2575
3079
  import { useClient as useClient5 } from "sanity";
2576
3080
 
2577
3081
  // src/components/content-filters/DocumentFilter.tsx
2578
- import { SearchIcon } from "@sanity/icons";
2579
- import { Autocomplete, Badge as Badge3, Card as Card4, Flex as Flex4, Stack as Stack6, Text as Text8 } from "@sanity/ui";
2580
- import { useCallback as useCallback3, useEffect as useEffect2, useRef, useState as useState3 } from "react";
3082
+ import { SearchIcon as SearchIcon2 } from "@sanity/icons";
3083
+ import { Autocomplete as Autocomplete2, Badge as Badge4, Card as Card7, Flex as Flex8, Stack as Stack9, Text as Text12 } from "@sanity/ui";
3084
+ import { useCallback as useCallback6, useEffect as useEffect3, useRef as useRef2, useState as useState3 } from "react";
2581
3085
  import { useClient as useClient3 } from "sanity";
2582
- import { jsx as jsx9, jsxs as jsxs7 } from "react/jsx-runtime";
3086
+ import { jsx as jsx13, jsxs as jsxs11 } from "react/jsx-runtime";
2583
3087
  var SEARCH_DEBOUNCE_MS = 300;
2584
3088
  function DocumentFilter({
2585
3089
  value,
@@ -2589,13 +3093,13 @@ function DocumentFilter({
2589
3093
  const client = useClient3({ apiVersion: API_VERSION });
2590
3094
  const [options, setOptions] = useState3([]);
2591
3095
  const [loading, setLoading] = useState3(false);
2592
- const timer = useRef(null);
2593
- useEffect2(() => {
3096
+ const timer = useRef2(null);
3097
+ useEffect3(() => {
2594
3098
  return () => {
2595
3099
  if (timer.current) clearTimeout(timer.current);
2596
3100
  };
2597
3101
  }, []);
2598
- const handleQueryChange = useCallback3(
3102
+ const handleQueryChange = useCallback6(
2599
3103
  (query) => {
2600
3104
  if (timer.current) clearTimeout(timer.current);
2601
3105
  const trimmed = (query ?? "").trim();
@@ -2639,7 +3143,7 @@ function DocumentFilter({
2639
3143
  },
2640
3144
  [client]
2641
3145
  );
2642
- const handleSelect = useCallback3(
3146
+ const handleSelect = useCallback6(
2643
3147
  (selected) => {
2644
3148
  const option = options.find((o) => o.value === selected);
2645
3149
  const slug = option?.payload.slug ?? selected;
@@ -2650,29 +3154,29 @@ function DocumentFilter({
2650
3154
  },
2651
3155
  [options, onChange, onPerspectiveHint]
2652
3156
  );
2653
- const renderOption = useCallback3((option) => {
3157
+ const renderOption = useCallback6((option) => {
2654
3158
  const { provenance, releaseId } = option.payload;
2655
3159
  const badgeTone = provenance === "published" ? "positive" : provenance === "release" ? "primary" : "caution";
2656
3160
  const badgeLabel = provenance === "published" ? "Published" : provenance === "release" ? releaseId ?? "Release" : "Draft";
2657
- return /* @__PURE__ */ jsx9(Card4, { as: "button", padding: 3, children: /* @__PURE__ */ jsxs7(Flex4, { align: "center", gap: 2, children: [
2658
- /* @__PURE__ */ jsxs7(Stack6, { flex: 1, space: 1, children: [
2659
- /* @__PURE__ */ jsx9(Text8, { size: 1, weight: "semibold", children: option.payload.title }),
2660
- /* @__PURE__ */ jsx9(Text8, { muted: true, size: 1, children: option.payload.path })
3161
+ return /* @__PURE__ */ jsx13(Card7, { as: "button", padding: 3, children: /* @__PURE__ */ jsxs11(Flex8, { align: "center", gap: 2, children: [
3162
+ /* @__PURE__ */ jsxs11(Stack9, { flex: 1, space: 1, children: [
3163
+ /* @__PURE__ */ jsx13(Text12, { size: 1, weight: "semibold", children: option.payload.title }),
3164
+ /* @__PURE__ */ jsx13(Text12, { muted: true, size: 1, children: option.payload.path })
2661
3165
  ] }),
2662
- /* @__PURE__ */ jsx9(Badge3, { fontSize: 0, tone: badgeTone, children: badgeLabel })
3166
+ /* @__PURE__ */ jsx13(Badge4, { fontSize: 0, tone: badgeTone, children: badgeLabel })
2663
3167
  ] }) });
2664
3168
  }, []);
2665
- const renderValue = useCallback3((_value, option) => {
3169
+ const renderValue = useCallback6((_value, option) => {
2666
3170
  if (option?.payload.title) {
2667
3171
  return `${option.payload.title} (${option.payload.slug})`;
2668
3172
  }
2669
3173
  return _value;
2670
3174
  }, []);
2671
- return /* @__PURE__ */ jsx9(
2672
- Autocomplete,
3175
+ return /* @__PURE__ */ jsx13(
3176
+ Autocomplete2,
2673
3177
  {
2674
3178
  filterOption: () => true,
2675
- icon: SearchIcon,
3179
+ icon: SearchIcon2,
2676
3180
  id: "document-filter-input",
2677
3181
  loading,
2678
3182
  onChange: handleSelect,
@@ -2698,33 +3202,33 @@ function classifyDocId(id) {
2698
3202
  }
2699
3203
 
2700
3204
  // src/components/content-filters/PerspectiveFilter.tsx
2701
- import { SearchIcon as SearchIcon2 } from "@sanity/icons";
2702
- import { Autocomplete as Autocomplete2, Badge as Badge4, Card as Card5, Flex as Flex5, Stack as Stack7, Text as Text9 } from "@sanity/ui";
2703
- import { useEffect as useEffect3, useMemo as useMemo2, useState as useState4 } from "react";
3205
+ import { SearchIcon as SearchIcon3 } from "@sanity/icons";
3206
+ import { Autocomplete as Autocomplete3, Badge as Badge5, Card as Card8, Flex as Flex9, Stack as Stack10, Text as Text13 } from "@sanity/ui";
3207
+ import { useEffect as useEffect4, useMemo as useMemo4, useState as useState4 } from "react";
2704
3208
  import {
2705
- getReleaseIdFromReleaseDocumentId,
2706
- useActiveReleases,
2707
- useArchivedReleases,
3209
+ getReleaseIdFromReleaseDocumentId as getReleaseIdFromReleaseDocumentId3,
3210
+ useActiveReleases as useActiveReleases3,
3211
+ useArchivedReleases as useArchivedReleases3,
2708
3212
  useClient as useClient4
2709
3213
  } from "sanity";
2710
- import { jsx as jsx10, jsxs as jsxs8 } from "react/jsx-runtime";
3214
+ import { jsx as jsx14, jsxs as jsxs12 } from "react/jsx-runtime";
2711
3215
  function PerspectiveFilter({ value, onChange }) {
2712
3216
  const client = useClient4({ apiVersion: API_VERSION });
2713
3217
  const [reportPerspectives, setReportPerspectives] = useState4([]);
2714
- const { data: activeReleases } = useActiveReleases();
2715
- const { data: archivedReleases } = useArchivedReleases();
2716
- useEffect3(() => {
3218
+ const { data: activeReleases } = useActiveReleases3();
3219
+ const { data: archivedReleases } = useArchivedReleases3();
3220
+ useEffect4(() => {
2717
3221
  client.fetch(distinctPerspectivesQuery).then(
2718
3222
  (data) => setReportPerspectives((data ?? []).filter(Boolean).sort())
2719
3223
  ).catch(() => setReportPerspectives([]));
2720
3224
  }, [client]);
2721
- const options = useMemo2(() => {
3225
+ const options = useMemo4(() => {
2722
3226
  const releaseMap = /* @__PURE__ */ new Map();
2723
3227
  for (const release of [
2724
3228
  ...activeReleases ?? [],
2725
3229
  ...archivedReleases ?? []
2726
3230
  ]) {
2727
- const releaseId = getReleaseIdFromReleaseDocumentId(release._id);
3231
+ const releaseId = getReleaseIdFromReleaseDocumentId3(release._id);
2728
3232
  const title = release.metadata?.title ?? releaseId;
2729
3233
  releaseMap.set(releaseId, title);
2730
3234
  }
@@ -2744,27 +3248,27 @@ function PerspectiveFilter({ value, onChange }) {
2744
3248
  }));
2745
3249
  return result;
2746
3250
  }, [activeReleases, archivedReleases, reportPerspectives]);
2747
- return /* @__PURE__ */ jsx10(
2748
- Autocomplete2,
3251
+ return /* @__PURE__ */ jsx14(
3252
+ Autocomplete3,
2749
3253
  {
2750
3254
  filterOption: (query, option) => {
2751
3255
  const q = query.toLowerCase();
2752
3256
  const opt = option;
2753
3257
  return opt.value.toLowerCase().includes(q) || (opt.payload?.title ?? "").toLowerCase().includes(q);
2754
3258
  },
2755
- icon: SearchIcon2,
3259
+ icon: SearchIcon3,
2756
3260
  id: "perspective-filter-input",
2757
3261
  onChange,
2758
3262
  options,
2759
3263
  placeholder: "Search by title or ID\u2026",
2760
3264
  renderOption: (option) => {
2761
3265
  const opt = option;
2762
- return /* @__PURE__ */ jsx10(Card5, { as: "button", padding: 3, children: /* @__PURE__ */ jsxs8(Flex5, { align: "center", gap: 2, children: [
2763
- /* @__PURE__ */ jsxs8(Stack7, { flex: 1, space: 1, children: [
2764
- /* @__PURE__ */ jsx10(Text9, { size: 1, weight: "semibold", children: opt.payload.title }),
2765
- opt.payload.title !== opt.value && /* @__PURE__ */ jsx10(Text9, { muted: true, size: 1, children: opt.value })
3266
+ return /* @__PURE__ */ jsx14(Card8, { as: "button", padding: 3, children: /* @__PURE__ */ jsxs12(Flex9, { align: "center", gap: 2, children: [
3267
+ /* @__PURE__ */ jsxs12(Stack10, { flex: 1, space: 1, children: [
3268
+ /* @__PURE__ */ jsx14(Text13, { size: 1, weight: "semibold", children: opt.payload.title }),
3269
+ opt.payload.title !== opt.value && /* @__PURE__ */ jsx14(Text13, { muted: true, size: 1, children: opt.value })
2766
3270
  ] }),
2767
- opt.payload.hasReport && /* @__PURE__ */ jsx10(Badge4, { fontSize: 0, tone: "positive", children: "Has reports" })
3271
+ opt.payload.hasReport && /* @__PURE__ */ jsx14(Badge5, { fontSize: 0, tone: "positive", children: "Has reports" })
2768
3272
  ] }) });
2769
3273
  },
2770
3274
  renderValue: (v, option) => {
@@ -2780,15 +3284,15 @@ function PerspectiveFilter({ value, onChange }) {
2780
3284
  }
2781
3285
 
2782
3286
  // src/components/report-card/ReportCard.tsx
2783
- import { Badge as Badge8, Card as Card6, Flex as Flex8, Text as Text12 } from "@sanity/ui";
2784
- import { useCallback as useCallback4 } from "react";
3287
+ import { Badge as Badge9, Card as Card9, Flex as Flex12, Text as Text16 } from "@sanity/ui";
3288
+ import { useCallback as useCallback7 } from "react";
2785
3289
 
2786
3290
  // src/components/primitives/DeltaIndicator.tsx
2787
- import { Text as Text10 } from "@sanity/ui";
2788
- import { jsx as jsx11 } from "react/jsx-runtime";
3291
+ import { Text as Text14 } from "@sanity/ui";
3292
+ import { jsx as jsx15 } from "react/jsx-runtime";
2789
3293
  function DeltaIndicator({ delta, size = 1 }) {
2790
- return /* @__PURE__ */ jsx11(
2791
- Text10,
3294
+ return /* @__PURE__ */ jsx15(
3295
+ Text14,
2792
3296
  {
2793
3297
  size,
2794
3298
  style: {
@@ -2800,18 +3304,18 @@ function DeltaIndicator({ delta, size = 1 }) {
2800
3304
  }
2801
3305
 
2802
3306
  // src/components/report-card/ReportMeta.tsx
2803
- import { Stack as Stack8, Text as Text11 } from "@sanity/ui";
3307
+ import { Stack as Stack11, Text as Text15 } from "@sanity/ui";
2804
3308
 
2805
3309
  // src/components/report-card/AreaTags.tsx
2806
- import { Badge as Badge5, Flex as Flex6 } from "@sanity/ui";
2807
- import { jsx as jsx12, jsxs as jsxs9 } from "react/jsx-runtime";
3310
+ import { Badge as Badge6, Flex as Flex10 } from "@sanity/ui";
3311
+ import { jsx as jsx16, jsxs as jsxs13 } from "react/jsx-runtime";
2808
3312
  function AreaTags({ areas, targetDocuments }) {
2809
3313
  const hasAreas = areas && areas.length > 0;
2810
3314
  const hasDocs = targetDocuments && targetDocuments.length > 0;
2811
3315
  if (!hasAreas && !hasDocs) return null;
2812
- return /* @__PURE__ */ jsxs9(Flex6, { gap: 1, paddingTop: 1, wrap: "wrap", children: [
2813
- hasAreas && areas.map((area) => /* @__PURE__ */ jsx12(
2814
- Badge5,
3316
+ return /* @__PURE__ */ jsxs13(Flex10, { gap: 1, paddingTop: 1, wrap: "wrap", children: [
3317
+ hasAreas && areas.map((area) => /* @__PURE__ */ jsx16(
3318
+ Badge6,
2815
3319
  {
2816
3320
  fontSize: 0,
2817
3321
  mode: "outline",
@@ -2820,7 +3324,7 @@ function AreaTags({ areas, targetDocuments }) {
2820
3324
  },
2821
3325
  `area-${area}`
2822
3326
  )),
2823
- hasDocs && targetDocuments.map((doc) => /* @__PURE__ */ jsx12(Badge5, { fontSize: 0, mode: "outline", tone: "primary", children: doc }, `doc-${doc}`))
3327
+ hasDocs && targetDocuments.map((doc) => /* @__PURE__ */ jsx16(Badge6, { fontSize: 0, mode: "outline", tone: "primary", children: doc }, `doc-${doc}`))
2824
3328
  ] });
2825
3329
  }
2826
3330
 
@@ -2864,7 +3368,7 @@ function formatCardDate(iso) {
2864
3368
  }
2865
3369
 
2866
3370
  // src/components/report-card/ReportMeta.tsx
2867
- import { jsx as jsx13, jsxs as jsxs10 } from "react/jsx-runtime";
3371
+ import { jsx as jsx17, jsxs as jsxs14 } from "react/jsx-runtime";
2868
3372
  function ReportMeta({ data }) {
2869
3373
  const segments = [data.mode, data.source];
2870
3374
  if (data.models && data.models.length > 0) {
@@ -2876,15 +3380,15 @@ function ReportMeta({ data }) {
2876
3380
  if (data.durationMs && data.durationMs > 0) {
2877
3381
  segments.push(formatDuration(data.durationMs));
2878
3382
  }
2879
- return /* @__PURE__ */ jsxs10(Stack8, { flex: 1, space: 1, children: [
2880
- /* @__PURE__ */ jsx13(Text11, { weight: "semibold", children: data.tag ?? formatCardDate(data.completedAt) }),
2881
- /* @__PURE__ */ jsx13(Text11, { muted: true, size: 1, children: segments.join(" \xB7 ") }),
2882
- /* @__PURE__ */ jsx13(AreaTags, { areas: data.areas, targetDocuments: data.targetDocuments })
3383
+ return /* @__PURE__ */ jsxs14(Stack11, { flex: 1, space: 1, children: [
3384
+ /* @__PURE__ */ jsx17(Text15, { weight: "semibold", children: data.tag ?? formatCardDate(data.completedAt) }),
3385
+ /* @__PURE__ */ jsx17(Text15, { muted: true, size: 1, children: segments.join(" \xB7 ") }),
3386
+ /* @__PURE__ */ jsx17(AreaTags, { areas: data.areas, targetDocuments: data.targetDocuments })
2883
3387
  ] });
2884
3388
  }
2885
3389
 
2886
3390
  // src/components/primitives/ScoreBadge.tsx
2887
- import { Badge as Badge6 } from "@sanity/ui";
3391
+ import { Badge as Badge7 } from "@sanity/ui";
2888
3392
 
2889
3393
  // src/lib/scoring.ts
2890
3394
  var TONE_MAP = {
@@ -2916,11 +3420,11 @@ function rowBackground(index) {
2916
3420
  }
2917
3421
 
2918
3422
  // src/components/primitives/ScoreBadge.tsx
2919
- import { jsx as jsx14 } from "react/jsx-runtime";
3423
+ import { jsx as jsx18 } from "react/jsx-runtime";
2920
3424
  function ScoreBadge({ score, fontSize = 1 }) {
2921
3425
  const rounded = Math.round(score);
2922
- return /* @__PURE__ */ jsx14(
2923
- Badge6,
3426
+ return /* @__PURE__ */ jsx18(
3427
+ Badge7,
2924
3428
  {
2925
3429
  fontSize,
2926
3430
  style: { minWidth: 48, textAlign: "center" },
@@ -2931,18 +3435,18 @@ function ScoreBadge({ score, fontSize = 1 }) {
2931
3435
  }
2932
3436
 
2933
3437
  // src/components/primitives/StatusBadges.tsx
2934
- import { Badge as Badge7, Flex as Flex7 } from "@sanity/ui";
2935
- import { jsxs as jsxs11 } from "react/jsx-runtime";
3438
+ import { Badge as Badge8, Flex as Flex11 } from "@sanity/ui";
3439
+ import { jsxs as jsxs15 } from "react/jsx-runtime";
2936
3440
  function StatusBadges({ regressed, improved }) {
2937
3441
  const hasRegressed = regressed && regressed.length > 0;
2938
3442
  const hasImproved = improved && improved.length > 0;
2939
3443
  if (!hasRegressed && !hasImproved) return null;
2940
- return /* @__PURE__ */ jsxs11(Flex7, { gap: 1, children: [
2941
- hasRegressed && /* @__PURE__ */ jsxs11(Badge7, { fontSize: 0, tone: "critical", children: [
3444
+ return /* @__PURE__ */ jsxs15(Flex11, { gap: 1, children: [
3445
+ hasRegressed && /* @__PURE__ */ jsxs15(Badge8, { fontSize: 0, tone: "critical", children: [
2942
3446
  regressed.length,
2943
3447
  " regressed"
2944
3448
  ] }),
2945
- hasImproved && /* @__PURE__ */ jsxs11(Badge7, { fontSize: 0, tone: "positive", children: [
3449
+ hasImproved && /* @__PURE__ */ jsxs15(Badge8, { fontSize: 0, tone: "positive", children: [
2946
3450
  improved.length,
2947
3451
  " improved"
2948
3452
  ] })
@@ -2950,38 +3454,38 @@ function StatusBadges({ regressed, improved }) {
2950
3454
  }
2951
3455
 
2952
3456
  // src/components/report-card/ReportCard.tsx
2953
- import { jsx as jsx15, jsxs as jsxs12 } from "react/jsx-runtime";
3457
+ import { jsx as jsx19, jsxs as jsxs16 } from "react/jsx-runtime";
2954
3458
  function ReportCard({ data, onSelectReport }) {
2955
- const handleClick = useCallback4(() => {
3459
+ const handleClick = useCallback7(() => {
2956
3460
  onSelectReport(data.reportId);
2957
3461
  }, [data.reportId, onSelectReport]);
2958
- return /* @__PURE__ */ jsx15(
2959
- Card6,
3462
+ return /* @__PURE__ */ jsx19(
3463
+ Card9,
2960
3464
  {
2961
3465
  onClick: handleClick,
2962
3466
  padding: 3,
2963
3467
  radius: 2,
2964
3468
  shadow: 1,
2965
3469
  style: { cursor: "pointer" },
2966
- children: /* @__PURE__ */ jsxs12(Flex8, { align: "center", gap: 3, children: [
2967
- /* @__PURE__ */ jsx15(ScoreBadge, { score: data.overall }),
2968
- /* @__PURE__ */ jsx15(ReportMeta, { data }),
2969
- data.comparisonDelta != null && /* @__PURE__ */ jsx15(DeltaIndicator, { delta: data.comparisonDelta }),
2970
- /* @__PURE__ */ jsx15(StatusBadges, { improved: data.improved, regressed: data.regressed }),
2971
- /* @__PURE__ */ jsx15(Text12, { muted: true, size: 0, title: new Date(data.completedAt).toISOString(), children: formatRelativeTime(data.completedAt) }),
2972
- data.trigger && /* @__PURE__ */ jsx15(Badge8, { fontSize: 0, tone: "default", children: data.trigger })
3470
+ children: /* @__PURE__ */ jsxs16(Flex12, { align: "center", gap: 3, children: [
3471
+ /* @__PURE__ */ jsx19(ScoreBadge, { score: data.overall }),
3472
+ /* @__PURE__ */ jsx19(ReportMeta, { data }),
3473
+ data.comparisonDelta != null && /* @__PURE__ */ jsx19(DeltaIndicator, { delta: data.comparisonDelta }),
3474
+ /* @__PURE__ */ jsx19(StatusBadges, { improved: data.improved, regressed: data.regressed }),
3475
+ /* @__PURE__ */ jsx19(Text16, { muted: true, size: 0, title: new Date(data.completedAt).toISOString(), children: formatRelativeTime(data.completedAt) }),
3476
+ data.trigger && /* @__PURE__ */ jsx19(Badge9, { fontSize: 0, tone: "default", children: data.trigger })
2973
3477
  ] })
2974
3478
  }
2975
3479
  );
2976
3480
  }
2977
3481
 
2978
3482
  // src/components/search-bar/SearchBar.tsx
2979
- import { SearchIcon as SearchIcon3 } from "@sanity/icons";
2980
- import { Card as Card8, Flex as Flex11, Text as Text15 } from "@sanity/ui";
3483
+ import { SearchIcon as SearchIcon4 } from "@sanity/icons";
3484
+ import { Card as Card11, Flex as Flex15, Text as Text19 } from "@sanity/ui";
2981
3485
  import {
2982
- useCallback as useCallback7,
2983
- useEffect as useEffect4,
2984
- useRef as useRef2,
3486
+ useCallback as useCallback10,
3487
+ useEffect as useEffect5,
3488
+ useRef as useRef3,
2985
3489
  useState as useState5
2986
3490
  } from "react";
2987
3491
 
@@ -3122,21 +3626,21 @@ function filterAndExclude(values, query, dim, activeTokens) {
3122
3626
 
3123
3627
  // src/components/search-bar/FilterBadge.tsx
3124
3628
  import { CloseIcon } from "@sanity/icons";
3125
- import { Badge as Badge9, Flex as Flex9, Text as Text13 } from "@sanity/ui";
3126
- import { useCallback as useCallback5 } from "react";
3127
- import { jsx as jsx16, jsxs as jsxs13 } from "react/jsx-runtime";
3629
+ import { Badge as Badge10, Flex as Flex13, Text as Text17 } from "@sanity/ui";
3630
+ import { useCallback as useCallback8 } from "react";
3631
+ import { jsx as jsx20, jsxs as jsxs17 } from "react/jsx-runtime";
3128
3632
  function FilterBadge({ token, onRemove }) {
3129
3633
  const dim = DIMENSIONS.find((d) => d.key === token.dimension);
3130
3634
  const tone = dim?.tone ?? "default";
3131
- const handleRemove = useCallback5(
3635
+ const handleRemove = useCallback8(
3132
3636
  (e) => {
3133
3637
  e.stopPropagation();
3134
3638
  onRemove(token.id);
3135
3639
  },
3136
3640
  [onRemove, token.id]
3137
3641
  );
3138
- return /* @__PURE__ */ jsx16(
3139
- Badge9,
3642
+ return /* @__PURE__ */ jsx20(
3643
+ Badge10,
3140
3644
  {
3141
3645
  fontSize: 0,
3142
3646
  style: {
@@ -3145,20 +3649,20 @@ function FilterBadge({ token, onRemove }) {
3145
3649
  userSelect: "none"
3146
3650
  },
3147
3651
  tone,
3148
- children: /* @__PURE__ */ jsxs13(Flex9, { align: "center", gap: 1, children: [
3149
- /* @__PURE__ */ jsxs13(Text13, { size: 0, children: [
3652
+ children: /* @__PURE__ */ jsxs17(Flex13, { align: "center", gap: 1, children: [
3653
+ /* @__PURE__ */ jsxs17(Text17, { size: 0, children: [
3150
3654
  token.dimension,
3151
3655
  ":",
3152
3656
  token.label
3153
3657
  ] }),
3154
- /* @__PURE__ */ jsx16(
3155
- Text13,
3658
+ /* @__PURE__ */ jsx20(
3659
+ Text17,
3156
3660
  {
3157
3661
  muted: true,
3158
3662
  onClick: handleRemove,
3159
3663
  size: 0,
3160
3664
  style: { cursor: "pointer", lineHeight: 1 },
3161
- children: /* @__PURE__ */ jsx16(CloseIcon, {})
3665
+ children: /* @__PURE__ */ jsx20(CloseIcon, {})
3162
3666
  }
3163
3667
  )
3164
3668
  ] })
@@ -3167,9 +3671,9 @@ function FilterBadge({ token, onRemove }) {
3167
3671
  }
3168
3672
 
3169
3673
  // src/components/search-bar/SuggestionList.tsx
3170
- import { Badge as Badge10, Card as Card7, Flex as Flex10, Stack as Stack9, Text as Text14 } from "@sanity/ui";
3171
- import { useCallback as useCallback6 } from "react";
3172
- import { jsx as jsx17, jsxs as jsxs14 } from "react/jsx-runtime";
3674
+ import { Badge as Badge11, Card as Card10, Flex as Flex14, Stack as Stack12, Text as Text18 } from "@sanity/ui";
3675
+ import { useCallback as useCallback9 } from "react";
3676
+ import { jsx as jsx21, jsxs as jsxs18 } from "react/jsx-runtime";
3173
3677
  function SuggestionList({
3174
3678
  suggestions,
3175
3679
  activeIndex,
@@ -3178,8 +3682,8 @@ function SuggestionList({
3178
3682
  if (suggestions.length === 0) return null;
3179
3683
  const groups = groupByCategory(suggestions);
3180
3684
  let globalIndex = -1;
3181
- return /* @__PURE__ */ jsx17(
3182
- Card7,
3685
+ return /* @__PURE__ */ jsx21(
3686
+ Card10,
3183
3687
  {
3184
3688
  overflow: "auto",
3185
3689
  radius: 2,
@@ -3192,9 +3696,9 @@ function SuggestionList({
3192
3696
  top: "100%",
3193
3697
  zIndex: 100
3194
3698
  },
3195
- children: /* @__PURE__ */ jsx17(Stack9, { padding: 1, space: 1, children: groups.map(([category, items]) => /* @__PURE__ */ jsxs14(Stack9, { space: 0, children: [
3196
- /* @__PURE__ */ jsx17(
3197
- Text14,
3699
+ children: /* @__PURE__ */ jsx21(Stack12, { padding: 1, space: 1, children: groups.map(([category, items]) => /* @__PURE__ */ jsxs18(Stack12, { space: 0, children: [
3700
+ /* @__PURE__ */ jsx21(
3701
+ Text18,
3198
3702
  {
3199
3703
  muted: true,
3200
3704
  size: 0,
@@ -3210,7 +3714,7 @@ function SuggestionList({
3210
3714
  items.map((suggestion) => {
3211
3715
  globalIndex++;
3212
3716
  const isActive = globalIndex === activeIndex;
3213
- return /* @__PURE__ */ jsx17(
3717
+ return /* @__PURE__ */ jsx21(
3214
3718
  SuggestionItem,
3215
3719
  {
3216
3720
  active: isActive,
@@ -3232,20 +3736,20 @@ function SuggestionItem({
3232
3736
  const dim = DIMENSIONS.find((d) => d.key === suggestion.dimension);
3233
3737
  const tone = dim?.tone ?? "default";
3234
3738
  const isHint = suggestion.category === "Filters";
3235
- const handleClick = useCallback6(() => {
3739
+ const handleClick = useCallback9(() => {
3236
3740
  onSelect(suggestion);
3237
3741
  }, [onSelect, suggestion]);
3238
- return /* @__PURE__ */ jsx17(
3239
- Card7,
3742
+ return /* @__PURE__ */ jsx21(
3743
+ Card10,
3240
3744
  {
3241
3745
  onClick: handleClick,
3242
3746
  padding: 2,
3243
3747
  radius: 2,
3244
3748
  style: { cursor: "pointer" },
3245
3749
  tone: active ? "primary" : "default",
3246
- children: /* @__PURE__ */ jsxs14(Flex10, { align: "center", gap: 2, children: [
3247
- !isHint && /* @__PURE__ */ jsx17(Badge10, { fontSize: 0, tone, children: suggestion.dimension }),
3248
- /* @__PURE__ */ jsx17(Text14, { size: 1, children: suggestion.label })
3750
+ children: /* @__PURE__ */ jsxs18(Flex14, { align: "center", gap: 2, children: [
3751
+ !isHint && /* @__PURE__ */ jsx21(Badge11, { fontSize: 0, tone, children: suggestion.dimension }),
3752
+ /* @__PURE__ */ jsx21(Text18, { size: 1, children: suggestion.label })
3249
3753
  ] })
3250
3754
  }
3251
3755
  );
@@ -3260,7 +3764,7 @@ function groupByCategory(suggestions) {
3260
3764
  }
3261
3765
 
3262
3766
  // src/components/search-bar/SearchBar.tsx
3263
- import { jsx as jsx18, jsxs as jsxs15 } from "react/jsx-runtime";
3767
+ import { jsx as jsx22, jsxs as jsxs19 } from "react/jsx-runtime";
3264
3768
  function SearchBar({
3265
3769
  tokens,
3266
3770
  query,
@@ -3272,9 +3776,9 @@ function SearchBar({
3272
3776
  }) {
3273
3777
  const [focused, setFocused] = useState5(false);
3274
3778
  const [activeIndex, setActiveIndex] = useState5(-1);
3275
- const inputRef = useRef2(null);
3276
- const blurTimerRef = useRef2(null);
3277
- useEffect4(() => {
3779
+ const inputRef = useRef3(null);
3780
+ const blurTimerRef = useRef3(null);
3781
+ useEffect5(() => {
3278
3782
  return () => {
3279
3783
  if (blurTimerRef.current) {
3280
3784
  clearTimeout(blurTimerRef.current);
@@ -3282,10 +3786,10 @@ function SearchBar({
3282
3786
  };
3283
3787
  }, []);
3284
3788
  const suggestions = focused ? computeSuggestions({ query, activeTokens: tokens, models, areas }) : [];
3285
- useEffect4(() => {
3789
+ useEffect5(() => {
3286
3790
  setActiveIndex(-1);
3287
3791
  }, [query, tokens.length]);
3288
- const handleTokenRemove = useCallback7(
3792
+ const handleTokenRemove = useCallback10(
3289
3793
  (id) => {
3290
3794
  onTokenRemove(id);
3291
3795
  requestAnimationFrame(() => {
@@ -3294,7 +3798,7 @@ function SearchBar({
3294
3798
  },
3295
3799
  [onTokenRemove]
3296
3800
  );
3297
- const handleSuggestionSelect = useCallback7(
3801
+ const handleSuggestionSelect = useCallback10(
3298
3802
  (suggestion) => {
3299
3803
  if (suggestion.category === "Filters") {
3300
3804
  onQueryChange(suggestion.value);
@@ -3313,7 +3817,7 @@ function SearchBar({
3313
3817
  },
3314
3818
  [onTokenAdd, onQueryChange]
3315
3819
  );
3316
- const handleKeyDown = useCallback7(
3820
+ const handleKeyDown = useCallback10(
3317
3821
  (e) => {
3318
3822
  if (e.key === "ArrowDown") {
3319
3823
  e.preventDefault();
@@ -3341,41 +3845,41 @@ function SearchBar({
3341
3845
  handleSuggestionSelect
3342
3846
  ]
3343
3847
  );
3344
- const handleInputChange = useCallback7(
3848
+ const handleInputChange = useCallback10(
3345
3849
  (e) => {
3346
3850
  const value = e.target.value;
3347
3851
  onQueryChange(value);
3348
3852
  },
3349
3853
  [onQueryChange]
3350
3854
  );
3351
- const handleBlur = useCallback7(() => {
3855
+ const handleBlur = useCallback10(() => {
3352
3856
  blurTimerRef.current = setTimeout(() => {
3353
3857
  blurTimerRef.current = null;
3354
3858
  setFocused(false);
3355
3859
  }, 200);
3356
3860
  }, []);
3357
- const handleFocus = useCallback7(() => {
3861
+ const handleFocus = useCallback10(() => {
3358
3862
  if (blurTimerRef.current) {
3359
3863
  clearTimeout(blurTimerRef.current);
3360
3864
  blurTimerRef.current = null;
3361
3865
  }
3362
3866
  setFocused(true);
3363
3867
  }, []);
3364
- const handleBarClick = useCallback7(() => {
3868
+ const handleBarClick = useCallback10(() => {
3365
3869
  inputRef.current?.focus();
3366
3870
  }, []);
3367
- return /* @__PURE__ */ jsxs15("div", { style: { position: "relative" }, children: [
3368
- /* @__PURE__ */ jsx18(
3369
- Card8,
3871
+ return /* @__PURE__ */ jsxs19("div", { style: { position: "relative" }, children: [
3872
+ /* @__PURE__ */ jsx22(
3873
+ Card11,
3370
3874
  {
3371
3875
  border: true,
3372
3876
  onClick: handleBarClick,
3373
3877
  padding: 2,
3374
3878
  radius: 2,
3375
3879
  style: { cursor: "text" },
3376
- children: /* @__PURE__ */ jsxs15(Flex11, { align: "center", gap: 1, wrap: "wrap", children: [
3377
- /* @__PURE__ */ jsx18(Text15, { muted: true, size: 1, style: { flexShrink: 0, padding: "0 4px" }, children: /* @__PURE__ */ jsx18(SearchIcon3, {}) }),
3378
- tokens.map((token) => /* @__PURE__ */ jsx18(
3880
+ children: /* @__PURE__ */ jsxs19(Flex15, { align: "center", gap: 1, wrap: "wrap", children: [
3881
+ /* @__PURE__ */ jsx22(Text19, { muted: true, size: 1, style: { flexShrink: 0, padding: "0 4px" }, children: /* @__PURE__ */ jsx22(SearchIcon4, {}) }),
3882
+ tokens.map((token) => /* @__PURE__ */ jsx22(
3379
3883
  FilterBadge,
3380
3884
  {
3381
3885
  onRemove: handleTokenRemove,
@@ -3383,7 +3887,7 @@ function SearchBar({
3383
3887
  },
3384
3888
  token.id
3385
3889
  )),
3386
- /* @__PURE__ */ jsx18(
3890
+ /* @__PURE__ */ jsx22(
3387
3891
  "input",
3388
3892
  {
3389
3893
  onBlur: handleBlur,
@@ -3410,7 +3914,7 @@ function SearchBar({
3410
3914
  ] })
3411
3915
  }
3412
3916
  ),
3413
- focused && suggestions.length > 0 && /* @__PURE__ */ jsx18(
3917
+ focused && suggestions.length > 0 && /* @__PURE__ */ jsx22(
3414
3918
  SuggestionList,
3415
3919
  {
3416
3920
  activeIndex,
@@ -3422,7 +3926,7 @@ function SearchBar({
3422
3926
  }
3423
3927
 
3424
3928
  // src/components/LatestReports.tsx
3425
- import { jsx as jsx19, jsxs as jsxs16 } from "react/jsx-runtime";
3929
+ import { jsx as jsx23, jsxs as jsxs20 } from "react/jsx-runtime";
3426
3930
  var SORT_LABELS = {
3427
3931
  date: "Date",
3428
3932
  name: "Name",
@@ -3449,7 +3953,7 @@ function LatestReports({
3449
3953
  });
3450
3954
  const [availableModels, setAvailableModels] = useState6([]);
3451
3955
  const [availableAreas, setAvailableAreas] = useState6([]);
3452
- useEffect5(() => {
3956
+ useEffect6(() => {
3453
3957
  setInitialLoading(true);
3454
3958
  setHasMore(true);
3455
3959
  client.fetch(latestReportsQuery, {
@@ -3467,7 +3971,7 @@ function LatestReports({
3467
3971
  setInitialLoading(false);
3468
3972
  });
3469
3973
  }, [client, pageSize, mode, source]);
3470
- const handleLoadMore = useCallback8(() => {
3974
+ const handleLoadMore = useCallback11(() => {
3471
3975
  if (loadingMore || !hasMore) return;
3472
3976
  setLoadingMore(true);
3473
3977
  const nextLimit = reports.length + pageSize;
@@ -3484,11 +3988,11 @@ function LatestReports({
3484
3988
  setLoadingMore(false);
3485
3989
  });
3486
3990
  }, [client, hasMore, loadingMore, mode, pageSize, reports.length, source]);
3487
- useEffect5(() => {
3991
+ useEffect6(() => {
3488
3992
  client.fetch(distinctModelsQuery).then((data) => setAvailableModels((data ?? []).sort())).catch(() => setAvailableModels([]));
3489
3993
  client.fetch(distinctAreasQuery).then((data) => setAvailableAreas((data ?? []).sort())).catch(() => setAvailableAreas([]));
3490
3994
  }, [client]);
3491
- const activeFilters = useMemo3(() => {
3995
+ const activeFilters = useMemo5(() => {
3492
3996
  const result = { models: [], areas: [], datePreset: null };
3493
3997
  for (const token of filterTokens) {
3494
3998
  switch (token.dimension) {
@@ -3505,7 +4009,7 @@ function LatestReports({
3505
4009
  }
3506
4010
  return result;
3507
4011
  }, [filterTokens]);
3508
- const filteredReports = useMemo3(() => {
4012
+ const filteredReports = useMemo5(() => {
3509
4013
  let result = reports;
3510
4014
  if (searchQuery.trim()) {
3511
4015
  const query = searchQuery.toLowerCase().trim();
@@ -3568,7 +4072,7 @@ function LatestReports({
3568
4072
  });
3569
4073
  return result;
3570
4074
  }, [reports, searchQuery, activeFilters, documentSlug, perspective, sort]);
3571
- const handleTokenAdd = useCallback8((token) => {
4075
+ const handleTokenAdd = useCallback11((token) => {
3572
4076
  setFilterTokens((prev) => {
3573
4077
  const dim = token.dimension;
3574
4078
  const isMulti = dim === "area";
@@ -3578,38 +4082,38 @@ function LatestReports({
3578
4082
  return [...prev, token];
3579
4083
  });
3580
4084
  }, []);
3581
- const handleTokenRemove = useCallback8((id) => {
4085
+ const handleTokenRemove = useCallback11((id) => {
3582
4086
  setFilterTokens((prev) => prev.filter((t) => t.id !== id));
3583
4087
  }, []);
3584
- const toggleSortDirection = useCallback8(() => {
4088
+ const toggleSortDirection = useCallback11(() => {
3585
4089
  setSort((prev) => ({
3586
4090
  ...prev,
3587
4091
  direction: prev.direction === "asc" ? "desc" : "asc"
3588
4092
  }));
3589
4093
  }, []);
3590
- const handleSortFieldChange = useCallback8((field) => {
4094
+ const handleSortFieldChange = useCallback11((field) => {
3591
4095
  setSort(
3592
4096
  (prev) => prev.field === field ? { ...prev, direction: prev.direction === "asc" ? "desc" : "asc" } : { direction: "desc", field }
3593
4097
  );
3594
4098
  }, []);
3595
4099
  const hasActiveFilters = searchQuery.trim() !== "" || filterTokens.length > 0 || documentSlug.trim() !== "" || perspective.trim() !== "";
3596
- const handleClearFilters = useCallback8(() => {
4100
+ const handleClearFilters = useCallback11(() => {
3597
4101
  setSearchQuery("");
3598
4102
  setFilterTokens([]);
3599
4103
  setDocumentSlug("");
3600
4104
  setPerspective("");
3601
4105
  }, []);
3602
4106
  if (initialLoading) {
3603
- return /* @__PURE__ */ jsx19(Card9, { padding: 4, children: /* @__PURE__ */ jsx19(Text16, { muted: true, children: "Loading reports\u2026" }) });
4107
+ return /* @__PURE__ */ jsx23(Card12, { padding: 4, children: /* @__PURE__ */ jsx23(Text20, { muted: true, children: "Loading reports\u2026" }) });
3604
4108
  }
3605
4109
  if (reports.length === 0) {
3606
- return /* @__PURE__ */ jsx19(Card9, { padding: 4, children: /* @__PURE__ */ jsx19(Text16, { muted: true, children: "No reports found. Run the pipeline with --publish to create reports." }) });
4110
+ return /* @__PURE__ */ jsx23(Card12, { padding: 4, children: /* @__PURE__ */ jsx23(Text20, { muted: true, children: "No reports found. Run the pipeline with --publish to create reports." }) });
3607
4111
  }
3608
- return /* @__PURE__ */ jsxs16(Stack10, { space: 3, children: [
3609
- /* @__PURE__ */ jsx19(Card9, { padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs16(Stack10, { space: 3, children: [
3610
- /* @__PURE__ */ jsxs16(Stack10, { space: 1, children: [
3611
- /* @__PURE__ */ jsx19(Text16, { muted: true, size: 0, children: "Search & filter" }),
3612
- /* @__PURE__ */ jsx19(
4112
+ return /* @__PURE__ */ jsxs20(Stack13, { space: 3, children: [
4113
+ /* @__PURE__ */ jsx23(Card12, { padding: 3, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs20(Stack13, { space: 3, children: [
4114
+ /* @__PURE__ */ jsxs20(Stack13, { space: 1, children: [
4115
+ /* @__PURE__ */ jsx23(Text20, { muted: true, size: 0, children: "Search & filter" }),
4116
+ /* @__PURE__ */ jsx23(
3613
4117
  SearchBar,
3614
4118
  {
3615
4119
  areas: availableAreas,
@@ -3622,10 +4126,10 @@ function LatestReports({
3622
4126
  }
3623
4127
  )
3624
4128
  ] }),
3625
- /* @__PURE__ */ jsxs16(Flex12, { gap: 2, children: [
3626
- /* @__PURE__ */ jsx19(Box6, { flex: 1, children: /* @__PURE__ */ jsxs16(Stack10, { space: 1, children: [
3627
- /* @__PURE__ */ jsx19(Text16, { muted: true, size: 0, children: "Document" }),
3628
- /* @__PURE__ */ jsx19(
4129
+ /* @__PURE__ */ jsxs20(Flex16, { gap: 2, children: [
4130
+ /* @__PURE__ */ jsx23(Box8, { flex: 1, children: /* @__PURE__ */ jsxs20(Stack13, { space: 1, children: [
4131
+ /* @__PURE__ */ jsx23(Text20, { muted: true, size: 0, children: "Document" }),
4132
+ /* @__PURE__ */ jsx23(
3629
4133
  DocumentFilter,
3630
4134
  {
3631
4135
  onChange: setDocumentSlug,
@@ -3634,9 +4138,9 @@ function LatestReports({
3634
4138
  }
3635
4139
  )
3636
4140
  ] }) }),
3637
- /* @__PURE__ */ jsx19(Box6, { flex: 1, children: /* @__PURE__ */ jsxs16(Stack10, { space: 1, children: [
3638
- /* @__PURE__ */ jsx19(Text16, { muted: true, size: 0, children: "Content release" }),
3639
- /* @__PURE__ */ jsx19(
4141
+ /* @__PURE__ */ jsx23(Box8, { flex: 1, children: /* @__PURE__ */ jsxs20(Stack13, { space: 1, children: [
4142
+ /* @__PURE__ */ jsx23(Text20, { muted: true, size: 0, children: "Content release" }),
4143
+ /* @__PURE__ */ jsx23(
3640
4144
  PerspectiveFilter,
3641
4145
  {
3642
4146
  onChange: setPerspective,
@@ -3645,20 +4149,20 @@ function LatestReports({
3645
4149
  )
3646
4150
  ] }) })
3647
4151
  ] }),
3648
- (documentSlug.trim() || perspective.trim()) && /* @__PURE__ */ jsxs16(Flex12, { align: "center", gap: 1, children: [
3649
- documentSlug.trim() && /* @__PURE__ */ jsxs16(Badge11, { fontSize: 0, tone: "primary", children: [
4152
+ (documentSlug.trim() || perspective.trim()) && /* @__PURE__ */ jsxs20(Flex16, { align: "center", gap: 1, children: [
4153
+ documentSlug.trim() && /* @__PURE__ */ jsxs20(Badge12, { fontSize: 0, tone: "primary", children: [
3650
4154
  "Document: ",
3651
4155
  documentSlug.trim()
3652
4156
  ] }),
3653
- perspective.trim() && /* @__PURE__ */ jsxs16(Badge11, { fontSize: 0, tone: "primary", children: [
4157
+ perspective.trim() && /* @__PURE__ */ jsxs20(Badge12, { fontSize: 0, tone: "primary", children: [
3654
4158
  "Perspective: ",
3655
4159
  perspective.trim()
3656
4160
  ] })
3657
4161
  ] })
3658
4162
  ] }) }),
3659
- /* @__PURE__ */ jsxs16(Flex12, { align: "center", gap: 2, paddingX: 1, wrap: "wrap", children: [
3660
- /* @__PURE__ */ jsx19(Text16, { muted: true, size: 1, children: filteredReports.length === reports.length ? `${reports.length} reports` : `${filteredReports.length} of ${reports.length} reports` }),
3661
- hasActiveFilters && /* @__PURE__ */ jsx19(
4163
+ /* @__PURE__ */ jsxs20(Flex16, { align: "center", gap: 2, paddingX: 1, wrap: "wrap", children: [
4164
+ /* @__PURE__ */ jsx23(Text20, { muted: true, size: 1, children: filteredReports.length === reports.length ? `${reports.length} reports` : `${filteredReports.length} of ${reports.length} reports` }),
4165
+ hasActiveFilters && /* @__PURE__ */ jsx23(
3662
4166
  Button,
3663
4167
  {
3664
4168
  fontSize: 0,
@@ -3668,11 +4172,11 @@ function LatestReports({
3668
4172
  tone: "critical"
3669
4173
  }
3670
4174
  ),
3671
- /* @__PURE__ */ jsxs16(Flex12, { align: "center", gap: 1, style: { marginLeft: "auto" }, children: [
3672
- /* @__PURE__ */ jsx19(
4175
+ /* @__PURE__ */ jsxs20(Flex16, { align: "center", gap: 1, style: { marginLeft: "auto" }, children: [
4176
+ /* @__PURE__ */ jsx23(
3673
4177
  MenuButton,
3674
4178
  {
3675
- button: /* @__PURE__ */ jsx19(
4179
+ button: /* @__PURE__ */ jsx23(
3676
4180
  Button,
3677
4181
  {
3678
4182
  fontSize: 1,
@@ -3682,8 +4186,8 @@ function LatestReports({
3682
4186
  }
3683
4187
  ),
3684
4188
  id: "sort-menu",
3685
- menu: /* @__PURE__ */ jsxs16(Menu, { children: [
3686
- /* @__PURE__ */ jsx19(
4189
+ menu: /* @__PURE__ */ jsxs20(Menu, { children: [
4190
+ /* @__PURE__ */ jsx23(
3687
4191
  MenuItem,
3688
4192
  {
3689
4193
  onClick: () => handleSortFieldChange("date"),
@@ -3691,7 +4195,7 @@ function LatestReports({
3691
4195
  text: "Date"
3692
4196
  }
3693
4197
  ),
3694
- /* @__PURE__ */ jsx19(
4198
+ /* @__PURE__ */ jsx23(
3695
4199
  MenuItem,
3696
4200
  {
3697
4201
  onClick: () => handleSortFieldChange("score"),
@@ -3699,7 +4203,7 @@ function LatestReports({
3699
4203
  text: "Score"
3700
4204
  }
3701
4205
  ),
3702
- /* @__PURE__ */ jsx19(
4206
+ /* @__PURE__ */ jsx23(
3703
4207
  MenuItem,
3704
4208
  {
3705
4209
  onClick: () => handleSortFieldChange("name"),
@@ -3711,7 +4215,7 @@ function LatestReports({
3711
4215
  popover: { portal: true }
3712
4216
  }
3713
4217
  ),
3714
- /* @__PURE__ */ jsx19(
4218
+ /* @__PURE__ */ jsx23(
3715
4219
  Button,
3716
4220
  {
3717
4221
  fontSize: 1,
@@ -3723,9 +4227,9 @@ function LatestReports({
3723
4227
  )
3724
4228
  ] })
3725
4229
  ] }),
3726
- filteredReports.length === 0 ? /* @__PURE__ */ jsx19(Card9, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs16(Stack10, { space: 3, children: [
3727
- /* @__PURE__ */ jsx19(Text16, { align: "center", muted: true, size: 2, children: "No reports match the current filters." }),
3728
- /* @__PURE__ */ jsx19(Flex12, { justify: "center", children: /* @__PURE__ */ jsx19(
4230
+ filteredReports.length === 0 ? /* @__PURE__ */ jsx23(Card12, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs20(Stack13, { space: 3, children: [
4231
+ /* @__PURE__ */ jsx23(Text20, { align: "center", muted: true, size: 2, children: "No reports match the current filters." }),
4232
+ /* @__PURE__ */ jsx23(Flex16, { justify: "center", children: /* @__PURE__ */ jsx23(
3729
4233
  Button,
3730
4234
  {
3731
4235
  fontSize: 1,
@@ -3734,7 +4238,7 @@ function LatestReports({
3734
4238
  text: "Clear all filters"
3735
4239
  }
3736
4240
  ) })
3737
- ] }) }) : /* @__PURE__ */ jsx19(Stack10, { space: 2, children: filteredReports.map((report) => /* @__PURE__ */ jsx19(
4241
+ ] }) }) : /* @__PURE__ */ jsx23(Stack13, { space: 2, children: filteredReports.map((report) => /* @__PURE__ */ jsx23(
3738
4242
  ReportCard,
3739
4243
  {
3740
4244
  data: fromReportListItem(report),
@@ -3742,7 +4246,7 @@ function LatestReports({
3742
4246
  },
3743
4247
  report._id
3744
4248
  )) }),
3745
- hasMore && /* @__PURE__ */ jsx19(Flex12, { justify: "center", paddingY: 3, children: /* @__PURE__ */ jsx19(
4249
+ hasMore && /* @__PURE__ */ jsx23(Flex16, { justify: "center", paddingY: 3, children: /* @__PURE__ */ jsx23(
3746
4250
  Button,
3747
4251
  {
3748
4252
  disabled: loadingMore,
@@ -3790,28 +4294,28 @@ function getDateThreshold(preset) {
3790
4294
 
3791
4295
  // src/components/report-detail/ReportDetail.tsx
3792
4296
  import { ArrowLeftIcon as ArrowLeftIcon2 } from "@sanity/icons";
3793
- import { Box as Box12, Button as Button3, Stack as Stack19, Text as Text26, useToast } from "@sanity/ui";
3794
- import { useCallback as useCallback9, useEffect as useEffect6, useState as useState8 } from "react";
4297
+ import { Box as Box14, Button as Button3, Stack as Stack22, Text as Text30, useToast } from "@sanity/ui";
4298
+ import { useCallback as useCallback12, useEffect as useEffect7, useState as useState8 } from "react";
3795
4299
  import { useClient as useClient6 } from "sanity";
3796
4300
 
3797
4301
  // src/components/report-detail/AreaScoreTable.tsx
3798
4302
  import React from "react";
3799
- import { Card as Card11, Stack as Stack11, Text as Text18 } from "@sanity/ui";
4303
+ import { Card as Card14, Stack as Stack14, Text as Text22 } from "@sanity/ui";
3800
4304
 
3801
4305
  // src/components/primitives/ScoreCell.tsx
3802
- import { Card as Card10, Text as Text17 } from "@sanity/ui";
3803
- import { jsx as jsx20 } from "react/jsx-runtime";
4306
+ import { Card as Card13, Text as Text21 } from "@sanity/ui";
4307
+ import { jsx as jsx24 } from "react/jsx-runtime";
3804
4308
  function ScoreCell({ score, size = 1 }) {
3805
4309
  const rounded = Math.round(score);
3806
- return /* @__PURE__ */ jsx20(Card10, { padding: 1, radius: 2, tone: scoreTone(rounded), children: /* @__PURE__ */ jsx20(Text17, { align: "center", size, weight: "medium", children: rounded }) });
4310
+ return /* @__PURE__ */ jsx24(Card13, { padding: 1, radius: 2, tone: scoreTone(rounded), children: /* @__PURE__ */ jsx24(Text21, { align: "center", size, weight: "medium", children: rounded }) });
3807
4311
  }
3808
4312
 
3809
4313
  // src/components/report-detail/AreaScoreTable.tsx
3810
- import { jsx as jsx21, jsxs as jsxs17 } from "react/jsx-runtime";
4314
+ import { jsx as jsx25, jsxs as jsxs21 } from "react/jsx-runtime";
3811
4315
  function AreaScoreTable({ scores }) {
3812
- return /* @__PURE__ */ jsx21(Card11, { overflow: "auto", padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs17(Stack11, { space: 4, children: [
3813
- /* @__PURE__ */ jsx21(Text18, { size: 2, weight: "semibold", children: "Per-Area Scores" }),
3814
- /* @__PURE__ */ jsxs17(
4316
+ return /* @__PURE__ */ jsx25(Card14, { overflow: "auto", padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs21(Stack14, { space: 4, children: [
4317
+ /* @__PURE__ */ jsx25(Text22, { size: 2, weight: "semibold", children: "Per-Area Scores" }),
4318
+ /* @__PURE__ */ jsxs21(
3815
4319
  "div",
3816
4320
  {
3817
4321
  style: {
@@ -3820,9 +4324,9 @@ function AreaScoreTable({ scores }) {
3820
4324
  gridTemplateColumns: "2fr 1fr 1fr 1fr 1fr 1fr 1fr"
3821
4325
  },
3822
4326
  children: [
3823
- /* @__PURE__ */ jsx21(ColumnHeader, { borderBottom: true, label: "Area" }),
3824
- /* @__PURE__ */ jsx21(ColumnHeader, { borderBottom: true, label: "Score", tooltip: GLOSSARY.score }),
3825
- /* @__PURE__ */ jsx21(
4327
+ /* @__PURE__ */ jsx25(ColumnHeader, { borderBottom: true, label: "Area" }),
4328
+ /* @__PURE__ */ jsx25(ColumnHeader, { borderBottom: true, label: "Score", tooltip: GLOSSARY.score }),
4329
+ /* @__PURE__ */ jsx25(
3826
4330
  ColumnHeader,
3827
4331
  {
3828
4332
  borderBottom: true,
@@ -3830,7 +4334,7 @@ function AreaScoreTable({ scores }) {
3830
4334
  tooltip: GLOSSARY.taskCompletion
3831
4335
  }
3832
4336
  ),
3833
- /* @__PURE__ */ jsx21(
4337
+ /* @__PURE__ */ jsx25(
3834
4338
  ColumnHeader,
3835
4339
  {
3836
4340
  borderBottom: true,
@@ -3838,7 +4342,7 @@ function AreaScoreTable({ scores }) {
3838
4342
  tooltip: GLOSSARY.codeCorrectness
3839
4343
  }
3840
4344
  ),
3841
- /* @__PURE__ */ jsx21(
4345
+ /* @__PURE__ */ jsx25(
3842
4346
  ColumnHeader,
3843
4347
  {
3844
4348
  borderBottom: true,
@@ -3846,10 +4350,10 @@ function AreaScoreTable({ scores }) {
3846
4350
  tooltip: GLOSSARY.docCoverage
3847
4351
  }
3848
4352
  ),
3849
- /* @__PURE__ */ jsx21(ColumnHeader, { borderBottom: true, label: "Lift", tooltip: GLOSSARY.docLift }),
3850
- /* @__PURE__ */ jsx21(ColumnHeader, { borderBottom: true, label: "Tests", tooltip: GLOSSARY.tests }),
3851
- scores.map((score, i) => /* @__PURE__ */ jsxs17(React.Fragment, { children: [
3852
- /* @__PURE__ */ jsx21(
4353
+ /* @__PURE__ */ jsx25(ColumnHeader, { borderBottom: true, label: "Lift", tooltip: GLOSSARY.docLift }),
4354
+ /* @__PURE__ */ jsx25(ColumnHeader, { borderBottom: true, label: "Tests", tooltip: GLOSSARY.tests }),
4355
+ scores.map((score, i) => /* @__PURE__ */ jsxs21(React.Fragment, { children: [
4356
+ /* @__PURE__ */ jsx25(
3853
4357
  "div",
3854
4358
  {
3855
4359
  style: {
@@ -3857,14 +4361,14 @@ function AreaScoreTable({ scores }) {
3857
4361
  borderRadius: 4,
3858
4362
  padding: "8px 0 8px 4px"
3859
4363
  },
3860
- children: /* @__PURE__ */ jsx21(Text18, { size: 1, weight: "medium", children: score.feature })
4364
+ children: /* @__PURE__ */ jsx25(Text22, { size: 1, weight: "medium", children: score.feature })
3861
4365
  }
3862
4366
  ),
3863
- /* @__PURE__ */ jsx21("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx21(ScoreCell, { score: score.totalScore }) }),
3864
- /* @__PURE__ */ jsx21("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx21(ScoreCell, { score: score.taskCompletion }) }),
3865
- /* @__PURE__ */ jsx21("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx21(ScoreCell, { score: score.codeCorrectness }) }),
3866
- /* @__PURE__ */ jsx21("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx21(ScoreCell, { score: score.docCoverage }) }),
3867
- /* @__PURE__ */ jsx21(
4367
+ /* @__PURE__ */ jsx25("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx25(ScoreCell, { score: score.totalScore }) }),
4368
+ /* @__PURE__ */ jsx25("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx25(ScoreCell, { score: score.taskCompletion }) }),
4369
+ /* @__PURE__ */ jsx25("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx25(ScoreCell, { score: score.codeCorrectness }) }),
4370
+ /* @__PURE__ */ jsx25("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx25(ScoreCell, { score: score.docCoverage }) }),
4371
+ /* @__PURE__ */ jsx25(
3868
4372
  "div",
3869
4373
  {
3870
4374
  style: {
@@ -3872,10 +4376,10 @@ function AreaScoreTable({ scores }) {
3872
4376
  background: rowBackground(i),
3873
4377
  display: "flex"
3874
4378
  },
3875
- children: /* @__PURE__ */ jsx21(Text18, { size: 1, children: formatDelta(score.docLift) })
4379
+ children: /* @__PURE__ */ jsx25(Text22, { size: 1, children: formatDelta(score.docLift) })
3876
4380
  }
3877
4381
  ),
3878
- /* @__PURE__ */ jsx21(
4382
+ /* @__PURE__ */ jsx25(
3879
4383
  "div",
3880
4384
  {
3881
4385
  style: {
@@ -3883,7 +4387,7 @@ function AreaScoreTable({ scores }) {
3883
4387
  background: rowBackground(i),
3884
4388
  display: "flex"
3885
4389
  },
3886
- children: /* @__PURE__ */ jsx21(Text18, { muted: true, size: 1, children: score.testCount })
4390
+ children: /* @__PURE__ */ jsx25(Text22, { muted: true, size: 1, children: score.testCount })
3887
4391
  }
3888
4392
  )
3889
4393
  ] }, score.feature))
@@ -3894,13 +4398,13 @@ function AreaScoreTable({ scores }) {
3894
4398
  }
3895
4399
 
3896
4400
  // src/components/report-detail/ComparisonSummary.tsx
3897
- import { Badge as Badge12, Box as Box7, Card as Card12, Flex as Flex13, Grid as Grid2, Stack as Stack12, Text as Text19, Tooltip as Tooltip3 } from "@sanity/ui";
3898
- import { jsx as jsx22, jsxs as jsxs18 } from "react/jsx-runtime";
4401
+ import { Badge as Badge13, Box as Box9, Card as Card15, Flex as Flex17, Grid as Grid2, Stack as Stack15, Text as Text23, Tooltip as Tooltip3 } from "@sanity/ui";
4402
+ import { jsx as jsx26, jsxs as jsxs22 } from "react/jsx-runtime";
3899
4403
  function ComparisonSummary({ comparison }) {
3900
- return /* @__PURE__ */ jsx22(Card12, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs18(Stack12, { space: 4, children: [
3901
- /* @__PURE__ */ jsxs18(Flex13, { align: "center", gap: 3, wrap: "wrap", children: [
3902
- /* @__PURE__ */ jsx22(Text19, { size: 2, weight: "semibold", children: "Comparison" }),
3903
- /* @__PURE__ */ jsx22(
4404
+ return /* @__PURE__ */ jsx26(Card15, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs22(Stack15, { space: 4, children: [
4405
+ /* @__PURE__ */ jsxs22(Flex17, { align: "center", gap: 3, wrap: "wrap", children: [
4406
+ /* @__PURE__ */ jsx26(Text23, { size: 2, weight: "semibold", children: "Comparison" }),
4407
+ /* @__PURE__ */ jsx26(
3904
4408
  DeltaCard,
3905
4409
  {
3906
4410
  delta: comparison.deltas.overall,
@@ -3908,7 +4412,7 @@ function ComparisonSummary({ comparison }) {
3908
4412
  tooltip: GLOSSARY.overallDelta
3909
4413
  }
3910
4414
  ),
3911
- comparison.deltas.actualDelta != null && /* @__PURE__ */ jsx22(
4415
+ comparison.deltas.actualDelta != null && /* @__PURE__ */ jsx26(
3912
4416
  DeltaCard,
3913
4417
  {
3914
4418
  delta: comparison.deltas.actualDelta,
@@ -3916,7 +4420,7 @@ function ComparisonSummary({ comparison }) {
3916
4420
  tooltip: GLOSSARY.actualDelta
3917
4421
  }
3918
4422
  ),
3919
- comparison.deltas.retrievalGapDelta != null && /* @__PURE__ */ jsx22(
4423
+ comparison.deltas.retrievalGapDelta != null && /* @__PURE__ */ jsx26(
3920
4424
  DeltaCard,
3921
4425
  {
3922
4426
  delta: comparison.deltas.retrievalGapDelta,
@@ -3926,8 +4430,8 @@ function ComparisonSummary({ comparison }) {
3926
4430
  }
3927
4431
  )
3928
4432
  ] }),
3929
- /* @__PURE__ */ jsxs18(Grid2, { columns: [1, 1, 3], gap: 3, children: [
3930
- comparison.improved.length > 0 && /* @__PURE__ */ jsx22(
4433
+ /* @__PURE__ */ jsxs22(Grid2, { columns: [1, 1, 3], gap: 3, children: [
4434
+ comparison.improved.length > 0 && /* @__PURE__ */ jsx26(
3931
4435
  AreaBadgeGroup,
3932
4436
  {
3933
4437
  areas: comparison.improved,
@@ -3935,7 +4439,7 @@ function ComparisonSummary({ comparison }) {
3935
4439
  tone: "positive"
3936
4440
  }
3937
4441
  ),
3938
- comparison.regressed.length > 0 && /* @__PURE__ */ jsx22(
4442
+ comparison.regressed.length > 0 && /* @__PURE__ */ jsx26(
3939
4443
  AreaBadgeGroup,
3940
4444
  {
3941
4445
  areas: comparison.regressed,
@@ -3943,7 +4447,7 @@ function ComparisonSummary({ comparison }) {
3943
4447
  tone: "critical"
3944
4448
  }
3945
4449
  ),
3946
- comparison.unchanged.length > 0 && /* @__PURE__ */ jsx22(
4450
+ comparison.unchanged.length > 0 && /* @__PURE__ */ jsx26(
3947
4451
  AreaBadgeGroup,
3948
4452
  {
3949
4453
  areas: comparison.unchanged,
@@ -3962,19 +4466,19 @@ function DeltaCard({
3962
4466
  }) {
3963
4467
  const isPositive = invertedPolarity ? delta < 0 : delta > 0;
3964
4468
  const isNegative = invertedPolarity ? delta > 0 : delta < 0;
3965
- return /* @__PURE__ */ jsx22(
4469
+ return /* @__PURE__ */ jsx26(
3966
4470
  Tooltip3,
3967
4471
  {
3968
- content: /* @__PURE__ */ jsx22(Box7, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx22(Text19, { size: 1, children: tooltip }) }),
4472
+ content: /* @__PURE__ */ jsx26(Box9, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx26(Text23, { size: 1, children: tooltip }) }),
3969
4473
  placement: "bottom",
3970
4474
  portal: true,
3971
- children: /* @__PURE__ */ jsx22(
3972
- Card12,
4475
+ children: /* @__PURE__ */ jsx26(
4476
+ Card15,
3973
4477
  {
3974
4478
  padding: 2,
3975
4479
  radius: 2,
3976
4480
  tone: isPositive ? "positive" : isNegative ? "critical" : "default",
3977
- children: /* @__PURE__ */ jsxs18(Text19, { size: 1, weight: "bold", children: [
4481
+ children: /* @__PURE__ */ jsxs22(Text23, { size: 1, weight: "bold", children: [
3978
4482
  formatDelta(delta),
3979
4483
  " ",
3980
4484
  label
@@ -3989,9 +4493,9 @@ function AreaBadgeGroup({
3989
4493
  label,
3990
4494
  tone
3991
4495
  }) {
3992
- return /* @__PURE__ */ jsxs18(Stack12, { space: 2, children: [
3993
- /* @__PURE__ */ jsx22(
3994
- Text19,
4496
+ return /* @__PURE__ */ jsxs22(Stack15, { space: 2, children: [
4497
+ /* @__PURE__ */ jsx26(
4498
+ Text23,
3995
4499
  {
3996
4500
  muted: true,
3997
4501
  size: 0,
@@ -4000,21 +4504,21 @@ function AreaBadgeGroup({
4000
4504
  children: label
4001
4505
  }
4002
4506
  ),
4003
- /* @__PURE__ */ jsx22(Flex13, { gap: 1, wrap: "wrap", children: areas.map((a) => /* @__PURE__ */ jsx22(Badge12, { tone, children: a }, a)) })
4507
+ /* @__PURE__ */ jsx26(Flex17, { gap: 1, wrap: "wrap", children: areas.map((a) => /* @__PURE__ */ jsx26(Badge13, { tone, children: a }, a)) })
4004
4508
  ] });
4005
4509
  }
4006
4510
 
4007
4511
  // src/components/report-detail/JudgmentList.tsx
4008
4512
  import { useState as useState7 } from "react";
4009
- import { HelpCircleIcon as HelpCircleIcon2 } from "@sanity/icons";
4010
- import { Badge as Badge13, Box as Box8, Card as Card13, Flex as Flex14, Stack as Stack13, Text as Text20, Tooltip as Tooltip4 } from "@sanity/ui";
4513
+ import { HelpCircleIcon as HelpCircleIcon4 } from "@sanity/icons";
4514
+ import { Badge as Badge14, Box as Box10, Card as Card16, Flex as Flex18, Stack as Stack16, Text as Text24, Tooltip as Tooltip4 } from "@sanity/ui";
4011
4515
 
4012
4516
  // src/components/primitives/InlineCode.tsx
4013
- import { Fragment as Fragment2, jsx as jsx23 } from "react/jsx-runtime";
4517
+ import { Fragment as Fragment4, jsx as jsx27 } from "react/jsx-runtime";
4014
4518
  function InlineCode({ text }) {
4015
4519
  const parts = text.split(/`([^`]+)`/);
4016
- return /* @__PURE__ */ jsx23(Fragment2, { children: parts.map(
4017
- (part, i) => i % 2 === 1 ? /* @__PURE__ */ jsx23(
4520
+ return /* @__PURE__ */ jsx27(Fragment4, { children: parts.map(
4521
+ (part, i) => i % 2 === 1 ? /* @__PURE__ */ jsx27(
4018
4522
  "code",
4019
4523
  {
4020
4524
  style: {
@@ -4026,12 +4530,12 @@ function InlineCode({ text }) {
4026
4530
  children: part
4027
4531
  },
4028
4532
  i
4029
- ) : /* @__PURE__ */ jsx23("span", { children: part }, i)
4533
+ ) : /* @__PURE__ */ jsx27("span", { children: part }, i)
4030
4534
  ) });
4031
4535
  }
4032
4536
 
4033
4537
  // src/components/report-detail/JudgmentList.tsx
4034
- import { jsx as jsx24, jsxs as jsxs19 } from "react/jsx-runtime";
4538
+ import { jsx as jsx28, jsxs as jsxs23 } from "react/jsx-runtime";
4035
4539
  function groupByArea(judgments) {
4036
4540
  const byArea = /* @__PURE__ */ new Map();
4037
4541
  for (const j of judgments) {
@@ -4046,36 +4550,36 @@ var DIMENSION_LABELS = DIMENSION_LABELS_KEBAB;
4046
4550
  function JudgmentList({ judgments }) {
4047
4551
  if (judgments.length === 0) return null;
4048
4552
  const grouped = groupByArea(judgments);
4049
- return /* @__PURE__ */ jsx24(Card13, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs19(Stack13, { space: 4, children: [
4050
- /* @__PURE__ */ jsxs19(Flex14, { align: "center", gap: 3, wrap: "wrap", children: [
4051
- /* @__PURE__ */ jsx24(Text20, { size: 2, weight: "semibold", children: "Low-Scoring Judgments" }),
4052
- /* @__PURE__ */ jsx24(
4553
+ return /* @__PURE__ */ jsx28(Card16, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs23(Stack16, { space: 4, children: [
4554
+ /* @__PURE__ */ jsxs23(Flex18, { align: "center", gap: 3, wrap: "wrap", children: [
4555
+ /* @__PURE__ */ jsx28(Text24, { size: 2, weight: "semibold", children: "Low-Scoring Judgments" }),
4556
+ /* @__PURE__ */ jsx28(
4053
4557
  Tooltip4,
4054
4558
  {
4055
- content: /* @__PURE__ */ jsx24(Box8, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx24(Text20, { size: 1, children: GLOSSARY.lowScoringJudgments }) }),
4559
+ content: /* @__PURE__ */ jsx28(Box10, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx28(Text24, { size: 1, children: GLOSSARY.lowScoringJudgments }) }),
4056
4560
  placement: "bottom",
4057
4561
  portal: true,
4058
- children: /* @__PURE__ */ jsx24(Text20, { muted: true, size: 0, children: /* @__PURE__ */ jsx24(HelpCircleIcon2, {}) })
4562
+ children: /* @__PURE__ */ jsx28(Text24, { muted: true, size: 0, children: /* @__PURE__ */ jsx28(HelpCircleIcon4, {}) })
4059
4563
  }
4060
4564
  ),
4061
- /* @__PURE__ */ jsx24(Card13, { padding: 2, radius: 2, tone: "critical", children: /* @__PURE__ */ jsxs19(Text20, { size: 1, weight: "bold", children: [
4565
+ /* @__PURE__ */ jsx28(Card16, { padding: 2, radius: 2, tone: "critical", children: /* @__PURE__ */ jsxs23(Text24, { size: 1, weight: "bold", children: [
4062
4566
  judgments.length,
4063
4567
  " judgment",
4064
4568
  judgments.length === 1 ? "" : "s",
4065
4569
  " below 70"
4066
4570
  ] }) })
4067
4571
  ] }),
4068
- grouped.map(([area, areaJudgments]) => /* @__PURE__ */ jsx24(Card13, { padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsxs19(Stack13, { space: 3, children: [
4069
- /* @__PURE__ */ jsxs19(Text20, { size: 1, weight: "semibold", children: [
4572
+ grouped.map(([area, areaJudgments]) => /* @__PURE__ */ jsx28(Card16, { padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsxs23(Stack16, { space: 3, children: [
4573
+ /* @__PURE__ */ jsxs23(Text24, { size: 1, weight: "semibold", children: [
4070
4574
  area,
4071
4575
  " ",
4072
- /* @__PURE__ */ jsxs19(Text20, { muted: true, size: 1, weight: "regular", as: "span", children: [
4576
+ /* @__PURE__ */ jsxs23(Text24, { muted: true, size: 1, weight: "regular", as: "span", children: [
4073
4577
  "(",
4074
4578
  areaJudgments.length,
4075
4579
  ")"
4076
4580
  ] })
4077
4581
  ] }),
4078
- areaJudgments.map((j, i) => /* @__PURE__ */ jsx24(JudgmentCard, { judgment: j }, `${area}-${i}`))
4582
+ areaJudgments.map((j, i) => /* @__PURE__ */ jsx28(JudgmentCard, { judgment: j }, `${area}-${i}`))
4079
4583
  ] }) }, area))
4080
4584
  ] }) });
4081
4585
  }
@@ -4084,18 +4588,18 @@ function JudgmentCard({ judgment }) {
4084
4588
  const dimLabel = DIMENSION_LABELS[judgment.dimension] ?? judgment.dimension;
4085
4589
  const sep = judgment.taskId.indexOf(" - ");
4086
4590
  const taskName = sep > 0 ? judgment.taskId.substring(sep + 3) : judgment.taskId;
4087
- return /* @__PURE__ */ jsx24(
4088
- Card13,
4591
+ return /* @__PURE__ */ jsx28(
4592
+ Card16,
4089
4593
  {
4090
4594
  padding: 3,
4091
4595
  radius: 2,
4092
4596
  shadow: 1,
4093
4597
  style: { cursor: "pointer" },
4094
4598
  onClick: () => setExpanded(!expanded),
4095
- children: /* @__PURE__ */ jsxs19(Stack13, { space: 3, children: [
4096
- /* @__PURE__ */ jsxs19(Flex14, { align: "center", gap: 2, wrap: "wrap", children: [
4097
- /* @__PURE__ */ jsx24(Card13, { padding: 2, radius: 2, tone: scoreTone(judgment.score), children: /* @__PURE__ */ jsx24(
4098
- Text20,
4599
+ children: /* @__PURE__ */ jsxs23(Stack16, { space: 3, children: [
4600
+ /* @__PURE__ */ jsxs23(Flex18, { align: "center", gap: 2, wrap: "wrap", children: [
4601
+ /* @__PURE__ */ jsx28(Card16, { padding: 2, radius: 2, tone: scoreTone(judgment.score), children: /* @__PURE__ */ jsx28(
4602
+ Text24,
4099
4603
  {
4100
4604
  align: "center",
4101
4605
  size: 1,
@@ -4104,32 +4608,32 @@ function JudgmentCard({ judgment }) {
4104
4608
  children: judgment.score
4105
4609
  }
4106
4610
  ) }),
4107
- /* @__PURE__ */ jsx24(Badge13, { tone: "default", children: dimLabel }),
4108
- /* @__PURE__ */ jsx24(Text20, { size: 1, weight: "medium", children: taskName }),
4109
- /* @__PURE__ */ jsx24(Text20, { muted: true, size: 0, children: judgment.modelId }),
4110
- /* @__PURE__ */ jsx24(Text20, { muted: true, size: 0, style: { marginLeft: "auto" }, children: expanded ? "\u25B2" : "\u25BC" })
4611
+ /* @__PURE__ */ jsx28(Badge14, { tone: "default", children: dimLabel }),
4612
+ /* @__PURE__ */ jsx28(Text24, { size: 1, weight: "medium", children: taskName }),
4613
+ /* @__PURE__ */ jsx28(Text24, { muted: true, size: 0, children: judgment.modelId }),
4614
+ /* @__PURE__ */ jsx28(Text24, { muted: true, size: 0, style: { marginLeft: "auto" }, children: expanded ? "\u25B2" : "\u25BC" })
4111
4615
  ] }),
4112
- expanded && /* @__PURE__ */ jsxs19(Stack13, { space: 3, children: [
4113
- /* @__PURE__ */ jsx24(Card13, { padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsx24(
4114
- Text20,
4616
+ expanded && /* @__PURE__ */ jsxs23(Stack16, { space: 3, children: [
4617
+ /* @__PURE__ */ jsx28(Card16, { padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsx28(
4618
+ Text24,
4115
4619
  {
4116
4620
  muted: true,
4117
4621
  size: 1,
4118
4622
  style: { lineHeight: 1.6, whiteSpace: "pre-wrap" },
4119
- children: /* @__PURE__ */ jsx24(InlineCode, { text: judgment.reason })
4623
+ children: /* @__PURE__ */ jsx28(InlineCode, { text: judgment.reason })
4120
4624
  }
4121
4625
  ) }),
4122
- judgment.canonicalDocs && judgment.canonicalDocs.length > 0 && /* @__PURE__ */ jsxs19(Flex14, { align: "center", gap: 2, wrap: "wrap", children: [
4123
- /* @__PURE__ */ jsx24(Text20, { muted: true, size: 0, children: "Docs:" }),
4626
+ judgment.canonicalDocs && judgment.canonicalDocs.length > 0 && /* @__PURE__ */ jsxs23(Flex18, { align: "center", gap: 2, wrap: "wrap", children: [
4627
+ /* @__PURE__ */ jsx28(Text24, { muted: true, size: 0, children: "Docs:" }),
4124
4628
  judgment.canonicalDocs.map((doc) => {
4125
- const badge = /* @__PURE__ */ jsx24(Badge13, { mode: "outline", tone: "primary", children: doc.slug });
4126
- return /* @__PURE__ */ jsx24(
4629
+ const badge = /* @__PURE__ */ jsx28(Badge14, { mode: "outline", tone: "primary", children: doc.slug });
4630
+ return /* @__PURE__ */ jsx28(
4127
4631
  Tooltip4,
4128
4632
  {
4129
- content: /* @__PURE__ */ jsx24(Box8, { padding: 2, children: /* @__PURE__ */ jsx24(Text20, { size: 1, children: doc.title || doc.slug }) }),
4633
+ content: /* @__PURE__ */ jsx28(Box10, { padding: 2, children: /* @__PURE__ */ jsx28(Text24, { size: 1, children: doc.title || doc.slug }) }),
4130
4634
  placement: "bottom",
4131
4635
  portal: true,
4132
- children: doc.documentId ? /* @__PURE__ */ jsx24(
4636
+ children: doc.documentId ? /* @__PURE__ */ jsx28(
4133
4637
  "a",
4134
4638
  {
4135
4639
  href: `/intent/edit/id=${doc.documentId}`,
@@ -4153,9 +4657,9 @@ function JudgmentCard({ judgment }) {
4153
4657
  import { Grid as Grid3 } from "@sanity/ui";
4154
4658
 
4155
4659
  // src/components/primitives/StatCard.tsx
4156
- import { HelpCircleIcon as HelpCircleIcon3 } from "@sanity/icons";
4157
- import { Box as Box9, Card as Card14, Stack as Stack14, Text as Text21, Tooltip as Tooltip5 } from "@sanity/ui";
4158
- import { Fragment as Fragment3, jsx as jsx25, jsxs as jsxs20 } from "react/jsx-runtime";
4660
+ import { HelpCircleIcon as HelpCircleIcon5 } from "@sanity/icons";
4661
+ import { Box as Box11, Card as Card17, Stack as Stack17, Text as Text25, Tooltip as Tooltip5 } from "@sanity/ui";
4662
+ import { Fragment as Fragment5, jsx as jsx29, jsxs as jsxs24 } from "react/jsx-runtime";
4159
4663
  function StatCard({
4160
4664
  label,
4161
4665
  value,
@@ -4163,24 +4667,24 @@ function StatCard({
4163
4667
  suffix,
4164
4668
  tone = "default"
4165
4669
  }) {
4166
- return /* @__PURE__ */ jsx25(Card14, { padding: 3, radius: 2, shadow: 1, tone, children: /* @__PURE__ */ jsxs20(Stack14, { space: 2, children: [
4167
- /* @__PURE__ */ jsxs20(Text21, { muted: true, size: 1, children: [
4670
+ return /* @__PURE__ */ jsx29(Card17, { padding: 3, radius: 2, shadow: 1, tone, children: /* @__PURE__ */ jsxs24(Stack17, { space: 2, children: [
4671
+ /* @__PURE__ */ jsxs24(Text25, { muted: true, size: 1, children: [
4168
4672
  label,
4169
- tooltip && /* @__PURE__ */ jsxs20(Fragment3, { children: [
4673
+ tooltip && /* @__PURE__ */ jsxs24(Fragment5, { children: [
4170
4674
  " ",
4171
- /* @__PURE__ */ jsx25(
4675
+ /* @__PURE__ */ jsx29(
4172
4676
  Tooltip5,
4173
4677
  {
4174
- content: /* @__PURE__ */ jsx25(Box9, { padding: 2, children: /* @__PURE__ */ jsx25(Text21, { size: 1, children: tooltip }) }),
4678
+ content: /* @__PURE__ */ jsx29(Box11, { padding: 2, children: /* @__PURE__ */ jsx29(Text25, { size: 1, children: tooltip }) }),
4175
4679
  portal: true,
4176
- children: /* @__PURE__ */ jsx25("span", { style: { cursor: "help" }, children: /* @__PURE__ */ jsx25(HelpCircleIcon3, {}) })
4680
+ children: /* @__PURE__ */ jsx29("span", { style: { cursor: "help" }, children: /* @__PURE__ */ jsx29(HelpCircleIcon5, {}) })
4177
4681
  }
4178
4682
  )
4179
4683
  ] })
4180
4684
  ] }),
4181
- /* @__PURE__ */ jsxs20(Text21, { size: 3, weight: "bold", children: [
4685
+ /* @__PURE__ */ jsxs24(Text25, { size: 3, weight: "bold", children: [
4182
4686
  value,
4183
- suffix && /* @__PURE__ */ jsxs20("span", { style: { fontSize: "0.6em", fontWeight: 400 }, children: [
4687
+ suffix && /* @__PURE__ */ jsxs24("span", { style: { fontSize: "0.6em", fontWeight: 400 }, children: [
4184
4688
  " ",
4185
4689
  suffix
4186
4690
  ] })
@@ -4189,7 +4693,7 @@ function StatCard({
4189
4693
  }
4190
4694
 
4191
4695
  // src/components/report-detail/OverviewStats.tsx
4192
- import { jsx as jsx26, jsxs as jsxs21 } from "react/jsx-runtime";
4696
+ import { jsx as jsx30, jsxs as jsxs25 } from "react/jsx-runtime";
4193
4697
  function OverviewStats({
4194
4698
  overall,
4195
4699
  durationMs,
@@ -4197,8 +4701,8 @@ function OverviewStats({
4197
4701
  isFullMode
4198
4702
  }) {
4199
4703
  const overallTone = scoreTone(overall.avgScore);
4200
- return /* @__PURE__ */ jsxs21(Grid3, { columns: [1, 1, 2, isFullMode ? 4 : 4], gap: 3, children: [
4201
- /* @__PURE__ */ jsx26(
4704
+ return /* @__PURE__ */ jsxs25(Grid3, { columns: [1, 1, 2, isFullMode ? 4 : 4], gap: 3, children: [
4705
+ /* @__PURE__ */ jsx30(
4202
4706
  StatCard,
4203
4707
  {
4204
4708
  label: "Overall Score",
@@ -4207,7 +4711,7 @@ function OverviewStats({
4207
4711
  value: overall.avgScore.toFixed(1)
4208
4712
  }
4209
4713
  ),
4210
- /* @__PURE__ */ jsx26(
4714
+ /* @__PURE__ */ jsx30(
4211
4715
  StatCard,
4212
4716
  {
4213
4717
  label: "Doc Lift",
@@ -4216,7 +4720,7 @@ function OverviewStats({
4216
4720
  value: overall.avgDocLift.toFixed(1)
4217
4721
  }
4218
4722
  ),
4219
- isFullMode && overall.avgActualScore != null && /* @__PURE__ */ jsx26(
4723
+ isFullMode && overall.avgActualScore != null && /* @__PURE__ */ jsx30(
4220
4724
  StatCard,
4221
4725
  {
4222
4726
  label: "Actual Score",
@@ -4225,7 +4729,7 @@ function OverviewStats({
4225
4729
  value: overall.avgActualScore.toFixed(1)
4226
4730
  }
4227
4731
  ),
4228
- isFullMode && overall.avgRetrievalGap != null && /* @__PURE__ */ jsx26(
4732
+ isFullMode && overall.avgRetrievalGap != null && /* @__PURE__ */ jsx30(
4229
4733
  StatCard,
4230
4734
  {
4231
4735
  label: "Retrieval Gap",
@@ -4235,7 +4739,7 @@ function OverviewStats({
4235
4739
  value: overall.avgRetrievalGap.toFixed(1)
4236
4740
  }
4237
4741
  ),
4238
- isFullMode && overall.avgInfrastructureEfficiency != null && /* @__PURE__ */ jsx26(
4742
+ isFullMode && overall.avgInfrastructureEfficiency != null && /* @__PURE__ */ jsx30(
4239
4743
  StatCard,
4240
4744
  {
4241
4745
  label: "Infra Efficiency",
@@ -4243,8 +4747,8 @@ function OverviewStats({
4243
4747
  value: formatPercent(overall.avgInfrastructureEfficiency)
4244
4748
  }
4245
4749
  ),
4246
- /* @__PURE__ */ jsx26(StatCard, { label: "Duration", value: formatDuration(durationMs) }),
4247
- /* @__PURE__ */ jsx26(
4750
+ /* @__PURE__ */ jsx30(StatCard, { label: "Duration", value: formatDuration(durationMs) }),
4751
+ /* @__PURE__ */ jsx30(
4248
4752
  StatCard,
4249
4753
  {
4250
4754
  label: "Tests",
@@ -4256,31 +4760,31 @@ function OverviewStats({
4256
4760
  }
4257
4761
 
4258
4762
  // src/components/report-detail/ProvenanceCard.tsx
4259
- import { Card as Card15, Flex as Flex15, Grid as Grid4, Stack as Stack15, Text as Text22 } from "@sanity/ui";
4260
- import { jsx as jsx27, jsxs as jsxs22 } from "react/jsx-runtime";
4763
+ import { Card as Card18, Flex as Flex19, Grid as Grid4, Stack as Stack18, Text as Text26 } from "@sanity/ui";
4764
+ import { jsx as jsx31, jsxs as jsxs26 } from "react/jsx-runtime";
4261
4765
  var VIEWABLE_PROMPTFOO_MODES = /* @__PURE__ */ new Set(["agentic", "observed"]);
4262
4766
  function ProvenanceCard({ provenance }) {
4263
- return /* @__PURE__ */ jsx27(Card15, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs22(Stack15, { space: 4, children: [
4264
- /* @__PURE__ */ jsx27(Text22, { size: 2, weight: "semibold", children: "Provenance" }),
4265
- /* @__PURE__ */ jsxs22(Grid4, { columns: [1, 2, 3], gap: 4, children: [
4266
- /* @__PURE__ */ jsx27(Field, { label: "Mode", value: provenance.mode }),
4267
- /* @__PURE__ */ jsx27(Field, { label: "Source", value: provenance.source.name }),
4268
- /* @__PURE__ */ jsx27(
4767
+ return /* @__PURE__ */ jsx31(Card18, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs26(Stack18, { space: 4, children: [
4768
+ /* @__PURE__ */ jsx31(Text26, { size: 2, weight: "semibold", children: "Provenance" }),
4769
+ /* @__PURE__ */ jsxs26(Grid4, { columns: [1, 2, 3], gap: 4, children: [
4770
+ /* @__PURE__ */ jsx31(Field, { label: "Mode", value: provenance.mode }),
4771
+ /* @__PURE__ */ jsx31(Field, { label: "Source", value: provenance.source.name }),
4772
+ /* @__PURE__ */ jsx31(
4269
4773
  Field,
4270
4774
  {
4271
4775
  label: "Trigger",
4272
4776
  value: provenance.trigger.type + (provenance.trigger.workflow ? ` (${provenance.trigger.workflow})` : "")
4273
4777
  }
4274
4778
  ),
4275
- /* @__PURE__ */ jsx27(
4779
+ /* @__PURE__ */ jsx31(
4276
4780
  Field,
4277
4781
  {
4278
4782
  label: "Models",
4279
4783
  value: provenance.models.map((m) => m.label).join(", ")
4280
4784
  }
4281
4785
  ),
4282
- /* @__PURE__ */ jsx27(Field, { label: "Grader Model", mono: true, value: provenance.graderModel }),
4283
- provenance.contextHash && /* @__PURE__ */ jsx27(
4786
+ /* @__PURE__ */ jsx31(Field, { label: "Grader Model", mono: true, value: provenance.graderModel }),
4787
+ provenance.contextHash && /* @__PURE__ */ jsx31(
4284
4788
  Field,
4285
4789
  {
4286
4790
  label: "Context Hash",
@@ -4289,8 +4793,8 @@ function ProvenanceCard({ provenance }) {
4289
4793
  }
4290
4794
  )
4291
4795
  ] }),
4292
- provenance.git && /* @__PURE__ */ jsx27(GitInfo, { git: provenance.git }),
4293
- /* @__PURE__ */ jsx27(PromptfooLinks, { provenance })
4796
+ provenance.git && /* @__PURE__ */ jsx31(GitInfo, { git: provenance.git }),
4797
+ /* @__PURE__ */ jsx31(PromptfooLinks, { provenance })
4294
4798
  ] }) });
4295
4799
  }
4296
4800
  function Field({
@@ -4298,9 +4802,9 @@ function Field({
4298
4802
  mono,
4299
4803
  value
4300
4804
  }) {
4301
- return /* @__PURE__ */ jsxs22(Stack15, { space: 1, children: [
4302
- /* @__PURE__ */ jsx27(
4303
- Text22,
4805
+ return /* @__PURE__ */ jsxs26(Stack18, { space: 1, children: [
4806
+ /* @__PURE__ */ jsx31(
4807
+ Text26,
4304
4808
  {
4305
4809
  muted: true,
4306
4810
  size: 0,
@@ -4309,19 +4813,19 @@ function Field({
4309
4813
  children: label
4310
4814
  }
4311
4815
  ),
4312
- /* @__PURE__ */ jsx27(Text22, { size: 1, style: mono ? { fontFamily: "monospace" } : void 0, children: value })
4816
+ /* @__PURE__ */ jsx31(Text26, { size: 1, style: mono ? { fontFamily: "monospace" } : void 0, children: value })
4313
4817
  ] });
4314
4818
  }
4315
4819
  function GitInfo({ git }) {
4316
- return /* @__PURE__ */ jsx27(Card15, { border: true, padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsxs22(Flex15, { align: "center", gap: 3, wrap: "wrap", children: [
4317
- /* @__PURE__ */ jsx27(Text22, { muted: true, size: 1, weight: "semibold", children: "Git" }),
4318
- /* @__PURE__ */ jsxs22(Text22, { size: 1, children: [
4820
+ return /* @__PURE__ */ jsx31(Card18, { border: true, padding: 3, radius: 2, tone: "transparent", children: /* @__PURE__ */ jsxs26(Flex19, { align: "center", gap: 3, wrap: "wrap", children: [
4821
+ /* @__PURE__ */ jsx31(Text26, { muted: true, size: 1, weight: "semibold", children: "Git" }),
4822
+ /* @__PURE__ */ jsxs26(Text26, { size: 1, children: [
4319
4823
  git.repo,
4320
4824
  " / ",
4321
4825
  git.branch
4322
4826
  ] }),
4323
- /* @__PURE__ */ jsx27(Text22, { muted: true, size: 1, style: { fontFamily: "monospace" }, children: git.sha.slice(0, 12) }),
4324
- git.prNumber && /* @__PURE__ */ jsx27(Text22, { size: 1, children: /* @__PURE__ */ jsxs22(
4827
+ /* @__PURE__ */ jsx31(Text26, { muted: true, size: 1, style: { fontFamily: "monospace" }, children: git.sha.slice(0, 12) }),
4828
+ git.prNumber && /* @__PURE__ */ jsx31(Text26, { size: 1, children: /* @__PURE__ */ jsxs26(
4325
4829
  "a",
4326
4830
  {
4327
4831
  href: `https://github.com/${git.repo}/pull/${git.prNumber}`,
@@ -4344,14 +4848,14 @@ function PromptfooLinks({
4344
4848
  (e) => VIEWABLE_PROMPTFOO_MODES.has(e.mode)
4345
4849
  );
4346
4850
  if (viewable.length === 0) return null;
4347
- return /* @__PURE__ */ jsx27(Flex15, { gap: 3, wrap: "wrap", children: viewable.map((entry) => /* @__PURE__ */ jsx27(Text22, { size: 1, children: /* @__PURE__ */ jsxs22("a", { href: entry.url, rel: "noopener noreferrer", target: "_blank", children: [
4851
+ return /* @__PURE__ */ jsx31(Flex19, { gap: 3, wrap: "wrap", children: viewable.map((entry) => /* @__PURE__ */ jsx31(Text26, { size: 1, children: /* @__PURE__ */ jsxs26("a", { href: entry.url, rel: "noopener noreferrer", target: "_blank", children: [
4348
4852
  "View in Promptfoo (",
4349
4853
  entry.mode,
4350
4854
  ") \u2192"
4351
4855
  ] }) }, entry.mode)) });
4352
4856
  }
4353
4857
  if (provenance.promptfooUrl && VIEWABLE_PROMPTFOO_MODES.has(provenance.mode)) {
4354
- return /* @__PURE__ */ jsx27(Text22, { size: 1, children: /* @__PURE__ */ jsx27(
4858
+ return /* @__PURE__ */ jsx31(Text26, { size: 1, children: /* @__PURE__ */ jsx31(
4355
4859
  "a",
4356
4860
  {
4357
4861
  href: provenance.promptfooUrl,
@@ -4366,32 +4870,32 @@ function PromptfooLinks({
4366
4870
 
4367
4871
  // src/components/report-detail/RecommendationsSection.tsx
4368
4872
  import React3 from "react";
4369
- import { Badge as Badge14, Box as Box10, Card as Card16, Flex as Flex16, Stack as Stack16, Text as Text23, Tooltip as Tooltip6 } from "@sanity/ui";
4370
- import { HelpCircleIcon as HelpCircleIcon4 } from "@sanity/icons";
4371
- import { jsx as jsx28, jsxs as jsxs23 } from "react/jsx-runtime";
4873
+ import { Badge as Badge15, Box as Box12, Card as Card19, Flex as Flex20, Stack as Stack19, Text as Text27, Tooltip as Tooltip6 } from "@sanity/ui";
4874
+ import { HelpCircleIcon as HelpCircleIcon6 } from "@sanity/icons";
4875
+ import { jsx as jsx32, jsxs as jsxs27 } from "react/jsx-runtime";
4372
4876
  function RecommendationsSection({
4373
4877
  recommendations
4374
4878
  }) {
4375
4879
  if (recommendations.gaps.length === 0) return null;
4376
- return /* @__PURE__ */ jsx28(Card16, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs23(Stack16, { space: 4, children: [
4377
- /* @__PURE__ */ jsxs23(Flex16, { align: "center", gap: 3, wrap: "wrap", children: [
4378
- /* @__PURE__ */ jsx28(Text23, { size: 2, weight: "semibold", children: "Recommendations" }),
4379
- /* @__PURE__ */ jsx28(
4880
+ return /* @__PURE__ */ jsx32(Card19, { padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs27(Stack19, { space: 4, children: [
4881
+ /* @__PURE__ */ jsxs27(Flex20, { align: "center", gap: 3, wrap: "wrap", children: [
4882
+ /* @__PURE__ */ jsx32(Text27, { size: 2, weight: "semibold", children: "Recommendations" }),
4883
+ /* @__PURE__ */ jsx32(
4380
4884
  Tooltip6,
4381
4885
  {
4382
- content: /* @__PURE__ */ jsx28(Box10, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx28(Text23, { size: 1, children: GLOSSARY.recommendations }) }),
4886
+ content: /* @__PURE__ */ jsx32(Box12, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx32(Text27, { size: 1, children: GLOSSARY.recommendations }) }),
4383
4887
  placement: "bottom",
4384
4888
  portal: true,
4385
- children: /* @__PURE__ */ jsx28(Text23, { muted: true, size: 0, children: /* @__PURE__ */ jsx28(HelpCircleIcon4, {}) })
4889
+ children: /* @__PURE__ */ jsx32(Text27, { muted: true, size: 0, children: /* @__PURE__ */ jsx32(HelpCircleIcon6, {}) })
4386
4890
  }
4387
4891
  ),
4388
- /* @__PURE__ */ jsx28(
4892
+ /* @__PURE__ */ jsx32(
4389
4893
  Tooltip6,
4390
4894
  {
4391
- content: /* @__PURE__ */ jsx28(Box10, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx28(Text23, { size: 1, children: GLOSSARY.totalPotentialLift }) }),
4895
+ content: /* @__PURE__ */ jsx32(Box12, { padding: 2, style: { maxWidth: 260 }, children: /* @__PURE__ */ jsx32(Text27, { size: 1, children: GLOSSARY.totalPotentialLift }) }),
4392
4896
  placement: "bottom",
4393
4897
  portal: true,
4394
- children: /* @__PURE__ */ jsx28(Card16, { padding: 2, radius: 2, tone: "positive", children: /* @__PURE__ */ jsxs23(Text23, { size: 1, weight: "bold", children: [
4898
+ children: /* @__PURE__ */ jsx32(Card19, { padding: 2, radius: 2, tone: "positive", children: /* @__PURE__ */ jsxs27(Text27, { size: 1, weight: "bold", children: [
4395
4899
  "+",
4396
4900
  recommendations.totalPotentialLift.toFixed(1),
4397
4901
  " pts potential lift"
@@ -4399,7 +4903,7 @@ function RecommendationsSection({
4399
4903
  }
4400
4904
  )
4401
4905
  ] }),
4402
- /* @__PURE__ */ jsxs23(
4906
+ /* @__PURE__ */ jsxs27(
4403
4907
  "div",
4404
4908
  {
4405
4909
  style: {
@@ -4408,9 +4912,9 @@ function RecommendationsSection({
4408
4912
  gridTemplateColumns: "auto 2fr 2fr 1fr 1fr 1fr"
4409
4913
  },
4410
4914
  children: [
4411
- /* @__PURE__ */ jsx28(ColumnHeader, { borderBottom: true, label: "#" }),
4412
- /* @__PURE__ */ jsx28(ColumnHeader, { borderBottom: true, label: "Area" }),
4413
- /* @__PURE__ */ jsx28(
4915
+ /* @__PURE__ */ jsx32(ColumnHeader, { borderBottom: true, label: "#" }),
4916
+ /* @__PURE__ */ jsx32(ColumnHeader, { borderBottom: true, label: "Area" }),
4917
+ /* @__PURE__ */ jsx32(
4414
4918
  ColumnHeader,
4415
4919
  {
4416
4920
  borderBottom: true,
@@ -4418,8 +4922,8 @@ function RecommendationsSection({
4418
4922
  tooltip: GLOSSARY.failureMode
4419
4923
  }
4420
4924
  ),
4421
- /* @__PURE__ */ jsx28(ColumnHeader, { borderBottom: true, label: "Action" }),
4422
- /* @__PURE__ */ jsx28(
4925
+ /* @__PURE__ */ jsx32(ColumnHeader, { borderBottom: true, label: "Action" }),
4926
+ /* @__PURE__ */ jsx32(
4423
4927
  ColumnHeader,
4424
4928
  {
4425
4929
  borderBottom: true,
@@ -4427,7 +4931,7 @@ function RecommendationsSection({
4427
4931
  tooltip: GLOSSARY.estimatedLift
4428
4932
  }
4429
4933
  ),
4430
- /* @__PURE__ */ jsx28(
4934
+ /* @__PURE__ */ jsx32(
4431
4935
  ColumnHeader,
4432
4936
  {
4433
4937
  borderBottom: true,
@@ -4435,7 +4939,7 @@ function RecommendationsSection({
4435
4939
  tooltip: GLOSSARY.confidence
4436
4940
  }
4437
4941
  ),
4438
- recommendations.gaps.map((gap, i) => /* @__PURE__ */ jsx28(RecommendationRow, { gap, index: i }, `gap-${i}`))
4942
+ recommendations.gaps.map((gap, i) => /* @__PURE__ */ jsx32(RecommendationRow, { gap, index: i }, `gap-${i}`))
4439
4943
  ]
4440
4944
  }
4441
4945
  )
@@ -4447,8 +4951,8 @@ function RecommendationRow({
4447
4951
  }) {
4448
4952
  const confIcon = gap.confidence === "high" ? "\u{1F7E2}" : gap.confidence === "medium" ? "\u{1F7E1}" : "\u{1F534}";
4449
4953
  const bg = rowBackground(index);
4450
- return /* @__PURE__ */ jsxs23(React3.Fragment, { children: [
4451
- /* @__PURE__ */ jsx28(
4954
+ return /* @__PURE__ */ jsxs27(React3.Fragment, { children: [
4955
+ /* @__PURE__ */ jsx32(
4452
4956
  "div",
4453
4957
  {
4454
4958
  style: {
@@ -4458,10 +4962,10 @@ function RecommendationRow({
4458
4962
  display: "flex",
4459
4963
  padding: "8px 4px"
4460
4964
  },
4461
- children: /* @__PURE__ */ jsx28(Text23, { muted: true, size: 1, children: index + 1 })
4965
+ children: /* @__PURE__ */ jsx32(Text27, { muted: true, size: 1, children: index + 1 })
4462
4966
  }
4463
4967
  ),
4464
- /* @__PURE__ */ jsx28(
4968
+ /* @__PURE__ */ jsx32(
4465
4969
  "div",
4466
4970
  {
4467
4971
  style: {
@@ -4470,10 +4974,10 @@ function RecommendationRow({
4470
4974
  display: "flex",
4471
4975
  padding: "8px 0"
4472
4976
  },
4473
- children: /* @__PURE__ */ jsx28(Text23, { size: 1, weight: "medium", children: gap.area })
4977
+ children: /* @__PURE__ */ jsx32(Text27, { size: 1, weight: "medium", children: gap.area })
4474
4978
  }
4475
4979
  ),
4476
- /* @__PURE__ */ jsx28(
4980
+ /* @__PURE__ */ jsx32(
4477
4981
  "div",
4478
4982
  {
4479
4983
  style: {
@@ -4482,8 +4986,8 @@ function RecommendationRow({
4482
4986
  display: "flex",
4483
4987
  padding: "8px 0"
4484
4988
  },
4485
- children: /* @__PURE__ */ jsx28(
4486
- Badge14,
4989
+ children: /* @__PURE__ */ jsx32(
4990
+ Badge15,
4487
4991
  {
4488
4992
  tone: gap.failureMode === "missing-docs" ? "critical" : gap.failureMode === "incorrect-docs" ? "critical" : gap.failureMode === "outdated-docs" ? "caution" : "default",
4489
4993
  children: gap.failureMode
@@ -4491,7 +4995,7 @@ function RecommendationRow({
4491
4995
  )
4492
4996
  }
4493
4997
  ),
4494
- /* @__PURE__ */ jsx28(
4998
+ /* @__PURE__ */ jsx32(
4495
4999
  "div",
4496
5000
  {
4497
5001
  style: {
@@ -4500,10 +5004,10 @@ function RecommendationRow({
4500
5004
  display: "flex",
4501
5005
  padding: "8px 0"
4502
5006
  },
4503
- children: /* @__PURE__ */ jsx28(Text23, { muted: true, size: 1, children: gap.remediation })
5007
+ children: /* @__PURE__ */ jsx32(Text27, { muted: true, size: 1, children: gap.remediation })
4504
5008
  }
4505
5009
  ),
4506
- /* @__PURE__ */ jsx28(
5010
+ /* @__PURE__ */ jsx32(
4507
5011
  "div",
4508
5012
  {
4509
5013
  style: {
@@ -4512,13 +5016,13 @@ function RecommendationRow({
4512
5016
  display: "flex",
4513
5017
  padding: "8px 0"
4514
5018
  },
4515
- children: /* @__PURE__ */ jsx28(Card16, { padding: 2, radius: 2, tone: "positive", children: /* @__PURE__ */ jsxs23(Text23, { align: "center", size: 1, weight: "medium", children: [
5019
+ children: /* @__PURE__ */ jsx32(Card19, { padding: 2, radius: 2, tone: "positive", children: /* @__PURE__ */ jsxs27(Text27, { align: "center", size: 1, weight: "medium", children: [
4516
5020
  "+",
4517
5021
  gap.estimatedLift.toFixed(1)
4518
5022
  ] }) })
4519
5023
  }
4520
5024
  ),
4521
- /* @__PURE__ */ jsx28(
5025
+ /* @__PURE__ */ jsx32(
4522
5026
  "div",
4523
5027
  {
4524
5028
  style: {
@@ -4527,7 +5031,7 @@ function RecommendationRow({
4527
5031
  display: "flex",
4528
5032
  padding: "8px 0"
4529
5033
  },
4530
- children: /* @__PURE__ */ jsxs23(Text23, { size: 1, children: [
5034
+ children: /* @__PURE__ */ jsxs27(Text27, { size: 1, children: [
4531
5035
  confIcon,
4532
5036
  " ",
4533
5037
  gap.confidence
@@ -4540,16 +5044,16 @@ function RecommendationRow({
4540
5044
  // src/components/report-detail/ReportHeader.tsx
4541
5045
  import { ArrowLeftIcon, ClipboardIcon } from "@sanity/icons";
4542
5046
  import {
4543
- Badge as Badge15,
4544
- Box as Box11,
5047
+ Badge as Badge16,
5048
+ Box as Box13,
4545
5049
  Button as Button2,
4546
- Card as Card17,
4547
- Flex as Flex17,
4548
- Stack as Stack17,
4549
- Text as Text24,
5050
+ Card as Card20,
5051
+ Flex as Flex21,
5052
+ Stack as Stack20,
5053
+ Text as Text28,
4550
5054
  Tooltip as Tooltip7
4551
5055
  } from "@sanity/ui";
4552
- import { Fragment as Fragment4, jsx as jsx29, jsxs as jsxs24 } from "react/jsx-runtime";
5056
+ import { Fragment as Fragment6, jsx as jsx33, jsxs as jsxs28 } from "react/jsx-runtime";
4553
5057
  function ReportHeader({
4554
5058
  completedAt,
4555
5059
  mode,
@@ -4562,9 +5066,9 @@ function ReportHeader({
4562
5066
  const dateLabel = formatCardDate(completedAt);
4563
5067
  const title = tag ?? dateLabel;
4564
5068
  const hasTag = Boolean(tag);
4565
- return /* @__PURE__ */ jsxs24(Fragment4, { children: [
4566
- /* @__PURE__ */ jsxs24(Flex17, { align: "center", gap: 3, children: [
4567
- /* @__PURE__ */ jsx29(
5069
+ return /* @__PURE__ */ jsxs28(Fragment6, { children: [
5070
+ /* @__PURE__ */ jsxs28(Flex21, { align: "center", gap: 3, children: [
5071
+ /* @__PURE__ */ jsx33(
4568
5072
  Button2,
4569
5073
  {
4570
5074
  icon: ArrowLeftIcon,
@@ -4573,23 +5077,23 @@ function ReportHeader({
4573
5077
  text: "Back"
4574
5078
  }
4575
5079
  ),
4576
- /* @__PURE__ */ jsxs24(Stack17, { flex: 1, space: 1, children: [
4577
- /* @__PURE__ */ jsx29(Text24, { size: 3, weight: "bold", children: title }),
4578
- hasTag && /* @__PURE__ */ jsx29(Text24, { muted: true, size: 1, children: dateLabel })
5080
+ /* @__PURE__ */ jsxs28(Stack20, { flex: 1, space: 1, children: [
5081
+ /* @__PURE__ */ jsx33(Text28, { size: 3, weight: "bold", children: title }),
5082
+ hasTag && /* @__PURE__ */ jsx33(Text28, { muted: true, size: 1, children: dateLabel })
4579
5083
  ] }),
4580
- /* @__PURE__ */ jsxs24(Flex17, { gap: 2, children: [
4581
- /* @__PURE__ */ jsx29(Badge15, { mode: "outline", tone: "default", children: sourceName }),
4582
- /* @__PURE__ */ jsx29(Badge15, { tone: "primary", children: mode })
5084
+ /* @__PURE__ */ jsxs28(Flex21, { gap: 2, children: [
5085
+ /* @__PURE__ */ jsx33(Badge16, { mode: "outline", tone: "default", children: sourceName }),
5086
+ /* @__PURE__ */ jsx33(Badge16, { tone: "primary", children: mode })
4583
5087
  ] })
4584
5088
  ] }),
4585
- /* @__PURE__ */ jsx29(
5089
+ /* @__PURE__ */ jsx33(
4586
5090
  Tooltip7,
4587
5091
  {
4588
- content: /* @__PURE__ */ jsx29(Box11, { padding: 2, children: /* @__PURE__ */ jsx29(Text24, { size: 1, children: "Click to copy report ID" }) }),
5092
+ content: /* @__PURE__ */ jsx33(Box13, { padding: 2, children: /* @__PURE__ */ jsx33(Text28, { size: 1, children: "Click to copy report ID" }) }),
4589
5093
  placement: "bottom",
4590
5094
  portal: true,
4591
- children: /* @__PURE__ */ jsx29(
4592
- Card17,
5095
+ children: /* @__PURE__ */ jsx33(
5096
+ Card20,
4593
5097
  {
4594
5098
  border: true,
4595
5099
  onClick: onCopyId,
@@ -4597,9 +5101,9 @@ function ReportHeader({
4597
5101
  radius: 2,
4598
5102
  style: { cursor: "pointer" },
4599
5103
  tone: "transparent",
4600
- children: /* @__PURE__ */ jsxs24(Flex17, { align: "center", gap: 3, children: [
4601
- /* @__PURE__ */ jsx29(
4602
- Text24,
5104
+ children: /* @__PURE__ */ jsxs28(Flex21, { align: "center", gap: 3, children: [
5105
+ /* @__PURE__ */ jsx33(
5106
+ Text28,
4603
5107
  {
4604
5108
  muted: true,
4605
5109
  size: 0,
@@ -4611,8 +5115,8 @@ function ReportHeader({
4611
5115
  children: "Report ID"
4612
5116
  }
4613
5117
  ),
4614
- /* @__PURE__ */ jsx29(
4615
- Text24,
5118
+ /* @__PURE__ */ jsx33(
5119
+ Text28,
4616
5120
  {
4617
5121
  size: 1,
4618
5122
  style: {
@@ -4622,7 +5126,7 @@ function ReportHeader({
4622
5126
  children: reportId
4623
5127
  }
4624
5128
  ),
4625
- /* @__PURE__ */ jsx29(Box11, { style: { marginLeft: "auto" }, children: /* @__PURE__ */ jsx29(Text24, { muted: true, size: 1, children: /* @__PURE__ */ jsx29(ClipboardIcon, {}) }) })
5129
+ /* @__PURE__ */ jsx33(Box13, { style: { marginLeft: "auto" }, children: /* @__PURE__ */ jsx33(Text28, { muted: true, size: 1, children: /* @__PURE__ */ jsx33(ClipboardIcon, {}) }) })
4626
5130
  ] })
4627
5131
  }
4628
5132
  )
@@ -4633,18 +5137,18 @@ function ReportHeader({
4633
5137
 
4634
5138
  // src/components/report-detail/ThreeLayerTable.tsx
4635
5139
  import React4 from "react";
4636
- import { Badge as Badge16, Card as Card18, Flex as Flex18, Stack as Stack18, Text as Text25 } from "@sanity/ui";
4637
- import { jsx as jsx30, jsxs as jsxs25 } from "react/jsx-runtime";
5140
+ import { Badge as Badge17, Card as Card21, Flex as Flex22, Stack as Stack21, Text as Text29 } from "@sanity/ui";
5141
+ import { jsx as jsx34, jsxs as jsxs29 } from "react/jsx-runtime";
4638
5142
  function ThreeLayerTable({ scores }) {
4639
5143
  const filtered = scores.filter((s) => s.actualScore != null);
4640
5144
  if (filtered.length === 0) return null;
4641
5145
  const hasInverted = filtered.some((s) => s.invertedRetrievalGap);
4642
- return /* @__PURE__ */ jsx30(Card18, { overflow: "auto", padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs25(Stack18, { space: 4, children: [
4643
- /* @__PURE__ */ jsxs25(Flex18, { align: "center", gap: 3, children: [
4644
- /* @__PURE__ */ jsx30(Text25, { size: 2, weight: "semibold", children: "Three-Layer Decomposition" }),
4645
- /* @__PURE__ */ jsx30(Badge16, { tone: "primary", children: "full mode" })
5146
+ return /* @__PURE__ */ jsx34(Card21, { overflow: "auto", padding: 4, radius: 2, shadow: 1, children: /* @__PURE__ */ jsxs29(Stack21, { space: 4, children: [
5147
+ /* @__PURE__ */ jsxs29(Flex22, { align: "center", gap: 3, children: [
5148
+ /* @__PURE__ */ jsx34(Text29, { size: 2, weight: "semibold", children: "Three-Layer Decomposition" }),
5149
+ /* @__PURE__ */ jsx34(Badge17, { tone: "primary", children: "full mode" })
4646
5150
  ] }),
4647
- /* @__PURE__ */ jsxs25(
5151
+ /* @__PURE__ */ jsxs29(
4648
5152
  "div",
4649
5153
  {
4650
5154
  style: {
@@ -4653,9 +5157,9 @@ function ThreeLayerTable({ scores }) {
4653
5157
  gridTemplateColumns: "2fr 1fr 1fr 1fr 1fr 1fr"
4654
5158
  },
4655
5159
  children: [
4656
- /* @__PURE__ */ jsx30(ColumnHeader, { borderBottom: true, label: "Area" }),
4657
- /* @__PURE__ */ jsx30(ColumnHeader, { borderBottom: true, label: "Floor", tooltip: GLOSSARY.floor }),
4658
- /* @__PURE__ */ jsx30(
5160
+ /* @__PURE__ */ jsx34(ColumnHeader, { borderBottom: true, label: "Area" }),
5161
+ /* @__PURE__ */ jsx34(ColumnHeader, { borderBottom: true, label: "Floor", tooltip: GLOSSARY.floor }),
5162
+ /* @__PURE__ */ jsx34(
4659
5163
  ColumnHeader,
4660
5164
  {
4661
5165
  borderBottom: true,
@@ -4663,8 +5167,8 @@ function ThreeLayerTable({ scores }) {
4663
5167
  tooltip: GLOSSARY.ceiling
4664
5168
  }
4665
5169
  ),
4666
- /* @__PURE__ */ jsx30(ColumnHeader, { borderBottom: true, label: "Actual", tooltip: GLOSSARY.actual }),
4667
- /* @__PURE__ */ jsx30(
5170
+ /* @__PURE__ */ jsx34(ColumnHeader, { borderBottom: true, label: "Actual", tooltip: GLOSSARY.actual }),
5171
+ /* @__PURE__ */ jsx34(
4668
5172
  ColumnHeader,
4669
5173
  {
4670
5174
  borderBottom: true,
@@ -4672,7 +5176,7 @@ function ThreeLayerTable({ scores }) {
4672
5176
  tooltip: GLOSSARY.retGap
4673
5177
  }
4674
5178
  ),
4675
- /* @__PURE__ */ jsx30(
5179
+ /* @__PURE__ */ jsx34(
4676
5180
  ColumnHeader,
4677
5181
  {
4678
5182
  borderBottom: true,
@@ -4680,8 +5184,8 @@ function ThreeLayerTable({ scores }) {
4680
5184
  tooltip: GLOSSARY.efficiency
4681
5185
  }
4682
5186
  ),
4683
- filtered.map((score, i) => /* @__PURE__ */ jsxs25(React4.Fragment, { children: [
4684
- /* @__PURE__ */ jsx30(
5187
+ filtered.map((score, i) => /* @__PURE__ */ jsxs29(React4.Fragment, { children: [
5188
+ /* @__PURE__ */ jsx34(
4685
5189
  "div",
4686
5190
  {
4687
5191
  style: {
@@ -4689,13 +5193,13 @@ function ThreeLayerTable({ scores }) {
4689
5193
  borderRadius: 4,
4690
5194
  padding: "8px 0 8px 4px"
4691
5195
  },
4692
- children: /* @__PURE__ */ jsx30(Text25, { size: 1, weight: "medium", children: score.feature })
5196
+ children: /* @__PURE__ */ jsx34(Text29, { size: 1, weight: "medium", children: score.feature })
4693
5197
  }
4694
5198
  ),
4695
- /* @__PURE__ */ jsx30("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx30(ScoreCell, { score: score.floorScore ?? 0 }) }),
4696
- /* @__PURE__ */ jsx30("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx30(ScoreCell, { score: score.ceilingScore ?? score.totalScore }) }),
4697
- /* @__PURE__ */ jsx30("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx30(ScoreCell, { score: score.actualScore ?? 0 }) }),
4698
- /* @__PURE__ */ jsx30(
5199
+ /* @__PURE__ */ jsx34("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx34(ScoreCell, { score: score.floorScore ?? 0 }) }),
5200
+ /* @__PURE__ */ jsx34("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx34(ScoreCell, { score: score.ceilingScore ?? score.totalScore }) }),
5201
+ /* @__PURE__ */ jsx34("div", { style: { background: rowBackground(i), padding: "6px 0" }, children: /* @__PURE__ */ jsx34(ScoreCell, { score: score.actualScore ?? 0 }) }),
5202
+ /* @__PURE__ */ jsx34(
4699
5203
  "div",
4700
5204
  {
4701
5205
  style: {
@@ -4704,10 +5208,10 @@ function ThreeLayerTable({ scores }) {
4704
5208
  display: "flex",
4705
5209
  padding: "6px 0"
4706
5210
  },
4707
- children: /* @__PURE__ */ jsx30(Text25, { size: 1, children: score.retrievalGap != null ? score.retrievalGap.toFixed(1) : "\u2014" })
5211
+ children: /* @__PURE__ */ jsx34(Text29, { size: 1, children: score.retrievalGap != null ? score.retrievalGap.toFixed(1) : "\u2014" })
4708
5212
  }
4709
5213
  ),
4710
- /* @__PURE__ */ jsx30(
5214
+ /* @__PURE__ */ jsx34(
4711
5215
  "div",
4712
5216
  {
4713
5217
  style: {
@@ -4716,7 +5220,7 @@ function ThreeLayerTable({ scores }) {
4716
5220
  display: "flex",
4717
5221
  padding: "6px 0"
4718
5222
  },
4719
- children: /* @__PURE__ */ jsxs25(Text25, { size: 1, children: [
5223
+ children: /* @__PURE__ */ jsxs29(Text29, { size: 1, children: [
4720
5224
  formatPercent(score.infrastructureEfficiency),
4721
5225
  score.invertedRetrievalGap && " \u26A0\uFE0F"
4722
5226
  ] })
@@ -4726,18 +5230,18 @@ function ThreeLayerTable({ scores }) {
4726
5230
  ]
4727
5231
  }
4728
5232
  ),
4729
- hasInverted && /* @__PURE__ */ jsx30(Text25, { muted: true, size: 0, children: GLOSSARY.invertedRetGap })
5233
+ hasInverted && /* @__PURE__ */ jsx34(Text29, { muted: true, size: 0, children: GLOSSARY.invertedRetGap })
4730
5234
  ] }) });
4731
5235
  }
4732
5236
 
4733
5237
  // src/components/report-detail/ReportDetail.tsx
4734
- import { jsx as jsx31, jsxs as jsxs26 } from "react/jsx-runtime";
5238
+ import { jsx as jsx35, jsxs as jsxs30 } from "react/jsx-runtime";
4735
5239
  function ReportDetail({ onBack, reportId }) {
4736
5240
  const client = useClient6({ apiVersion: API_VERSION });
4737
5241
  const toast = useToast();
4738
5242
  const [loading, setLoading] = useState8(true);
4739
5243
  const [report, setReport] = useState8(null);
4740
- useEffect6(() => {
5244
+ useEffect7(() => {
4741
5245
  let cancelled = false;
4742
5246
  setLoading(true);
4743
5247
  client.fetch(reportDetailQuery, { reportId }).then((data) => {
@@ -4752,7 +5256,7 @@ function ReportDetail({ onBack, reportId }) {
4752
5256
  cancelled = true;
4753
5257
  };
4754
5258
  }, [client, reportId]);
4755
- const handleCopyReportId = useCallback9(() => {
5259
+ const handleCopyReportId = useCallback12(() => {
4756
5260
  if (!report) return;
4757
5261
  navigator.clipboard.writeText(report.reportId).then(() => {
4758
5262
  toast.push({
@@ -4769,11 +5273,11 @@ function ReportDetail({ onBack, reportId }) {
4769
5273
  });
4770
5274
  }, [report, toast]);
4771
5275
  if (loading) {
4772
- return /* @__PURE__ */ jsx31(LoadingState, { message: "Loading report\u2026" });
5276
+ return /* @__PURE__ */ jsx35(LoadingState, { message: "Loading report\u2026" });
4773
5277
  }
4774
5278
  if (!report) {
4775
- return /* @__PURE__ */ jsx31(Box12, { padding: 5, children: /* @__PURE__ */ jsxs26(Stack19, { space: 4, children: [
4776
- /* @__PURE__ */ jsx31(
5279
+ return /* @__PURE__ */ jsx35(Box14, { padding: 5, children: /* @__PURE__ */ jsxs30(Stack22, { space: 4, children: [
5280
+ /* @__PURE__ */ jsx35(
4777
5281
  Button3,
4778
5282
  {
4779
5283
  icon: ArrowLeftIcon2,
@@ -4782,14 +5286,14 @@ function ReportDetail({ onBack, reportId }) {
4782
5286
  text: "Back"
4783
5287
  }
4784
5288
  ),
4785
- /* @__PURE__ */ jsx31(Text26, { align: "center", muted: true, size: 2, children: "Report not found" })
5289
+ /* @__PURE__ */ jsx35(Text30, { align: "center", muted: true, size: 2, children: "Report not found" })
4786
5290
  ] }) });
4787
5291
  }
4788
5292
  const { comparison, provenance, summary } = report;
4789
5293
  const totalTests = summary.scores.reduce((n, s) => n + s.testCount, 0);
4790
5294
  const isFullMode = summary.evaluationMode === "full" || summary.scores.some((s) => s.actualScore != null);
4791
- return /* @__PURE__ */ jsx31(Box12, { padding: 4, children: /* @__PURE__ */ jsxs26(Stack19, { space: 5, children: [
4792
- /* @__PURE__ */ jsx31(
5295
+ return /* @__PURE__ */ jsx35(Box14, { padding: 4, children: /* @__PURE__ */ jsxs30(Stack22, { space: 5, children: [
5296
+ /* @__PURE__ */ jsx35(
4793
5297
  ReportHeader,
4794
5298
  {
4795
5299
  completedAt: report.completedAt,
@@ -4801,7 +5305,7 @@ function ReportDetail({ onBack, reportId }) {
4801
5305
  tag: report.tag
4802
5306
  }
4803
5307
  ),
4804
- /* @__PURE__ */ jsx31(
5308
+ /* @__PURE__ */ jsx35(
4805
5309
  OverviewStats,
4806
5310
  {
4807
5311
  durationMs: report.durationMs,
@@ -4810,20 +5314,20 @@ function ReportDetail({ onBack, reportId }) {
4810
5314
  totalTests
4811
5315
  }
4812
5316
  ),
4813
- isFullMode && /* @__PURE__ */ jsx31(ThreeLayerTable, { scores: summary.scores }),
4814
- /* @__PURE__ */ jsx31(AreaScoreTable, { scores: summary.scores }),
4815
- summary.recommendations && summary.recommendations.gaps.length > 0 && /* @__PURE__ */ jsx31(RecommendationsSection, { recommendations: summary.recommendations }),
4816
- summary.lowScoringJudgments && summary.lowScoringJudgments.length > 0 && /* @__PURE__ */ jsx31(JudgmentList, { judgments: summary.lowScoringJudgments }),
4817
- comparison && /* @__PURE__ */ jsx31(ComparisonSummary, { comparison }),
4818
- /* @__PURE__ */ jsx31(ProvenanceCard, { provenance })
5317
+ isFullMode && /* @__PURE__ */ jsx35(ThreeLayerTable, { scores: summary.scores }),
5318
+ /* @__PURE__ */ jsx35(AreaScoreTable, { scores: summary.scores }),
5319
+ summary.recommendations && summary.recommendations.gaps.length > 0 && /* @__PURE__ */ jsx35(RecommendationsSection, { recommendations: summary.recommendations }),
5320
+ summary.lowScoringJudgments && summary.lowScoringJudgments.length > 0 && /* @__PURE__ */ jsx35(JudgmentList, { judgments: summary.lowScoringJudgments }),
5321
+ comparison && /* @__PURE__ */ jsx35(ComparisonSummary, { comparison }),
5322
+ /* @__PURE__ */ jsx35(ProvenanceCard, { provenance })
4819
5323
  ] }) });
4820
5324
  }
4821
5325
 
4822
5326
  // src/components/ScoreTimeline.tsx
4823
- import { Card as Card19, Flex as Flex19, Select as Select2, Stack as Stack20, Text as Text27 } from "@sanity/ui";
4824
- import { useCallback as useCallback10, useEffect as useEffect7, useMemo as useMemo4, useState as useState9 } from "react";
5327
+ import { Card as Card22, Flex as Flex23, Select as Select2, Stack as Stack23, Text as Text31 } from "@sanity/ui";
5328
+ import { useCallback as useCallback13, useEffect as useEffect8, useMemo as useMemo6, useState as useState9 } from "react";
4825
5329
  import { useClient as useClient7 } from "sanity";
4826
- import { jsx as jsx32, jsxs as jsxs27 } from "react/jsx-runtime";
5330
+ import { jsx as jsx36, jsxs as jsxs31 } from "react/jsx-runtime";
4827
5331
  var CHART_HEIGHT = 220;
4828
5332
  var CHART_WIDTH = 800;
4829
5333
  var PAD_BOTTOM = 30;
@@ -4862,7 +5366,7 @@ function ScoreTimeline({ mode = null, source = null }) {
4862
5366
  const [loading, setLoading] = useState9(true);
4863
5367
  const [rangeDays, setRangeDays] = useState9(30);
4864
5368
  const [selectedArea, setSelectedArea] = useState9(null);
4865
- const areaNames = useMemo4(() => {
5369
+ const areaNames = useMemo6(() => {
4866
5370
  const names = /* @__PURE__ */ new Set();
4867
5371
  for (const dp of dataPoints) {
4868
5372
  for (const s of dp.scores) {
@@ -4871,7 +5375,7 @@ function ScoreTimeline({ mode = null, source = null }) {
4871
5375
  }
4872
5376
  return Array.from(names).sort();
4873
5377
  }, [dataPoints]);
4874
- const fetchData = useCallback10(async () => {
5378
+ const fetchData = useCallback13(async () => {
4875
5379
  setLoading(true);
4876
5380
  try {
4877
5381
  const startDate = rangeDays ? daysAgo(rangeDays) : "1970-01-01T00:00:00Z";
@@ -4886,10 +5390,10 @@ function ScoreTimeline({ mode = null, source = null }) {
4886
5390
  setLoading(false);
4887
5391
  }
4888
5392
  }, [client, mode, rangeDays, source]);
4889
- useEffect7(() => {
5393
+ useEffect8(() => {
4890
5394
  void fetchData();
4891
5395
  }, [fetchData]);
4892
- const chartPoints = useMemo4(() => {
5396
+ const chartPoints = useMemo6(() => {
4893
5397
  const pts = [];
4894
5398
  const scored = dataPoints.map((dp) => ({
4895
5399
  date: dp.completedAt,
@@ -4903,18 +5407,18 @@ function ScoreTimeline({ mode = null, source = null }) {
4903
5407
  });
4904
5408
  return pts;
4905
5409
  }, [dataPoints, selectedArea]);
4906
- const avgScore = useMemo4(() => {
5410
+ const avgScore = useMemo6(() => {
4907
5411
  if (chartPoints.length === 0) return 0;
4908
5412
  return chartPoints.reduce((sum, p) => sum + p.score, 0) / chartPoints.length;
4909
5413
  }, [chartPoints]);
4910
- const handleRangeChange = useCallback10(
5414
+ const handleRangeChange = useCallback13(
4911
5415
  (e) => {
4912
5416
  const val = e.currentTarget.value;
4913
5417
  setRangeDays(val === "all" ? null : Number(val));
4914
5418
  },
4915
5419
  []
4916
5420
  );
4917
- const handleAreaChange = useCallback10(
5421
+ const handleAreaChange = useCallback13(
4918
5422
  (e) => {
4919
5423
  const val = e.currentTarget.value;
4920
5424
  setSelectedArea(val || null);
@@ -4922,22 +5426,22 @@ function ScoreTimeline({ mode = null, source = null }) {
4922
5426
  []
4923
5427
  );
4924
5428
  const polylinePoints = chartPoints.map((p) => `${p.x},${p.y}`).join(" ");
4925
- return /* @__PURE__ */ jsxs27(Stack20, { space: 4, children: [
4926
- /* @__PURE__ */ jsxs27(Flex19, { gap: 3, children: [
4927
- /* @__PURE__ */ jsx32(
5429
+ return /* @__PURE__ */ jsxs31(Stack23, { space: 4, children: [
5430
+ /* @__PURE__ */ jsxs31(Flex23, { gap: 3, children: [
5431
+ /* @__PURE__ */ jsx36(
4928
5432
  Select2,
4929
5433
  {
4930
5434
  onChange: handleRangeChange,
4931
5435
  value: rangeDays?.toString() ?? "all",
4932
- children: TIME_RANGES.map((r) => /* @__PURE__ */ jsx32("option", { value: r.days?.toString() ?? "all", children: r.label }, r.label))
5436
+ children: TIME_RANGES.map((r) => /* @__PURE__ */ jsx36("option", { value: r.days?.toString() ?? "all", children: r.label }, r.label))
4933
5437
  }
4934
5438
  ),
4935
- /* @__PURE__ */ jsxs27(Select2, { onChange: handleAreaChange, value: selectedArea ?? "", children: [
4936
- /* @__PURE__ */ jsx32("option", { value: "", children: "Overall" }),
4937
- areaNames.map((name) => /* @__PURE__ */ jsx32("option", { value: name, children: name }, name))
5439
+ /* @__PURE__ */ jsxs31(Select2, { onChange: handleAreaChange, value: selectedArea ?? "", children: [
5440
+ /* @__PURE__ */ jsx36("option", { value: "", children: "Overall" }),
5441
+ areaNames.map((name) => /* @__PURE__ */ jsx36("option", { value: name, children: name }, name))
4938
5442
  ] })
4939
5443
  ] }),
4940
- /* @__PURE__ */ jsx32(Card19, { padding: 3, radius: 2, shadow: 1, children: loading ? /* @__PURE__ */ jsx32(Flex19, { align: "center", justify: "center", style: { height: 200 }, children: /* @__PURE__ */ jsx32(Text27, { muted: true, size: 1, children: "Loading\u2026" }) }) : chartPoints.length === 0 ? /* @__PURE__ */ jsx32(Flex19, { align: "center", justify: "center", style: { height: 200 }, children: /* @__PURE__ */ jsx32(Text27, { muted: true, size: 1, children: "No reports found for this time range" }) }) : /* @__PURE__ */ jsxs27(
5444
+ /* @__PURE__ */ jsx36(Card22, { padding: 3, radius: 2, shadow: 1, children: loading ? /* @__PURE__ */ jsx36(Flex23, { align: "center", justify: "center", style: { height: 200 }, children: /* @__PURE__ */ jsx36(Text31, { muted: true, size: 1, children: "Loading\u2026" }) }) : chartPoints.length === 0 ? /* @__PURE__ */ jsx36(Flex23, { align: "center", justify: "center", style: { height: 200 }, children: /* @__PURE__ */ jsx36(Text31, { muted: true, size: 1, children: "No reports found for this time range" }) }) : /* @__PURE__ */ jsxs31(
4941
5445
  "svg",
4942
5446
  {
4943
5447
  style: { display: "block", width: "100%" },
@@ -4945,8 +5449,8 @@ function ScoreTimeline({ mode = null, source = null }) {
4945
5449
  children: [
4946
5450
  Y_TICKS.map((tick) => {
4947
5451
  const y = PAD_TOP + PLOT_HEIGHT - tick / Y_MAX * PLOT_HEIGHT;
4948
- return /* @__PURE__ */ jsxs27("g", { children: [
4949
- /* @__PURE__ */ jsx32(
5452
+ return /* @__PURE__ */ jsxs31("g", { children: [
5453
+ /* @__PURE__ */ jsx36(
4950
5454
  "line",
4951
5455
  {
4952
5456
  stroke: "#ccc",
@@ -4957,7 +5461,7 @@ function ScoreTimeline({ mode = null, source = null }) {
4957
5461
  y2: y
4958
5462
  }
4959
5463
  ),
4960
- /* @__PURE__ */ jsx32(
5464
+ /* @__PURE__ */ jsx36(
4961
5465
  "text",
4962
5466
  {
4963
5467
  dominantBaseline: "middle",
@@ -4977,7 +5481,7 @@ function ScoreTimeline({ mode = null, source = null }) {
4977
5481
  chartPoints.length - 1
4978
5482
  ].map((idx) => {
4979
5483
  const p = chartPoints[idx];
4980
- return /* @__PURE__ */ jsx32(
5484
+ return /* @__PURE__ */ jsx36(
4981
5485
  "text",
4982
5486
  {
4983
5487
  fill: "#999",
@@ -4989,7 +5493,7 @@ function ScoreTimeline({ mode = null, source = null }) {
4989
5493
  },
4990
5494
  idx
4991
5495
  );
4992
- }) : chartPoints.map((p, idx) => /* @__PURE__ */ jsx32(
5496
+ }) : chartPoints.map((p, idx) => /* @__PURE__ */ jsx36(
4993
5497
  "text",
4994
5498
  {
4995
5499
  fill: "#999",
@@ -5001,7 +5505,7 @@ function ScoreTimeline({ mode = null, source = null }) {
5001
5505
  },
5002
5506
  idx
5003
5507
  )),
5004
- /* @__PURE__ */ jsx32(
5508
+ /* @__PURE__ */ jsx36(
5005
5509
  "polyline",
5006
5510
  {
5007
5511
  fill: "none",
@@ -5011,7 +5515,7 @@ function ScoreTimeline({ mode = null, source = null }) {
5011
5515
  strokeWidth: 2.5
5012
5516
  }
5013
5517
  ),
5014
- chartPoints.map((p, idx) => /* @__PURE__ */ jsx32(
5518
+ chartPoints.map((p, idx) => /* @__PURE__ */ jsx36(
5015
5519
  "circle",
5016
5520
  {
5017
5521
  cx: p.x,
@@ -5020,7 +5524,7 @@ function ScoreTimeline({ mode = null, source = null }) {
5020
5524
  r: 4,
5021
5525
  stroke: "#fff",
5022
5526
  strokeWidth: 1.5,
5023
- children: /* @__PURE__ */ jsxs27("title", { children: [
5527
+ children: /* @__PURE__ */ jsxs31("title", { children: [
5024
5528
  formatDate2(p.date),
5025
5529
  ": ",
5026
5530
  Math.round(p.score)
@@ -5031,7 +5535,7 @@ function ScoreTimeline({ mode = null, source = null }) {
5031
5535
  ]
5032
5536
  }
5033
5537
  ) }),
5034
- /* @__PURE__ */ jsxs27(Text27, { muted: true, size: 1, children: [
5538
+ /* @__PURE__ */ jsxs31(Text31, { muted: true, size: 1, children: [
5035
5539
  chartPoints.length,
5036
5540
  " data point",
5037
5541
  chartPoints.length !== 1 ? "s" : ""
@@ -5041,7 +5545,7 @@ function ScoreTimeline({ mode = null, source = null }) {
5041
5545
  var ScoreTimeline_default = ScoreTimeline;
5042
5546
 
5043
5547
  // src/components/Dashboard.tsx
5044
- import { jsx as jsx33, jsxs as jsxs28 } from "react/jsx-runtime";
5548
+ import { jsx as jsx37, jsxs as jsxs32 } from "react/jsx-runtime";
5045
5549
  var VIEW_PARAM_MAP = {
5046
5550
  compare: "compare",
5047
5551
  timeline: "timeline"
@@ -5053,7 +5557,7 @@ function Dashboard() {
5053
5557
  const reportId = routerState.reportId ?? null;
5054
5558
  const isDetail = reportId !== null;
5055
5559
  const activeTab = isDetail ? "latest" : VIEW_PARAM_MAP[routerState.view ?? ""] ?? "latest";
5056
- const navigateToTab = useCallback11(
5560
+ const navigateToTab = useCallback14(
5057
5561
  (tab) => {
5058
5562
  if (tab === "latest") {
5059
5563
  router.navigate({});
@@ -5063,58 +5567,58 @@ function Dashboard() {
5063
5567
  },
5064
5568
  [router]
5065
5569
  );
5066
- const handleSelectReport = useCallback11(
5570
+ const handleSelectReport = useCallback14(
5067
5571
  (id) => {
5068
5572
  router.navigate({ reportId: id });
5069
5573
  },
5070
5574
  [router]
5071
5575
  );
5072
- const handleBack = useCallback11(() => {
5576
+ const handleBack = useCallback14(() => {
5073
5577
  router.navigate({});
5074
5578
  }, [router]);
5075
5579
  const [source, setSource] = useState10(null);
5076
5580
  const [mode, setMode] = useState10(null);
5077
5581
  const [sources, setSources] = useState10([]);
5078
5582
  const [modes, setModes] = useState10([]);
5079
- useEffect8(() => {
5583
+ useEffect9(() => {
5080
5584
  client.fetch(distinctSourcesQuery).then((data) => setSources(data ?? [])).catch(() => setSources([]));
5081
5585
  client.fetch(distinctModesQuery).then((data) => setModes(data ?? [])).catch(() => setModes([]));
5082
5586
  }, [client]);
5083
- return /* @__PURE__ */ jsx33(Container, { width: 2, children: /* @__PURE__ */ jsxs28(Stack21, { padding: 4, space: 4, children: [
5084
- /* @__PURE__ */ jsxs28(Flex20, { align: "center", gap: 3, children: [
5085
- /* @__PURE__ */ jsxs28(Stack21, { flex: 1, space: 1, children: [
5086
- /* @__PURE__ */ jsx33(Text28, { size: 3, weight: "bold", children: "AI Literacy" }),
5087
- /* @__PURE__ */ jsx33(Text28, { muted: true, size: 1, children: "Evaluation reports and score trending" })
5587
+ return /* @__PURE__ */ jsx37(Container, { width: 2, children: /* @__PURE__ */ jsxs32(Stack24, { padding: 4, space: 4, children: [
5588
+ /* @__PURE__ */ jsxs32(Flex24, { align: "center", gap: 3, children: [
5589
+ /* @__PURE__ */ jsxs32(Stack24, { flex: 1, space: 1, children: [
5590
+ /* @__PURE__ */ jsx37(Text32, { size: 3, weight: "bold", children: "AI Literacy" }),
5591
+ /* @__PURE__ */ jsx37(Text32, { muted: true, size: 1, children: "Evaluation reports and score trends" })
5088
5592
  ] }),
5089
- !isDetail && /* @__PURE__ */ jsxs28(Flex20, { gap: 2, children: [
5090
- /* @__PURE__ */ jsxs28(
5593
+ !isDetail && /* @__PURE__ */ jsxs32(Flex24, { gap: 2, children: [
5594
+ /* @__PURE__ */ jsxs32(
5091
5595
  Select3,
5092
5596
  {
5093
5597
  fontSize: 1,
5094
5598
  onChange: (e) => setSource(e.currentTarget.value || null),
5095
5599
  value: source ?? "",
5096
5600
  children: [
5097
- /* @__PURE__ */ jsx33("option", { value: "", children: "All sources" }),
5098
- sources.map((s) => /* @__PURE__ */ jsx33("option", { value: s, children: s }, s))
5601
+ /* @__PURE__ */ jsx37("option", { value: "", children: "All sources" }),
5602
+ sources.map((s) => /* @__PURE__ */ jsx37("option", { value: s, children: s }, s))
5099
5603
  ]
5100
5604
  }
5101
5605
  ),
5102
- /* @__PURE__ */ jsxs28(
5606
+ /* @__PURE__ */ jsxs32(
5103
5607
  Select3,
5104
5608
  {
5105
5609
  fontSize: 1,
5106
5610
  onChange: (e) => setMode(e.currentTarget.value || null),
5107
5611
  value: mode ?? "",
5108
5612
  children: [
5109
- /* @__PURE__ */ jsx33("option", { value: "", children: "All modes" }),
5110
- modes.map((m) => /* @__PURE__ */ jsx33("option", { value: m, children: m }, m))
5613
+ /* @__PURE__ */ jsx37("option", { value: "", children: "All modes" }),
5614
+ modes.map((m) => /* @__PURE__ */ jsx37("option", { value: m, children: m }, m))
5111
5615
  ]
5112
5616
  }
5113
5617
  )
5114
5618
  ] })
5115
5619
  ] }),
5116
- !isDetail && /* @__PURE__ */ jsxs28(TabList, { space: 1, children: [
5117
- /* @__PURE__ */ jsx33(
5620
+ !isDetail && /* @__PURE__ */ jsxs32(TabList, { space: 1, children: [
5621
+ /* @__PURE__ */ jsx37(
5118
5622
  Tab,
5119
5623
  {
5120
5624
  "aria-controls": "latest-panel",
@@ -5124,7 +5628,7 @@ function Dashboard() {
5124
5628
  selected: activeTab === "latest"
5125
5629
  }
5126
5630
  ),
5127
- /* @__PURE__ */ jsx33(
5631
+ /* @__PURE__ */ jsx37(
5128
5632
  Tab,
5129
5633
  {
5130
5634
  "aria-controls": "timeline-panel",
@@ -5134,7 +5638,7 @@ function Dashboard() {
5134
5638
  selected: activeTab === "timeline"
5135
5639
  }
5136
5640
  ),
5137
- /* @__PURE__ */ jsx33(
5641
+ /* @__PURE__ */ jsx37(
5138
5642
  Tab,
5139
5643
  {
5140
5644
  "aria-controls": "compare-panel",
@@ -5145,7 +5649,7 @@ function Dashboard() {
5145
5649
  }
5146
5650
  )
5147
5651
  ] }),
5148
- !isDetail && activeTab === "latest" && /* @__PURE__ */ jsx33(TabPanel, { "aria-labelledby": "latest-tab", id: "latest-panel", children: /* @__PURE__ */ jsx33(
5652
+ !isDetail && activeTab === "latest" && /* @__PURE__ */ jsx37(TabPanel, { "aria-labelledby": "latest-tab", id: "latest-panel", children: /* @__PURE__ */ jsx37(
5149
5653
  LatestReports,
5150
5654
  {
5151
5655
  mode,
@@ -5153,9 +5657,9 @@ function Dashboard() {
5153
5657
  source
5154
5658
  }
5155
5659
  ) }),
5156
- !isDetail && activeTab === "timeline" && /* @__PURE__ */ jsx33(TabPanel, { "aria-labelledby": "timeline-tab", id: "timeline-panel", children: /* @__PURE__ */ jsx33(ScoreTimeline_default, { mode, source }) }),
5157
- !isDetail && activeTab === "compare" && /* @__PURE__ */ jsx33(TabPanel, { "aria-labelledby": "compare-tab", id: "compare-panel", children: /* @__PURE__ */ jsx33(ComparisonView, {}) }),
5158
- isDetail && reportId && /* @__PURE__ */ jsx33(ReportDetail, { onBack: handleBack, reportId })
5660
+ !isDetail && activeTab === "timeline" && /* @__PURE__ */ jsx37(TabPanel, { "aria-labelledby": "timeline-tab", id: "timeline-panel", children: /* @__PURE__ */ jsx37(ScoreTimeline_default, { mode, source }) }),
5661
+ !isDetail && activeTab === "compare" && /* @__PURE__ */ jsx37(TabPanel, { "aria-labelledby": "compare-tab", id: "compare-panel", children: /* @__PURE__ */ jsx37(ComparisonView, {}) }),
5662
+ isDetail && reportId && /* @__PURE__ */ jsx37(ReportDetail, { onBack: handleBack, reportId })
5159
5663
  ] }) });
5160
5664
  }
5161
5665
 
@@ -5176,9 +5680,9 @@ function ailfTool(options = {}) {
5176
5680
 
5177
5681
  // src/actions/RunEvaluationAction.tsx
5178
5682
  import { BarChartIcon as BarChartIcon2 } from "@sanity/icons";
5179
- import { useCallback as useCallback12, useEffect as useEffect9, useRef as useRef3, useState as useState11 } from "react";
5683
+ import { useCallback as useCallback15, useEffect as useEffect10, useRef as useRef4, useState as useState11 } from "react";
5180
5684
  import {
5181
- getReleaseIdFromReleaseDocumentId as getReleaseIdFromReleaseDocumentId2,
5685
+ getReleaseIdFromReleaseDocumentId as getReleaseIdFromReleaseDocumentId4,
5182
5686
  useClient as useClient9,
5183
5687
  useCurrentUser,
5184
5688
  useDataset,
@@ -5207,9 +5711,9 @@ function createRunEvaluationAction(options = {}) {
5207
5711
  const projectId = useProjectId();
5208
5712
  const currentUser = useCurrentUser();
5209
5713
  const [state, setState] = useState11({ status: "loading" });
5210
- const requestedAtRef = useRef3(null);
5211
- const perspectiveId = getReleaseIdFromReleaseDocumentId2(release._id);
5212
- useEffect9(() => {
5714
+ const requestedAtRef = useRef4(null);
5715
+ const perspectiveId = getReleaseIdFromReleaseDocumentId4(release._id);
5716
+ useEffect10(() => {
5213
5717
  let cancelled = false;
5214
5718
  client.fetch(contentImpactQuery, buildReportQueryParams(perspectiveId)).then((results) => {
5215
5719
  if (cancelled) return;
@@ -5232,7 +5736,7 @@ function createRunEvaluationAction(options = {}) {
5232
5736
  cancelled = true;
5233
5737
  };
5234
5738
  }, [client, perspectiveId]);
5235
- useEffect9(() => {
5739
+ useEffect10(() => {
5236
5740
  if (state.status !== "requested" && state.status !== "polling") return;
5237
5741
  const { requestId, startedAt } = state;
5238
5742
  if (state.status === "requested") {
@@ -5282,7 +5786,7 @@ function createRunEvaluationAction(options = {}) {
5282
5786
  }, POLL_INTERVAL_MS);
5283
5787
  return () => clearInterval(interval);
5284
5788
  }, [client, perspectiveId, state]);
5285
- useEffect9(() => {
5789
+ useEffect10(() => {
5286
5790
  if (state.status !== "error") return;
5287
5791
  const timer = setTimeout(() => {
5288
5792
  client.fetch(contentImpactQuery, buildReportQueryParams(perspectiveId)).then((results) => {
@@ -5302,7 +5806,7 @@ function createRunEvaluationAction(options = {}) {
5302
5806
  }, 15e3);
5303
5807
  return () => clearTimeout(timer);
5304
5808
  }, [client, perspectiveId, state]);
5305
- const handleRequest = useCallback12(async () => {
5809
+ const handleRequest = useCallback15(async () => {
5306
5810
  const releaseTitle = release.metadata?.title ?? perspectiveId ?? "release";
5307
5811
  const tag = `release-${slugify(releaseTitle)}-${dateStamp()}`;
5308
5812
  const now = Date.now();
@@ -5424,9 +5928,12 @@ var ailfPlugin = definePlugin({
5424
5928
  tools: [ailfTool()]
5425
5929
  });
5426
5930
  export {
5931
+ AssertionInput,
5932
+ CanonicalDocInput,
5427
5933
  GLOSSARY,
5428
5934
  GraduateToNativeAction,
5429
5935
  MirrorBanner,
5936
+ ReleasePicker,
5430
5937
  SyncStatusBadge,
5431
5938
  ailfPlugin,
5432
5939
  ailfTool,