@cleocode/worktree 2026.10.27 → 2026.11.1-canary.10

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 (38) hide show
  1. package/dist/.source-stamp.json +4 -0
  2. package/dist/git.d.ts +0 -13
  3. package/dist/git.d.ts.map +1 -1
  4. package/dist/git.js +0 -18
  5. package/dist/git.js.map +1 -1
  6. package/dist/index.d.ts +12 -4
  7. package/dist/index.d.ts.map +1 -1
  8. package/dist/index.js +13 -5
  9. package/dist/index.js.map +1 -1
  10. package/dist/worktree-create.d.ts +32 -1
  11. package/dist/worktree-create.d.ts.map +1 -1
  12. package/dist/worktree-create.js +153 -34
  13. package/dist/worktree-create.js.map +1 -1
  14. package/dist/worktree-destroy.d.ts +5 -5
  15. package/dist/worktree-destroy.d.ts.map +1 -1
  16. package/dist/worktree-destroy.js +79 -120
  17. package/dist/worktree-destroy.js.map +1 -1
  18. package/dist/worktree-dispose.d.ts +193 -0
  19. package/dist/worktree-dispose.d.ts.map +1 -0
  20. package/dist/worktree-dispose.js +608 -0
  21. package/dist/worktree-dispose.js.map +1 -0
  22. package/dist/worktree-locate.d.ts +2 -0
  23. package/dist/worktree-locate.d.ts.map +1 -1
  24. package/dist/worktree-locate.js +12 -1
  25. package/dist/worktree-locate.js.map +1 -1
  26. package/dist/worktree-lock.d.ts +56 -7
  27. package/dist/worktree-lock.d.ts.map +1 -1
  28. package/dist/worktree-lock.js +315 -100
  29. package/dist/worktree-lock.js.map +1 -1
  30. package/dist/worktree-prune.d.ts +1 -3
  31. package/dist/worktree-prune.d.ts.map +1 -1
  32. package/dist/worktree-prune.js +20 -241
  33. package/dist/worktree-prune.js.map +1 -1
  34. package/native/worktree-napi.darwin-arm64.node +0 -0
  35. package/native/worktree-napi.linux-arm64-gnu.node +0 -0
  36. package/native/worktree-napi.linux-x64-gnu.node +0 -0
  37. package/native/worktree-napi.win32-x64-msvc.node +0 -0
  38. package/package.json +4 -4
@@ -9,12 +9,11 @@
9
9
  * @task T1161
10
10
  * @adr ADR-062
11
11
  */
12
- import { existsSync, rmSync } from 'node:fs';
12
+ import { existsSync } from 'node:fs';
13
13
  import { countUnmergedCommits, getGitRoot, gitSilent, gitSync } from './git.js';
14
- import { destroyWorktree as napiDestroyWorktree } from './napi-binding.js';
15
14
  import { computeProjectHash, resolveTaskWorktreePath } from './paths.js';
16
15
  import { appendWorktreeAuditLog, removeWorktreeFromSentinelIndex } from './worktree-audit.js';
17
- import { describeDisposalBlockers, guardWorktreeDisposal } from './worktree-dependents.js';
16
+ import { disposeWorktree } from './worktree-dispose.js';
18
17
  import { runWorktreeHooks } from './worktree-hooks.js';
19
18
  import { locateTaskWorktree } from './worktree-locate.js';
20
19
  import { releaseWorktreeTaskLock } from './worktree-lock.js';
@@ -22,12 +21,12 @@ import { releaseWorktreeTaskLock } from './worktree-lock.js';
22
21
  * Destroy the git worktree for a task.
23
22
  *
24
23
  * Steps:
25
- * 1. Check for uncommitted changes (dirty detection).
24
+ * 1. Ask {@link disposeWorktree} (T13924) whether the worktree may go: kept
25
+ * unless nothing in it is lost; `force` archives the unpreserved work first.
26
26
  * 2. Run pre-remove hooks.
