@netnodeag/kraftwerk 0.4.1 → 0.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/yaml.js CHANGED
@@ -3,7 +3,7 @@ import path from "node:path";
3
3
  import { Ajv } from "ajv";
4
4
  import { parse } from "yaml";
5
5
  import { envelopeContract } from "./envelope.js";
6
- import { containsText, fileNonEmpty, slotsFilled } from "./gates.js";
6
+ import { checkScript, containsText, fileNonEmpty, slotsFilled } from "./gates.js";
7
7
  import { Run } from "./run.js";
8
8
  import { summaryTable } from "./stats.js";
9
9
  import { runStamp } from "./workflow.js";
@@ -41,7 +41,7 @@ import { runStamp } from "./workflow.js";
41
41
  * prompt itself. Not in v1 (roadmap): approval loops,
42
42
  * AGENTS.md-style context files, skills.
43
43
  */
44
- const GATE_HINT = "Gates: file_non_empty: <file> | slots_filled: <file> | contains: {file, text, label?}";
44
+ const GATE_HINT = "Gates: file_non_empty: <file> | slots_filled: <file> | contains: {file, text, label?} | check: <script> or {run, label?}";
45
45
  const VARIABLES = ["request", "agent"];
46
46
  let compiledSchema;
47
47
  async function schemaValidator() {
@@ -56,7 +56,7 @@ const MCP_HINT = "MCP servers: {command, args?, env?} (stdio) OR {url} (remote s
56
56
  const CLI_HINT = "CLIs: <command prefix>: <one-line usage hint> — name e.g. git, ddev, npm run (no special characters)";
57
57
  function formatAjvErrors(errors, file) {
58
58
  // oneOf mismatches (gates, steps, mcp) explode into per-branch errors; keep it readable.
59
- const relevant = errors.filter((e) => e.keyword !== "oneOf" || !/\/gates\/|\/steps\/\d+$|^\/mcp\//.test(e.instancePath));
59
+ const relevant = errors.filter((e) => e.keyword !== "oneOf" || !/\/gates\/|\/if\/|\/steps\/\d+$|^\/mcp\//.test(e.instancePath));
60
60
  const lines = relevant.slice(0, 4).map((e) => {
61
61
  const where = e.instancePath || "/";
62
62
  if (e.keyword === "additionalProperties") {
@@ -67,7 +67,9 @@ function formatAjvErrors(errors, file) {
67
67
  }
68
68
  return `${where}: ${e.message}`;
69
69
  });
70
- const gateHint = errors.some((e) => e.instancePath.includes("/gates/")) ? `\n${GATE_HINT}` : "";
70
+ const gateHint = errors.some((e) => e.instancePath.includes("/gates/") || e.instancePath.includes("/if/"))
71
+ ? `\n${GATE_HINT}`
72
+ : "";
71
73
  const stepHint = errors.some((e) => e.keyword === "oneOf" && /\/steps\/\d+$/.test(e.instancePath))
72
74
  ? `\n${STEP_HINT}`
73
75
  : "";
@@ -215,7 +217,14 @@ export async function loadWorkflow(givenPath) {
215
217
  if (seen.has(s.name))
216
218
  at(`step name "${s.name}" is a duplicate`);
217
219
  seen.add(s.name);
218
- const gates = (s.gates ?? []).map((g, j) => buildGate(g, (message) => fail(`steps[${i}].gates[${j}]: ${message}`)));
220
+ const gates = [];
221
+ for (const [j, g] of (s.gates ?? []).entries()) {
222
+ gates.push(await buildGate(g, resolveText, `steps[${i}].gates[${j}]`, (message) => fail(`steps[${i}].gates[${j}]: ${message}`)));
223
+ }
224
+ const preconditions = [];
225
+ for (const [j, g] of (s.if ?? []).entries()) {
226
+ preconditions.push(await buildGate(g, resolveText, `steps[${i}].if[${j}]`, (message) => fail(`steps[${i}].if[${j}]: ${message}`)));
227
+ }
219
228
  if (s.run !== undefined) {
220
229
  const script = await resolveText(s.run, `steps[${i}].run`);
221
230
  for (const match of script.matchAll(/\$\{\{\s*(\w+)\s*\}\}/g)) {
@@ -223,7 +232,7 @@ export async function loadWorkflow(givenPath) {
223
232
  at(`unknown variable \${{ ${match[1]} }} — run steps only support \${{ request }} (plus env: REQUEST, RUN_DIR, PHASE, WORKFLOW_DIR)`);
224
233
  }
225
234
  }
226
- steps.push({ kind: "script", name: s.name, script, gates });
235
+ steps.push({ kind: "script", name: s.name, script, gates, preconditions });
227
236
  continue;
228
237
  }
229
238
  const agent = agents.get(s.agent);
@@ -236,7 +245,7 @@ export async function loadWorkflow(givenPath) {
236
245
  at(`unknown variable \${{ ${match[1]} }} — available: ${VARIABLES.join(", ")}`);
237
246
  }
238
247
  }
239
- steps.push({ kind: "agent", name: s.name, agent: agent, prompt, gates });
248
+ steps.push({ kind: "agent", name: s.name, agent: agent, prompt, gates, preconditions });
240
249
  }
241
250
  const requires = raw.requires ?? [];
242
251
  return {
@@ -278,6 +287,24 @@ export async function loadWorkflow(givenPath) {
278
287
  : { name: s.name, kind: "agent", agent: s.agent.id, model: s.agent.model }),
279
288
  });
280
289
  for (const step of steps) {
290
+ // `if:` preconditions — deterministic checks on run-dir files. Any
291
+ // unmet precondition SKIPS the step (the run continues); this is how
292
+ // a workflow avoids spawning an agent when there is nothing to do.
293
+ if (step.preconditions.length > 0) {
294
+ const unmet = [];
295
+ for (const pre of step.preconditions) {
296
+ const failure = await pre.check(runDir);
297
+ if (failure)
298
+ unmet.push(`${pre.name}: ${failure}`);
299
+ }
300
+ if (unmet.length > 0) {
301
+ console.log(`\n▸ Phase "${step.name}" — skipped (if: not met)`);
302
+ for (const reason of unmet)
303
+ console.log(` ↷ ${reason}`);
304
+ await run.trace("phase_skipped", { phase: step.name, unmet });
305
+ continue;
306
+ }
307
+ }
281
308
  if (step.kind === "script") {
282
309
  await run.scriptPhase({
283
310
  name: step.name,
@@ -309,7 +336,7 @@ export async function loadWorkflow(givenPath) {
309
336
  /** Back-compat alias for the single-file entry point. */
310
337
  export const loadWorkflowYaml = loadWorkflow;
311
338
  /** One YAML gate entry (single-key mapping, schema-checked) -> a Gate. */
312
- function buildGate(g, at) {
339
+ async function buildGate(g, resolveText, field, at) {
313
340
  const [gateName, value] = Object.entries(g)[0];
314
341
  switch (gateName) {
315
342
  case "file_non_empty":
@@ -318,6 +345,12 @@ function buildGate(g, at) {
318
345
  return slotsFilled(value);
319
346
  case "contains":
320
347
  return containsText(value.file, value.text, value.label ?? value.text);
348
+ case "check": {
349
+ // String form: `check: scripts/x.sh`; object form: `check: {run, label?}`.
350
+ const ref = typeof value === "string" ? value : value.run;
351
+ const label = typeof value === "string" ? ref : (value.label ?? value.run);
352
+ return checkScript(await resolveText(ref, field), label);
353
+ }
321
354
  default:
322
355
  return at(`unknown gate "${gateName}" — ${GATE_HINT}`);
323
356
  }
@@ -1 +1 @@
1
- @font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/ibm-plex-sans-latin-400-normal-CDDApCn2.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-400-normal-CYLoc0-x.woff) format("woff")}@font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/ibm-plex-sans-latin-500-normal-6ng42L7E.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-500-normal-BgVn5rGT.woff) format("woff")}@font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/ibm-plex-sans-latin-600-normal-CuJfVYMP.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-600-normal-Cu4Hd6ag.woff) format("woff")}@font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/ibm-plex-sans-latin-700-normal-Bxkt5Cjx.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-700-normal-Bth3BMcD.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/ibm-plex-mono-latin-400-normal-DMJ8VG8y.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-400-normal-CvHOgSBP.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/ibm-plex-mono-latin-500-normal-DSY6xOcd.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-500-normal-CB9ihrfo.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/ibm-plex-mono-latin-600-normal-BgSNZQsw.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-600-normal-DWFSQ4vo.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/ibm-plex-mono-latin-700-normal-7sUh57Bg.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-700-normal-CNHXzs6v.woff) format("woff")}:root{--font-sans: "IBM Plex Sans";--font-mono: "IBM Plex Mono";--bg: #141512;--bg-deep: #0e0f0d;--panel: #1b1d19;--panel-2: #22241f;--line: #2e312a;--line-soft: #262822;--ink: #ecebe3;--ink-2: #b3b1a4;--muted: #7c7a6e;--accent: #f5a623;--accent-dim: rgba(245, 166, 35, .14);--ok: #56c15a;--ok-dim: rgba(86, 193, 90, .14);--fail: #e5484d;--fail-dim: rgba(229, 72, 77, .14);--run: #f5a623;--pending: #4c4e46;--shadow: 0 1px 0 rgba(255, 255, 255, .03) inset, 0 8px 24px rgba(0, 0, 0, .35);color-scheme:dark}:root[data-theme=light]{--bg: #f1f0ea;--bg-deep: #e8e7df;--panel: #fbfaf6;--panel-2: #f3f2ec;--line: #d9d7cc;--line-soft: #e3e1d6;--ink: #1d1e19;--ink-2: #55564c;--muted: #8a887b;--accent: #c77c11;--accent-dim: rgba(199, 124, 17, .12);--ok: #2e8f38;--ok-dim: rgba(46, 143, 56, .12);--fail: #c73538;--fail-dim: rgba(199, 53, 56, .1);--run: #c77c11;--pending: #c9c7bb;--shadow: 0 1px 2px rgba(29, 30, 25, .06);color-scheme:light}*{box-sizing:border-box;margin:0;padding:0}html{height:100%}body{min-height:100%;background:radial-gradient(1200px 400px at 50% -200px,rgba(245,166,35,.05),transparent 70%),var(--bg);color:var(--ink);font-family:var(--font-sans),sans-serif;font-size:14px;line-height:1.5;-webkit-font-smoothing:antialiased}a{color:inherit;text-decoration:none}button{font:inherit;color:inherit;background:none;border:0;cursor:pointer}code,pre,.mono{font-family:var(--font-mono),monospace}.topbar{position:sticky;top:0;z-index:10;display:flex;align-items:center;gap:14px;padding:10px 20px;background:color-mix(in srgb,var(--bg) 86%,transparent);-webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);border-bottom:1px solid var(--line)}.wordmark{display:flex;align-items:center;gap:10px}.wordmark .lamp-block{width:22px;height:22px;border-radius:5px;background:linear-gradient(135deg,var(--accent),#d2820b);display:grid;place-items:center;box-shadow:0 0 14px #f5a62359}.wordmark .lamp-block span{width:7px;height:7px;border-radius:2px;background:#141512}.wordmark b{font-family:var(--font-mono),monospace;font-size:13.5px;font-weight:700;letter-spacing:.14em;text-transform:uppercase}.wordmark small{font-size:11px;letter-spacing:.22em;text-transform:uppercase;color:var(--muted)}.topbar .spacer{flex:1}.topbar nav{display:flex;gap:4px;margin-left:10px}.topbar nav a{font-size:11px;font-weight:600;letter-spacing:.14em;text-transform:uppercase;color:var(--muted);padding:4px 10px;border-radius:6px}.topbar nav a:hover{color:var(--ink);background:var(--panel-2)}.topbar .outdir{font-family:var(--font-mono),monospace;font-size:11px;color:var(--muted);max-width:44vw;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.theme-btn{border:1px solid var(--line);border-radius:6px;padding:4px 10px;font-size:11.5px;letter-spacing:.08em;text-transform:uppercase;color:var(--ink-2)}.theme-btn:hover{border-color:var(--accent);color:var(--ink)}.shell{max-width:1240px;margin:0 auto;padding:26px 20px 80px}.microlabel{font-size:10.5px;font-weight:600;letter-spacing:.18em;text-transform:uppercase;color:var(--muted)}.num{font-variant-numeric:tabular-nums}.lamp{width:9px;height:9px;border-radius:50%;flex:none;position:relative}.lamp.ok{background:var(--ok);box-shadow:0 0 6px color-mix(in srgb,var(--ok) 60%,transparent)}.lamp.failed,.lamp.blocked{background:var(--fail);box-shadow:0 0 6px color-mix(in srgb,var(--fail) 60%,transparent)}.lamp.aborted{background:var(--pending)}.lamp.pending{background:transparent;border:1.5px solid var(--pending)}.lamp.running{background:var(--run);animation:lamp-pulse 1.4s ease-in-out infinite}@keyframes lamp-pulse{0%,to{box-shadow:0 0 4px color-mix(in srgb,var(--run) 55%,transparent);opacity:1}50%{box-shadow:0 0 14px var(--run);opacity:.75}}.status-word{font-size:11px;font-weight:650;letter-spacing:.14em;text-transform:uppercase}.status-word.ok{color:var(--ok)}.status-word.failed,.status-word.blocked{color:var(--fail)}.status-word.running{color:var(--run)}.status-word.aborted,.status-word.pending{color:var(--muted)}.page-head{display:flex;align-items:baseline;gap:14px;margin:6px 2px 18px}.page-head h1{font-size:19px;font-weight:650;letter-spacing:-.01em}.page-head .count{color:var(--muted);font-size:13px}.run-list{display:grid;gap:10px}.run-card{display:grid;grid-template-columns:12px 200px 1fr auto;gap:8px 16px;align-items:center;background:var(--panel);border:1px solid var(--line);border-radius:8px;padding:13px 18px;box-shadow:var(--shadow);transition:border-color .12s ease,transform .12s ease}.run-card:hover{border-color:color-mix(in srgb,var(--accent) 55%,var(--line));transform:translateY(-1px)}.run-card .rid{font-family:var(--font-mono),monospace;font-size:12.5px;color:var(--ink-2)}.run-card .wf{font-weight:650;font-size:14px}.run-card .req{color:var(--muted);font-size:12.5px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;max-width:52ch}.run-card .meta{display:flex;gap:18px;align-items:center;font-family:var(--font-mono),monospace;font-size:12px;color:var(--ink-2)}.progress-track{width:90px;height:4px;border-radius:2px;background:var(--line-soft);overflow:hidden}.progress-track i{display:block;height:100%;background:var(--accent);border-radius:2px}.run-card.is-ok .progress-track i{background:var(--ok)}.run-card.is-failed .progress-track i{background:var(--fail)}.empty{border:1px dashed var(--line);border-radius:8px;padding:40px;text-align:center;color:var(--muted)}.crumbs{display:flex;align-items:center;gap:8px;font-size:12.5px;color:var(--muted);margin-bottom:14px}.crumbs a:hover{color:var(--accent)}.crumbs .sep{color:var(--line)}.detail-head{display:flex;flex-wrap:wrap;align-items:center;gap:10px 16px;margin-bottom:6px}.detail-head h1{font-size:18px;font-weight:650}.detail-head .rid{font-family:var(--font-mono),monospace;font-size:12px;color:var(--muted)}.detail-req{color:var(--ink-2);font-size:13px;margin-bottom:18px;max-width:90ch}.statgrid{display:flex;flex-wrap:wrap;gap:26px;margin-bottom:22px}.stat .microlabel{margin-bottom:1px}.stat .v{font-family:var(--font-mono),monospace;font-size:15px;font-weight:600}.columns{display:grid;grid-template-columns:minmax(430px,5fr) minmax(360px,4fr);gap:18px;align-items:start}@media(max-width:1020px){.columns{grid-template-columns:1fr}}.panel{background:var(--panel);border:1px solid var(--line);border-radius:8px;box-shadow:var(--shadow);overflow:hidden}.panel-head{display:flex;align-items:center;gap:10px;padding:10px 16px;border-bottom:1px solid var(--line-soft);background:var(--panel-2)}.panel-head .microlabel{color:var(--ink-2)}.panel-head .spacer{flex:1}.phases{padding:6px 0}.phase-row{position:relative;padding:10px 16px 10px 40px}.phase-row+.phase-row{border-top:1px solid var(--line-soft)}.phase-row .lamp{position:absolute;left:17px;top:16px}.phase-row:before{content:"";position:absolute;left:21px;top:0;bottom:0;width:1px;background:var(--line-soft)}.phase-row:first-child:before{top:16px}.phase-row:last-child:before{bottom:auto;height:16px}.phase-row .lamp{z-index:1}.phase-top{display:flex;align-items:baseline;gap:10px;flex-wrap:wrap}.phase-name{font-weight:650;font-size:13.5px}.chip{font-family:var(--font-mono),monospace;font-size:10.5px;border:1px solid var(--line);border-radius:4px;padding:1px 7px;color:var(--ink-2)}.chip.agent{border-color:color-mix(in srgb,var(--accent) 40%,var(--line));color:var(--accent)}.phase-top .right{margin-left:auto;display:flex;gap:14px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--muted)}.phase-sub{margin-top:3px;font-size:12.5px;color:var(--ink-2);max-width:72ch}.phase-activity{margin-top:3px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--run)}.phase-activity:before{content:"▸ "}.gate-line{margin-top:5px;display:flex;flex-wrap:wrap;gap:6px}.gate{display:inline-flex;align-items:center;gap:5px;font-family:var(--font-mono),monospace;font-size:10.5px;border-radius:4px;padding:1.5px 7px;background:var(--ok-dim);color:var(--ok)}.gate.failed{background:var(--fail-dim);color:var(--fail)}.gate-fail-msg{margin-top:4px;font-size:12px;color:var(--fail)}.file-list{max-height:300px;overflow:auto}.file-row{display:flex;align-items:center;gap:10px;width:100%;text-align:left;padding:7px 16px;font-family:var(--font-mono),monospace;font-size:12.5px;border-bottom:1px solid var(--line-soft);color:var(--ink-2)}.file-row:last-child{border-bottom:0}.file-row:hover{background:var(--panel-2);color:var(--ink)}.file-row.active{background:var(--accent-dim);color:var(--ink)}.file-row .fname{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.file-row .fsize{color:var(--muted);font-size:11px}.viewer{border-top:1px solid var(--line)}.viewer-body pre{padding:14px 16px;overflow:auto;max-height:560px;font-size:11.8px;line-height:1.55;white-space:pre-wrap;word-break:break-word;color:var(--ink-2)}.viewer-body iframe{width:100%;height:620px;border:0;background:#fff;display:block}.viewer-body img{max-width:100%;display:block;padding:14px 16px}.viewer-note{padding:6px 16px;font-size:11px;color:var(--muted);border-bottom:1px solid var(--line-soft)}.open-raw{font-size:11px;letter-spacing:.06em;text-transform:uppercase;color:var(--muted);border:1px solid var(--line);border-radius:5px;padding:2px 8px}.open-raw:hover{color:var(--accent);border-color:var(--accent)}.live-note{display:inline-flex;align-items:center;gap:7px;font-size:11px;color:var(--muted)}.wf-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(300px,1fr));gap:12px}.wf-card{display:flex;flex-direction:column;gap:6px;background:var(--panel);border:1px solid var(--line);border-radius:8px;padding:16px 18px;box-shadow:var(--shadow);transition:border-color .12s ease,transform .12s ease}.wf-card:hover{border-color:color-mix(in srgb,var(--accent) 55%,var(--line));transform:translateY(-1px)}.wf-card-head{display:flex;align-items:baseline;gap:10px}.wf-name{font-weight:650;font-size:15px;font-family:var(--font-mono),monospace}.wf-desc{color:var(--ink-2);font-size:12.5px;flex:1}.wf-meta{display:flex;gap:8px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--muted)}.wf-workspace{font-size:11.5px;color:var(--ink-2);white-space:pre-wrap}.aid-0{--aid: var(--accent)}.aid-1{--aid: #4fb8a8}.aid-2{--aid: #a78bfa}.aid-3{--aid: #e5793b}.agent-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(280px,1fr));gap:0}.agent-card{padding:14px 18px;border-right:1px solid var(--line-soft);border-bottom:1px solid var(--line-soft)}.agent-head{display:flex;align-items:center;gap:8px;flex-wrap:wrap}.agent-head b{font-size:13.5px}.agent-head .spacer{flex:1}.agent-id{font-size:11px;color:var(--muted)}.agent-dot{width:10px;height:10px;border-radius:3px;background:var(--aid);box-shadow:0 0 8px color-mix(in srgb,var(--aid) 45%,transparent)}.agent-tools{display:flex;flex-wrap:wrap;gap:5px;margin-top:8px}.tool-chip{font-family:var(--font-mono),monospace;font-size:10.5px;border:1px solid var(--line);border-radius:4px;padding:1px 6px;color:var(--ink-2)}.agent-persona{margin-top:8px;font-size:12px;color:var(--muted);line-height:1.55;white-space:pre-wrap}.pipeline{padding:8px 0}.step-node{position:relative;display:flex;gap:14px;padding:12px 18px}.step-node+.step-node{border-top:1px solid var(--line-soft)}.step-node:before{content:"";position:absolute;left:30px;top:0;bottom:0;width:1px;background:var(--line-soft)}.step-node:first-child:before{top:18px}.step-node:last-child:before{bottom:auto;height:18px}.step-index{position:relative;z-index:1;flex:none;width:25px;height:25px;border-radius:6px;margin-top:1px;display:grid;place-items:center;font-family:var(--font-mono),monospace;font-size:11.5px;font-weight:700;background:color-mix(in srgb,var(--aid) 16%,var(--panel));border:1px solid color-mix(in srgb,var(--aid) 55%,var(--line));color:var(--aid)}.step-index.is-script{--aid: var(--ink-2)}.step-body{flex:1;min-width:0}.agent-chip{border-color:color-mix(in srgb,var(--aid) 50%,var(--line));color:var(--aid)}.step-source{margin-top:6px}.step-source summary{cursor:pointer;font-size:11px;letter-spacing:.1em;text-transform:uppercase;color:var(--muted);-webkit-user-select:none;user-select:none}.step-source summary:hover{color:var(--accent)}.step-source pre{margin-top:6px;padding:10px 12px;border:1px solid var(--line-soft);border-radius:6px;background:var(--bg-deep);font-size:11.5px;line-height:1.55;white-space:pre-wrap;word-break:break-word;color:var(--ink-2);max-height:360px;overflow:auto}.gate.neutral{background:var(--panel-2);color:var(--ink-2);border:1px solid var(--line-soft)}::-webkit-scrollbar{width:10px;height:10px}::-webkit-scrollbar-thumb{background:var(--line);border-radius:5px;border:2px solid transparent;background-clip:content-box}::-webkit-scrollbar-track{background:transparent}.run-form{display:flex;gap:10px}.run-form input[type=text]{flex:1;font:13px/1.4 var(--font-mono),monospace;color:var(--ink);background:var(--panel-2);border:1px solid var(--line);border-radius:7px;padding:9px 12px;outline:none}.run-form input[type=text]:focus{border-color:var(--accent)}.run-btn{font:600 12.5px/1 var(--font-sans),sans-serif;white-space:nowrap;color:#141512;background:var(--accent);border-radius:7px;padding:10px 16px}.run-btn:hover{filter:brightness(1.08)}.run-btn:disabled{opacity:.45;cursor:not-allowed;filter:none}.run-opts{display:flex;flex-wrap:wrap;gap:6px 22px;margin-top:10px}.run-opts label{display:inline-flex;align-items:center;gap:7px;font-size:12.5px;color:var(--ink-2);cursor:pointer}.run-opts input[type=checkbox]{accent-color:var(--accent)}.run-opts .opt-hint{color:var(--muted)}.sandbox-chip{border:1px solid var(--line);color:var(--ink-2)}.stop-btn{font:600 12px/1 var(--font-sans),sans-serif;color:var(--fail);background:var(--fail-dim);border:1px solid color-mix(in srgb,var(--fail) 40%,transparent);border-radius:7px;padding:7px 13px}.stop-btn:hover{border-color:var(--fail)}.stop-btn:disabled{opacity:.5;cursor:default}.shell:has(.runs-screen){max-width:none;padding:0}.runs-screen{display:grid;grid-template-columns:300px minmax(0,1fr);align-items:start}.runs-side{position:sticky;top:45px;height:calc(100vh - 45px);display:flex;flex-direction:column;border-right:1px solid var(--line);background:var(--panel)}.side-head{display:flex;align-items:center;gap:10px;padding:10px 14px;border-bottom:1px solid var(--line-soft);background:var(--panel-2)}.side-head .spacer{flex:1}.side-list{flex:1;overflow-y:auto}.side-row{display:flex;align-items:flex-start;gap:9px;padding:9px 12px 9px 14px;border-bottom:1px solid var(--line-soft);border-left:2px solid transparent}.side-row .lamp{margin-top:4px}.side-row:hover{background:var(--panel-2)}.side-row.active{background:var(--accent-dim);border-left-color:var(--accent)}.side-row-body{flex:1;min-width:0}.side-row-top{display:flex;align-items:baseline;gap:8px}.side-wf{font-weight:650;font-size:12.5px;flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.side-when{font-family:var(--font-mono),monospace;font-size:10.5px;color:var(--muted)}.side-row-sub{display:flex;align-items:baseline;gap:8px;margin-top:1px}.side-req{flex:1;font-size:11.5px;color:var(--muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.side-row.active .side-req{color:var(--ink-2)}.side-meta{font-family:var(--font-mono),monospace;font-size:10.5px;color:var(--muted)}.runs-main{padding:16px 20px 40px;min-width:0}.runs-main .detail-head .spacer{flex:1}.tabs{display:flex;gap:2px;background:var(--panel-2);border:1px solid var(--line);border-radius:7px;padding:2px}.tabs button{font-size:11px;font-weight:600;letter-spacing:.1em;text-transform:uppercase;color:var(--muted);padding:5px 13px;border-radius:5px}.tabs button:hover{color:var(--ink)}.tabs button.active{background:var(--panel);color:var(--ink);box-shadow:var(--shadow)}.run-tab{max-width:1080px}.art-layout{display:grid;grid-template-columns:280px minmax(0,1fr);gap:14px;height:calc(100vh - 168px);min-height:420px}.art-files{display:flex;flex-direction:column;min-height:0}.art-files .file-list{flex:1;max-height:none}.art-viewer{display:flex;flex-direction:column;min-height:0}.art-viewer .viewer{flex:1;display:flex;flex-direction:column;min-height:0;border-top:0}.art-viewer .viewer-body{flex:1;min-height:0}.art-viewer .viewer-body iframe{height:100%}.art-viewer .viewer-body pre{max-height:none;height:100%;box-sizing:border-box}.art-viewer .viewer-body img{max-height:100%;object-fit:contain}.art-viewer .empty{flex:1;display:grid;place-items:center}@media(max-width:940px){.runs-screen{grid-template-columns:1fr}.runs-side{display:none}.art-layout{grid-template-columns:1fr;height:auto}.art-files .file-list{max-height:240px}.art-viewer .viewer-body iframe{height:560px}}
1
+ @font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/ibm-plex-sans-latin-400-normal-CDDApCn2.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-400-normal-CYLoc0-x.woff) format("woff")}@font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/ibm-plex-sans-latin-500-normal-6ng42L7E.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-500-normal-BgVn5rGT.woff) format("woff")}@font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/ibm-plex-sans-latin-600-normal-CuJfVYMP.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-600-normal-Cu4Hd6ag.woff) format("woff")}@font-face{font-family:IBM Plex Sans;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/ibm-plex-sans-latin-700-normal-Bxkt5Cjx.woff2) format("woff2"),url(/assets/ibm-plex-sans-latin-700-normal-Bth3BMcD.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/ibm-plex-mono-latin-400-normal-DMJ8VG8y.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-400-normal-CvHOgSBP.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/ibm-plex-mono-latin-500-normal-DSY6xOcd.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-500-normal-CB9ihrfo.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/ibm-plex-mono-latin-600-normal-BgSNZQsw.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-600-normal-DWFSQ4vo.woff) format("woff")}@font-face{font-family:IBM Plex Mono;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/ibm-plex-mono-latin-700-normal-7sUh57Bg.woff2) format("woff2"),url(/assets/ibm-plex-mono-latin-700-normal-CNHXzs6v.woff) format("woff")}:root{--font-sans: "IBM Plex Sans";--font-mono: "IBM Plex Mono";--bg: #141512;--bg-deep: #0e0f0d;--panel: #1b1d19;--panel-2: #22241f;--line: #2e312a;--line-soft: #262822;--ink: #ecebe3;--ink-2: #b3b1a4;--muted: #7c7a6e;--accent: #f5a623;--accent-dim: rgba(245, 166, 35, .14);--ok: #56c15a;--ok-dim: rgba(86, 193, 90, .14);--fail: #e5484d;--fail-dim: rgba(229, 72, 77, .14);--run: #f5a623;--pending: #4c4e46;--shadow: 0 1px 0 rgba(255, 255, 255, .03) inset, 0 8px 24px rgba(0, 0, 0, .35);color-scheme:dark}:root[data-theme=light]{--bg: #f1f0ea;--bg-deep: #e8e7df;--panel: #fbfaf6;--panel-2: #f3f2ec;--line: #d9d7cc;--line-soft: #e3e1d6;--ink: #1d1e19;--ink-2: #55564c;--muted: #8a887b;--accent: #c77c11;--accent-dim: rgba(199, 124, 17, .12);--ok: #2e8f38;--ok-dim: rgba(46, 143, 56, .12);--fail: #c73538;--fail-dim: rgba(199, 53, 56, .1);--run: #c77c11;--pending: #c9c7bb;--shadow: 0 1px 2px rgba(29, 30, 25, .06);color-scheme:light}*{box-sizing:border-box;margin:0;padding:0}html{height:100%}body{min-height:100%;background:radial-gradient(1200px 400px at 50% -200px,rgba(245,166,35,.05),transparent 70%),var(--bg);color:var(--ink);font-family:var(--font-sans),sans-serif;font-size:14px;line-height:1.5;-webkit-font-smoothing:antialiased}a{color:inherit;text-decoration:none}button{font:inherit;color:inherit;background:none;border:0;cursor:pointer}code,pre,.mono{font-family:var(--font-mono),monospace}.topbar{position:sticky;top:0;z-index:10;display:flex;align-items:center;gap:14px;padding:10px 20px;background:color-mix(in srgb,var(--bg) 86%,transparent);-webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);border-bottom:1px solid var(--line)}.wordmark{display:flex;align-items:center;gap:10px}.wordmark .lamp-block{width:22px;height:22px;border-radius:5px;background:linear-gradient(135deg,var(--accent),#d2820b);display:grid;place-items:center;box-shadow:0 0 14px #f5a62359}.wordmark .lamp-block span{width:7px;height:7px;border-radius:2px;background:#141512}.wordmark b{font-family:var(--font-mono),monospace;font-size:13.5px;font-weight:700;letter-spacing:.14em;text-transform:uppercase}.wordmark small{font-size:11px;letter-spacing:.22em;text-transform:uppercase;color:var(--muted)}.topbar .spacer{flex:1}.topbar nav{display:flex;gap:4px;margin-left:10px}.topbar nav a{font-size:11px;font-weight:600;letter-spacing:.14em;text-transform:uppercase;color:var(--muted);padding:4px 10px;border-radius:6px}.topbar nav a:hover{color:var(--ink);background:var(--panel-2)}.topbar .outdir{font-family:var(--font-mono),monospace;font-size:11px;color:var(--muted);max-width:44vw;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.theme-btn{border:1px solid var(--line);border-radius:6px;padding:4px 10px;font-size:11.5px;letter-spacing:.08em;text-transform:uppercase;color:var(--ink-2)}.theme-btn:hover{border-color:var(--accent);color:var(--ink)}.shell{max-width:1240px;margin:0 auto;padding:26px 20px 80px}.microlabel{font-size:10.5px;font-weight:600;letter-spacing:.18em;text-transform:uppercase;color:var(--muted)}.num{font-variant-numeric:tabular-nums}.lamp{width:9px;height:9px;border-radius:50%;flex:none;position:relative}.lamp.ok{background:var(--ok);box-shadow:0 0 6px color-mix(in srgb,var(--ok) 60%,transparent)}.lamp.failed,.lamp.blocked{background:var(--fail);box-shadow:0 0 6px color-mix(in srgb,var(--fail) 60%,transparent)}.lamp.aborted{background:var(--pending)}.lamp.pending{background:transparent;border:1.5px solid var(--pending)}.lamp.running{background:var(--run);animation:lamp-pulse 1.4s ease-in-out infinite}@keyframes lamp-pulse{0%,to{box-shadow:0 0 4px color-mix(in srgb,var(--run) 55%,transparent);opacity:1}50%{box-shadow:0 0 14px var(--run);opacity:.75}}.status-word{font-size:11px;font-weight:650;letter-spacing:.14em;text-transform:uppercase}.status-word.ok{color:var(--ok)}.status-word.failed,.status-word.blocked{color:var(--fail)}.status-word.running{color:var(--run)}.status-word.aborted,.status-word.pending{color:var(--muted)}.page-head{display:flex;align-items:baseline;gap:14px;margin:6px 2px 18px}.page-head h1{font-size:19px;font-weight:650;letter-spacing:-.01em}.page-head .count{color:var(--muted);font-size:13px}.run-list{display:grid;gap:10px}.run-card{display:grid;grid-template-columns:12px 200px 1fr auto;gap:8px 16px;align-items:center;background:var(--panel);border:1px solid var(--line);border-radius:8px;padding:13px 18px;box-shadow:var(--shadow);transition:border-color .12s ease,transform .12s ease}.run-card:hover{border-color:color-mix(in srgb,var(--accent) 55%,var(--line));transform:translateY(-1px)}.run-card .rid{font-family:var(--font-mono),monospace;font-size:12.5px;color:var(--ink-2)}.run-card .wf{font-weight:650;font-size:14px}.run-card .req{color:var(--muted);font-size:12.5px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;max-width:52ch}.run-card .meta{display:flex;gap:18px;align-items:center;font-family:var(--font-mono),monospace;font-size:12px;color:var(--ink-2)}.progress-track{width:90px;height:4px;border-radius:2px;background:var(--line-soft);overflow:hidden}.progress-track i{display:block;height:100%;background:var(--accent);border-radius:2px}.run-card.is-ok .progress-track i{background:var(--ok)}.run-card.is-failed .progress-track i{background:var(--fail)}.empty{border:1px dashed var(--line);border-radius:8px;padding:40px;text-align:center;color:var(--muted)}.crumbs{display:flex;align-items:center;gap:8px;font-size:12.5px;color:var(--muted);margin-bottom:14px}.crumbs a:hover{color:var(--accent)}.crumbs .sep{color:var(--line)}.detail-head{display:flex;flex-wrap:wrap;align-items:center;gap:10px 16px;margin-bottom:6px}.detail-head h1{font-size:18px;font-weight:650}.detail-head .rid{font-family:var(--font-mono),monospace;font-size:12px;color:var(--muted)}.detail-req{color:var(--ink-2);font-size:13px;margin-bottom:18px;max-width:90ch}.statgrid{display:flex;flex-wrap:wrap;gap:26px;margin-bottom:22px}.stat .microlabel{margin-bottom:1px}.stat .v{font-family:var(--font-mono),monospace;font-size:15px;font-weight:600}.columns{display:grid;grid-template-columns:minmax(430px,5fr) minmax(360px,4fr);gap:18px;align-items:start}@media(max-width:1020px){.columns{grid-template-columns:1fr}}.panel{background:var(--panel);border:1px solid var(--line);border-radius:8px;box-shadow:var(--shadow);overflow:hidden}.panel-head{display:flex;align-items:center;gap:10px;padding:10px 16px;border-bottom:1px solid var(--line-soft);background:var(--panel-2)}.panel-head .microlabel{color:var(--ink-2)}.panel-head .spacer{flex:1}.phases{padding:6px 0}.phase-row{position:relative;padding:10px 16px 10px 40px}.phase-row+.phase-row{border-top:1px solid var(--line-soft)}.phase-row .lamp{position:absolute;left:17px;top:16px}.phase-row:before{content:"";position:absolute;left:21px;top:0;bottom:0;width:1px;background:var(--line-soft)}.phase-row:first-child:before{top:16px}.phase-row:last-child:before{bottom:auto;height:16px}.phase-row .lamp{z-index:1}.phase-top{display:flex;align-items:baseline;gap:10px;flex-wrap:wrap}.phase-name{font-weight:650;font-size:13.5px}.chip{font-family:var(--font-mono),monospace;font-size:10.5px;border:1px solid var(--line);border-radius:4px;padding:1px 7px;color:var(--ink-2)}.chip.agent{border-color:color-mix(in srgb,var(--accent) 40%,var(--line));color:var(--accent)}.phase-top .right{margin-left:auto;display:flex;gap:14px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--muted)}.phase-sub{margin-top:3px;font-size:12.5px;color:var(--ink-2);max-width:72ch}.phase-activity{margin-top:3px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--run)}.phase-activity:before{content:"▸ "}.gate-line{margin-top:5px;display:flex;flex-wrap:wrap;gap:6px}.gate{display:inline-flex;align-items:center;gap:5px;font-family:var(--font-mono),monospace;font-size:10.5px;border-radius:4px;padding:1.5px 7px;background:var(--ok-dim);color:var(--ok)}.gate.failed{background:var(--fail-dim);color:var(--fail)}.gate-fail-msg{margin-top:4px;font-size:12px;color:var(--fail)}.file-list{max-height:300px;overflow:auto}.file-row{display:flex;align-items:center;gap:10px;width:100%;text-align:left;padding:7px 16px;font-family:var(--font-mono),monospace;font-size:12.5px;border-bottom:1px solid var(--line-soft);color:var(--ink-2)}.file-row:last-child{border-bottom:0}.file-row:hover{background:var(--panel-2);color:var(--ink)}.file-row.active{background:var(--accent-dim);color:var(--ink)}.file-row .fname{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.file-row .fsize{color:var(--muted);font-size:11px}.viewer{border-top:1px solid var(--line)}.viewer-body pre{padding:14px 16px;overflow:auto;max-height:560px;font-size:11.8px;line-height:1.55;white-space:pre-wrap;word-break:break-word;color:var(--ink-2)}.viewer-body iframe{width:100%;height:620px;border:0;background:#fff;display:block}.viewer-body img{max-width:100%;display:block;padding:14px 16px}.viewer-note{padding:6px 16px;font-size:11px;color:var(--muted);border-bottom:1px solid var(--line-soft)}.open-raw{font-size:11px;letter-spacing:.06em;text-transform:uppercase;color:var(--muted);border:1px solid var(--line);border-radius:5px;padding:2px 8px}.open-raw:hover{color:var(--accent);border-color:var(--accent)}.live-note{display:inline-flex;align-items:center;gap:7px;font-size:11px;color:var(--muted)}.wf-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(300px,1fr));gap:12px}.wf-card{display:flex;flex-direction:column;gap:6px;background:var(--panel);border:1px solid var(--line);border-radius:8px;padding:16px 18px;box-shadow:var(--shadow);transition:border-color .12s ease,transform .12s ease}.wf-card:hover{border-color:color-mix(in srgb,var(--accent) 55%,var(--line));transform:translateY(-1px)}.wf-card-head{display:flex;align-items:baseline;gap:10px}.wf-name{font-weight:650;font-size:15px;font-family:var(--font-mono),monospace}.wf-desc{color:var(--ink-2);font-size:12.5px;flex:1}.wf-meta{display:flex;gap:8px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--muted)}.wf-workspace{font-size:11.5px;color:var(--ink-2);white-space:pre-wrap}.aid-0{--aid: var(--accent)}.aid-1{--aid: #4fb8a8}.aid-2{--aid: #a78bfa}.aid-3{--aid: #e5793b}.agent-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(280px,1fr));gap:0}.agent-card{padding:14px 18px;border-right:1px solid var(--line-soft);border-bottom:1px solid var(--line-soft)}.agent-head{display:flex;align-items:center;gap:8px;flex-wrap:wrap}.agent-head b{font-size:13.5px}.agent-head .spacer{flex:1}.agent-id{font-size:11px;color:var(--muted)}.agent-dot{width:10px;height:10px;border-radius:3px;background:var(--aid);box-shadow:0 0 8px color-mix(in srgb,var(--aid) 45%,transparent)}.agent-tools{display:flex;flex-wrap:wrap;gap:5px;margin-top:8px}.tool-chip{font-family:var(--font-mono),monospace;font-size:10.5px;border:1px solid var(--line);border-radius:4px;padding:1px 6px;color:var(--ink-2)}.agent-persona{margin-top:8px;font-size:12px;color:var(--muted);line-height:1.55;white-space:pre-wrap}.pipeline{padding:8px 0}.step-node{position:relative;display:flex;gap:14px;padding:12px 18px}.step-node+.step-node{border-top:1px solid var(--line-soft)}.step-node:before{content:"";position:absolute;left:30px;top:0;bottom:0;width:1px;background:var(--line-soft)}.step-node:first-child:before{top:18px}.step-node:last-child:before{bottom:auto;height:18px}.step-index{position:relative;z-index:1;flex:none;width:25px;height:25px;border-radius:6px;margin-top:1px;display:grid;place-items:center;font-family:var(--font-mono),monospace;font-size:11.5px;font-weight:700;background:color-mix(in srgb,var(--aid) 16%,var(--panel));border:1px solid color-mix(in srgb,var(--aid) 55%,var(--line));color:var(--aid)}.step-index.is-script{--aid: var(--ink-2)}.step-body{flex:1;min-width:0}.agent-chip{border-color:color-mix(in srgb,var(--aid) 50%,var(--line));color:var(--aid)}.step-source{margin-top:6px}.step-source summary{cursor:pointer;font-size:11px;letter-spacing:.1em;text-transform:uppercase;color:var(--muted);-webkit-user-select:none;user-select:none}.step-source summary:hover{color:var(--accent)}.step-source pre{margin-top:6px;padding:10px 12px;border:1px solid var(--line-soft);border-radius:6px;background:var(--bg-deep);font-size:11.5px;line-height:1.55;white-space:pre-wrap;word-break:break-word;color:var(--ink-2);max-height:360px;overflow:auto}.gate.neutral{background:var(--panel-2);color:var(--ink-2);border:1px solid var(--line-soft)}::-webkit-scrollbar{width:10px;height:10px}::-webkit-scrollbar-thumb{background:var(--line);border-radius:5px;border:2px solid transparent;background-clip:content-box}::-webkit-scrollbar-track{background:transparent}.run-form{display:flex;gap:10px}.run-form input[type=text]{flex:1;font:13px/1.4 var(--font-mono),monospace;color:var(--ink);background:var(--panel-2);border:1px solid var(--line);border-radius:7px;padding:9px 12px;outline:none}.run-form input[type=text]:focus{border-color:var(--accent)}.run-btn{font:600 12.5px/1 var(--font-sans),sans-serif;white-space:nowrap;color:#141512;background:var(--accent);border-radius:7px;padding:10px 16px}.run-btn:hover{filter:brightness(1.08)}.run-btn:disabled{opacity:.45;cursor:not-allowed;filter:none}.run-opts{display:flex;flex-wrap:wrap;gap:6px 22px;margin-top:10px}.run-opts label{display:inline-flex;align-items:center;gap:7px;font-size:12.5px;color:var(--ink-2);cursor:pointer}.run-opts input[type=checkbox]{accent-color:var(--accent)}.run-opts .opt-hint{color:var(--muted)}.sandbox-chip{border:1px solid var(--line);color:var(--ink-2)}.stop-btn{font:600 12px/1 var(--font-sans),sans-serif;color:var(--fail);background:var(--fail-dim);border:1px solid color-mix(in srgb,var(--fail) 40%,transparent);border-radius:7px;padding:7px 13px}.stop-btn:hover{border-color:var(--fail)}.stop-btn:disabled{opacity:.5;cursor:default}.shell:has(.runs-screen){max-width:none;padding:0}.runs-screen{display:grid;grid-template-columns:300px minmax(0,1fr);align-items:start}.runs-side{position:sticky;top:45px;height:calc(100vh - 45px);display:flex;flex-direction:column;border-right:1px solid var(--line);background:var(--panel)}.side-head{display:flex;align-items:center;gap:10px;padding:10px 14px;border-bottom:1px solid var(--line-soft);background:var(--panel-2)}.side-head .spacer{flex:1}.side-list{flex:1;overflow-y:auto}.side-row{display:flex;align-items:flex-start;gap:9px;padding:9px 12px 9px 14px;border-bottom:1px solid var(--line-soft);border-left:2px solid transparent}.side-row .lamp{margin-top:4px}.side-row:hover{background:var(--panel-2)}.side-row.active{background:var(--accent-dim);border-left-color:var(--accent)}.side-row-body{flex:1;min-width:0}.side-row-top{display:flex;align-items:baseline;gap:8px}.side-wf{font-weight:650;font-size:12.5px;flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.side-when{font-family:var(--font-mono),monospace;font-size:10.5px;color:var(--muted)}.side-row-sub{display:flex;align-items:baseline;gap:8px;margin-top:1px}.side-req{flex:1;font-size:11.5px;color:var(--muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.side-row.active .side-req{color:var(--ink-2)}.side-meta{font-family:var(--font-mono),monospace;font-size:10.5px;color:var(--muted)}.runs-main{padding:16px 20px 40px;min-width:0}.runs-main .detail-head .spacer{flex:1}.tabs{display:flex;gap:2px;background:var(--panel-2);border:1px solid var(--line);border-radius:7px;padding:2px}.tabs button{font-size:11px;font-weight:600;letter-spacing:.1em;text-transform:uppercase;color:var(--muted);padding:5px 13px;border-radius:5px}.tabs button:hover{color:var(--ink)}.tabs button.active{background:var(--panel);color:var(--ink);box-shadow:var(--shadow)}.run-tab{max-width:1080px}.art-layout{display:grid;grid-template-columns:280px minmax(0,1fr);gap:14px;height:calc(100vh - 168px);min-height:420px}.art-files{display:flex;flex-direction:column;min-height:0}.art-files .file-list{flex:1;max-height:none}.art-viewer{display:flex;flex-direction:column;min-height:0}.art-viewer .viewer{flex:1;display:flex;flex-direction:column;min-height:0;border-top:0}.art-viewer .viewer-body{flex:1;min-height:0}.art-viewer .viewer-body iframe{height:100%}.art-viewer .viewer-body pre{max-height:none;height:100%;box-sizing:border-box}.art-viewer .viewer-body img{max-height:100%;object-fit:contain}.art-viewer .empty{flex:1;display:grid;place-items:center}@media(max-width:940px){.runs-screen{grid-template-columns:1fr}.runs-side{display:none}.art-layout{grid-template-columns:1fr;height:auto}.art-files .file-list{max-height:240px}.art-viewer .viewer-body iframe{height:560px}}.chat-main{display:flex;flex-direction:column;height:calc(100vh - 45px);padding:16px 20px}.chat-thread{display:flex;flex-direction:column;flex:1;min-height:0;max-width:980px;width:100%;margin:0 auto}.chat-thread .detail-head{flex:none}.chat-thread .detail-head .rid{overflow:hidden;text-overflow:ellipsis;white-space:nowrap;max-width:34ch}.chat-scroll{flex:1;min-height:0;overflow-y:auto;padding:14px 2px 20px;display:flex;flex-direction:column;gap:10px}.chat-scroll .empty{margin:auto;border:0}.msg{max-width:76ch;white-space:pre-wrap;word-break:break-word;font-size:13.5px;line-height:1.6}.msg.user{align-self:flex-end;background:var(--accent-dim);border:1px solid color-mix(in srgb,var(--accent) 35%,var(--line));border-radius:10px 10px 3px;padding:9px 14px}.msg.agent{align-self:flex-start;background:var(--panel);border:1px solid var(--line);border-radius:10px 10px 10px 3px;padding:9px 14px;box-shadow:var(--shadow)}.msg.error{align-self:flex-start;color:var(--fail);font-size:12.5px}.msg.thought{align-self:flex-start;max-width:76ch}.msg.thought summary{cursor:pointer;font-size:11px;letter-spacing:.1em;text-transform:uppercase;color:var(--muted);-webkit-user-select:none;user-select:none}.msg.thought div{margin-top:5px;padding:8px 12px;border-left:2px solid var(--line);color:var(--muted);font-size:12px;white-space:pre-wrap;word-break:break-word}.tool-card{align-self:flex-start;display:inline-flex;align-items:center;gap:9px;font-family:var(--font-mono),monospace;font-size:11.5px;color:var(--ink-2);background:var(--panel-2);border:1px solid var(--line-soft);border-radius:6px;padding:5px 11px;max-width:90ch}.tool-card .tool-title{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.perm-card{align-self:flex-start;border:1px solid color-mix(in srgb,var(--accent) 45%,var(--line));background:var(--accent-dim);border-radius:8px;padding:10px 14px;max-width:76ch}.perm-card .perm-title{font-size:13px}.perm-card .perm-title .microlabel{color:var(--accent);margin-right:8px}.perm-actions{display:flex;flex-wrap:wrap;gap:8px;margin-top:9px}.perm-btn{font:600 12px/1 var(--font-sans),sans-serif;border-radius:6px;padding:7px 13px;border:1px solid var(--line)}.perm-btn.allow{color:#141512;background:var(--accent);border-color:transparent}.perm-btn.allow:hover{filter:brightness(1.08)}.perm-btn.deny{color:var(--ink-2)}.perm-btn.deny:hover{border-color:var(--fail);color:var(--fail)}.perm-resolved{margin-top:6px;font-size:12px;color:var(--muted);font-family:var(--font-mono),monospace}.chat-working{display:flex;align-items:center;gap:8px;font-size:12px;color:var(--muted)}.composer{flex:none;display:flex;gap:10px;align-items:flex-end;padding:10px 0 4px;border-top:1px solid var(--line)}.composer textarea{flex:1;resize:none;font:13.5px/1.5 var(--font-sans),sans-serif;color:var(--ink);background:var(--panel-2);border:1px solid var(--line);border-radius:8px;padding:10px 13px;outline:none}.composer textarea:focus{border-color:var(--accent)}.new-chat{max-width:640px;margin:0 auto;width:100%}.new-chat-panel{overflow:visible}.agent-pick{display:grid;grid-template-columns:repeat(3,1fr);gap:10px;padding:14px 16px}.agent-pick-btn{display:flex;flex-direction:column;gap:3px;text-align:left;border:1px solid var(--line);border-radius:8px;padding:11px 13px;background:var(--panel-2)}.agent-pick-btn b{font-family:var(--font-mono),monospace;font-size:13px}.agent-pick-btn span{font-size:11px;color:var(--muted)}.agent-pick-btn:hover{border-color:color-mix(in srgb,var(--accent) 55%,var(--line))}.agent-pick-btn.active{border-color:var(--accent);background:var(--accent-dim)}@media(max-width:940px){.chat-main{height:auto;min-height:calc(100vh - 45px)}.agent-pick{grid-template-columns:1fr}}.know-intro{padding:12px 16px;font-size:12.5px;line-height:1.6;color:var(--ink-2)}.know-intro code{font-size:11.5px}.know-newbundle{display:flex;gap:10px;padding:14px 16px}.know-newbundle input{flex:1;font:13px/1.4 var(--font-mono),monospace;color:var(--ink);background:var(--panel-2);border:1px solid var(--line);border-radius:8px;padding:9px 12px;outline:none}.know-newbundle input:focus{border-color:var(--accent)}.know-table{width:100%;border-collapse:collapse;font-size:12.5px}.know-table td{padding:8px 16px;border-bottom:1px solid var(--line-soft);vertical-align:baseline}.know-table tr:last-child td{border-bottom:none}.know-table a{color:var(--ink);text-decoration:none}.know-table a:hover b{color:var(--accent)}.know-id{font-family:var(--font-mono),monospace;font-size:11px;color:var(--muted);margin-left:8px}.know-type{font-size:11.5px;color:var(--ink-2);white-space:nowrap}.know-flags{text-align:right;white-space:nowrap}.chip.trust.unverified{color:var(--muted)}.chip.trust.machine-confirmed{border-color:color-mix(in srgb,var(--accent) 40%,var(--line));color:var(--accent)}.chip.trust.human-reviewed{border-color:color-mix(in srgb,var(--ok) 45%,var(--line));color:var(--ok);background:var(--ok-dim)}.chip.stale,.chip.deprecated{border-color:color-mix(in srgb,var(--fail) 45%,var(--line));color:var(--fail);background:var(--fail-dim)}.chip.draft{border-color:color-mix(in srgb,var(--run) 45%,var(--line));color:var(--run)}.know-sub{display:flex;align-items:center;gap:8px;margin:-8px 2px 14px}.know-sub .rid{font-family:var(--font-mono),monospace;font-size:12px;color:var(--muted)}.know-meta{display:flex;flex-direction:column;gap:8px;padding:12px 16px;font-size:12.5px}.know-meta>div{display:flex;gap:14px;align-items:baseline}.know-meta .microlabel{width:90px;flex:none}.know-verify-entry{display:inline-block;margin-right:14px}.know-folder-row td{padding:10px 16px 4px;border-bottom:none}.know-folder{font-family:var(--font-mono),monospace;font-size:11px;color:var(--muted);letter-spacing:.04em}.know-indent{padding-left:30px!important}.team-screen{grid-template-columns:240px minmax(0,1fr)}.team-screen.has-sessions{grid-template-columns:240px 260px minmax(0,1fr)}.team-emoji{font-size:17px;line-height:1.3;flex:none}.team-emoji-lg{font-size:34px;line-height:1}.team-wf-list{display:flex;flex-wrap:wrap;gap:8px;padding:12px 16px}.team-wf-list .chip{text-decoration:none}.team-form{display:flex;flex-direction:column;gap:14px;padding:16px;max-width:680px}.team-form-row{display:flex;gap:10px;align-items:flex-end}.team-field{display:flex;flex-direction:column;gap:5px}.team-field,.team-field-label{font-size:10.5px;color:var(--muted);text-transform:uppercase;letter-spacing:.06em}.team-field input,.team-field select,.team-field textarea{font:13px/1.5 var(--font-mono),monospace;color:var(--ink);background:var(--panel-2);border:1px solid var(--line);border-radius:8px;padding:8px 11px;outline:none;text-transform:none;letter-spacing:normal}.team-field textarea{resize:vertical;font-family:var(--font-mono),monospace}.team-field input:focus,.team-field select:focus,.team-field textarea:focus{border-color:var(--accent)}.emoji-pick{display:flex;gap:6px;flex-wrap:wrap}.emoji-pick button{font-size:16px;padding:5px 9px;background:var(--panel-2);border:1px solid var(--line);border-radius:8px;cursor:pointer}.emoji-pick button:hover{border-color:color-mix(in srgb,var(--accent) 55%,var(--line))}.emoji-pick button.active{border-color:var(--accent);background:var(--accent-dim)}.wf-checks{display:flex;flex-direction:column;gap:7px;padding:4px 0}.wf-checks label{display:flex;align-items:baseline;gap:8px;font-size:12.5px;color:var(--ink-2);text-transform:none;letter-spacing:normal;cursor:pointer}.wf-checks b{font-family:var(--font-mono),monospace;font-size:12px}.wf-checks .opt-hint{color:var(--muted);font-size:11.5px}@media(max-width:900px){.team-screen,.team-screen.has-sessions{grid-template-columns:1fr}.team-form-row{flex-direction:column;align-items:stretch}}