@gentbajko/slopify 0.7.0 → 0.8.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. package/dist/adapters/llm/codex.js +3 -0
  2. package/dist/adapters/llm/gemini-workspace.js +24 -1
  3. package/dist/adapters/llm/gemini.js +1 -1
  4. package/dist/adapters/llm/openrouter.js +1 -0
  5. package/dist/assets/models.yaml +470 -0
  6. package/dist/catalog/registry.js +147 -0
  7. package/dist/catalog/schema.js +91 -0
  8. package/dist/catalog/store.js +90 -0
  9. package/dist/catalog/validate.js +43 -0
  10. package/dist/edge/http/actions.js +1 -1
  11. package/dist/edge/http/app.js +4 -0
  12. package/dist/edge/http/open-folder.js +61 -0
  13. package/dist/edge/http/planning.js +101 -0
  14. package/dist/edge/http/projects.js +4 -2
  15. package/dist/edge/http/providers.js +28 -0
  16. package/dist/edge/open-folder.js +25 -0
  17. package/dist/kernel/db/migrations/0003-batch-queue.sql +11 -0
  18. package/dist/kernel/ports/llm.js +1 -0
  19. package/dist/kernel/ports/text.js +26 -0
  20. package/dist/kernel/runner/providers.js +8 -6
  21. package/dist/kernel/runner/queue.js +65 -0
  22. package/dist/main.js +43 -6
  23. package/dist/slices/admission/repo.js +13 -2
  24. package/dist/slices/admission/start.js +9 -8
  25. package/dist/slices/article/continuation.js +8 -1
  26. package/dist/slices/article/segments.js +1 -0
  27. package/dist/slices/batch/index.js +82 -0
  28. package/dist/slices/control/index.js +4 -1
  29. package/dist/slices/control/providers.js +18 -1
  30. package/dist/slices/estimate/index.js +81 -0
  31. package/dist/slices/narration/chunk.js +21 -22
  32. package/dist/slices/narration/plan.js +58 -0
  33. package/dist/slices/narration/run.js +6 -27
  34. package/dist/slices/research/run.js +4 -0
  35. package/dist/slices/storage/staging.js +2 -1
  36. package/dist/slices/thumbnail/run.js +3 -0
  37. package/dist/web/assets/index-DkC4WXhk.css +1 -0
  38. package/dist/web/assets/index-GszhBVNn.js +130 -0
  39. package/dist/web/index.html +2 -2
  40. package/package.json +2 -1
  41. package/dist/web/assets/index-6QIQ-TzO.css +0 -1
  42. package/dist/web/assets/index-CNgWL-ct.js +0 -130
@@ -0,0 +1,58 @@
1
+ import { z } from "zod";
2
+ import { transact } from "../../kernel/db/tx.js";
3
+ import { splitText } from "../../kernel/ports/text.js";
4
+ import { insertPiece, piecesOf } from "../../kernel/runner/piece-repo.js";
5
+ const payload = z.object({ text: z.string(), file: z.string().optional() });
6
+ // Old whole-text plans can exceed a newly known account limit. Preserve finished
7
+ // pieces and their paths, and split only unfinished work before any request starts.
8
+ export function planNarration(deps, stageId, texts, maxCharacters, finished) {
9
+ const old = piecesOf(deps.db, stageId, "chunk");
10
+ const source = old.length
11
+ ? old
12
+ : texts.map((text, idx) => ({
13
+ id: deps.ids.next(),
14
+ stageId,
15
+ kind: "chunk",
16
+ idx: idx + 1,
17
+ state: "pending",
18
+ payload: JSON.stringify({ text }),
19
+ }));
20
+ const planned = [];
21
+ for (const piece of source) {
22
+ const data = payload.parse(JSON.parse(piece.payload ?? "null"));
23
+ if (finished(piece)) {
24
+ planned.push({ ...piece, idx: planned.length + 1 });
25
+ continue;
26
+ }
27
+ for (const [part, text] of splitText(data.text, maxCharacters).entries())
28
+ planned.push({
29
+ ...piece,
30
+ id: part === 0 ? piece.id : deps.ids.next(),
31
+ idx: planned.length + 1,
32
+ state: "pending",
33
+ payload: JSON.stringify({ text }),
34
+ });
35
+ }
36
+ if (old.length &&
37
+ planned.length === old.length &&
38
+ planned.every((p, i) => p.id === old[i]?.id &&
39
+ payload.parse(JSON.parse(p.payload ?? "null")).text ===
40
+ payload.parse(JSON.parse(old[i]?.payload ?? "null")).text))
41
+ return old;
42
+ transact(deps.db, () => {
43
+ // Negative temporary indices avoid colliding with a retained completed piece.
44
+ deps.db
45
+ .prepare("UPDATE stage_pieces SET idx=-idx WHERE stage_id=? AND kind='chunk'")
46
+ .run(stageId);
47
+ const known = new Set(old.map((p) => p.id));
48
+ for (const piece of planned) {
49
+ if (known.has(piece.id))
50
+ deps.db
51
+ .prepare("UPDATE stage_pieces SET idx=?,state=?,payload=? WHERE id=?")
52
+ .run(piece.idx, piece.state, piece.payload, piece.id);
53
+ else
54
+ insertPiece(deps.db, piece);
55
+ }
56
+ });
57
+ return planned;
58
+ }
@@ -1,8 +1,7 @@
1
1
  import { existsSync, mkdirSync, readFileSync, statSync, writeFileSync } from "node:fs";
2
2
  import { dirname } from "node:path";
3
3
  import { z } from "zod";
4
- import { transact } from "../../kernel/db/tx.js";
5
- import { insertPiece, piecesOf, setPiece } from "../../kernel/runner/piece-repo.js";
4
+ import { piecesOf, setPiece } from "../../kernel/runner/piece-repo.js";
6
5
  import { entryModes } from "../admission/model.js";
7
6
  import { projectById, setStageProgress, stagesOf } from "../admission/repo.js";
8
7
  import { entryCategories } from "../library/model.js";
@@ -12,6 +11,7 @@ import { probeDurationMs } from "../video/ffmpeg.js";
12
11
  import { chunkNarration, defaultChunking } from "./chunk.js";
13
12
  import { joinNarration } from "./concat.js";
14
13
  import { observeNarration } from "./live.js";
14
+ import { planNarration } from "./plan.js";
15
15
  // An empty narration source fails the stage immediately with no retries. Thrown from the
16
16
  // slice rather than from a provider call, so the attempt wrapper never sees it.
17
17
  export const nothingToNarrate = "nothing to narrate";