27
- * 3. Unlock the worktree (`git worktree unlock`).
28
- * 4. Remove the worktree directory (`git worktree remove --force`).
29
- * 5. Optionally delete the task branch.
30
- * 6. Run post-destroy hooks.
27
+ * 3. Dispose of it (re-proved right before removal).
28
+ * 4. Optionally delete the task branch.
29
+ * 5. Run post-destroy hooks.
31
30
  *
32
31
  * Integration (merging commits back to the target branch) is performed by
33
32
  * `completeAgentWorktreeViaMerge` before this function is called. Non-fatal
@@ -57,139 +56,90 @@ export async function destroyWorktree(projectRoot, options) {
57
56
  let branchDeleted = false;
58
57
  let error;
59
58
  const hookResults = [];
60
- // Step 1: Dirty detection.
61
- let dirty = false;
62
- if (existsSync(worktreePath)) {
63
- try {
64
- const status = gitSync(['status', '--porcelain'], worktreePath);
65
- dirty = status.length > 0;
66
- }
67
- catch {
68
- // If git status fails, assume not dirty to avoid blocking cleanup.
69
- dirty = false;
70
- }
71
- }
72
- if (dirty && !force) {
59
+ // Step 1: the one disposal engine decides first (T13924). Without proof that
60
+ // nothing in the worktree is lost it is kept; `force` archives the
61
+ // unpreserved work (ref + patch + receipt) first. The dependents/evidence
62
+ // guard always holds. The pre-remove hooks run only once removal is decided.
63
+ const reason = options.reason ?? 'manual';
64
+ const dispose = (probe) => disposeWorktree({
65
+ worktreePath,
66
+ gitRoot,
67
+ projectRoot,
68
+ taskId,
69
+ reason,
70
+ evidence: options.evidence,
71
+ force,
72
+ probe,
73
+ });
74
+ const refuse = (disposal) => {
75
+ const message = disposal.kept
76
+ ? (disposal.keptReason ?? '')
77
+ : `Worktree kept: ${disposal.keptReason ?? 'not proven preserved'}. Commit and push it, or pass --force to archive it and remove it.`;
78
+ appendWorktreeAuditLog(projectRoot, {
79
+ action: 'destroy',
80
+ xdgPath: worktreePath,
81
+ taskId,
82
+ branch,
83
+ reason,
84
+ success: false,
85
+ error: message,
86
+ });
73
87
  return {
74
88
  taskId,
75
89
  worktreeRemoved: false,
76
90
  branchDeleted: false,
77
- error: 'Worktree has uncommitted changes - destroy aborted',
78
- dirty,
91
+ error: message,
92
+ dirty: disposal.unpreserved !== undefined,
79
93
  force,
80
94
  hookResults,
95
+ ...(disposal.kept ? { kept: disposal.kept } : {}),
96
+ ...(disposal.archive ? { archive: disposal.archive } : {}),
81
97
  };
82
- }
83
- // T13696: never delete files something outside the worktree still needs —
84
- // a sibling's symlinked node_modules, or evidence that exists only here.
85
- if (existsSync(worktreePath)) {
86
- const kept = guardWorktreeDisposal(worktreePath, {
87
- taskId,
88
- reason: options.reason ?? 'manual',
89
- gitRoot,
90
- projectRoot,
91
- evidence: options.evidence,
92
- });
93
- if (kept !== null) {
94
- const message = describeDisposalBlockers(worktreePath, kept);
95
- appendWorktreeAuditLog(projectRoot, {
96
- action: 'destroy',
97
- xdgPath: worktreePath,
98
- taskId,
99
- branch,
100
- reason: options.reason ?? 'manual',
101
- success: false,
102
- error: message,
103
- });
104
- return {
105
- taskId,
106
- worktreeRemoved: false,
107
- branchDeleted: false,
108
- error: message,
109
- dirty,
110
- force,
111
- hookResults,
112
- kept,
113
- };
114
- }
115
- }
116
- // Step 2: Run pre-remove hooks.
117
- if (hooks.length > 0 && existsSync(worktreePath)) {
118
- try {
119
- const preRemoveResults = await runWorktreeHooks(hooks, 'pre-remove', worktreePath);
120
- hookResults.push(...preRemoveResults);
121
- }
122
- catch (err) {
123
- const message = err instanceof Error ? err.message : String(err);
124
- return {
125
- taskId,
126
- worktreeRemoved: false,
127
- branchDeleted: false,
128
- error: `Pre-remove hook failed: ${message}`,
129
- dirty,
130
- force,
131
- hookResults,
132
- };
133
- }
134
- }
135
- // Step 3: Unlock + remove the worktree (T9982 — git plumbing routed through
136
- // @cleocode/worktree-napi → worktrunk-core::git_wt::destroy_worktree).
137
- // The TS layer still owns the unlock + filesystem-rm fallback so a locked or
138
- // partially-removed worktree can be force-cleaned without a second napi call.
98
+ };
99
+ let dirty = false;
100
+ let archive;
139
101
  if (existsSync(worktreePath)) {
140
- gitSilent(['worktree', 'unlock', worktreePath], gitRoot);
141
- try {
142
- const result = napiDestroyWorktree({
143
- repoRoot: gitRoot,
144
- worktreePath,
145
- force: true,
146
- });
147
- worktreeRemoved = result.removed;
148
- // T11033 — NAPI may report success even when untracked directories
149
- // (e.g. .cleo/) survive inside the worktree. Verify on-disk reality.
150
- if (worktreeRemoved && existsSync(worktreePath)) {
151
- worktreeRemoved = false; // trigger filesystem fallback below
152
- }
153
- }
154
- catch (err) {
155
- // napi reported failure — fall back to filesystem rm so the audit log
156
- // still captures the cleanup attempt.
157
- try {
158
- rmSync(worktreePath, { recursive: true, force: true });
159
- worktreeRemoved = true;
160
- }
161
- catch (err2) {
162
- if (!error) {
163
- error = `Failed to remove worktree: napi=${err instanceof Error ? err.message : String(err)}; fs=${err2 instanceof Error ? err2.message : String(err2)}`;
164
- }
165
- }
166
- }
167
- // Filesystem fallback when NAPI reported success but directory survived.
168
- if (!worktreeRemoved && existsSync(worktreePath)) {
102
+ const plan = dispose(true);
103
+ if (plan.keptReason !== undefined)
104
+ return refuse(plan);
105
+ dirty = plan.unpreserved !== undefined;
106
+ // Step 2: Run pre-remove hooks.
107
+ if (hooks.length > 0) {
169
108
  try {
170
- rmSync(worktreePath, { recursive: true, force: true });
171
- worktreeRemoved = true;
109
+ const preRemoveResults = await runWorktreeHooks(hooks, 'pre-remove', worktreePath);
110
+ hookResults.push(...preRemoveResults);
172
111
  }
173
- catch (err2) {
174
- if (!error) {
175
- error = `Failed to remove worktree directory after NAPI: ${err2 instanceof Error ? err2.message : String(err2)}`;
176
- }
112
+ catch (err) {
113
+ const message = err instanceof Error ? err.message : String(err);
114
+ return {
115
+ taskId,
116
+ worktreeRemoved: false,
117
+ branchDeleted: false,
118
+ error: `Pre-remove hook failed: ${message}`,
119
+ dirty,
120
+ force,
121
+ hookResults,
122
+ };
177
123
  }
178
124
  }
125
+ // Step 3: dispose for real; the engine re-proves right before removing.
126
+ const disposal = dispose(false);
127
+ if (!disposal.removed)
128
+ return refuse(disposal);
129
+ archive = disposal.archive;
130
+ worktreeRemoved = true;
179
131
  }
180
132
  else if (located !== null) {
181
133
  // Registered with git but absent from disk — a stale registration. Pruning
182
134
  // it IS the removal; without this the entry lingers forever.
183
135
  gitSilent(['worktree', 'prune'], gitRoot);
184
136
  worktreeRemoved = true;
137
+ releaseWorktreeTaskLock(projectHash, taskId);
185
138
  }
186
139
  else {
187
140
  worktreeRemoved = true; // genuinely absent: not on disk, not registered
188
- }
189
- // T12506: the worktree is gone, so its per-task lock guards nothing — free
190
- // it so the next spawn of this task provisions without waiting for a TTL.
191
- if (worktreeRemoved)
192
141
  releaseWorktreeTaskLock(projectHash, taskId);
142
+ }
193
143
  // Step 4: Optionally delete the branch.
194
144
  if (deleteBranch) {
195
145
  try {
@@ -253,6 +203,15 @@ export async function destroyWorktree(projectRoot, options) {
253
203
  if (destroySucceeded) {
254
204
  removeWorktreeFromSentinelIndex(gitRoot, taskId);
255
205
  }
256
- return { taskId, worktreeRemoved, branchDeleted, error, dirty, force, hookResults };
206
+ return {
207
+ taskId,
208
+ worktreeRemoved,
209
+ branchDeleted,
210
+ error,
211
+ dirty,
212
+ force,
213
+ hookResults,
214
+ ...(archive ? { archive } : {}),
215
+ };
257
216
  }
258
217
  //# sourceMappingURL=worktree-destroy.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"worktree-destroy.js","sourceRoot":"","sources":["../src/worktree-destroy.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"worktree-destroy.js","sourceRoot":"","sources":["../src/worktree-destroy.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,193 @@
1
+ /**
2
+ * The one worktree disposal engine (T13924, durability C-F2).
3
+ *
4
+ * Every path that deletes a worktree (complete, cancel, `worktree destroy`,
5
+ * `worktree prune --orphaned`, the merge sweep, gc and the sentient prune)
6
+ * calls {@link disposeWorktree}. It removes a worktree only with proof that
7
+ * nothing in it is lost:
8
+ *
9
+ * - **guard**: nothing outside links into it and no evidence lives only there
10
+ * ({@link guardWorktreeDisposal}, T13696/T13700);
11
+ * - **not in use**: the caller's in-use probe (a live task lock or claim)
12
+ * answers `null`; a probe that throws counts as in use;
13
+ * - **content**: no tracked change, and every untracked or ignored path is
14
+ * either `node_modules`, rebuildable output of a merged checkout, or the
15
+ * identical tree in the main checkout ({@link unprovenContent});
16
+ * - **commits**: every commit HEAD reaches is also held by a remote-tracking
17
+ * ref or the project's local default branch ({@link unpreservedCommits}).
18
+ *
19
+ * Every probe fails closed: a git or read error is "not proven", never clean.
20
+ * Without proof the worktree is kept with the failing clause named. With
21
+ * `force` (`cleo worktree destroy --force` only) the unpreserved work is
22
+ * archived first, a ref under `refs/cleo/archive/` plus a patch and a receipt
23
+ * under `<projectRoot>/.cleo/archive/worktrees/`, and the worktree is removed
24
+ * only once the archive is verified.
25
+ *
26
+ * Nothing else in the repository may call the raw removals (arch gate 41,
27
+ * `scripts/lint-no-raw-worktree-removal.mjs`).
28
+ *
29
+ * @task T13924
30
+ * @task T14276
31
+ */
32
+ import type { DisposeWorktreeOptions, DisposeWorktreeResult, WorktreeArchiveReceipt } from '@cleocode/contracts';
33
+ /**
34
+ * What one cleanup run may spend proving trees identical (T14146). Shared
35
+ * across every checkout the run inspects; once spent, the rest is unproven.
36
+ */
37
+ export interface CompareBudget {
38
+ /** Entries (files, directories, links) still allowed. */
39
+ entries: number;
40
+ /** File bytes still allowed to be read. */
41
+ bytes: number;
42
+ }
43
+ /**
44
+ * A fresh per-run budget: 200 000 entries and 2 GiB of file bytes.
45
+ *
46
+ * @returns A budget to share across one run's checks.
47
+ */
48
+ export declare function newCompareBudget(): CompareBudget;
49
+ /**
50
+ * Build output a merged, clean checkout can always rebuild from its source,
51
+ * so losing it loses nothing (T14146): `dist/`, `.turbo/` and `coverage/`
52
+ * (and anything inside them), and `*.tsbuildinfo` files, only where the build
53
+ * writes them: the checkout root or a `packages/<name>/` root. The same name
54
+ * deeper down (`secrets/dist/key.pem`) is not build output and stays strict.
55
+ *
56
+ * @param rel - Path relative to the checkout root, `/`-separated.
57
+ * @returns Whether the path is rebuildable output.
58
+ */
59
+ export declare function isRegenerable(rel: string): boolean;
60
+ /** How {@link unprovenContent} treats ignored content (T14146). */
61
+ export interface UnprovenContentOptions {
62
+ /** Shared per-run comparison budget; a fresh one when omitted. */
63
+ budget?: CompareBudget;
64
+ /** Ignored `node_modules` counts as redundant (worktrees, not repository copies). */
65
+ exemptNodeModules?: boolean;
66
+ /**
67
+ * Ignored build output ({@link isRegenerable}) counts as redundant. Only for
68
+ * a checkout whose commits are merged: its source rebuilds the output.
69
+ */
70
+ exemptRegenerable?: boolean;
71
+ }
72
+ /**
73
+ * What in a checkout is not proven redundant, or `null` when nothing is.
74
+ *
75
+ * Tracked changes never are; untracked content is when the main checkout
76
+ * holds the identical tree at the same path, or (exempt by default) when it
77
+ * is `node_modules`. Ignored content (which
78
+ * `--porcelain` alone never lists: an edited `.env`, an agent's nested
79
+ * `.claude/worktrees/x/`) is redundant only when exempted by `opts`
80
+ * (`node_modules`, merged build output) or when the main checkout holds the
81
+ * identical tree at the same path (what `.worktreeinclude` seeded, unchanged).
82
+ * Fail-closed: a git or read error is unproven.
83
+ *
84
+ * @param path - Checkout root.
85
+ * @param projectRoot - The main checkout seeded copies are compared against.
86
+ * @param opts - Budget and exemptions (default: `node_modules` exempt, nothing else).
87
+ * @returns Why the checkout must be kept, or `null`.
88
+ * @task T14142
89
+ * @task T14146
90
+ */
91
+ export declare function unprovenContent(path: string, projectRoot: string, opts?: UnprovenContentOptions): string | null;
92
+ /**
93
+ * Whether the checkout's commits survive its removal, or why not.
94
+ *
95
+ * Every commit HEAD reaches must also be reachable from a remote-tracking ref
96
+ * or from the project's local default branch (a local integration before any
97
+ * push). Another local branch does not count: it is often a task branch this
98
+ * engine, or `git branch -D`, removes later, which would chain the loss. An
99
+ * unborn HEAD holds no commits. Fail-closed: any git error is "commits not
100
+ * proven preserved".
101
+ *
102
+ * @param path - Checkout root.
103
+ * @param defaultBranch - The project's default branch; resolved as in
104
+ * {@link DisposeWorktreeOptions.defaultBranch} when omitted.
105
+ * @returns Why its commits are not preserved, or `null`.
106
+ * @task T13924
107
+ */
108
+ export declare function unpreservedCommits(path: string, defaultBranch?: string): string | null;
109
+ /**
110
+ * Archive everything a worktree holds before it is removed (T13924): an
111
+ * archive commit whose parent is HEAD and whose tree is the checkout's
112
+ * tracked, untracked and ignored content (bar `node_modules`, and ignored
113
+ * build output), held by `refs/cleo/archive/<name>/<stamp>`, plus a binary patch from
114
+ * HEAD and a JSON receipt under `<projectRoot>/.cleo/archive/worktrees/`. The
115
+ * worktree's own index and files are not touched (a temporary index is used).
116
+ *
117
+ * @param worktreePath - Checkout to archive.
118
+ * @param gitRoot - Repository the archive ref is written to.
119
+ * @param projectRoot - Main checkout whose `.cleo/archive/worktrees/` holds the patch and receipt.
120
+ * @param meta - Owning task and disposal reason, recorded on the receipt.
121
+ * @returns The verified receipt, or why the archive could not be written.
122
+ * @task T13924
123
+ */
124
+ export declare function archiveWorktree(worktreePath: string, gitRoot: string, projectRoot: string, meta: {
125
+ taskId: string | null;
126
+ reason: string;
127
+ }): WorktreeArchiveReceipt | {
128
+ error: string;
129
+ };
130
+ /**
131
+ * Dispose of a worktree with per-item proof that nothing is lost (T13924).
132
+ * See the module comment for the proof; this is the only function that
133
+ * deletes a worktree.
134
+ *
135
+ * @param opts - The worktree, its task, the reason and the overrides.
136
+ * @returns Whether it was removed, or why it was kept, and any archive written.
137
+ * @task T13924
138
+ */
139
+ export declare function disposeWorktree(opts: DisposeWorktreeOptions): DisposeWorktreeResult;
140
+ /** Options for {@link disposeOwnedWorktree}. */
141
+ export interface DisposeOwnedWorktreeOptions {
142
+ /** Project hash the task lock is keyed by. */
143
+ projectHash: string;
144
+ /** Task whose lock `lockToken` must hold. */
145
+ taskId: string;
146
+ /** The task's canonical worktree path; any other path is kept. */
147
+ worktreePath: string;
148
+ /** Branch the checkout must be on; a checkout on another branch is kept. */
149
+ branch: string;
150
+ /** Token of the caller's own lock acquisition. */
151
+ lockToken: string;
152
+ /** Why it is disposed (audit and archive receipt). */
153
+ reason: string;
154
+ /** Repository root; read from the worktree when omitted. */
155
+ gitRoot?: string;
156
+ /** Main checkout; the repository's main worktree when omitted. */
157
+ projectRoot?: string;
158
+ /** Archive unpreserved work, then remove (as {@link disposeWorktree}). */
159
+ force?: boolean;
160
+ /** Extra in-use probe, run under the lock right before the removal. */
161
+ inUse?: () => string | null;
162
+ }
163
+ /** Outcome of {@link disposeOwnedWorktree}. */
164
+ export interface DisposeOwnedWorktreeResult {
165
+ /** `removed`: the directory is gone. `kept`: it is untouched. */
166
+ outcome: 'removed' | 'kept';
167
+ /** Why it was kept, or how it went. */
168
+ reason: string;
169
+ /** Whether the caller's lock was released (only ever with its token, after a removal). */
170
+ lockReleased: boolean;
171
+ /** The engine's result, when the engine ran. */
172
+ disposal?: DisposeWorktreeResult;
173
+ }
174
+ /**
175
+ * Dispose of a worktree only while the caller still owns its task lock
176
+ * (T14407). For a caller that created the worktree under the lock and must
177
+ * now remove it (a failed provision or spawn).
178
+ *
179
+ * Under the lock's own mutex, held for the whole check and disposal (a live
180
+ * holder's mutex is never broken as stale), it checks that `lockToken` still
181
+ * holds the lock, that `worktreePath` is the task's canonical path and that
182
+ * the checkout there is on `branch`, then runs {@link disposeWorktree}'s proof
183
+ * and removal, then releases the lock with `lockToken`. A concurrent re-spawn
184
+ * cannot re-enter or reclaim the lock in between, so it never loses a
185
+ * worktree it owns. Fails closed: any failed or unreadable lookup, token
186
+ * mismatch or path mismatch keeps the worktree. The branch is not deleted.
187
+ *
188
+ * @param opts - Lock identity, exact path and branch, and disposal options.
189
+ * @returns Whether it was removed or kept, why, and whether the lock was released.
190
+ * @task T14407
191
+ */
192
+ export declare function disposeOwnedWorktree(opts: DisposeOwnedWorktreeOptions): DisposeOwnedWorktreeResult;
193
+ //# sourceMappingURL=worktree-dispose.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"worktree-dispose.d.ts","sourceRoot":"","sources":["../src/worktree-dispose.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AAkBH,OAAO,KAAK,EACV,sBAAsB,EACtB,qBAAqB,EACrB,sBAAsB,EACvB,MAAM,qBAAqB,CAAC;AAwD7B;;;GAGG;AACH,MAAM,WAAW,aAAa;IAC5B,yDAAyD;IACzD,OAAO,EAAE,MAAM,CAAC;IAChB,2CAA2C;IAC3C,KAAK,EAAE,MAAM,CAAC;CACf;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,IAAI,aAAa,CAEhD;AAQD;;;;;;;;;GASG;AACH,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAMlD;AAsCD,mEAAmE;AACnE,MAAM,WAAW,sBAAsB;IACrC,kEAAkE;IAClE,MAAM,CAAC,EAAE,aAAa,CAAC;IACvB,qFAAqF;IACrF,iBAAiB,CAAC,EAAE,OAAO,CAAC;IAC5B;;;OAGG;IACH,iBAAiB,CAAC,EAAE,OAAO,CAAC;CAC7B;AAoBD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,eAAe,CAC7B,IAAI,EAAE,MAAM,EACZ,WAAW,EAAE,MAAM,EACnB,IAAI,GAAE,sBAA2B,GAChC,MAAM,GAAG,IAAI,CAwBf;AAiCD;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,MAAM,EAAE,aAAa,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAetF;AAcD;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,eAAe,CAC7B,YAAY,EAAE,MAAM,EACpB,OAAO,EAAE,MAAM,EACf,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE;IAAE,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GAC9C,sBAAsB,GAAG;IAAE,KAAK,EAAE,MAAM,CAAA;CAAE,CA4E5C;AAqDD;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAAC,IAAI,EAAE,sBAAsB,GAAG,qBAAqB,CAEnF;AA2FD,gDAAgD;AAChD,MAAM,WAAW,2BAA2B;IAC1C,8CAA8C;IAC9C,WAAW,EAAE,MAAM,CAAC;IACpB,6CAA6C;IAC7C,MAAM,EAAE,MAAM,CAAC;IACf,kEAAkE;IAClE,YAAY,EAAE,MAAM,CAAC;IACrB,4EAA4E;IAC5E,MAAM,EAAE,MAAM,CAAC;IACf,kDAAkD;IAClD,SAAS,EAAE,MAAM,CAAC;IAClB,sDAAsD;IACtD,MAAM,EAAE,MAAM,CAAC;IACf,4DAA4D;IAC5D,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,kEAAkE;IAClE,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,0EAA0E;IAC1E,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,uEAAuE;IACvE,KAAK,CAAC,EAAE,MAAM,MAAM,GAAG,IAAI,CAAC;CAC7B;AAED,+CAA+C;AAC/C,MAAM,WAAW,0BAA0B;IACzC,iEAAiE;IACjE,OAAO,EAAE,SAAS,GAAG,MAAM,CAAC;IAC5B,uCAAuC;IACvC,MAAM,EAAE,MAAM,CAAC;IACf,0FAA0F;IAC1F,YAAY,EAAE,OAAO,CAAC;IACtB,gDAAgD;IAChD,QAAQ,CAAC,EAAE,qBAAqB,CAAC;CAClC;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,oBAAoB,CAClC,IAAI,EAAE,2BAA2B,GAChC,0BAA0B,CAyD5B"}