@@ -53,7 +53,8 @@ export async function runNarration(deps, context, providers) {
53
53
  if (texts.length === 0) {
54
54
  throw new Error(nothingToNarrate);
55
55
  }
56
- const files = await speakChunks(deps, context, providers, choice, plan(deps, context, texts));
56
+ const planned = planNarration(deps, context.stage.id, texts, deps.maxCharacters?.(choice.provider, choice.model) ?? 1000000, (piece) => finished(deps, projectId, piece) !== undefined);
57
+ const files = await speakChunks(deps, context, providers, choice, planned);
57
58
  await storeBody(deps, context, choice, files, outputs);
58
59
  await speakSegments(deps, context, providers, choice, outputs);
59
60
  deps.log.write("info", "narration.done", {
@@ -71,29 +72,7 @@ function narrationSource(deps, outputs, projectId) {
71
72
  }
72
73
  return readFileSync(outputPath(deps.paths, projectId, article.path), "utf8");
73
74
  }
74
- // The chunk list, planned once and kept. A retry after a failure finds the rows the first
75
- // run wrote and narrates only the ones that did not finish.
76
- function plan(deps, context, texts) {
77
- const existing = piecesOf(deps.db, context.stage.id, "chunk");
78
- if (existing.length > 0) {
79
- return existing;
80
- }
81
- const planned = texts.map((text, index) => ({
82
- id: deps.ids.next(),
83
- stageId: context.stage.id,
84
- kind: "chunk",
85
- idx: index + 1,
86
- state: "pending",
87
- payload: JSON.stringify({ text }),
88
- }));
89
- transact(deps.db, () => {
90
- for (const piece of planned) {
91
- insertPiece(deps.db, piece);
92
- }
93
- });
94
- return planned;
95
- }
96
- // Every chunk is synthesized in parallel. A chunk a previous run finished is not spoken
75
+ // Chunks are scheduled through the shared provider queue. A chunk a previous run finished is not spoken
97
76
  // again, and one that fails takes down the whole stage while its siblings finish and keep their
98
77
  // audio for the next resume.
99
78
  async function speakChunks(deps, context, providers, choice, pieces) {
@@ -107,7 +86,7 @@ async function speakChunks(deps, context, providers, choice, pieces) {
107
86
  if (kept !== undefined) {
108
87
  return { ok: true, file: kept };
109
88
  }
110
- const file = `${chunkDir}/${String(piece.idx).padStart(3, "0")}.mp3`;
89
+ const file = `${chunkDir}/${piece.id}.mp3`;
111
90
  setPiece(deps.db, piece.id, "running", piece.payload);
112
91
  try {
113
92
  const spoken = await providers.forPiece(piece.id).tts({
@@ -52,6 +52,7 @@ async function research(deps, context, providers, choice, brief) {
52
52
  const answer = await providers.llm({
53
53
  provider: choice.provider,
54
54
  model: choice.model,
55
+ ...(choice.thinking === undefined ? {} : { thinking: choice.thinking }),
55
56
  messages: synthesisMessages(brief, findings),
56
57
  previewLabel: "Writing research notes",
57
58
  check: (given) => sourcedAnswer("the synthesis", given.text),
@@ -71,6 +72,7 @@ async function research(deps, context, providers, choice, brief) {
71
72
  stage: "research",
72
73
  provider: choice.provider,
73
74
  model: choice.model,
75
+ ...(choice.thinking === undefined ? {} : { thinking: choice.thinking }),
74
76
  ...tokens,
75
77
  });
76
78
  deps.log.write("info", "research.done", {
@@ -89,6 +91,7 @@ async function plan(deps, context, providers, choice, brief, add) {
89
91
  const answer = await providers.llm({
90
92
  provider: choice.provider,
91
93
  model: choice.model,
94
+ ...(choice.thinking === undefined ? {} : { thinking: choice.thinking }),
92
95
  messages: plannerMessages(brief),
93
96
  previewLabel: "Planning research",
94
97
  // An empty answer, or one with no chapter in it, is a failed attempt.
@@ -130,6 +133,7 @@ async function researchChapters(deps, context, providers, choice, brief, chapter
130
133
  const answer = await providers.forPiece(piece.id).llm({
131
134
  provider: choice.provider,
132
135
  model: choice.model,
136
+ ...(choice.thinking === undefined ? {} : { thinking: choice.thinking }),
133
137
  messages: subAgentMessages(brief, kept.title, outline),
134
138
  previewLabel: kept.title,
135
139
  // Grounding is asked for explicitly, so a model without it says so
@@ -140,7 +140,8 @@ export function attachStagedFile(deps, input) {
140
140
  try {
141
141
  transact(deps.db, () => {
142
142
  insertOutput(deps.db, output);
143
- deleteStagedFile(deps.db, staged.id);
143
+ if (!input.retainStaged)
144
+ deleteStagedFile(deps.db, staged.id);
144
145
  });
145
146
  }
146
147
  catch (error) {
@@ -81,6 +81,7 @@ async function byLlm(deps, context, providers, project) {
81
81
  const answer = await providers.llm({
82
82
  provider: llm.provider,
83
83
  model: llm.model,
84
+ ...(llm.thinking === undefined ? {} : { thinking: llm.thinking }),
84
85
  messages,
85
86
  // An empty answer is a failed attempt, and the wrapper is what retries it.
86
87
  check: (given) => writtenPrompt(given.text),
@@ -151,6 +152,7 @@ async function make(deps, context, providers, project, choice, prompt) {
151
152
  const made = await providers.image({
152
153
  provider: choice.provider,
153
154
  model: choice.model,
155
+ ...(choice.thinking === undefined ? {} : { thinking: choice.thinking }),
154
156
  prompt,
155
157
  aspect: project.format,
156
158
  });
@@ -175,6 +177,7 @@ async function make(deps, context, providers, project, choice, prompt) {
175
177
  prompt,
176
178
  provider: choice.provider,
177
179
  model: choice.model,
180
+ ...(choice.thinking === undefined ? {} : { thinking: choice.thinking }),
178
181
  },
179
182
  createdAt: deps.clock.now().toISOString(),
180
183
  };
@@ -0,0 +1 @@
1
+ @font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/barlow-vietnamese-400-normal-Dpl4UHAZ.woff2)format("woff2"),url(/assets/barlow-vietnamese-400-normal-BFeobeCK.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/barlow-latin-ext-400-normal-HxX4XjxC.woff2)format("woff2"),url(/assets/barlow-latin-ext-400-normal-CvBsJvxq.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:400;src:url(/assets/barlow-latin-400-normal-qiz4-Cze.woff2)format("woff2"),url(/assets/barlow-latin-400-normal-fsAxiSwU.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/barlow-vietnamese-500-normal-zTViEIzf.woff2)format("woff2"),url(/assets/barlow-vietnamese-500-normal-GNfB7rCE.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/barlow-latin-ext-500-normal-DOaysfXq.woff2)format("woff2"),url(/assets/barlow-latin-ext-500-normal-CJPcKP2Q.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:500;src:url(/assets/barlow-latin-500-normal-BPAOfeC8.woff2)format("woff2"),url(/assets/barlow-latin-500-normal-C1h8hMer.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/barlow-vietnamese-600-normal-DcjprdFV.woff2)format("woff2"),url(/assets/barlow-vietnamese-600-normal-CA_GiK2e.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/barlow-latin-ext-600-normal-B8NK_A3D.woff2)format("woff2"),url(/assets/barlow-latin-ext-600-normal-DMVRjfRT.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/barlow-latin-600-normal-DILqtrty.woff2)format("woff2"),url(/assets/barlow-latin-600-normal-CNwfPWQD.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/barlow-vietnamese-700-normal-D6euyNzi.woff2)format("woff2"),url(/assets/barlow-vietnamese-700-normal-4Jt4k04K.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/barlow-latin-ext-700-normal-BLuWmldJ.woff2)format("woff2"),url(/assets/barlow-latin-ext-700-normal-CctuGmmz.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/barlow-latin-700-normal-A9pxMQ4z.woff2)format("woff2"),url(/assets/barlow-latin-700-normal-__SGTsZ1.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:800;src:url(/assets/barlow-vietnamese-800-normal-Cl1Mc_Dv.woff2)format("woff2"),url(/assets/barlow-vietnamese-800-normal-D0VWpbij.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:800;src:url(/assets/barlow-latin-ext-800-normal-BiucknKG.woff2)format("woff2"),url(/assets/barlow-latin-ext-800-normal-D7I3yvUw.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow;font-style:normal;font-display:swap;font-weight:800;src:url(/assets/barlow-latin-800-normal-s1sAMnoV.woff2)format("woff2"),url(/assets/barlow-latin-800-normal-BdVooDN4.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Barlow Condensed;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/barlow-condensed-vietnamese-600-normal-A5AYRdjN.woff2)format("woff2"),url(/assets/barlow-condensed-vietnamese-600-normal-CNlPk46_.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow Condensed;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/barlow-condensed-latin-ext-600-normal-18ESti3H.woff2)format("woff2"),url(/assets/barlow-condensed-latin-ext-600-normal-Clv9cIcR.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow Condensed;font-style:normal;font-display:swap;font-weight:600;src:url(/assets/barlow-condensed-latin-600-normal-DepVgxBB.woff2)format("woff2"),url(/assets/barlow-condensed-latin-600-normal-BFJEwTuo.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Barlow Condensed;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/barlow-condensed-vietnamese-700-normal-DYeBwlKR.woff2)format("woff2"),url(/assets/barlow-condensed-vietnamese-700-normal-DhIzd8Tb.woff)format("woff");unicode-range:U+102-103,U+110-111,U+128-129,U+168-169,U+1A0-1A1,U+1AF-1B0,U+300-301,U+303-304,U+308-309,U+323,U+329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Barlow Condensed;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/barlow-condensed-latin-ext-700-normal-CwuXbfVR.woff2)format("woff2"),url(/assets/barlow-condensed-latin-ext-700-normal-BIHFfxf0.woff)format("woff");unicode-range:U+100-2BA,U+2BD-2C5,U+2C7-2CC,U+2CE-2D7,U+2DD-2FF,U+304,U+308,U+329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Barlow Condensed;font-style:normal;font-display:swap;font-weight:700;src:url(/assets/barlow-condensed-latin-700-normal-v1xN8_Wq.woff2)format("woff2"),url(/assets/barlow-condensed-latin-700-normal-Dmwat-ge.woff)format("woff");unicode-range:U+??,U+131,U+152-153,U+2BB-2BC,U+2C6,U+2DA,U+2DC,U+304,U+308,U+329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@layer properties{@supports (((-webkit-hyphens:none)) and (not (margin-trim:inline))) or ((-moz-orient:inline) and (not (color:rgb(from red r g b)))){*,:before,:after,::backdrop{--tw-translate-x:0;--tw-translate-y:0;--tw-translate-z:0;--tw-rotate-x:initial;--tw-rotate-y:initial;--tw-rotate-z:initial;--tw-skew-x:initial;--tw-skew-y:initial;--tw-space-y-reverse:0;--tw-divide-y-reverse:0;--tw-border-style:solid;--tw-leading:initial;--tw-font-weight:initial;--tw-tracking:initial;--tw-ordinal:initial;--tw-slashed-zero:initial;--tw-numeric-figure:initial;--tw-numeric-spacing:initial;--tw-numeric-fraction:initial;--tw-shadow:0 0 #0000;--tw-shadow-color:initial;--tw-shadow-alpha:100%;--tw-inset-shadow:0 0 #0000;--tw-inset-shadow-color:initial;--tw-inset-shadow-alpha:100%;--tw-ring-color:initial;--tw-ring-shadow:0 0 #0000;--tw-inset-ring-color:initial;--tw-inset-ring-shadow:0 0 #0000;--tw-ring-inset:initial;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-offset-shadow:0 0 #0000;--tw-outline-style:solid;--tw-duration:initial;--tw-ease:initial;--tw-content:""}}}@layer theme{:root,:host{--font-sans:"Barlow", system-ui, sans-serif;--font-mono:ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;--color-white:#fff;--spacing:.25rem;--container-md:28rem;--container-2xl:42rem;--font-weight-medium:500;--font-weight-semibold:600;--font-weight-bold:700;--font-weight-extrabold:800;--leading-tight:1.25;--leading-relaxed:1.625;--ease-out:cubic-bezier(0, 0, .2, 1);--animate-spin:spin 1s linear infinite;--aspect-video:16 / 9;--default-transition-duration:.15s;--default-transition-timing-function:cubic-bezier(.4, 0, .2, 1);--default-font-family:var(--font-sans);--default-mono-font-family:var(--font-mono);--color-bg:#141416;--color-panel:#1b1b1f;--color-panel2:#202026;--color-line:#2a2a30;--color-line2:#35353d;--color-ink:#e6e3dc;--color-ink2:#9a978f;--color-ink3:#8a887f;--color-accent:#9bcb4f;--color-accent-ink:#17200b;--color-accent-edge:#6d9333;--color-done:#6f9a3a;--color-red:#e86960;--color-red-tint:#e8696014;--color-amber:#e2a247;--color-lamp-run:#9bcb4f;--color-lamp-halo:#9bcb4f2e;--color-lamp-off:#2c2c33;--color-lamp-ring:#3a3a42;--color-run-text:#9bcb4f;--color-focus:#9bcb4f;--color-shadow:#08080a3d;--color-scrim:#14141699;--color-screen:#0b0b0d;--font-condensed:"Barlow Condensed", "Barlow", system-ui, sans-serif;--text-label:12px;--text-label--line-height:1.2;--text-small:13px;--text-small--line-height:1.45;--text-body:14px;--text-body--line-height:1.45;--text-row:16px;--text-row--line-height:1.35;--text-title:18px;--text-title--line-height:1.3;--text-wordmark:20px;--text-wordmark--line-height:1.2;--text-counter:32px;--text-counter--line-height:1.1;--radius-control:4px;--radius-panel:6px;--animate-lamp-pulse:lamp-pulse 1.2s ease-in-out infinite;--animate-dialog-in:dialog-in .2s ease-out;--animate-tick-in:tick-in .15s ease-out}}@layer base{*,:after,:before,::backdrop{box-sizing:border-box;border:0 solid;margin:0;padding:0}::file-selector-button{box-sizing:border-box;border:0 solid;margin:0;padding:0}html,:host{-webkit-text-size-adjust:100%;tab-size:4;line-height:1.5;font-family:var(--default-font-family,-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", "Noto Sans", Arial, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji");font-feature-settings:var(--default-font-feature-settings,normal);font-variation-settings:var(--default-font-variation-settings,normal);-webkit-tap-highlight-color:transparent}hr{height:0;color:inherit;border-top-width:1px}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,samp,pre{font-family:var(--default-mono-font-family,ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace);font-feature-settings:var(--default-mono-font-feature-settings,normal);font-variation-settings:var(--default-mono-font-variation-settings,normal);font-size:1em}small{font-size:80%}sub,sup{vertical-align:baseline;font-size:75%;line-height:0;position:relative}sub{bottom:-.25em}sup{top:-.5em}table{text-indent:0;border-color:inherit;border-collapse:collapse}:-moz-focusring:where(:not(iframe)){outline:auto}progress{vertical-align:baseline}summary{display:list-item}ol,ul,menu{list-style:none}img,svg,video,canvas,audio,iframe,embed,object{vertical-align:middle;display:block}img,video{max-width:100%;height:auto}button,input,select,optgroup,textarea{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}::file-selector-button{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}:where(select:is([multiple],[size])) optgroup{font-weight:bolder}:where(select:is([multiple],[size])) optgroup option{padding-inline-start:20px}::file-selector-button{margin-inline-end:4px}::placeholder{opacity:1}@supports (not ((-webkit-appearance:-apple-pay-button))) or (contain-intrinsic-size:1px){::placeholder{color:currentColor}@supports (color:color-mix(in lab, red, red)){::placeholder{color:color-mix(in oklab, currentcolor 50%, transparent)}}}textarea{resize:vertical}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-date-and-time-value{min-height:1lh;text-align:inherit}::-webkit-datetime-edit{display:inline-flex}::-webkit-datetime-edit-fields-wrapper{padding:0}::-webkit-datetime-edit{padding-block:0}::-webkit-datetime-edit-year-field{padding-block:0}::-webkit-datetime-edit-month-field{padding-block:0}::-webkit-datetime-edit-day-field{padding-block:0}::-webkit-datetime-edit-hour-field{padding-block:0}::-webkit-datetime-edit-minute-field{padding-block:0}::-webkit-datetime-edit-second-field{padding-block:0}::-webkit-datetime-edit-millisecond-field{padding-block:0}::-webkit-datetime-edit-meridiem-field{padding-block:0}::-webkit-calendar-picker-indicator{line-height:1}:-moz-ui-invalid{box-shadow:none}button,input:where([type=button],[type=reset],[type=submit]){appearance:button}::file-selector-button{appearance:button}::-webkit-inner-spin-button{height:auto}::-webkit-outer-spin-button{height:auto}[hidden]:where(:not([hidden=until-found])){display:none!important}:root{--lightningcss-light: ;--lightningcss-dark:initial;color-scheme:dark}body{background:var(--color-bg);color:var(--color-ink);font-family:var(--font-sans);font-size:var(--text-body);line-height:var(--text-body--line-height);margin:0}:focus-visible{outline:2px solid var(--color-focus);outline-offset:2px}[disabled],[aria-disabled=true]{opacity:.45;pointer-events:none}}@layer components;@layer utilities{.pointer-events-auto{pointer-events:auto}.pointer-events-none{pointer-events:none}.collapse{visibility:collapse}.visible{visibility:visible}.sr-only{clip-path:inset(50%);white-space:nowrap;border-width:0;width:1px;height:1px;margin:-1px;padding:0;position:absolute;overflow:hidden}.absolute{position:absolute}.fixed{position:fixed}.relative{position:relative}.static{position:static}.sticky{position:sticky}.inset-0{inset:0}.inset-x-0{inset-inline:0}.top-1{top:var(--spacing)}.top-1\/2{top:50%}.top-\[2px\]{top:2px}.top-\[3px\]{top:3px}.right-1{right:var(--spacing)}.right-5{right:calc(var(--spacing) * 5)}.right-\[8px\]{right:8px}.right-\[10px\]{right:10px}.bottom-0{bottom:0}.bottom-5{bottom:calc(var(--spacing) * 5)}.left-1\/2{left:50%}.z-10{z-index:10}.z-30{z-index:30}.z-40{z-index:40}.z-50{z-index:50}.z-\[100\]{z-index:100}.z-\[101\]{z-index:101}.col-span-2{grid-column:span 2/span 2}.col-span-3{grid-column:span 3/span 3}.col-span-4{grid-column:span 4/span 4}.col-start-1{grid-column-start:1}.col-start-2{grid-column-start:2}.col-start-3{grid-column-start:3}.col-start-4{grid-column-start:4}.col-start-5{grid-column-start:5}.row-start-1{grid-row-start:1}.row-start-2{grid-row-start:2}.container{width:100%}@media (width>=40rem){.container{max-width:40rem}}@media (width>=48rem){.container{max-width:48rem}}@media (width>=64rem){.container{max-width:64rem}}@media (width>=80rem){.container{max-width:80rem}}@media (width>=96rem){.container{max-width:96rem}}.m-0{margin:0}.m-5{margin:calc(var(--spacing) * 5)}.mx-5{margin-inline:calc(var(--spacing) * 5)}.mx-auto{margin-inline:auto}.my-2{margin-block:calc(var(--spacing) * 2)}.my-3{margin-block:calc(var(--spacing) * 3)}.-mt-3{margin-top:calc(var(--spacing) * -3)}.-mt-\[6px\]{margin-top:-6px}.mt-0\.5{margin-top:calc(var(--spacing) * .5)}.mt-1{margin-top:var(--spacing)}.mt-2{margin-top:calc(var(--spacing) * 2)}.mt-3{margin-top:calc(var(--spacing) * 3)}.mt-4{margin-top:calc(var(--spacing) * 4)}.mt-5{margin-top:calc(var(--spacing) * 5)}.mt-\[6px\]{margin-top:6px}.mt-\[10px\]{margin-top:10px}.mt-\[22px\]{margin-top:22px}.mr-2{margin-right:calc(var(--spacing) * 2)}.mb-1{margin-bottom:var(--spacing)}.mb-2{margin-bottom:calc(var(--spacing) * 2)}.mb-3{margin-bottom:calc(var(--spacing) * 3)}.mb-4{margin-bottom:calc(var(--spacing) * 4)}.mb-\[5px\]{margin-bottom:5px}.mb-\[6px\]{margin-bottom:6px}.mb-\[10px\]{margin-bottom:10px}.-ml-px{margin-left:-1px}.ml-\[6px\]{margin-left:6px}.ml-auto{margin-left:auto}.block{display:block}.flex{display:flex}.grid{display:grid}.hidden{display:none}.inline{display:inline}.inline-block{display:inline-block}.inline-flex{display:inline-flex}.table{display:table}.aspect-\[9\/16\]{aspect-ratio:9/16}.aspect-video{aspect-ratio:var(--aspect-video)}.size-1\.5{width:calc(var(--spacing) * 1.5);height:calc(var(--spacing) * 1.5)}.size-3{width:calc(var(--spacing) * 3);height:calc(var(--spacing) * 3)}.size-3\.5{width:calc(var(--spacing) * 3.5);height:calc(var(--spacing) * 3.5)}.size-4{width:calc(var(--spacing) * 4);height:calc(var(--spacing) * 4)}.size-8{width:calc(var(--spacing) * 8);height:calc(var(--spacing) * 8)}.size-10{width:calc(var(--spacing) * 10);height:calc(var(--spacing) * 10)}.size-\[10px\]{width:10px;height:10px}.size-\[14px\]{width:14px;height:14px}.size-\[22px\]{width:22px;height:22px}.size-\[26px\]{width:26px;height:26px}.h-1\.5{height:calc(var(--spacing) * 1.5)}.h-2{height:calc(var(--spacing) * 2)}.h-3{height:calc(var(--spacing) * 3)}.h-4{height:calc(var(--spacing) * 4)}.h-7{height:calc(var(--spacing) * 7)}.h-8{height:calc(var(--spacing) * 8)}.h-9{height:calc(var(--spacing) * 9)}.h-12{height:calc(var(--spacing) * 12)}.h-14{height:calc(var(--spacing) * 14)}.h-24{height:calc(var(--spacing) * 24)}.h-28{height:calc(var(--spacing) * 28)}.h-\[2px\]{height:2px}.h-\[10px\]{height:10px}.h-\[18px\]{height:18px}.h-\[420px\]{height:420px}.h-\[520px\]{height:520px}.h-\[560px\]{height:560px}.h-fit{height:fit-content}.h-full{height:100%}.h-px{height:1px}.max-h-40{max-height:calc(var(--spacing) * 40)}.max-h-48{max-height:calc(var(--spacing) * 48)}.max-h-\[90dvh\]{max-height:90dvh}.max-h-\[360px\]{max-height:360px}.max-h-\[420px\]{max-height:420px}.max-h-\[min\(58vh\,560px\)\]{max-height:min(58vh,560px)}.max-h-\[min\(58vh\,640px\)\]{max-height:min(58vh,640px)}.min-h-0{min-height:0}.min-h-8{min-height:calc(var(--spacing) * 8)}.min-h-32{min-height:calc(var(--spacing) * 32)}.min-h-48{min-height:calc(var(--spacing) * 48)}.min-h-64{min-height:calc(var(--spacing) * 64)}.min-h-\[520px\]{min-height:520px}.min-h-screen{min-height:100vh}.w-2\/5{width:40%}.w-6{width:calc(var(--spacing) * 6)}.w-10{width:calc(var(--spacing) * 10)}.w-12{width:calc(var(--spacing) * 12)}.w-14{width:calc(var(--spacing) * 14)}.w-16{width:calc(var(--spacing) * 16)}.w-20{width:calc(var(--spacing) * 20)}.w-24{width:calc(var(--spacing) * 24)}.w-28{width:calc(var(--spacing) * 28)}.w-40{width:calc(var(--spacing) * 40)}.w-48{width:calc(var(--spacing) * 48)}.w-56{width:calc(var(--spacing) * 56)}.w-64{width:calc(var(--spacing) * 64)}.w-\[19\%\]{width:19%}.w-\[24\%\]{width:24%}.w-\[26\%\]{width:26%}.w-\[38\%\]{width:38%}.w-\[40ch\]{width:40ch}.w-\[64px\]{width:64px}.w-\[72px\]{width:72px}.w-\[90px\]{width:90px}.w-\[100px\]{width:100px}.w-\[104px\]{width:104px}.w-\[180px\]{width:180px}.w-\[calc\(100\%-2rem\)\]{width:calc(100% - 2rem)}.w-\[min\(340px\,calc\(100vw-2rem\)\)\]{width:min(340px,100vw - 2rem)}.w-auto{width:auto}.w-fit{width:fit-content}.w-full{width:100%}.max-w-\[75ch\]{max-width:75ch}.max-w-\[180px\]{max-width:180px}.max-w-\[260px\]{max-width:260px}.max-w-\[280px\]{max-width:280px}.max-w-\[360px\]{max-width:360px}.max-w-\[480px\]{max-width:480px}.max-w-\[520px\]{max-width:520px}.max-w-\[620px\]{max-width:620px}.max-w-\[720px\]{max-width:720px}.max-w-\[1100px\]{max-width:1100px}.max-w-\[1440px\]{max-width:1440px}.max-w-full{max-width:100%}.max-w-md{max-width:var(--container-md)}.min-w-0{min-width:0}.min-w-8{min-width:calc(var(--spacing) * 8)}.min-w-\[120px\]{min-width:120px}.min-w-\[160px\]{min-width:160px}.min-w-\[200px\]{min-width:200px}.min-w-\[var\(--radix-select-trigger-width\)\]{min-width:var(--radix-select-trigger-width)}.flex-1{flex:1}.shrink-0{flex-shrink:0}.grow{flex-grow:1}.basis-full{flex-basis:100%}.table-fixed{table-layout:fixed}.border-collapse{border-collapse:collapse}.origin-left{transform-origin:0}.-translate-x-1\/2{--tw-translate-x:calc(calc(1 / 2 * 100%) * -1);translate:var(--tw-translate-x) var(--tw-translate-y)}.-translate-y-1\/2{--tw-translate-y:calc(calc(1 / 2 * 100%) * -1);translate:var(--tw-translate-x) var(--tw-translate-y)}.transform{transform:var(--tw-rotate-x,) var(--tw-rotate-y,) var(--tw-rotate-z,) var(--tw-skew-x,) var(--tw-skew-y,)}.animate-lamp-pulse{animation:var(--animate-lamp-pulse)}.animate-spin{animation:var(--animate-spin)}.animate-tick-in{animation:var(--animate-tick-in)}.cursor-default{cursor:default}.cursor-pointer{cursor:pointer}.resize{resize:both}.resize-y{resize:vertical}.\[scrollbar-width\:thin\]{scrollbar-width:thin}.\[scrollbar-gutter\:stable\]{scrollbar-gutter:stable}.list-decimal{list-style-type:decimal}.list-disc{list-style-type:disc}.list-none{list-style-type:none}.appearance-none{appearance:none}.grid-cols-1{grid-template-columns:repeat(1,minmax(0,1fr))}.grid-cols-2{grid-template-columns:repeat(2,minmax(0,1fr))}.grid-cols-3{grid-template-columns:repeat(3,minmax(0,1fr))}.grid-cols-\[1fr_auto\]{grid-template-columns:1fr auto}.grid-cols-\[14px_24px_110px_auto_minmax\(0\,1fr\)\]{grid-template-columns:14px 24px 110px auto minmax(0,1fr)}.grid-cols-\[14px_minmax\(0\,1fr\)_auto_32px\]{grid-template-columns:14px minmax(0,1fr) auto 32px}.grid-cols-\[60px_minmax\(0\,1fr\)_auto\]{grid-template-columns:60px minmax(0,1fr) auto}.grid-cols-\[140px_1fr_auto\]{grid-template-columns:140px 1fr auto}.grid-cols-\[240px_1fr\]{grid-template-columns:240px 1fr}.grid-cols-\[auto_minmax\(0\,1fr\)\]{grid-template-columns:auto minmax(0,1fr)}.grid-cols-\[minmax\(0\,1fr\)\]{grid-template-columns:minmax(0,1fr)}.grid-cols-\[minmax\(0\,1fr\)_1px_minmax\(0\,1fr\)\]{grid-template-columns:minmax(0,1fr) 1px minmax(0,1fr)}.grid-cols-\[minmax\(0\,1fr\)_auto_32px\]{grid-template-columns:minmax(0,1fr) auto 32px}.grid-cols-\[minmax\(0\,1fr\)_auto_auto_32px\]{grid-template-columns:minmax(0,1fr) auto auto 32px}.flex-col{flex-direction:column}.flex-col-reverse{flex-direction:column-reverse}.flex-wrap{flex-wrap:wrap}.items-baseline{align-items:baseline}.items-center{align-items:center}.items-end{align-items:flex-end}.items-start{align-items:flex-start}.items-stretch{align-items:stretch}.justify-between{justify-content:space-between}.justify-center{justify-content:center}.justify-end{justify-content:flex-end}.gap-1{gap:var(--spacing)}.gap-2{gap:calc(var(--spacing) * 2)}.gap-3{gap:calc(var(--spacing) * 3)}.gap-4{gap:calc(var(--spacing) * 4)}.gap-5{gap:calc(var(--spacing) * 5)}.gap-6{gap:calc(var(--spacing) * 6)}.gap-\[5px\]{gap:5px}.gap-\[6px\]{gap:6px}.gap-\[10px\]{gap:10px}.gap-\[14px\]{gap:14px}.gap-\[18px\]{gap:18px}:where(.space-y-1>:not(:last-child)){--tw-space-y-reverse:0;margin-block-start:calc(var(--spacing) * var(--tw-space-y-reverse));margin-block-end:calc(var(--spacing) * calc(1 - var(--tw-space-y-reverse)))}:where(.space-y-2>:not(:last-child)){--tw-space-y-reverse:0;margin-block-start:calc(calc(var(--spacing) * 2) * var(--tw-space-y-reverse));margin-block-end:calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-y-reverse)))}:where(.space-y-5>:not(:last-child)){--tw-space-y-reverse:0;margin-block-start:calc(calc(var(--spacing) * 5) * var(--tw-space-y-reverse));margin-block-end:calc(calc(var(--spacing) * 5) * calc(1 - var(--tw-space-y-reverse)))}.gap-x-3{column-gap:calc(var(--spacing) * 3)}.gap-x-4{column-gap:calc(var(--spacing) * 4)}.gap-x-5{column-gap:calc(var(--spacing) * 5)}.gap-x-\[14px\]{column-gap:14px}.gap-y-1{row-gap:var(--spacing)}.gap-y-2{row-gap:calc(var(--spacing) * 2)}.gap-y-\[4px\]{row-gap:4px}.gap-y-\[6px\]{row-gap:6px}:where(.divide-y>:not(:last-child)){--tw-divide-y-reverse:0;border-bottom-style:var(--tw-border-style);border-top-style:var(--tw-border-style);border-top-width:calc(1px * var(--tw-divide-y-reverse));border-bottom-width:calc(1px * calc(1 - var(--tw-divide-y-reverse)))}:where(.divide-line>:not(:last-child)){border-color:var(--color-line)}.self-start{align-self:flex-start}.justify-self-end{justify-self:flex-end}.justify-self-start{justify-self:flex-start}.truncate{text-overflow:ellipsis;white-space:nowrap;overflow:hidden}.overflow-auto{overflow:auto}.overflow-hidden{overflow:hidden}.overflow-x-auto{overflow-x:auto}.overflow-y-auto{overflow-y:auto}.rounded-\[2px\]{border-radius:2px}.rounded-control{border-radius:var(--radius-control)}.rounded-full{border-radius:2147483647px}.rounded-panel{border-radius:var(--radius-panel)}.border{border-style:var(--tw-border-style);border-width:1px}.border-2{border-style:var(--tw-border-style);border-width:2px}.border-t{border-top-style:var(--tw-border-style);border-top-width:1px}.border-r{border-right-style:var(--tw-border-style);border-right-width:1px}.border-b{border-bottom-style:var(--tw-border-style);border-bottom-width:1px}.border-b-2{border-bottom-style:var(--tw-border-style);border-bottom-width:2px}.border-l{border-left-style:var(--tw-border-style);border-left-width:1px}.border-l-2{border-left-style:var(--tw-border-style);border-left-width:2px}.\!border-lamp-run{border-color:var(--color-lamp-run)!important}.border-accent{border-color:var(--color-accent)}.border-current{border-color:currentColor}.border-line{border-color:var(--color-line)}.border-line2{border-color:var(--color-line2)}.border-red{border-color:var(--color-red)}.border-red\/30{border-color:#e869604d}@supports (color:color-mix(in lab, red, red)){.border-red\/30{border-color:color-mix(in oklab, var(--color-red) 30%, transparent)}}.border-transparent{border-color:#0000}.bg-accent{background-color:var(--color-accent)}.bg-amber{background-color:var(--color-amber)}.bg-current{background-color:currentColor}.bg-done{background-color:var(--color-done)}.bg-lamp-off{background-color:var(--color-lamp-off)}.bg-lamp-run{background-color:var(--color-lamp-run)}.bg-line2{background-color:var(--color-line2)}.bg-panel{background-color:var(--color-panel)}.bg-panel\/90{background-color:#1b1b1fe6}@supports (color:color-mix(in lab, red, red)){.bg-panel\/90{background-color:color-mix(in oklab, var(--color-panel) 90%, transparent)}}.bg-panel2{background-color:var(--color-panel2)}.bg-red{background-color:var(--color-red)}.bg-red-tint{background-color:var(--color-red-tint)}.bg-screen{background-color:var(--color-screen)}.bg-scrim{background-color:var(--color-scrim)}.bg-transparent{background-color:#0000}.object-cover{object-fit:cover}.p-0{padding:0}.p-1{padding:var(--spacing)}.p-3{padding:calc(var(--spacing) * 3)}.p-4{padding:calc(var(--spacing) * 4)}.p-5{padding:calc(var(--spacing) * 5)}.p-8{padding:calc(var(--spacing) * 8)}.p-\[10px\]{padding:10px}.p-\[18px\]{padding:18px}.px-2{padding-inline:calc(var(--spacing) * 2)}.px-3{padding-inline:calc(var(--spacing) * 3)}.px-4{padding-inline:calc(var(--spacing) * 4)}.px-5{padding-inline:calc(var(--spacing) * 5)}.px-\[4px\]{padding-inline:4px}.px-\[7px\]{padding-inline:7px}.px-\[10px\]{padding-inline:10px}.px-\[14px\]{padding-inline:14px}.py-1{padding-block:var(--spacing)}.py-2{padding-block:calc(var(--spacing) * 2)}.py-3{padding-block:calc(var(--spacing) * 3)}.py-4{padding-block:calc(var(--spacing) * 4)}.py-5{padding-block:calc(var(--spacing) * 5)}.py-6{padding-block:calc(var(--spacing) * 6)}.py-7{padding-block:calc(var(--spacing) * 7)}.py-\[1px\]{padding-block:1px}.py-\[2px\]{padding-block:2px}.py-\[3px\]{padding-block:3px}.py-\[5px\]{padding-block:5px}.py-\[6px\]{padding-block:6px}.py-\[10px\]{padding-block:10px}.py-\[14px\]{padding-block:14px}.pt-3{padding-top:calc(var(--spacing) * 3)}.pt-4{padding-top:calc(var(--spacing) * 4)}.pt-\[10px\]{padding-top:10px}.pt-\[14px\]{padding-top:14px}.pr-3{padding-right:calc(var(--spacing) * 3)}.pr-4{padding-right:calc(var(--spacing) * 4)}.pr-8{padding-right:calc(var(--spacing) * 8)}.pr-\[26px\]{padding-right:26px}.pb-1{padding-bottom:var(--spacing)}.pb-\[7px\]{padding-bottom:7px}.pb-\[14px\]{padding-bottom:14px}.pl-3{padding-left:calc(var(--spacing) * 3)}.pl-5{padding-left:calc(var(--spacing) * 5)}.pl-\[10px\]{padding-left:10px}.text-center{text-align:center}.text-left{text-align:left}.text-right{text-align:right}.align-top{vertical-align:top}.engraved{font-family:var(--font-condensed);font-size:var(--text-label);line-height:var(--text-label--line-height);letter-spacing:.09em;text-transform:uppercase;font-weight:600}.font-condensed{font-family:var(--font-condensed)}.font-mono{font-family:var(--font-mono)}.font-sans{font-family:var(--font-sans)}.text-body{font-size:var(--text-body);line-height:var(--tw-leading,var(--text-body--line-height))}.text-counter{font-size:var(--text-counter);line-height:var(--tw-leading,var(--text-counter--line-height))}.text-label{font-size:var(--text-label);line-height:var(--tw-leading,var(--text-label--line-height))}.text-row{font-size:var(--text-row);line-height:var(--tw-leading,var(--text-row--line-height))}.text-small{font-size:var(--text-small);line-height:var(--tw-leading,var(--text-small--line-height))}.text-title{font-size:var(--text-title);line-height:var(--tw-leading,var(--text-title--line-height))}.text-wordmark{font-size:var(--text-wordmark);line-height:var(--tw-leading,var(--text-wordmark--line-height))}.text-\[28px\]{font-size:28px}.leading-\[1\.5\]{--tw-leading:1.5;line-height:1.5}.leading-relaxed{--tw-leading:var(--leading-relaxed);line-height:var(--leading-relaxed)}.leading-tight{--tw-leading:var(--leading-tight);line-height:var(--leading-tight)}.font-bold{--tw-font-weight:var(--font-weight-bold);font-weight:var(--font-weight-bold)}.font-extrabold{--tw-font-weight:var(--font-weight-extrabold);font-weight:var(--font-weight-extrabold)}.font-medium{--tw-font-weight:var(--font-weight-medium);font-weight:var(--font-weight-medium)}.font-semibold{--tw-font-weight:var(--font-weight-semibold);font-weight:var(--font-weight-semibold)}.tracking-\[-0\.01em\]{--tw-tracking:-.01em;letter-spacing:-.01em}.tracking-\[-0\.02em\]{--tw-tracking:-.02em;letter-spacing:-.02em}.tracking-\[0\.02em\]{--tw-tracking:.02em;letter-spacing:.02em}.tracking-\[0\.12em\]{--tw-tracking:.12em;letter-spacing:.12em}.text-pretty{text-wrap:pretty}.break-words{overflow-wrap:break-word}.break-all{word-break:break-all}.whitespace-nowrap{white-space:nowrap}.whitespace-pre-wrap{white-space:pre-wrap}.\!text-ink{color:var(--color-ink)!important}.text-accent-ink{color:var(--color-accent-ink)}.text-amber{color:var(--color-amber)}.text-done{color:var(--color-done)}.text-ink{color:var(--color-ink)}.text-ink2{color:var(--color-ink2)}.text-ink3{color:var(--color-ink3)}.text-lamp-run{color:var(--color-lamp-run)}.text-red{color:var(--color-red)}.text-run-text{color:var(--color-run-text)}.text-transparent{color:#0000}.text-white{color:var(--color-white)}.uppercase{text-transform:uppercase}.italic{font-style:italic}.tabular-nums{--tw-numeric-spacing:tabular-nums;font-variant-numeric:var(--tw-ordinal,) var(--tw-slashed-zero,) var(--tw-numeric-figure,) var(--tw-numeric-spacing,) var(--tw-numeric-fraction,)}.underline{text-decoration-line:underline}.decoration-red{-webkit-text-decoration-color:var(--color-red);-webkit-text-decoration-color:var(--color-red);-webkit-text-decoration-color:var(--color-red);text-decoration-color:var(--color-red)}.decoration-2{text-decoration-thickness:2px}.underline-offset-2{text-underline-offset:2px}.underline-offset-4{text-underline-offset:4px}.underline-offset-\[3px\]{text-underline-offset:3px}.caret-ink{caret-color:var(--color-ink)}.accent-accent{accent-color:var(--color-accent)}.opacity-0{opacity:0}.shadow{--tw-shadow:0 1px 3px 0 var(--tw-shadow-color,#0000001a), 0 1px 2px -1px var(--tw-shadow-color,#0000001a);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-\[0_0_0_3px_var\(--color-lamp-halo\)\]{--tw-shadow:0 0 0 3px var(--tw-shadow-color,var(--color-lamp-halo));box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-\[0_4px_0_var\(--color-accent-edge\)\]{--tw-shadow:0 4px 0 var(--tw-shadow-color,var(--color-accent-edge));box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-\[0_8px_24px_var\(--color-shadow\)\]{--tw-shadow:0 8px 24px var(--tw-shadow-color,var(--color-shadow));box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-\[inset_0_0_0_1px_var\(--color-lamp-ring\)\]{--tw-shadow:inset 0 0 0 1px var(--tw-shadow-color,var(--color-lamp-ring));box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.outline-hidden{--tw-outline-style:none;outline-style:none}@media (forced-colors:active){.outline-hidden{outline-offset:2px;outline:2px solid #0000}}.outline{outline-style:var(--tw-outline-style);outline-width:1px}.transition-\[width\]{transition-property:width;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-colors{transition-property:color,background-color,border-color,outline-color,text-decoration-color,fill,stroke,--tw-gradient-from,--tw-gradient-via,--tw-gradient-to;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-opacity{transition-property:opacity;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-transform{transition-property:transform,translate,scale,rotate;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.duration-150{--tw-duration:.15s;transition-duration:.15s}.duration-200{--tw-duration:.2s;transition-duration:.2s}.duration-\[250ms\]{--tw-duration:.25s;transition-duration:.25s}.ease-out{--tw-ease:var(--ease-out);transition-timing-function:var(--ease-out)}.outline-none{--tw-outline-style:none;outline-style:none}.select-none{-webkit-user-select:none;user-select:none}.select-text{-webkit-user-select:text;user-select:text}@media (hover:hover){.group-hover\:opacity-100:is(:where(.group):hover *){opacity:1}}.file\:mr-2::file-selector-button{margin-right:calc(var(--spacing) * 2)}.file\:mr-3::file-selector-button{margin-right:calc(var(--spacing) * 3)}.file\:h-8::file-selector-button{height:calc(var(--spacing) * 8)}.file\:rounded-control::file-selector-button{border-radius:var(--radius-control)}.file\:border::file-selector-button{border-style:var(--tw-border-style);border-width:1px}.file\:border-line2::file-selector-button{border-color:var(--color-line2)}.file\:bg-panel2::file-selector-button{background-color:var(--color-panel2)}.file\:px-2::file-selector-button{padding-inline:calc(var(--spacing) * 2)}.file\:px-3::file-selector-button{padding-inline:calc(var(--spacing) * 3)}.file\:py-1::file-selector-button{padding-block:var(--spacing)}.file\:text-ink::file-selector-button{color:var(--color-ink)}.placeholder\:text-ink3::placeholder{color:var(--color-ink3)}.before\:absolute:before{content:var(--tw-content);position:absolute}.before\:inset-y-0:before{content:var(--tw-content);inset-block:0}.before\:left-0:before{content:var(--tw-content);left:0}.before\:w-\[3px\]:before{content:var(--tw-content);width:3px}.before\:bg-accent:before{content:var(--tw-content);background-color:var(--color-accent)}.after\:absolute:after{content:var(--tw-content);position:absolute}.after\:inset-0:after{content:var(--tw-content);inset:0}.after\:content-\[\'\'\]:after{--tw-content:"";content:var(--tw-content)}.first\:border-t-0:first-child{border-top-style:var(--tw-border-style);border-top-width:0}.last\:border-r-0:last-child{border-right-style:var(--tw-border-style);border-right-width:0}.last\:border-b-0:last-child{border-bottom-style:var(--tw-border-style);border-bottom-width:0}.focus-within\:opacity-100:focus-within{opacity:1}@media (hover:hover){.hover\:border-ink3:hover{border-color:var(--color-ink3)}.hover\:bg-accent-edge:hover{background-color:var(--color-accent-edge)}.hover\:bg-panel2:hover{background-color:var(--color-panel2)}.hover\:text-ink:hover{color:var(--color-ink)}.hover\:text-ink2:hover{color:var(--color-ink2)}}.focus\:bg-panel2:focus{background-color:var(--color-panel2)}.focus-visible\:outline-2:focus-visible{outline-style:var(--tw-outline-style);outline-width:2px}.focus-visible\:outline-offset-2:focus-visible{outline-offset:2px}.focus-visible\:outline-offset-\[-3px\]:focus-visible{outline-offset:-3px}.focus-visible\:outline-accent:focus-visible{outline-color:var(--color-accent)}.active\:translate-y-\[3px\]:active{--tw-translate-y:3px;translate:var(--tw-translate-x) var(--tw-translate-y)}.active\:shadow-\[0_1px_0_var\(--color-accent-edge\)\]:active{--tw-shadow:0 1px 0 var(--tw-shadow-color,var(--color-accent-edge));box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.disabled\:cursor-not-allowed:disabled{cursor:not-allowed}.disabled\:opacity-40:disabled{opacity:.4}.disabled\:opacity-50:disabled{opacity:.5}.disabled\:opacity-60:disabled{opacity:.6}.aria-invalid\:border-red[aria-invalid=true]{border-color:var(--color-red)}.data-highlighted\:bg-panel2[data-highlighted]{background-color:var(--color-panel2)}.data-\[placeholder\]\:text-ink3[data-placeholder]{color:var(--color-ink3)}.data-\[state\=on\]\:bg-panel2[data-state=on]{background-color:var(--color-panel2)}.data-\[state\=on\]\:text-ink[data-state=on]{color:var(--color-ink)}.data-\[state\=on\]\:shadow-\[inset_0_-2px_0_var\(--color-lamp-run\)\][data-state=on]{--tw-shadow:inset 0 -2px 0 var(--tw-shadow-color,var(--color-lamp-run));box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.data-\[state\=open\]\:animate-dialog-in[data-state=open]{animation:var(--animate-dialog-in)}@media (prefers-reduced-motion:reduce){.motion-reduce\:animate-none{animation:none}.motion-reduce\:transition-none{transition-property:none}.motion-reduce\:active\:translate-y-0:active{--tw-translate-y:0px;translate:var(--tw-translate-x) var(--tw-translate-y)}}@media (width>=900px){.min-\[900px\]\:grid-cols-6{grid-template-columns:repeat(6,minmax(0,1fr))}.min-\[900px\]\:grid-cols-\[200px_minmax\(0\,1fr\)\]{grid-template-columns:200px minmax(0,1fr)}}@media (width>=1100px){.min-\[1100px\]\:not-sr-only{clip-path:none;white-space:normal;width:auto;height:auto;margin:0;padding:0;position:static;overflow:visible}}@media (width>=1180px){.min-\[1180px\]\:sticky{position:sticky}.min-\[1180px\]\:top-6{top:calc(var(--spacing) * 6)}.min-\[1180px\]\:grid-cols-\[minmax\(0\,1fr\)_480px\]{grid-template-columns:minmax(0,1fr) 480px}}@media (width>=1280px){.min-\[1280px\]\:not-sr-only{clip-path:none;white-space:normal;width:auto;height:auto;margin:0;padding:0;position:static;overflow:visible}.min-\[1280px\]\:flex{display:flex}.min-\[1280px\]\:h-14{height:calc(var(--spacing) * 14)}.min-\[1280px\]\:flex-1{flex:1}.min-\[1280px\]\:gap-7{gap:calc(var(--spacing) * 7)}.min-\[1280px\]\:px-7{padding-inline:calc(var(--spacing) * 7)}.min-\[1280px\]\:py-\[18px\]{padding-block:18px}}@media (width>=40rem){.sm\:not-sr-only{clip-path:none;white-space:normal;width:auto;height:auto;margin:0;padding:0;position:static;overflow:visible}.sm\:block{display:block}.sm\:max-w-2xl{max-width:var(--container-2xl)}.sm\:min-w-\[220px\]{min-width:220px}.sm\:flex-1{flex:1}.sm\:grid-cols-3{grid-template-columns:repeat(3,minmax(0,1fr))}.sm\:grid-cols-\[140px_1fr\]{grid-template-columns:140px 1fr}.sm\:gap-3{gap:calc(var(--spacing) * 3)}.sm\:gap-4{gap:calc(var(--spacing) * 4)}.sm\:px-4{padding-inline:calc(var(--spacing) * 4)}.sm\:px-7{padding-inline:calc(var(--spacing) * 7)}}@media (width>=48rem){.md\:col-span-1{grid-column:span 1/span 1}.md\:col-start-2{grid-column-start:2}.md\:col-start-3{grid-column-start:3}.md\:col-start-4{grid-column-start:4}.md\:col-start-5{grid-column-start:5}.md\:row-start-1{grid-row-start:1}.md\:grid-cols-5{grid-template-columns:repeat(5,minmax(0,1fr))}.md\:grid-cols-\[14px_minmax\(0\,1fr\)_140px_100px_32px\]{grid-template-columns:14px minmax(0,1fr) 140px 100px 32px}.md\:grid-cols-\[260px_70px_minmax\(0\,1fr\)_auto_32px\]{grid-template-columns:260px 70px minmax(0,1fr) auto 32px}.md\:grid-cols-\[260px_minmax\(0\,1fr\)_auto_32px\]{grid-template-columns:260px minmax(0,1fr) auto 32px}}@media (width>=64rem){.lg\:sticky{position:sticky}.lg\:top-6{top:calc(var(--spacing) * 6)}.lg\:grid-cols-1{grid-template-columns:repeat(1,minmax(0,1fr))}.lg\:grid-cols-\[240px_minmax\(0\,1fr\)\]{grid-template-columns:240px minmax(0,1fr)}.lg\:grid-cols-\[minmax\(0\,1fr\)_360px\]{grid-template-columns:minmax(0,1fr) 360px}}.\[\&_\[data-slot\=toggle-group\]\]\:max-w-full [data-slot=toggle-group]{max-width:100%}.\[\&_\[data-slot\=toggle-group\]\]\:flex-wrap [data-slot=toggle-group]{flex-wrap:wrap}.\[\&_a\]\:font-semibold a{--tw-font-weight:var(--font-weight-semibold);font-weight:var(--font-weight-semibold)}.\[\&_a\]\:text-accent-ink a{color:var(--color-accent-ink)}.\[\&_button\]\:min-h-8 button{min-height:calc(var(--spacing) * 8)}.\[\&_button\]\:min-w-8 button{min-width:calc(var(--spacing) * 8)}.\[\&_code\]\:text-ink code{color:var(--color-ink)}.\[\&_p\+p\]\:mt-2 p+p{margin-top:calc(var(--spacing) * 2)}.\[\&\>span\]\:w-full>span{width:100%}}@media (prefers-color-scheme:light){:root:not([data-theme=dark]){--lightningcss-light:initial;--lightningcss-dark: ;color-scheme:light;--color-bg:#f4f2ec;--color-panel:#fbfaf7;--color-panel2:#eceae3;--color-line:#dad8d0;--color-line2:#c9c7be;--color-ink:#1c1c1e;--color-ink2:#5c5b56;--color-ink3:#6b6a64;--color-accent-edge:#6e9a33;--color-done:#55673f;--color-red:#b8332c;--color-red-tint:#b8332c14;--color-amber:#8f5e12;--color-lamp-run:#5f8a2b;--color-lamp-halo:#5f8a2b2e;--color-lamp-off:#dedcd4;--color-lamp-ring:#c9c7be;--color-run-text:#3f6b1c;--color-focus:#5f8a2b;--color-shadow:#3c37281f;--color-scrim:#3c3a3273;--color-screen:#1c1c1e}}:root[data-theme=light]{--lightningcss-light:initial;--lightningcss-dark: ;color-scheme:light;--color-bg:#f4f2ec;--color-panel:#fbfaf7;--color-panel2:#eceae3;--color-line:#dad8d0;--color-line2:#c9c7be;--color-ink:#1c1c1e;--color-ink2:#5c5b56;--color-ink3:#6b6a64;--color-accent-edge:#6e9a33;--color-done:#55673f;--color-red:#b8332c;--color-red-tint:#b8332c14;--color-amber:#8f5e12;--color-lamp-run:#5f8a2b;--color-lamp-halo:#5f8a2b2e;--color-lamp-off:#dedcd4;--color-lamp-ring:#c9c7be;--color-run-text:#3f6b1c;--color-focus:#5f8a2b;--color-shadow:#3c37281f;--color-scrim:#3c3a3273;--color-screen:#1c1c1e}:root[data-theme=dark]{--lightningcss-light: ;--lightningcss-dark:initial;color-scheme:dark}@keyframes lamp-pulse{50%{box-shadow:0 0 0 6px #0000}}@keyframes tick-in{0%{opacity:0}}@keyframes dialog-in{0%{opacity:0;transform:translate(-50%,calc(4px - 50%))}}@property --tw-translate-x{syntax:"*";inherits:false;initial-value:0}@property --tw-translate-y{syntax:"*";inherits:false;initial-value:0}@property --tw-translate-z{syntax:"*";inherits:false;initial-value:0}@property --tw-rotate-x{syntax:"*";inherits:false}@property --tw-rotate-y{syntax:"*";inherits:false}@property --tw-rotate-z{syntax:"*";inherits:false}@property --tw-skew-x{syntax:"*";inherits:false}@property --tw-skew-y{syntax:"*";inherits:false}@property --tw-space-y-reverse{syntax:"*";inherits:false;initial-value:0}@property --tw-divide-y-reverse{syntax:"*";inherits:false;initial-value:0}@property --tw-border-style{syntax:"*";inherits:false;initial-value:solid}@property --tw-leading{syntax:"*";inherits:false}@property --tw-font-weight{syntax:"*";inherits:false}@property --tw-tracking{syntax:"*";inherits:false}@property --tw-ordinal{syntax:"*";inherits:false}@property --tw-slashed-zero{syntax:"*";inherits:false}@property --tw-numeric-figure{syntax:"*";inherits:false}@property --tw-numeric-spacing{syntax:"*";inherits:false}@property --tw-numeric-fraction{syntax:"*";inherits:false}@property --tw-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-shadow-color{syntax:"*";inherits:false}@property --tw-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-inset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-shadow-color{syntax:"*";inherits:false}@property --tw-inset-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-ring-color{syntax:"*";inherits:false}@property --tw-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-ring-color{syntax:"*";inherits:false}@property --tw-inset-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-ring-inset{syntax:"*";inherits:false}@property --tw-ring-offset-width{syntax:"<length>";inherits:false;initial-value:0}@property --tw-ring-offset-color{syntax:"*";inherits:false;initial-value:#fff}@property --tw-ring-offset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-outline-style{syntax:"*";inherits:false;initial-value:solid}@property --tw-duration{syntax:"*";inherits:false}@property --tw-ease{syntax:"*";inherits:false}@property --tw-content{syntax:"*";inherits:false;initial-value:""}@keyframes spin{to{transform:rotate(360deg)}}