@flemist/mcp-project-tools 3.0.6 → 3.0.8

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.
@@ -5,15 +5,15 @@ import * as B from "fs";
5
5
  import * as T from "path";
6
6
  import it from "path";
7
7
  import { StreamableHTTPServerTransport as at } from "@modelcontextprotocol/sdk/server/streamableHttp.js";
8
- import { spawn as lt } from "child_process";
9
- import { z as p } from "zod";
8
+ import { spawn as ct } from "child_process";
9
+ import { z as h } from "zod";
10
10
  import K from "tree-kill";
11
- import { Pool as ct, poolRunWait as z } from "@flemist/time-limits";
11
+ import { Pool as lt, poolRunWait as z } from "@flemist/time-limits";
12
12
  import { priorityCreate as P } from "@flemist/priority-queue";
13
13
  import { useAbortController as ut, combineAbortSignals as dt } from "@flemist/async-utils";
14
14
  import ft from "node:os";
15
- import ht from "picomatch";
16
- import { webkit as mt, firefox as pt, chromium as gt } from "playwright";
15
+ import mt from "picomatch";
16
+ import { webkit as ht, firefox as pt, chromium as gt } from "playwright";
17
17
  function wt(t) {
18
18
  const { authToken: r } = t;
19
19
  return function(o, e, n) {
@@ -64,7 +64,7 @@ async function bt(t, r) {
64
64
  throw await e(), n;
65
65
  }
66
66
  }
67
- async function xt(t, r, s, o) {
67
+ async function St(t, r, s, o) {
68
68
  await q({
69
69
  logFilePath: s.logFilePath,
70
70
  message: "REQUEST",
@@ -73,7 +73,7 @@ async function xt(t, r, s, o) {
73
73
  let e = o ? G.get(o) : null;
74
74
  e || (e = await bt(s, o)), await e.handleRequest(t, r, t.body);
75
75
  }
76
- async function St(t, r, s) {
76
+ async function xt(t, r, s) {
77
77
  const o = s ? G.get(s) : null;
78
78
  if (!o) {
79
79
  r.status(400).json({ error: "No valid session found" });
@@ -85,7 +85,7 @@ function $t(t) {
85
85
  return async function(s, o) {
86
86
  try {
87
87
  const e = yt(s);
88
- s.method === "POST" ? await xt(s, o, t, e) : s.method === "GET" ? await St(s, o, e) : o.status(405).json({ error: "Method not allowed" });
88
+ s.method === "POST" ? await St(s, o, t, e) : s.method === "GET" ? await xt(s, o, e) : o.status(405).json({ error: "Method not allowed" });
89
89
  } catch (e) {
90
90
  console.error("Unhandled error in streamableHttpHandler", e), o.status(500).json({
91
91
  error: "Internal server error: " + (e instanceof Error ? e.message : "Unknown error")
@@ -95,7 +95,7 @@ function $t(t) {
95
95
  }
96
96
  const O = /* @__PURE__ */ new Map();
97
97
  let It = 0;
98
- const ie = 10, Mt = 1800 * 1e3, k = 2e3, Tt = 500, vt = 5e3;
98
+ const ie = 10, Mt = 1800 * 1e3, k = 1e4, Tt = 500, vt = 5e3;
99
99
  function Ct(t) {
100
100
  const { commandLine: r, commandLineRules: s } = t;
101
101
  let o = !1;
@@ -156,7 +156,7 @@ function H(t) {
156
156
  r.output = r.output.substring(0, k);
157
157
  }
158
158
  }
159
- function Dt(t, r) {
159
+ function Et(t, r) {
160
160
  const s = r.limit;
161
161
  if (t.length <= s) return t;
162
162
  const e = `
@@ -172,11 +172,11 @@ function C(t) {
172
172
 
173
173
  Provide valid parameters according to schema.`;
174
174
  }
175
- const Ie = p.object({
176
- id: p.number().describe(
175
+ const Ie = h.object({
176
+ id: h.number().describe(
177
177
  "Process ID to get detailed status information for. Get process IDs using process-list. Works for both running and completed processes. Examples: 1, 42, 123"
178
178
  ),
179
- outputLimit: p.number().max(k).default(k).describe(
179
+ outputLimit: h.number().max(k).default(k).describe(
180
180
  `Maximum number of output characters to capture and return from the process. Output exceeding this limit will be truncated with beginning/end preserved and middle removed. Maximum: ${k} characters. Default: ${k}.`
181
181
  )
182
182
  });
@@ -196,7 +196,7 @@ async function Y(t, r) {
196
196
  error: `Process ${o} not found. The process may have already completed and been cleaned up after 30 minutes, or the ID may be incorrect. Use process-list to see available processes and their current status.`
197
197
  };
198
198
  H({ process: n });
199
- const a = n.output + n.localOutput, i = Dt(a, { limit: e });
199
+ const a = n.output + n.localOutput, i = Et(a, { limit: e });
200
200
  return n.output = "", n.localOutput = "", {
201
201
  id: n.id,
202
202
  cwd: T.relative(r.workingDir || "", n.cwd),
@@ -210,7 +210,7 @@ async function Y(t, r) {
210
210
  error: n.error
211
211
  };
212
212
  }
213
- function Et(t, r) {
213
+ function Dt(t, r) {
214
214
  t(
215
215
  "process-status",
216
216
  {
@@ -241,17 +241,17 @@ function Me(t) {
241
241
  });
242
242
  }, vt);
243
243
  }
244
- const Te = p.object({
245
- id: p.number().describe(
244
+ const Te = h.object({
245
+ id: h.number().describe(
246
246
  "Process ID to wait for completion. Get process IDs using process-list. The process can be running or already completed. Examples: 1, 42, 123"
247
247
  ),
248
- waitTime: p.number().optional().describe(
248
+ waitTime: h.number().optional().describe(
249
249
  "Maximum time to wait in seconds for process completion. If omitted, waits indefinitely until process completes. If process is already completed, returns immediately. Examples: 30 (wait up to 30 seconds), 300 (wait up to 5 minutes)"
250
250
  ),
251
- autoKill: p.boolean().default(!1).describe(
251
+ autoKill: h.boolean().default(!1).describe(
252
252
  "Automatically terminate the process if waitTime expires and it is still running. Only applies when waitTime is specified. Default: false (let process continue running after timeout). Set to true for processes that should not run indefinitely"
253
253
  ),
254
- outputLimit: p.number().max(k).default(k).describe(
254
+ outputLimit: h.number().max(k).default(k).describe(
255
255
  `Maximum number of output characters to capture and return from the process. Output exceeding this limit will be truncated with beginning/end preserved and middle removed. Maximum: ${k} characters. Default: ${k}.`
256
256
  )
257
257
  });
@@ -259,9 +259,9 @@ async function ve(t, r) {
259
259
  let s;
260
260
  try {
261
261
  s = Te.parse(t);
262
- } catch (h) {
262
+ } catch (m) {
263
263
  return {
264
- error: C(h)
264
+ error: C(m)
265
265
  };
266
266
  }
267
267
  const { id: o, waitTime: e, autoKill: n, outputLimit: a } = s, i = O.get(o);
@@ -270,18 +270,18 @@ async function ve(t, r) {
270
270
  error: `Process ${o} not found. The process may have already completed and been cleaned up after 30 minutes, or the ID may be incorrect. Use process-list to see available processes and their current status.`
271
271
  };
272
272
  const u = Date.now();
273
- let l = !1, c = !1;
274
- e != null && await new Promise((m) => {
275
- const g = setInterval(() => {
276
- i.isRunning ? Date.now() - u >= e * 1e3 && (clearInterval(g), l = !0, n && i.pid && (Me(i.pid), c = !0), m()) : (clearInterval(g), m());
273
+ let c = !1, l = !1;
274
+ e != null && await new Promise((g) => {
275
+ const p = setInterval(() => {
276
+ i.isRunning ? Date.now() - u >= e * 1e3 && (clearInterval(p), c = !0, n && i.pid && (Me(i.pid), l = !0), g()) : (clearInterval(p), g());
277
277
  }, 100);
278
278
  });
279
279
  const f = (Date.now() - u) / 1e3;
280
280
  return {
281
281
  ...await Y({ id: o, outputLimit: a }, r),
282
282
  waitDuration: f,
283
- waitTimeExceeded: l,
284
- autoKillExecuted: c
283
+ waitTimeExceeded: c,
284
+ autoKillExecuted: l
285
285
  };
286
286
  }
287
287
  function Ft(t, r) {
@@ -306,20 +306,20 @@ ${e.trim()}`;
306
306
  }
307
307
  );
308
308
  }
309
- const Ce = p.object({
310
- cwd: p.string().optional().describe(
309
+ const Ce = h.object({
310
+ cwd: h.string().optional().describe(
311
311
  'Working directory for command execution, resolved relative to the current working directory. Leave empty to use current directory. Examples: "src" (run in src/ subdirectory), "../parent" (run in parent directory), "build/output" (run in nested subdirectory). Directory must exist'
312
312
  ),
313
- commandLine: p.string().describe(
313
+ commandLine: h.string().describe(
314
314
  'Complete command line to execute on the host machine. Include all arguments and options. Examples: "npm install", "pnpm build", "node script.js --verbose", "git status". Command must be in the allowed commands list for security'
315
315
  ),
316
- waitTime: p.number().optional().describe(
316
+ waitTime: h.number().optional().describe(
317
317
  "Time to wait in seconds for process completion before returning results. If specified, will wait this long then return final status. If omitted, returns immediately with initial status. Use process-wait or process-status to check progress later. Examples: 30 (wait 30 seconds), 120 (wait 2 minutes)"
318
318
  ),
319
- autoKill: p.boolean().default(!1).describe(
319
+ autoKill: h.boolean().default(!1).describe(
320
320
  "Automatically kill the process if waitTime expires and it is still running. Only applies when waitTime is specified. Default: false (let process continue running). Set to true for commands that should not run indefinitely"
321
321
  ),
322
- outputLimit: p.number().max(k).default(k).describe(
322
+ outputLimit: h.number().max(k).default(k).describe(
323
323
  `Maximum number of output characters to capture and return from the process. Output exceeding this limit will be truncated with beginning/end preserved and middle removed. Maximum: ${k} characters. Default: ${k}.`
324
324
  )
325
325
  });
@@ -336,7 +336,7 @@ async function Bt(t, r) {
336
336
  const { commandLine: o, waitTime: e, autoKill: n, outputLimit: a } = s, { commandLineRules: i } = r, u = T.resolve(r.workingDir || "", s.cwd || "");
337
337
  if (!Ct({ commandLine: o, commandLineRules: i })) {
338
338
  const d = i.map(
339
- (h) => `${h.rule.toUpperCase()}: /${h.regexp}/ (${h.note})`
339
+ (m) => `${m.rule.toUpperCase()}: /${m.regexp}/ (${m.note})`
340
340
  ).join(`
341
341
  `);
342
342
  return {
@@ -352,8 +352,8 @@ To use this command line, ask the user to modify the command line rules in the c
352
352
  return {
353
353
  error: `Maximum concurrent process limit reached (${ie} processes). Cannot start new process until existing processes complete. Use process-list to see active processes, or process-kill to terminate unnecessary processes.`
354
354
  };
355
- const c = kt(), f = {
356
- id: c,
355
+ const l = kt(), f = {
356
+ id: l,
357
357
  cwd: u,
358
358
  commandLine: o,
359
359
  startTime: /* @__PURE__ */ new Date(),
@@ -362,35 +362,35 @@ To use this command line, ask the user to modify the command line rules in the c
362
362
  localOutput: "",
363
363
  lastOutputTime: /* @__PURE__ */ new Date()
364
364
  };
365
- O.set(c, f);
365
+ O.set(l, f);
366
366
  try {
367
- const d = lt(o, [], {
367
+ const d = ct(o, [], {
368
368
  shell: !0,
369
369
  cwd: u,
370
370
  stdio: ["pipe", "pipe", "pipe"]
371
371
  });
372
372
  f.pid = d.pid;
373
- const h = (m) => {
374
- const g = m.toString();
375
- f.localOutput += g, H({ process: f }), console.log(g);
373
+ const m = (g) => {
374
+ const p = g.toString();
375
+ f.localOutput += p, H({ process: f }), console.log(p);
376
376
  };
377
- return d.stdout?.on("data", h), d.stderr?.on("data", h), d.on("close", (m) => {
378
- if (f.isRunning = !1, f.endTime = /* @__PURE__ */ new Date(), f.exitCode = m !== null ? m : void 0, f.output += f.localOutput, f.localOutput = "", f.output.length > k) {
379
- const b = `
377
+ return d.stdout?.on("data", m), d.stderr?.on("data", m), d.on("close", (g) => {
378
+ if (f.isRunning = !1, f.endTime = /* @__PURE__ */ new Date(), f.exitCode = g !== null ? g : void 0, f.output += f.localOutput, f.localOutput = "", f.output.length > k) {
379
+ const y = `
380
380
  ... [${f.output.length - k} characters trimmed] ...
381
- `, y = k - b.length;
382
- if (y > 0) {
383
- const x = Math.floor(y / 2);
384
- f.output = f.output.substring(0, x) + b + f.output.substring(
385
- f.output.length - (y - x)
381
+ `, w = k - y.length;
382
+ if (w > 0) {
383
+ const S = Math.floor(w / 2);
384
+ f.output = f.output.substring(0, S) + y + f.output.substring(
385
+ f.output.length - (w - S)
386
386
  );
387
387
  } else
388
388
  f.output = f.output.substring(0, k);
389
389
  }
390
- console.log(`Process ${c} (${o}) exited with code ${m}`);
391
- }), d.on("error", (m) => {
392
- f.isRunning = !1, f.endTime = /* @__PURE__ */ new Date(), f.error = m.message, console.error(`Process ${c} error:`, m.message);
393
- }), e != null ? ve({ id: c, waitTime: e, autoKill: n, outputLimit: a }, r) : Y({ id: c, outputLimit: a }, r);
390
+ console.log(`Process ${l} (${o}) exited with code ${g}`);
391
+ }), d.on("error", (g) => {
392
+ f.isRunning = !1, f.endTime = /* @__PURE__ */ new Date(), f.error = g.message, console.error(`Process ${l} error:`, g.message);
393
+ }), e != null ? ve({ id: l, waitTime: e, autoKill: n, outputLimit: a }, r) : Y({ id: l, outputLimit: a }, r);
394
394
  } catch (d) {
395
395
  return f.isRunning = !1, f.endTime = /* @__PURE__ */ new Date(), f.error = d instanceof Error ? d.message : "Unknown error", { error: f.error };
396
396
  }
@@ -420,17 +420,17 @@ ${n.trim()}`;
420
420
  }
421
421
  );
422
422
  }
423
- const ke = p.object({
424
- minOpenDateTime: p.string().optional().describe(
423
+ const ke = h.object({
424
+ minOpenDateTime: h.string().optional().describe(
425
425
  'Filter to processes started after this datetime. Accepts ISO format or space-separated format. Examples: "2024-01-15T10:30:00Z", "2024-01-15 10:30:00". Underscores and spaces are converted to standard ISO format internally'
426
426
  ),
427
- minCloseDateTime: p.string().optional().describe(
427
+ minCloseDateTime: h.string().optional().describe(
428
428
  'Filter to processes that finished after this datetime. Only applies to completed processes. Accepts ISO format or space-separated format. Examples: "2024-01-15T14:30:00Z", "2024-01-15 14:30:00". Useful for finding recently completed processes'
429
429
  ),
430
- activeOnly: p.boolean().default(!1).describe(
430
+ activeOnly: h.boolean().default(!1).describe(
431
431
  "Show only currently running processes. Set to true to exclude completed processes, false to show all processes (running and completed). Default: false (show all)"
432
432
  ),
433
- fields: p.array(p.string()).optional().describe(
433
+ fields: h.array(h.string()).optional().describe(
434
434
  'Specific process data fields to include in the response. If omitted, returns all available fields. Available fields: id, cwd, commandLine, pid, startTime, endTime, exitCode, isRunning, output, error. Examples: ["id", "commandLine", "isRunning"] for minimal info, ["id", "output", "exitCode"] for execution results'
435
435
  )
436
436
  });
@@ -439,42 +439,42 @@ async function Rt(t, r) {
439
439
  let s;
440
440
  try {
441
441
  s = ke.parse(t);
442
- } catch (l) {
442
+ } catch (c) {
443
443
  return {
444
- error: C(l)
444
+ error: C(c)
445
445
  };
446
446
  }
447
447
  const { minOpenDateTime: o, minCloseDateTime: e, activeOnly: n, fields: a } = s;
448
448
  let i = Array.from(O.values());
449
449
  if (o) {
450
- const l = new Date(o.replace(/[_\s]/g, "T"));
451
- i = i.filter((c) => c.startTime >= l);
450
+ const c = new Date(o.replace(/[_\s]/g, "T"));
451
+ i = i.filter((l) => l.startTime >= c);
452
452
  }
453
453
  if (e) {
454
- const l = new Date(e.replace(/[_\s]/g, "T"));
455
- i = i.filter((c) => c.endTime && c.endTime >= l);
456
- }
457
- return n && (i = i.filter((l) => l.isRunning)), { processes: i.map((l) => {
458
- H({ process: l });
459
- let c = {
460
- id: l.id,
461
- cwd: it.relative(r.workingDir || "", l.cwd),
462
- commandLine: l.commandLine,
463
- pid: l.pid,
464
- startTime: l.startTime.toISOString().replace(/[TZ]/g, " ").trim(),
465
- endTime: l.endTime?.toISOString().replace(/[TZ]/g, " ").trim(),
466
- exitCode: l.exitCode,
467
- isRunning: l.isRunning,
468
- output: l.output + l.localOutput,
469
- error: l.error
454
+ const c = new Date(e.replace(/[_\s]/g, "T"));
455
+ i = i.filter((l) => l.endTime && l.endTime >= c);
456
+ }
457
+ return n && (i = i.filter((c) => c.isRunning)), { processes: i.map((c) => {
458
+ H({ process: c });
459
+ let l = {
460
+ id: c.id,
461
+ cwd: it.relative(r.workingDir || "", c.cwd),
462
+ commandLine: c.commandLine,
463
+ pid: c.pid,
464
+ startTime: c.startTime.toISOString().replace(/[TZ]/g, " ").trim(),
465
+ endTime: c.endTime?.toISOString().replace(/[TZ]/g, " ").trim(),
466
+ exitCode: c.exitCode,
467
+ isRunning: c.isRunning,
468
+ output: c.output + c.localOutput,
469
+ error: c.error
470
470
  };
471
471
  if (a) {
472
472
  const f = {};
473
473
  for (const d of a)
474
- d in c && (f[d] = c[d]);
475
- c = f;
474
+ d in l && (f[d] = l[d]);
475
+ l = f;
476
476
  }
477
- return c;
477
+ return l;
478
478
  }) };
479
479
  }
480
480
  function Pt(t, r) {
@@ -493,15 +493,15 @@ function Pt(t, r) {
493
493
  const e = o.processes.map(
494
494
  (n) => `[${n.isRunning ? "RUNNING" : "COMPLETED"}] ${n.id}: ${n.commandLine}`
495
495
  ).join(`
496
- `);
496
+ `) || "No processes found";
497
497
  return `Method: process-list(${JSON.stringify(s)})
498
- Active processes:
498
+ Processes:
499
499
  ${e}`;
500
500
  }
501
501
  );
502
502
  }
503
- const Ne = p.object({
504
- id: p.number().describe(
503
+ const Ne = h.object({
504
+ id: h.number().describe(
505
505
  "Process ID of the process to terminate. Get process IDs using process-list. The process must be currently running. Examples: 1, 42, 123"
506
506
  )
507
507
  });
@@ -552,7 +552,7 @@ ${JSON.stringify(o, null, 2)}`;
552
552
  );
553
553
  }
554
554
  function Ut(t, r) {
555
- Nt(), r.run && Ot(t, r), r.status && Et(t, r), r.wait && Ft(t, r), r.list && Pt(t, r), r.kill && Lt(t);
555
+ Nt(), r.run && Ot(t, r), r.status && Dt(t, r), r.wait && Ft(t, r), r.list && Pt(t, r), r.kill && Lt(t);
556
556
  const s = r.commandLineRules?.map(
557
557
  (o) => `${o.rule.toUpperCase()}: ${o.regexp} (${o.note})`
558
558
  ) || [];
@@ -603,8 +603,8 @@ function Gt(t, r) {
603
603
  function jt(t) {
604
604
  return t.endsWith(":") && (t += "/"), T.resolve(t);
605
605
  }
606
- const De = new ct(ft.cpus().length);
607
- function le(t, r) {
606
+ const Ee = new lt(ft.cpus().length);
607
+ function ce(t, r) {
608
608
  t.totalSize += r.totalSize, t.maxFileDateModified = Math.max(
609
609
  t.maxFileDateModified,
610
610
  r.maxFileDateModified
@@ -613,7 +613,7 @@ function le(t, r) {
613
613
  const _t = function(r) {
614
614
  return r.code === "ENOENT";
615
615
  };
616
- function Ee(t) {
616
+ function De(t) {
617
617
  const r = t.paths;
618
618
  if (!r || r.length === 0)
619
619
  return Promise.resolve({
@@ -623,139 +623,139 @@ function Ee(t) {
623
623
  countDirs: 0,
624
624
  countLinks: 0
625
625
  });
626
- const s = t.level ?? 0, o = t.walkedIds ?? /* @__PURE__ */ new Set(), e = t.abortSignal, n = t.pool ?? De, a = t.handleError, i = t.priority ?? P(0), u = t.walkLinks ?? !1, l = t.log, c = t.handlePath, f = t.matchPath;
627
- async function d(m) {
628
- if (!(a && await a(m)) && !_t(m))
629
- throw m;
626
+ const s = t.level ?? 0, o = t.walkedIds ?? /* @__PURE__ */ new Set(), e = t.abortSignal, n = t.pool ?? Ee, a = t.handleError, i = t.priority ?? P(0), u = t.walkLinks ?? !1, c = t.log, l = t.handlePath, f = t.matchPath;
627
+ async function d(g) {
628
+ if (!(a && await a(g)) && !_t(g))
629
+ throw g;
630
630
  }
631
- function h(m) {
632
- return !(!l || l.minTotalContentSize != null && m < l.minTotalContentSize || l.maxNestedLevel != null && s > l.maxNestedLevel);
631
+ function m(g) {
632
+ return !(!c || c.minTotalContentSize != null && g < c.minTotalContentSize || c.maxNestedLevel != null && s > c.maxNestedLevel);
633
633
  }
634
- return ut(async (m) => {
635
- const g = dt(e, m), b = {
634
+ return ut(async (g) => {
635
+ const p = dt(e, g), y = {
636
636
  totalSize: 0,
637
637
  maxFileDateModified: 0,
638
638
  countFiles: 0,
639
639
  countDirs: 0,
640
640
  countLinks: 0
641
641
  };
642
- function y(w, M) {
643
- if (h(M.totalSize)) {
644
- const v = `${M.totalSize.toLocaleString("en-US").replace(/,/g, " ").padStart(19)}: ${w}`;
645
- l?.handleLog ? l.handleLog(v) : console.log(v);
642
+ function w(b, x) {
643
+ if (m(x.totalSize)) {
644
+ const v = `${x.totalSize.toLocaleString("en-US").replace(/,/g, " ").padStart(19)}: ${b}`;
645
+ c?.handleLog ? c.handleLog(v) : console.log(v);
646
646
  }
647
647
  }
648
- async function x(w, M, $, v) {
649
- return c ? await z({
648
+ async function S(b, x, $, v) {
649
+ return l ? await z({
650
650
  pool: n,
651
651
  func: async () => {
652
652
  try {
653
- return await c({
653
+ return await l({
654
654
  level: s,
655
- path: w,
656
- stat: M,
655
+ path: b,
656
+ stat: x,
657
657
  itemStat: $,
658
- totalStat: b,
659
- abortSignal: g
658
+ totalStat: y,
659
+ abortSignal: p
660
660
  });
661
- } catch (D) {
662
- return await d(D), !1;
661
+ } catch (E) {
662
+ return await d(E), !1;
663
663
  }
664
664
  },
665
665
  count: 1,
666
666
  priority: v,
667
- abortSignal: g
667
+ abortSignal: p
668
668
  }) : !0;
669
669
  }
670
- async function I(w, M, $, v) {
671
- v || (v = w);
672
- const D = await z({
670
+ async function M(b, x, $, v) {
671
+ v || (v = b);
672
+ const E = await z({
673
673
  pool: n,
674
- func: () => B.promises.lstat(w).catch(d),
674
+ func: () => B.promises.lstat(b).catch(d),
675
675
  count: 1,
676
- priority: P(M, P(1, i)),
677
- abortSignal: g
676
+ priority: P(x, P(1, i)),
677
+ abortSignal: p
678
678
  });
679
- if (!D || !$ && D.isFile())
679
+ if (!E || !$ && E.isFile())
680
680
  return null;
681
- const ne = Gt(w, D);
681
+ const ne = Gt(b, E);
682
682
  if (o.has(ne))
683
683
  return null;
684
684
  o.add(ne);
685
685
  let N = {
686
- totalSize: D.size,
687
- maxFileDateModified: D.isDirectory() ? 0 : D.mtimeMs,
686
+ totalSize: E.size,
687
+ maxFileDateModified: E.isDirectory() ? 0 : E.mtimeMs,
688
688
  countFiles: 0,
689
689
  countDirs: 0,
690
690
  countLinks: 0
691
691
  };
692
692
  const L = P(
693
- M,
694
- P(D.isDirectory() ? 2 : 3, i)
693
+ x,
694
+ P(E.isDirectory() ? 2 : 3, i)
695
695
  );
696
- if (D.isSymbolicLink()) {
696
+ if (E.isSymbolicLink()) {
697
697
  if (u) {
698
698
  const F = await z({
699
699
  pool: n,
700
- func: () => B.promises.readlink(w).catch(d).then((R) => R ?? null),
700
+ func: () => B.promises.readlink(b).catch(d).then((R) => R ?? null),
701
701
  count: 1,
702
702
  priority: L,
703
- abortSignal: g
703
+ abortSignal: p
704
704
  });
705
705
  if (F) {
706
- const R = T.isAbsolute(F) ? F : T.resolve(T.dirname(v), F), U = await I(
706
+ const R = T.isAbsolute(F) ? F : T.resolve(T.dirname(v), F), U = await M(
707
707
  R,
708
- M,
708
+ x,
709
709
  $,
710
710
  v
711
711
  );
712
712
  U && (N = U);
713
713
  }
714
714
  }
715
- return ($ || N.countFiles + N.countDirs + N.countLinks >= 1) && (N.countLinks += 1, await x(
715
+ return ($ || N.countFiles + N.countDirs + N.countLinks >= 1) && (N.countLinks += 1, await S(
716
716
  v,
717
- D,
717
+ E,
718
718
  N,
719
719
  L
720
- ) && (le(b, N), y(v, N))), N;
721
- } else if (D.isDirectory()) {
720
+ ) && (ce(y, N), w(v, N))), N;
721
+ } else if (E.isDirectory()) {
722
722
  const F = await z({
723
723
  pool: n,
724
- func: () => B.promises.readdir(w).catch(d),
724
+ func: () => B.promises.readdir(b).catch(d),
725
725
  count: 1,
726
726
  priority: i,
727
- abortSignal: g
727
+ abortSignal: p
728
728
  });
729
729
  if (F) {
730
730
  for (let R = 0, U = F.length; R < U; R++)
731
731
  F[R] = T.join(v, F[R]);
732
- N = await Ee({
732
+ N = await De({
733
733
  ...t,
734
734
  paths: F,
735
- abortSignal: g,
735
+ abortSignal: p,
736
736
  priority: L,
737
737
  level: s + 1,
738
738
  walkedIds: o
739
739
  });
740
740
  }
741
741
  }
742
- return ($ || N.countFiles + N.countDirs + N.countLinks >= 1) && (D.isDirectory() ? N.countDirs += 1 : D.isFile() && (N.countFiles += 1), await x(
742
+ return ($ || N.countFiles + N.countDirs + N.countLinks >= 1) && (E.isDirectory() ? N.countDirs += 1 : E.isFile() && (N.countFiles += 1), await S(
743
743
  v,
744
- D,
744
+ E,
745
745
  N,
746
746
  L
747
- ) && (le(b, N), y(v, N))), N;
747
+ ) && (ce(y, N), w(v, N))), N;
748
748
  }
749
- const S = [];
750
- for (let w = 0, M = r.length; w < M; w++) {
751
- const $ = jt(r[w]), v = f ? f($) : !0;
752
- v !== !1 && S.push(I($, w, v));
749
+ const I = [];
750
+ for (let b = 0, x = r.length; b < x; b++) {
751
+ const $ = jt(r[b]), v = f ? f($) : !0;
752
+ v !== !1 && I.push(M($, b, v));
753
753
  }
754
- return await Promise.all(S), b;
754
+ return await Promise.all(I), y;
755
755
  });
756
756
  }
757
757
  function Fe(t) {
758
- return Ee(t);
758
+ return De(t);
759
759
  }
760
760
  function Jt(t, r) {
761
761
  if (!r || r === ".")
@@ -769,7 +769,7 @@ function Kt(t) {
769
769
  const r = t.startsWith("!");
770
770
  return r && (t = t.substring(1)), t.startsWith("/") ? t = t.substring(1) : !t.startsWith("**") && !t.startsWith("../") && (t = `**/${t}`), r && (t = "!" + t), t;
771
771
  }
772
- function ce(t) {
772
+ function le(t) {
773
773
  return "^" + t;
774
774
  }
775
775
  async function Wt(t) {
@@ -785,16 +785,16 @@ async function Be(t) {
785
785
  return s;
786
786
  const o = [];
787
787
  return t.globs.forEach((e) => {
788
- e.value && (e.valueType === "file-contains-patterns" ? o.push(e) : e.valueType === "pattern" && s.push(e.exclude ? ce(e.value) : e.value));
788
+ e.value && (e.valueType === "file-contains-patterns" ? o.push(e) : e.valueType === "pattern" && s.push(e.exclude ? le(e.value) : e.value));
789
789
  }), o.length && await Promise.all(
790
790
  o.map(async (e) => {
791
791
  await z({
792
- pool: De,
792
+ pool: Ee,
793
793
  count: 1,
794
794
  func: async () => {
795
795
  const n = T.resolve(r, e.value), a = await Wt(n), i = T.relative(r, T.dirname(n));
796
796
  a.forEach((u) => {
797
- u = Kt(u), u = Jt(u, i), s.push(e.exclude ? ce(u) : u);
797
+ u = Kt(u), u = Jt(u, i), s.push(e.exclude ? le(u) : u);
798
798
  });
799
799
  }
800
800
  });
@@ -822,15 +822,15 @@ function Oe({
822
822
  return;
823
823
  let u;
824
824
  try {
825
- u = ht(i, {
825
+ u = mt(i, {
826
826
  nocase: s ?? !1,
827
827
  dot: !0,
828
828
  strictBrackets: !0
829
829
  // Validate bracket balance for patterns like "["
830
830
  });
831
- } catch (l) {
831
+ } catch (c) {
832
832
  throw new Error(
833
- `Invalid glob pattern: "${e}". ${l instanceof Error ? l.message : "Unknown error"}. Valid glob patterns use: * (match any characters), ** (match any directories), ? (match single character), [abc] (character class with balanced brackets), ! (negate pattern), ^ (exclude if included). Examples: "*.js", "src/**/*.ts", "!node_modules", "[abc]def.txt". Ensure all brackets [ ] are properly closed and balanced.`
833
+ `Invalid glob pattern: "${e}". ${c instanceof Error ? c.message : "Unknown error"}. Valid glob patterns use: * (match any characters), ** (match any directories), ? (match single character), [abc] (character class with balanced brackets), ! (negate pattern), ^ (exclude if included). Examples: "*.js", "src/**/*.ts", "!node_modules", "[abc]def.txt". Ensure all brackets [ ] are properly closed and balanced.`
834
834
  );
835
835
  }
836
836
  o.push({
@@ -842,9 +842,9 @@ function Oe({
842
842
  }), function(n) {
843
843
  n = n.replace(/\\/g, "/");
844
844
  let a = null, i = !1;
845
- for (let u = 0, l = o.length; u < l; u++) {
846
- const c = o[u];
847
- c.match(n) && (c.exclude ? i = !c.negative : (a = !c.negative, i = !1));
845
+ for (let u = 0, c = o.length; u < c; u++) {
846
+ const l = o[u];
847
+ l.match(n) && (l.exclude ? i = !l.negative : (a = !l.negative, i = !1));
848
848
  }
849
849
  return i ? !1 : a;
850
850
  };
@@ -865,24 +865,24 @@ async function Qt(t) {
865
865
  noCase: !0
866
866
  }),
867
867
  handlePath: async ({ path: n, stat: a, itemStat: i }) => {
868
- const u = T.relative(r, n), l = a.isDirectory(), c = a.isFile();
869
- if (!l && !c)
868
+ const u = T.relative(r, n), c = a.isDirectory(), l = a.isFile();
869
+ if (!c && !l)
870
870
  return !0;
871
- const f = (u || ".").replace(/\\/g, "/"), d = l ? "dir" : "file", h = l ? i.maxFileDateModified || null : a.mtimeMs, m = l ? i.totalSize : a.size, g = l ? i.countFiles : null, b = {
871
+ const f = (u || ".").replace(/\\/g, "/"), d = c ? "dir" : "file", m = c ? i.maxFileDateModified || null : a.mtimeMs, g = c ? i.totalSize : a.size, p = c ? i.countFiles : null, y = {
872
872
  path: f,
873
873
  type: d
874
874
  };
875
- if (t.result.dateModified && (b.dateModified = h), t.result.size && (b.size = m), t.result.countFiles && (b.countFiles = g), t.dateModified && h != null) {
876
- const [y, x] = t.dateModified;
877
- if (y != null && h < y || x != null && h > x)
875
+ if (t.result.dateModified && (y.dateModified = m), t.result.size && (y.size = g), t.result.countFiles && (y.countFiles = p), t.dateModified && m != null) {
876
+ const [w, S] = t.dateModified;
877
+ if (w != null && m < w || S != null && m > S)
878
878
  return !1;
879
879
  }
880
- if (t.totalSize && m != null) {
881
- const [y, x] = t.totalSize;
882
- if (y != null && m < y || x != null && m > x)
880
+ if (t.totalSize && g != null) {
881
+ const [w, S] = t.totalSize;
882
+ if (w != null && g < w || S != null && g > S)
883
883
  return !1;
884
884
  }
885
- return d === "file" && (o.countFiles = (o.countFiles ?? 0) + 1), d === "file" && m != null && (o.size = (o.size ?? 0) + m), h != null && (o.dateModified == null || h > o.dateModified) && (o.dateModified = h), l && !t.result.dirs || c && !t.result.files || s.push(b), !0;
885
+ return d === "file" && (o.countFiles = (o.countFiles ?? 0) + 1), d === "file" && g != null && (o.size = (o.size ?? 0) + g), m != null && (o.dateModified == null || m > o.dateModified) && (o.dateModified = m), c && !t.result.dirs || l && !t.result.files || s.push(y), !0;
886
886
  }
887
887
  }), { items: s, totals: o };
888
888
  }
@@ -894,11 +894,11 @@ function fe(t) {
894
894
  r /= de, s++;
895
895
  return `${s === 0 ? r.toString() : r.toFixed(2)}${ue[s]}`;
896
896
  }
897
- function he(t) {
897
+ function me(t) {
898
898
  const s = Date.now() - t;
899
899
  if (s < 0) return "0s";
900
- const o = Math.floor(s / 1e3), e = Math.floor(o / 60), n = Math.floor(e / 60), a = Math.floor(n / 24), i = Math.floor(a / 7), u = Math.floor(a / 30), l = Math.floor(a / 365);
901
- return l > 0 ? `${l}Y` : u > 0 ? `${u}M` : i > 0 ? `${i}w` : a > 0 ? `${a}d` : n > 0 ? `${n}h` : e > 0 ? `${e}m` : `${o}s`;
900
+ const o = Math.floor(s / 1e3), e = Math.floor(o / 60), n = Math.floor(e / 60), a = Math.floor(n / 24), i = Math.floor(a / 7), u = Math.floor(a / 30), c = Math.floor(a / 365);
901
+ return c > 0 ? `${c}Y` : u > 0 ? `${u}M` : i > 0 ? `${i}w` : a > 0 ? `${a}d` : n > 0 ? `${n}h` : e > 0 ? `${e}m` : `${o}s`;
902
902
  }
903
903
  function Ht(t, r) {
904
904
  return r?.length ? [...t].sort((s, o) => {
@@ -929,9 +929,9 @@ function Ht(t, r) {
929
929
  }
930
930
  if (u == null)
931
931
  return -1;
932
- const l = i > u ? 1 : i < u ? -1 : 0;
933
- if (l !== 0)
934
- return a.desc ? -l : l;
932
+ const c = i > u ? 1 : i < u ? -1 : 0;
933
+ if (c !== 0)
934
+ return a.desc ? -c : c;
935
935
  }
936
936
  return 0;
937
937
  }) : t;
@@ -964,11 +964,11 @@ function Yt(t, r) {
964
964
  const i = s[n];
965
965
  e += `
966
966
  `;
967
- for (let u = 0, l = o.length; u < l; u++) {
968
- const c = o[u];
969
- switch (u > 0 && (e += " | "), c) {
967
+ for (let u = 0, c = o.length; u < c; u++) {
968
+ const l = o[u];
969
+ switch (u > 0 && (e += " | "), l) {
970
970
  case "dateModified":
971
- e += i.dateModified ? he(i.dateModified) : "-";
971
+ e += i.dateModified ? me(i.dateModified) : "-";
972
972
  break;
973
973
  case "size":
974
974
  e += fe(i.size);
@@ -990,14 +990,14 @@ function Yt(t, r) {
990
990
  e.length > 0 && (e += `
991
991
  ---
992
992
  `);
993
- const n = fe(t.totals.size ?? 0), a = t.totals.dateModified ? `, last modified ${he(t.totals.dateModified)} ago` : "";
993
+ const n = fe(t.totals.size ?? 0), a = t.totals.dateModified ? `, last modified ${me(t.totals.dateModified)} ago` : "";
994
994
  e += `Totals: ${t.totals.countFiles ?? 0} files in dirs, ${n}${a}`;
995
995
  }
996
996
  return e;
997
997
  }
998
- const Vt = "3.0.6", Zt = {
998
+ const Vt = "3.0.8", Zt = {
999
999
  version: Vt
1000
- }, ds = "Project Tools", fs = "project-tools", hs = Zt.version, ms = "d00f70240703039df14c76176a055bce6b5484d2b552ba2c89820f03b8e5e60d", me = 25e3;
1000
+ }, ds = "Project Tools", fs = "project-tools", ms = Zt.version, hs = "d00f70240703039df14c76176a055bce6b5484d2b552ba2c89820f03b8e5e60d", he = 25e3;
1001
1001
  function pe(t) {
1002
1002
  const r = t.match(
1003
1003
  /^\s*(\d+(?:\.\d+)?)\s*([smhdwMY]|sec(onds?)?|min(utes?)?|hours?|days?|weeks?|months?|years?)\s*$/i
@@ -1053,42 +1053,42 @@ function ge(t) {
1053
1053
  );
1054
1054
  }
1055
1055
  }
1056
- const Re = p.object({
1057
- rootDir: p.string().optional().describe(
1056
+ const Re = h.object({
1057
+ rootDir: h.string().optional().describe(
1058
1058
  'Root directory to list files from, resolved relative to the current working directory. Leave empty to use current directory. Examples: "src" (list src/ subdirectory), "../parent" (list parent directory), "docs/api" (list nested subdirectory). Path must exist and be accessible'
1059
1059
  ),
1060
- globs: p.array(p.string()).optional().describe(
1060
+ globs: h.array(h.string()).optional().describe(
1061
1061
  'Glob patterns to filter which files/directories to include. Add leading ** to match files and dirs in subdirectories. Examples: ["**/*.js"] (JavaScript files), ["src/**/*.ts"] (TypeScript files in src), ["**/dir/"] (all directories named "dir"), ["!node_modules"] (exclude {rootDir}/node_modules). If omitted, includes all files matching other criteria. Supports standard glob syntax: * (any chars), ** (any dirs), ? (single char), [abc] (char class)'
1062
1062
  ),
1063
- showFiles: p.boolean().optional().describe(
1063
+ showFiles: h.boolean().optional().describe(
1064
1064
  "Whether to show regular files in the report table. Set to true to show files, false to hide them from the table. When both showFiles and showDirs are false, nothing will be shown in the table. It Does not affect totals. Default is false (do not show files in the table)"
1065
1065
  ),
1066
- showDirs: p.boolean().optional().describe(
1066
+ showDirs: h.boolean().optional().describe(
1067
1067
  "Whether to show directories in the report table. Set to true to show directories, false to hide them from the table. When both showFiles and showDirs are false, nothing will be shown in the table. It Does not affect totals. Default is true (show directories in the table)"
1068
1068
  ),
1069
- sortBy: p.array(
1070
- p.object({
1071
- field: p.enum(["type", "path", "lastModified", "size", "totalCountFiles"]).describe(
1069
+ sortBy: h.array(
1070
+ h.object({
1071
+ field: h.enum(["type", "path", "lastModified", "size", "totalCountFiles"]).describe(
1072
1072
  'Field to sort results by. "type" sorts files before directories. "path" sorts alphabetically by file/directory name. "lastModified" sorts by modification time (newest first when desc=true). "size" sorts by file/directory size (largest first when desc=true). "totalCountFiles" sorts by total files count (highest first when desc=true, directories only)'
1073
1073
  ),
1074
- desc: p.boolean().optional().describe("Sort in descending order (largest/newest first)")
1074
+ desc: h.boolean().optional().describe("Sort in descending order (largest/newest first)")
1075
1075
  })
1076
1076
  ).optional().describe(
1077
1077
  'Multi-level sorting configuration. Sorts are applied in array order - first sort is primary, second is secondary, etc. Example: [{field: "type", desc: false}, {field: "size", desc: true}] sorts by type ascending, then by size descending within each type'
1078
1078
  ),
1079
- fields: p.array(p.enum(["type", "path", "lastModified", "size", "totalCountFiles"])).optional().describe(
1079
+ fields: h.array(h.enum(["type", "path", "lastModified", "size", "totalCountFiles"])).optional().describe(
1080
1080
  'Which data fields to include in the formatted table output. "type" shows file/directory indicator. "path" shows relative file/directory path. "lastModified" shows last modification time as time-ago format (5m, 2h, 3d, etc). "size" shows file/directory size in human-readable format (KB, MB, GB). "totalCountFiles" shows total files count for directories (displays "-" for files). Adding lastModified, size, or totalCountFiles fields increases processing time. Do not set fields if you want to show only totals summary'
1081
1081
  ),
1082
- minTimeAgo: p.string().optional().describe(
1082
+ minTimeAgo: h.string().optional().describe(
1083
1083
  'Filter files/directories modified at least this long ago. Only items older than this duration will be included. Format: number + unit (s/m/h/d/w/M/Y). Examples: "1h" (modified more than 1 hour ago), "7d" (modified more than 7 days ago), "6M" (modified more than 6 months ago)'
1084
1084
  ),
1085
- maxTimeAgo: p.string().optional().describe(
1085
+ maxTimeAgo: h.string().optional().describe(
1086
1086
  'Filter files/directories modified at most this long ago. Only items newer than this duration will be included. Format: number + unit (s/m/h/d/w/M/Y). Examples: "1h" (modified within last hour), "7d" (modified within last 7 days), "1M" (modified within last month). Combine with minTimeAgo for date ranges'
1087
1087
  ),
1088
- minTotalSize: p.string().optional().describe(
1088
+ minTotalSize: h.string().optional().describe(
1089
1089
  'Filter files/directories with total size at least this large. Only items with size >= this value will be included. For directories, uses total size of all contents. Format: number + unit (B/KB/MB/GB/TB). Examples: "1KB" (at least 1 kilobyte), "100MB" (at least 100 megabytes), "1.5GB" (at least 1.5 gigabytes)'
1090
1090
  ),
1091
- maxTotalSize: p.string().optional().describe(
1091
+ maxTotalSize: h.string().optional().describe(
1092
1092
  'Filter files/directories with total size at most this large. Only items with size <= this value will be included. For directories, uses total size of all contents. Format: number + unit (B/KB/MB/GB/TB). Examples: "1MB" (up to 1 megabyte), "500KB" (up to 500 kilobytes), "10GB" (up to 10 gigabytes). Combine with minTotalSize for size ranges'
1093
1093
  )
1094
1094
  });
@@ -1096,9 +1096,9 @@ async function Xt(t, r) {
1096
1096
  let s;
1097
1097
  try {
1098
1098
  s = Re.parse(t);
1099
- } catch (g) {
1099
+ } catch (p) {
1100
1100
  return {
1101
- error: C(g)
1101
+ error: C(p)
1102
1102
  };
1103
1103
  }
1104
1104
  const {
@@ -1108,85 +1108,85 @@ async function Xt(t, r) {
1108
1108
  sortBy: a,
1109
1109
  minTimeAgo: i,
1110
1110
  maxTimeAgo: u,
1111
- minTotalSize: l,
1112
- maxTotalSize: c
1111
+ minTotalSize: c,
1112
+ maxTotalSize: l
1113
1113
  } = s;
1114
1114
  if (s.fields && s.fields.length > 0 && !s.fields.includes("path"))
1115
1115
  return {
1116
1116
  error: 'Fields array must include "path" field when fields are specified. The "path" field is required to identify files and directories in the output'
1117
1117
  };
1118
- const f = s.fields ? s.fields.map((g) => g === "totalCountFiles" ? "countFiles" : g === "lastModified" ? "dateModified" : g) : [];
1119
- let d = a?.map((g) => {
1120
- let b = g.field;
1121
- return b === "totalCountFiles" && (b = "countFiles"), b === "lastModified" && (b = "dateModified"), {
1122
- field: b,
1123
- desc: g.desc ?? !1
1118
+ const f = s.fields ? s.fields.map((p) => p === "totalCountFiles" ? "countFiles" : p === "lastModified" ? "dateModified" : p) : [];
1119
+ let d = a?.map((p) => {
1120
+ let y = p.field;
1121
+ return y === "totalCountFiles" && (y = "countFiles"), y === "lastModified" && (y = "dateModified"), {
1122
+ field: y,
1123
+ desc: p.desc ?? !1
1124
1124
  // Default to ascending if not specified
1125
1125
  };
1126
1126
  }) ?? null;
1127
1127
  (!d || d.length === 0) && (d = [{ field: "path", desc: !1 }]);
1128
- const h = d?.map((g) => g.field) || [], m = T.resolve(
1128
+ const m = d?.map((p) => p.field) || [], g = T.resolve(
1129
1129
  r.workingDir || "",
1130
1130
  s.rootDir || ""
1131
1131
  );
1132
1132
  try {
1133
1133
  try {
1134
- await B.promises.access(m, B.constants.F_OK);
1134
+ await B.promises.access(g, B.constants.F_OK);
1135
1135
  } catch ($) {
1136
1136
  if ($.code === "ENOENT")
1137
1137
  return {
1138
- error: `Directory does not exist: "${m}". Verify the path is correct and accessible. If using rootDir parameter, ensure it exists relative to the current working directory. Use fs-list without rootDir to list the current directory, or check parent directories first.`
1138
+ error: `Directory does not exist: "${g}". Verify the path is correct and accessible. If using rootDir parameter, ensure it exists relative to the current working directory. Use fs-list without rootDir to list the current directory, or check parent directories first.`
1139
1139
  };
1140
1140
  throw $;
1141
1141
  }
1142
- const g = o && o.length > 0 ? o.map(($) => ({
1142
+ const p = o && o.length > 0 ? o.map(($) => ({
1143
1143
  value: $,
1144
1144
  valueType: "pattern",
1145
1145
  exclude: !1
1146
- })) : [{ value: "**", valueType: "pattern", exclude: !1 }], b = r.globsExclude || [], y = [...g, ...b], x = {
1146
+ })) : [{ value: "**", valueType: "pattern", exclude: !1 }], y = r.globsExclude || [], w = [...p, ...y], S = {
1147
1147
  files: e ?? !1,
1148
1148
  dirs: n ?? !1,
1149
- dateModified: f.includes("dateModified") || h.includes("dateModified"),
1150
- size: f.includes("size") || h.includes("size"),
1151
- countFiles: f.includes("countFiles") || h.includes("countFiles")
1149
+ dateModified: f.includes("dateModified") || m.includes("dateModified"),
1150
+ size: f.includes("size") || m.includes("size"),
1151
+ countFiles: f.includes("countFiles") || m.includes("countFiles")
1152
1152
  };
1153
- let I = null, S = null;
1153
+ let M = null, I = null;
1154
1154
  if (i || u)
1155
1155
  try {
1156
- const $ = Date.now(), v = u ? $ - pe(u) : null, D = i ? $ - pe(i) : null;
1157
- I = [v, D];
1156
+ const $ = Date.now(), v = u ? $ - pe(u) : null, E = i ? $ - pe(i) : null;
1157
+ M = [v, E];
1158
1158
  } catch ($) {
1159
1159
  return {
1160
1160
  error: $ instanceof Error ? $.message : "Unknown error parsing time ago filter"
1161
1161
  };
1162
1162
  }
1163
- if (l || c)
1163
+ if (c || l)
1164
1164
  try {
1165
- const $ = l ? ge(l) : null, v = c ? ge(c) : null;
1166
- S = [$, v];
1165
+ const $ = c ? ge(c) : null, v = l ? ge(l) : null;
1166
+ I = [$, v];
1167
1167
  } catch ($) {
1168
1168
  return {
1169
1169
  error: $ instanceof Error ? $.message : "Unknown error parsing size filter"
1170
1170
  };
1171
1171
  }
1172
- const w = await Qt({
1173
- rootDir: m || null,
1174
- globs: y,
1175
- result: x,
1176
- dateModified: I,
1177
- totalSize: S
1172
+ const b = await Qt({
1173
+ rootDir: g || null,
1174
+ globs: w,
1175
+ result: S,
1176
+ dateModified: M,
1177
+ totalSize: I
1178
1178
  });
1179
- return w.items.length > me ? {
1180
- error: `Number of paths (${w.items.length}) exceeds maximum allowed (${me}). Consider using more specific glob patterns or filters to reduce the result set.`
1179
+ return b.items.length > he ? {
1180
+ error: `Number of paths (${b.items.length}) exceeds maximum allowed (${he}). Consider using more specific glob patterns or filters to reduce the result set.`
1181
1181
  } : {
1182
- output: Yt(w, {
1182
+ output: Yt(b, {
1183
1183
  sort: d,
1184
1184
  fields: f,
1185
1185
  totals: !0
1186
1186
  })
1187
1187
  };
1188
- } catch (g) {
1189
- return { error: g instanceof Error ? g.message : "Unknown error" };
1188
+ } catch (p) {
1189
+ return { error: p instanceof Error ? p.message : "Unknown error" };
1190
1190
  }
1191
1191
  }
1192
1192
  function er(t, r) {
@@ -1267,35 +1267,32 @@ function ye(t) {
1267
1267
  );
1268
1268
  }
1269
1269
  }
1270
- const Z = p.object({
1271
- name: p.string().describe(
1270
+ const Z = h.object({
1271
+ name: h.string().describe(
1272
1272
  "Unique name for the filesystem snapshot query. Recommended format: kebab-case-1, kebab-case-2, ..."
1273
1273
  ),
1274
- rootDir: p.string().optional().describe(
1274
+ rootDir: h.string().optional().describe(
1275
1275
  'Root directory to snapshot, resolved relative to the current working directory. Leave empty to use current directory. Examples: "src" (snapshot src/ subdirectory), "../parent" (snapshot parent directory), "docs/api" (snapshot nested subdirectory). Path must exist and be accessible'
1276
1276
  ),
1277
- globs: p.array(p.string()).optional().describe(
1277
+ globs: h.array(h.string()).optional().describe(
1278
1278
  'Glob patterns to filter which files/directories to include in snapshot. Add leading ** to match files and dirs in subdirectories. Examples: ["**/*.js"] (JavaScript files), ["src/**/*.ts"] (TypeScript files in src), ["**/dir/"] (all directories named "dir"), ["!node_modules"] (exclude {rootDir}/node_modules). If omitted, includes all files matching other criteria. Supports standard glob syntax: * (any chars), ** (any dirs), ? (single char), [abc] (char class)'
1279
1279
  ),
1280
- matchFiles: p.boolean().optional().describe(
1281
- "Include matched files in the snapshot with all parent directories"
1280
+ types: h.array(h.enum(["file", "dir"])).optional().describe(
1281
+ "Types of items to include in the snapshot. If omitted, includes both files and directories"
1282
1282
  ),
1283
- matchDirs: p.boolean().optional().describe(
1284
- "Include matched directories in the snapshot with all parent directories"
1285
- ),
1286
- extraFields: p.array(p.enum(["lastModified", "size", "countMatched"])).optional().describe(
1283
+ extraFields: h.array(h.enum(["lastModified", "size", "countMatched"])).optional().describe(
1287
1284
  'Which extra data fields to include in the snapshot tree output. "lastModified" shows last modification time as time-ago format (5m, 2h, 3d, etc). "size" shows file/directory size in human-readable format (KB, MB, GB). "countMatched" shows total matched items count'
1288
1285
  ),
1289
- minTimeAgo: p.string().optional().describe(
1286
+ minTimeAgo: h.string().optional().describe(
1290
1287
  'Filter files/directories modified at least this long ago. Only items older than this duration will be included. Format: number + unit (s/m/h/d/w/M/Y). Examples: "1h" (modified more than 1 hour ago), "7d" (modified more than 7 days ago), "6M" (modified more than 6 months ago)'
1291
1288
  ),
1292
- maxTimeAgo: p.string().optional().describe(
1289
+ maxTimeAgo: h.string().optional().describe(
1293
1290
  'Filter files/directories modified at most this long ago. Only items newer than this duration will be included. Format: number + unit (s/m/h/d/w/M/Y). Examples: "1h" (modified within last hour), "7d" (modified within last 7 days), "1M" (modified within last month). Combine with minTimeAgo for date ranges'
1294
1291
  ),
1295
- minTotalSize: p.string().optional().describe(
1292
+ minTotalSize: h.string().optional().describe(
1296
1293
  'Filter files/directories with total size at least this large. Only items with size >= this value will be included. For directories, uses total size of all contents. Format: number + unit (B/KB/MB/GB/TB). Examples: "1KB" (at least 1 kilobyte), "100MB" (at least 100 megabytes), "1.5GB" (at least 1.5 gigabytes)'
1297
1294
  ),
1298
- maxTotalSize: p.string().optional().describe(
1295
+ maxTotalSize: h.string().optional().describe(
1299
1296
  'Filter files/directories with total size at most this large. Only items with size <= this value will be included. For directories, uses total size of all contents. Format: number + unit (B/KB/MB/GB/TB). Examples: "1MB" (up to 1 megabyte), "500KB" (up to 500 kilobytes), "10GB" (up to 10 gigabytes). Combine with minTotalSize for size ranges'
1300
1297
  )
1301
1298
  }), be = new Map(
@@ -1323,71 +1320,70 @@ async function Pe(t, r, s) {
1323
1320
  const {
1324
1321
  name: e,
1325
1322
  globs: n,
1326
- matchFiles: a,
1327
- matchDirs: i,
1328
- minTimeAgo: u,
1329
- maxTimeAgo: l,
1323
+ types: a,
1324
+ minTimeAgo: i,
1325
+ maxTimeAgo: u,
1330
1326
  minTotalSize: c,
1331
- maxTotalSize: f
1327
+ maxTotalSize: l
1332
1328
  } = o;
1333
1329
  if (!s.sessionId)
1334
1330
  return {
1335
1331
  error: "Session ID is required"
1336
1332
  };
1337
- const d = V(s.sessionId);
1338
- if (d.fsSnapshotQueries.has(e))
1333
+ const f = V(s.sessionId);
1334
+ if (f.fsSnapshotQueries.has(e))
1339
1335
  return {
1340
1336
  error: `Filesystem snapshot query "${e}" already exists`
1341
1337
  };
1342
- const h = T.resolve(r.workingDir || "", o.rootDir || "").replace(/\\/g, "/");
1338
+ const d = T.resolve(r.workingDir || "", o.rootDir || "").replace(/\\/g, "/");
1343
1339
  try {
1344
1340
  try {
1345
- await B.promises.access(h, B.constants.F_OK);
1346
- } catch (w) {
1347
- if (w.code === "ENOENT")
1341
+ await B.promises.access(d, B.constants.F_OK);
1342
+ } catch (x) {
1343
+ if (x.code === "ENOENT")
1348
1344
  return {
1349
- error: `Directory does not exist: "${h}". Verify the path is correct and accessible. If using rootDir parameter, ensure it exists relative to the current working directory. Use fs-snapshot-query-create without rootDir to snapshot the current directory, or check parent directories first.`
1345
+ error: `Directory does not exist: "${d}". Verify the path is correct and accessible. If using rootDir parameter, ensure it exists relative to the current working directory. Use fs-snapshot-query-create without rootDir to snapshot the current directory, or check parent directories first.`
1350
1346
  };
1351
- throw w;
1347
+ throw x;
1352
1348
  }
1353
- const m = o.extraFields ? o.extraFields.map((w) => w === "lastModified" ? "dateModified" : w) : [];
1349
+ const m = o.extraFields ? o.extraFields.map((x) => x === "lastModified" ? "dateModified" : x) : [];
1354
1350
  m.includes("name") || m.push("name"), m.sort(tr);
1355
- const g = n && n.length > 0 ? n.map((w) => ({
1356
- value: w,
1351
+ const g = n && n.length > 0 ? n.map((x) => ({
1352
+ value: x,
1357
1353
  valueType: "pattern",
1358
1354
  exclude: !1
1359
- })) : [{ value: "**", valueType: "pattern", exclude: !1 }], b = r.globsExclude || [], y = [...g, ...b];
1360
- let x = null, I = null;
1361
- if (u || l)
1355
+ })) : [{ value: "**", valueType: "pattern", exclude: !1 }], p = r.globsExclude || [], y = [...g, ...p];
1356
+ let w = null, S = null;
1357
+ if (i || u)
1362
1358
  try {
1363
- const w = Date.now(), M = l ? w - we(l) : null, $ = u ? w - we(u) : null;
1364
- x = [M, $];
1365
- } catch (w) {
1359
+ const x = Date.now(), $ = u ? x - we(u) : null, v = i ? x - we(i) : null;
1360
+ w = [$, v];
1361
+ } catch (x) {
1366
1362
  return {
1367
- error: w instanceof Error ? w.message : "Unknown error parsing time ago filter"
1363
+ error: x instanceof Error ? x.message : "Unknown error parsing time ago filter"
1368
1364
  };
1369
1365
  }
1370
- if (c || f)
1366
+ if (c || l)
1371
1367
  try {
1372
- const w = c ? ye(c) : null, M = f ? ye(f) : null;
1373
- I = [w, M];
1374
- } catch (w) {
1368
+ const x = c ? ye(c) : null, $ = l ? ye(l) : null;
1369
+ S = [x, $];
1370
+ } catch (x) {
1375
1371
  return {
1376
- error: w instanceof Error ? w.message : "Unknown error parsing size filter"
1372
+ error: x instanceof Error ? x.message : "Unknown error parsing size filter"
1377
1373
  };
1378
1374
  }
1379
- const S = {
1375
+ const M = a ? a.includes("file") : !0, I = a ? a.includes("dir") : !0, b = {
1380
1376
  name: e,
1381
- rootDir: h,
1377
+ rootDir: d,
1382
1378
  globs: y,
1383
- matchFiles: a ?? null,
1384
- matchDirs: i ?? null,
1385
- dateModified: x,
1386
- totalSize: I,
1379
+ matchFiles: M,
1380
+ matchDirs: I,
1381
+ dateModified: w,
1382
+ totalSize: S,
1387
1383
  fields: m
1388
1384
  };
1389
- return d.fsSnapshotQueries.set(e, S), {
1390
- snapshotQuery: S
1385
+ return f.fsSnapshotQueries.set(e, b), {
1386
+ snapshotQuery: b
1391
1387
  };
1392
1388
  } catch (m) {
1393
1389
  return {
@@ -1441,12 +1437,12 @@ function j(t) {
1441
1437
  throw new Error("Impossible behavior: node not found in idToNode");
1442
1438
  const i = s.get(a);
1443
1439
  return i == null ? null : i.map((u) => {
1444
- const l = r.get(u);
1445
- if (l == null)
1440
+ const c = r.get(u);
1441
+ if (c == null)
1446
1442
  throw new Error(
1447
1443
  `Child node with id '${u}' not found in idToNode`
1448
1444
  );
1449
- return l;
1445
+ return c;
1450
1446
  });
1451
1447
  }
1452
1448
  };
@@ -1454,8 +1450,8 @@ function j(t) {
1454
1450
  function ze(t, r, s) {
1455
1451
  let o = null;
1456
1452
  for (let e = 0, n = r.length; e < n; e++) {
1457
- const a = r[e], i = t(a), u = i == null ? null : ze(t, i, s), l = s(a, u);
1458
- l != null && (o == null && (o = []), o.push(l));
1453
+ const a = r[e], i = t(a), u = i == null ? null : ze(t, i, s), c = s(a, u);
1454
+ c != null && (o == null && (o = []), o.push(c));
1459
1455
  }
1460
1456
  return o;
1461
1457
  }
@@ -1463,23 +1459,23 @@ function Le(t) {
1463
1459
  const { getId: r, getChilds: s, rootNodes: o, createSnapshotNode: e } = t, n = /* @__PURE__ */ new Map(), a = /* @__PURE__ */ new Map(), i = /* @__PURE__ */ new Map(), u = ze(
1464
1460
  s,
1465
1461
  o,
1466
- (c, f) => {
1467
- const d = e(c, f);
1468
- if (c != null && d != null) {
1469
- const h = r(c);
1470
- n.set(h, d), a.set(d, h);
1462
+ (l, f) => {
1463
+ const d = e(l, f);
1464
+ if (l != null && d != null) {
1465
+ const m = r(l);
1466
+ n.set(m, d), a.set(d, m);
1471
1467
  }
1472
1468
  return d != null && f != null && i.set(
1473
1469
  a.get(d),
1474
- f.map((h) => a.get(h))
1470
+ f.map((m) => a.get(m))
1475
1471
  ), d;
1476
1472
  }
1477
- ), l = e(null, u);
1478
- if (l == null)
1473
+ ), c = e(null, u);
1474
+ if (c == null)
1479
1475
  throw new Error("Impossible behavior: rootNode == null");
1480
- return n.set(null, l), u != null && i.set(
1476
+ return n.set(null, c), u != null && i.set(
1481
1477
  null,
1482
- u.map((c) => a.get(c))
1478
+ u.map((l) => a.get(l))
1483
1479
  ), {
1484
1480
  idToNode: n,
1485
1481
  idToChildIds: i
@@ -1510,38 +1506,38 @@ async function sr(t) {
1510
1506
  rootDir: o,
1511
1507
  noCase: !0
1512
1508
  }),
1513
- handlePath: async ({ path: i, stat: u, itemStat: l }) => {
1514
- const c = T.relative(o, i), f = u.isDirectory(), d = u.isFile();
1509
+ handlePath: async ({ path: i, stat: u, itemStat: c }) => {
1510
+ const l = T.relative(o, i), f = u.isDirectory(), d = u.isFile();
1515
1511
  if (!f && !d)
1516
1512
  return !0;
1517
- const h = W(c || "."), m = f ? "dir" : "file", g = f ? null : u.mtimeMs, b = u.size;
1518
- let y = !0;
1519
- if (d && !t.matchFiles && (y = !1), f && !t.matchDirs && (y = !1), y && d && t.dateModified && g != null) {
1520
- const [w, M] = t.dateModified;
1521
- (w != null && g < w || M != null && g > M) && (y = !1);
1513
+ const m = W(l || "."), g = f ? "dir" : "file", p = f ? null : u.mtimeMs, y = u.size;
1514
+ let w = !0;
1515
+ if (d && !t.matchFiles && (w = !1), f && !t.matchDirs && (w = !1), w && d && t.dateModified && p != null) {
1516
+ const [b, x] = t.dateModified;
1517
+ (b != null && p < b || x != null && p > x) && (w = !1);
1522
1518
  }
1523
- if (y && d && t.totalSize && b != null) {
1524
- const [w, M] = t.totalSize;
1525
- (w != null && b < w || M != null && b > M) && (y = !1);
1519
+ if (w && d && t.totalSize && y != null) {
1520
+ const [b, x] = t.totalSize;
1521
+ (b != null && y < b || x != null && y > x) && (w = !1);
1526
1522
  }
1527
- if (f && !y) {
1528
- if (!(l.countFiles && l.countFiles > 0)) return !1;
1529
- } else if (!y)
1523
+ if (f && !w) {
1524
+ if (!(c.countFiles && c.countFiles > 0)) return !1;
1525
+ } else if (!w)
1530
1526
  return !1;
1531
- const x = {
1532
- path: h ?? ".",
1527
+ const S = {
1528
+ path: m ?? ".",
1533
1529
  name: T.basename(i),
1534
- type: m,
1535
- dateModified: g,
1536
- size: b,
1537
- isMatched: y
1530
+ type: g,
1531
+ dateModified: p,
1532
+ size: y,
1533
+ isMatched: w
1538
1534
  };
1539
- if (h == null)
1540
- return n.dateModified = g, n.size = b, n.isMatched = y, !0;
1541
- r.set(h, x);
1542
- const I = W(T.dirname(h).replace(/\\/g, "/"));
1543
- let S = s.get(I);
1544
- return S || (S = [], s.set(I, S)), S.push(h), !0;
1535
+ if (m == null)
1536
+ return n.dateModified = p, n.size = y, n.isMatched = w, !0;
1537
+ r.set(m, S);
1538
+ const M = W(T.dirname(m).replace(/\\/g, "/"));
1539
+ let I = s.get(M);
1540
+ return I || (I = [], s.set(M, I)), I.push(m), !0;
1545
1541
  }
1546
1542
  }), {
1547
1543
  idToNode: r,
@@ -1571,7 +1567,7 @@ const or = [
1571
1567
  // max: 2,
1572
1568
  // },
1573
1569
  ];
1574
- function xe(t, r = or) {
1570
+ function Se(t, r = or) {
1575
1571
  const s = t.length;
1576
1572
  if (s === 0) return 0;
1577
1573
  const o = r.length;
@@ -1582,12 +1578,12 @@ function xe(t, r = or) {
1582
1578
  const a = t.charCodeAt(n);
1583
1579
  let i = !1;
1584
1580
  for (let u = 0; u < o; u++) {
1585
- const l = r[u];
1586
- if (l.match(a)) {
1587
- let c = 1;
1588
- for (; ++n < s && l.match(t.charCodeAt(n)) && c < l.max; )
1589
- c++;
1590
- if (c >= l.min) {
1581
+ const c = r[u];
1582
+ if (c.match(a)) {
1583
+ let l = 1;
1584
+ for (; ++n < s && c.match(t.charCodeAt(n)) && l < c.max; )
1585
+ l++;
1586
+ if (l >= c.min) {
1591
1587
  e++, i = !0;
1592
1588
  break;
1593
1589
  }
@@ -1599,21 +1595,21 @@ function xe(t, r = or) {
1599
1595
  }
1600
1596
  function Ue(t) {
1601
1597
  let r = 0;
1602
- return r += xe(t.textOpen) + 1, t.textClose != null && (r += xe(t.textClose) + 1), t.indent && (r += 1), r;
1598
+ return r += Se(t.textOpen) + 1, t.textClose != null && (r += Se(t.textClose) + 1), t.indent && (r += 1), r;
1603
1599
  }
1604
- const Se = ["B", "KB", "MB", "GB", "TB"], $e = 1024;
1600
+ const xe = ["B", "KB", "MB", "GB", "TB"], $e = 1024;
1605
1601
  function nr(t) {
1606
1602
  if (t == null) return "-";
1607
1603
  let r = t ?? 0, s = 0;
1608
- for (; r >= $e && s < Se.length - 1; )
1604
+ for (; r >= $e && s < xe.length - 1; )
1609
1605
  r /= $e, s++;
1610
- return `${s === 0 ? r.toString() : r.toFixed(2)}${Se[s]}`;
1606
+ return `${s === 0 ? r.toString() : r.toFixed(2)}${xe[s]}`;
1611
1607
  }
1612
1608
  function ir(t) {
1613
1609
  const s = Date.now() - t;
1614
1610
  if (s < 0) return "0s";
1615
- const o = Math.floor(s / 1e3), e = Math.floor(o / 60), n = Math.floor(e / 60), a = Math.floor(n / 24), i = Math.floor(a / 7), u = Math.floor(a / 30), l = Math.floor(a / 365);
1616
- return l > 0 ? `${l}Y` : u > 0 ? `${u}M` : i > 0 ? `${i}w` : a > 0 ? `${a}d` : n > 0 ? `${n}h` : e > 0 ? `${e}m` : `${o}s`;
1611
+ const o = Math.floor(s / 1e3), e = Math.floor(o / 60), n = Math.floor(e / 60), a = Math.floor(n / 24), i = Math.floor(a / 7), u = Math.floor(a / 30), c = Math.floor(a / 365);
1612
+ return c > 0 ? `${c}Y` : u > 0 ? `${u}M` : i > 0 ? `${i}w` : a > 0 ? `${a}d` : n > 0 ? `${n}h` : e > 0 ? `${e}m` : `${o}s`;
1617
1613
  }
1618
1614
  function ar(t) {
1619
1615
  return function(s, o) {
@@ -1628,62 +1624,62 @@ function ar(t) {
1628
1624
  }
1629
1625
  };
1630
1626
  }
1631
- function lr(t) {
1627
+ function cr(t) {
1632
1628
  const r = t.fields ?? [];
1633
1629
  return function(o, e) {
1634
1630
  let n = "", a, i = 0;
1635
1631
  const u = e ? e.length : 0;
1636
- let l = 1, c, f = 0, d = 0, h = 0, m = 0, g = null, b, y, x;
1632
+ let c = 1, l, f = 0, d = 0, m = 0, g = 0, p = null, y, w, S;
1637
1633
  if (e)
1638
- for (let S = 0; S < e.length; S++) {
1639
- const w = e[S];
1640
- i += w.countMatched, l += w.countTotal, f += w.tokens, d += w.tokensTotal, h += w.size, m += w.countFiles, w.dateModified != null && (g == null || w.dateModified > g) && (g = w.dateModified);
1634
+ for (let I = 0; I < e.length; I++) {
1635
+ const b = e[I];
1636
+ i += b.countMatched, c += b.countTotal, f += b.tokens, d += b.tokensTotal, m += b.size, g += b.countFiles, b.dateModified != null && (p == null || b.dateModified > p) && (p = b.dateModified);
1641
1637
  }
1642
- o ? (b = o.type, y = o.name, x = o.path, a = o.isMatched, a && (i += 1), o.type === "file" ? (h = o.size || 0, m = 1, g = o.dateModified || null) : o.dateModified != null && (g == null || o.dateModified > g) && (g = o.dateModified)) : (b = "dir", y = "<root>", x = ".", a = !0);
1643
- for (let S = 0, w = r.length; S < w; S++) {
1644
- const M = r[S];
1645
- switch (S > 0 && (n += " "), M) {
1638
+ o ? (y = o.type, w = o.name, S = o.path, a = o.isMatched, a && (i += 1), o.type === "file" ? (m = o.size || 0, g = 1, p = o.dateModified || null) : o.dateModified != null && (p == null || o.dateModified > p) && (p = o.dateModified)) : (y = "dir", w = "<root>", S = ".", a = !0);
1639
+ for (let I = 0, b = r.length; I < b; I++) {
1640
+ const x = r[I];
1641
+ switch (I > 0 && (n += " "), x) {
1646
1642
  case "dateModified":
1647
- n += g ? ir(g) : "-";
1643
+ n += p ? ir(p) : "-";
1648
1644
  break;
1649
1645
  case "size":
1650
- n += nr(h);
1646
+ n += nr(m);
1651
1647
  break;
1652
1648
  case "type":
1653
- n += b;
1649
+ n += y;
1654
1650
  break;
1655
1651
  case "name":
1656
- n += b === "dir" ? `${y}/` : y;
1652
+ n += y === "dir" ? `${w}/` : w;
1657
1653
  break;
1658
1654
  case "countMatched":
1659
1655
  n += i.toString();
1660
1656
  break;
1661
1657
  }
1662
1658
  }
1663
- const I = {
1659
+ const M = {
1664
1660
  indent: !0,
1665
1661
  textOpen: n,
1666
1662
  textClose: null
1667
1663
  };
1668
- return c = Ue(I), d += c, {
1669
- type: b,
1670
- name: y,
1671
- path: x,
1664
+ return l = Ue(M), d += l, {
1665
+ type: y,
1666
+ name: w,
1667
+ path: S,
1672
1668
  isMatched: a,
1673
1669
  countMatched: i,
1674
1670
  countChilds: u,
1675
- countTotal: l,
1676
- tokens: c,
1671
+ countTotal: c,
1672
+ tokens: l,
1677
1673
  tokensChilds: f,
1678
1674
  tokensTotal: d,
1679
- text: I,
1680
- size: h,
1681
- countFiles: m,
1682
- dateModified: g
1675
+ text: M,
1676
+ size: m,
1677
+ countFiles: g,
1678
+ dateModified: p
1683
1679
  };
1684
1680
  };
1685
1681
  }
1686
- async function cr(t) {
1682
+ async function lr(t) {
1687
1683
  const r = await sr(t), s = j(r), o = s.getChilds(s.root), e = Le({
1688
1684
  getId: (a) => {
1689
1685
  const i = s.getId(a);
@@ -1694,19 +1690,19 @@ async function cr(t) {
1694
1690
  return i;
1695
1691
  },
1696
1692
  getChilds: (a) => s.getChilds(a),
1697
- createSnapshotNode: lr(t),
1693
+ createSnapshotNode: cr(t),
1698
1694
  rootNodes: o ?? []
1699
1695
  }), n = ar(e.idToNode);
1700
1696
  return e.idToChildIds.forEach((a) => {
1701
1697
  a.sort(n);
1702
1698
  }), j(e);
1703
1699
  }
1704
- const X = p.object({
1705
- queryName: p.string().optional().describe("Name of previously created filesystem snapshot query, to use"),
1700
+ const X = h.object({
1701
+ queryName: h.string().optional().describe("Name of previously created filesystem snapshot query, to use"),
1706
1702
  query: Z.optional().describe(
1707
1703
  "Filesystem snapshot query creation options JSON to automatically create query"
1708
1704
  ),
1709
- name: p.string().describe(
1705
+ name: h.string().describe(
1710
1706
  "Unique name for the filesystem snapshot. Recommended format: kebab-case-1, kebab-case-2, ..."
1711
1707
  )
1712
1708
  });
@@ -1714,9 +1710,9 @@ async function Ae(t, r, s) {
1714
1710
  let o;
1715
1711
  try {
1716
1712
  o = X.parse(t);
1717
- } catch (c) {
1713
+ } catch (l) {
1718
1714
  return {
1719
- error: C(c)
1715
+ error: C(l)
1720
1716
  };
1721
1717
  }
1722
1718
  const { name: e, queryName: n, query: a } = o;
@@ -1733,42 +1729,42 @@ async function Ae(t, r, s) {
1733
1729
  return {
1734
1730
  error: "Either queryName or query must be provided, not both"
1735
1731
  };
1736
- let u, l = !1;
1732
+ let u, c = !1;
1737
1733
  if (n) {
1738
- const c = i.fsSnapshotQueries.get(n);
1739
- if (!c)
1734
+ const l = i.fsSnapshotQueries.get(n);
1735
+ if (!l)
1740
1736
  return {
1741
1737
  error: `Filesystem snapshot query "${n}" not found`
1742
1738
  };
1743
- u = c;
1739
+ u = l;
1744
1740
  } else if (a) {
1745
- const c = await Pe(
1741
+ const l = await Pe(
1746
1742
  a,
1747
1743
  r,
1748
1744
  s
1749
1745
  );
1750
- if (c.error != null)
1746
+ if (l.error != null)
1751
1747
  return {
1752
- error: c.error
1748
+ error: l.error
1753
1749
  };
1754
- u = c.snapshotQuery, l = !0;
1750
+ u = l.snapshotQuery, c = !0;
1755
1751
  } else
1756
1752
  return {
1757
1753
  error: "Either queryName or query must be provided"
1758
1754
  };
1759
1755
  try {
1760
- const c = await cr(u), f = {
1756
+ const l = await lr(u), f = {
1761
1757
  name: e,
1762
1758
  query: u,
1763
- tree: c
1759
+ tree: l
1764
1760
  };
1765
1761
  return i.fsSnapshots.set(e, f), {
1766
1762
  fsSnapshot: f,
1767
- queryCreated: l
1763
+ queryCreated: c
1768
1764
  };
1769
- } catch (c) {
1765
+ } catch (l) {
1770
1766
  return {
1771
- error: `Failed to create filesystem snapshot: ${c instanceof Error ? c.message : "Unknown error"}`
1767
+ error: `Failed to create filesystem snapshot: ${l instanceof Error ? l.message : "Unknown error"}`
1772
1768
  };
1773
1769
  }
1774
1770
  }
@@ -1825,64 +1821,64 @@ function fr(t) {
1825
1821
  reportNode: null,
1826
1822
  node: s.root
1827
1823
  });
1828
- let l = null, c = 0, f = 0;
1824
+ let c = null, l = 0, f = 0;
1829
1825
  for (; !r.isEmpty(); ) {
1830
- const { reportNode: d, node: h } = r.dequeue(), m = s.getChilds(h);
1831
- if (m == null || h.countChilds === 0 || m.length !== h.countChilds)
1826
+ const { reportNode: d, node: m } = r.dequeue(), g = s.getChilds(m);
1827
+ if (g == null || m.countChilds === 0 || g.length !== m.countChilds)
1832
1828
  throw new Error(
1833
1829
  "Impossible behavior: nodeChilds is null or length mismatch"
1834
1830
  );
1835
- let g = r.size();
1836
- for (let y = 0; y < m.length; y++)
1837
- m[y].countChilds > 0 && (g += 1);
1838
- const b = g * i.tokens;
1839
- if (o != null && c + h.countChilds + g > o || e != null && f + h.tokensChilds + b > e) {
1840
- const y = [];
1841
- let x = null, I = 0;
1842
- for (let w = 0, M = m.length; w < M; w++) {
1843
- const $ = m[w], v = I * i.tokens;
1844
- x != null && // Если общий лимит превышен, то не создаем новую группу, а продолжаем текущую. В случае достижения лимитов, последняя группа может содержать больше элементов, чем указано в лимитах группы, и это допустимо. Главное - дать в отчете полную картину.
1845
- !(o != null && c + 1 > o || e != null && f + i.tokens > e) && (n != null && x.countGrouped + 1 + I > n || a != null && x.tokensGrouped + $.tokens + v > a) && (y.push(x), c += 1, f += i.tokens, x = null, I = 0), x = i.add(x, $, w), $.countChilds > 0 && (I += 1);
1831
+ let p = r.size();
1832
+ for (let w = 0; w < g.length; w++)
1833
+ g[w].countChilds > 0 && (p += 1);
1834
+ const y = p * i.tokens;
1835
+ if (o != null && l + m.countChilds + p > o || e != null && f + m.tokensChilds + y > e) {
1836
+ const w = [];
1837
+ let S = null, M = 0;
1838
+ for (let b = 0, x = g.length; b < x; b++) {
1839
+ const $ = g[b], v = M * i.tokens;
1840
+ S != null && // Если общий лимит превышен, то не создаем новую группу, а продолжаем текущую. В случае достижения лимитов, последняя группа может содержать больше элементов, чем указано в лимитах группы, и это допустимо. Главное - дать в отчете полную картину.
1841
+ !(o != null && l + 1 > o || e != null && f + i.tokens > e) && (n != null && S.countGrouped + 1 + M > n || a != null && S.tokensGrouped + $.tokens + v > a) && (w.push(S), l += 1, f += i.tokens, S = null, M = 0), S = i.add(S, $, b), $.countChilds > 0 && (M += 1);
1846
1842
  }
1847
- x != null && (y.push(x), c += 1, f += i.tokens);
1848
- const S = y.map((w) => ({
1849
- text: i.getReportText(w)
1843
+ S != null && (w.push(S), l += 1, f += i.tokens);
1844
+ const I = w.map((b) => ({
1845
+ text: i.getReportText(b)
1850
1846
  }));
1851
1847
  if (d != null) {
1852
1848
  if (d.childs != null)
1853
1849
  throw new Error("Impossible behavior: reportNode.childs != null");
1854
- d.childs = S;
1850
+ d.childs = I;
1855
1851
  } else {
1856
- if (l != null)
1852
+ if (c != null)
1857
1853
  throw new Error("Impossible behavior: reportRootNodes != null");
1858
- l = S;
1854
+ c = I;
1859
1855
  }
1860
1856
  } else {
1861
- c += h.countChilds, f += h.tokensChilds;
1862
- const y = [];
1863
- for (let x = 0; x < m.length; x++) {
1864
- const I = m[x], S = {
1865
- text: I.text
1857
+ l += m.countChilds, f += m.tokensChilds;
1858
+ const w = [];
1859
+ for (let S = 0; S < g.length; S++) {
1860
+ const M = g[S], I = {
1861
+ text: M.text
1866
1862
  };
1867
- y.push(S);
1868
- const w = s.getChilds(I);
1869
- w != null && w.length > 0 && r.enqueue({
1870
- reportNode: S,
1871
- node: I
1863
+ w.push(I);
1864
+ const b = s.getChilds(M);
1865
+ b != null && b.length > 0 && r.enqueue({
1866
+ reportNode: I,
1867
+ node: M
1872
1868
  });
1873
1869
  }
1874
1870
  if (d != null) {
1875
1871
  if (d.childs != null)
1876
1872
  throw new Error("Impossible behavior: reportNode.childs != null");
1877
- d.childs = y;
1873
+ d.childs = w;
1878
1874
  } else {
1879
- if (l != null)
1875
+ if (c != null)
1880
1876
  throw new Error("Impossible behavior: reportRootNodes != null");
1881
- l = y;
1877
+ c = w;
1882
1878
  }
1883
1879
  }
1884
1880
  }
1885
- return l ?? [];
1881
+ return c ?? [];
1886
1882
  }
1887
1883
  function qe(t) {
1888
1884
  const {
@@ -1899,34 +1895,34 @@ function qe(t) {
1899
1895
  i = d;
1900
1896
  } else
1901
1897
  i = r.root;
1902
- let u, l = r.getChilds(i) ?? [];
1898
+ let u, c = r.getChilds(i) ?? [];
1903
1899
  if (o != null) {
1904
- const [d, h] = o;
1905
- if (d < 0 || h <= d || h >= l.length)
1900
+ const [d, m] = o;
1901
+ if (d < 0 || m <= d || m >= c.length)
1906
1902
  throw new Error(
1907
- `Invalid index range: ${d}-${h} for root nodes length ${l.length}`
1903
+ `Invalid index range: ${d}-${m} for root nodes length ${c.length}`
1908
1904
  );
1909
- const m = [];
1910
- let g = null;
1911
- for (let b = d; b <= h; b++) {
1912
- const y = l[b];
1913
- m.push(y), g = n.add(g, y, b);
1905
+ const g = [];
1906
+ let p = null;
1907
+ for (let y = d; y <= m; y++) {
1908
+ const w = c[y];
1909
+ g.push(w), p = n.add(p, w, y);
1914
1910
  }
1915
- l = m, u = {
1911
+ c = g, u = {
1916
1912
  ...i,
1917
- text: n.getReportText(g),
1918
- countChilds: g.countGrouped,
1919
- tokensChilds: g.tokensGrouped
1913
+ text: n.getReportText(p),
1914
+ countChilds: p.countGrouped,
1915
+ tokensChilds: p.tokensGrouped
1920
1916
  };
1921
1917
  } else
1922
1918
  u = i;
1923
- const c = {
1919
+ const l = {
1924
1920
  countChilds: 1,
1925
1921
  tokensChilds: u.tokens
1926
1922
  }, f = {
1927
1923
  ...r,
1928
- root: c,
1929
- getChilds: (d) => d === c ? [u] : d === u ? l : r.getChilds(d)
1924
+ root: l,
1925
+ getChilds: (d) => d === l ? [u] : d === u ? c : r.getChilds(d)
1930
1926
  };
1931
1927
  return fr({
1932
1928
  tree: f,
@@ -1952,7 +1948,7 @@ function Ge(t, r) {
1952
1948
  }
1953
1949
  return o(t, ""), s;
1954
1950
  }
1955
- class hr {
1951
+ class mr {
1956
1952
  tokens = 16;
1957
1953
  // +1 indent, +1 for line break
1958
1954
  getReportText = (r) => ({
@@ -1967,15 +1963,15 @@ class hr {
1967
1963
  tokensGrouped: s.tokens
1968
1964
  } : (r.indexRange[1] = o, r.countGrouped += 1, r.countMatched += s.countMatched, r.tokensGrouped += s.tokens, r);
1969
1965
  }
1970
- const je = p.object({
1971
- snapshotName: p.string().optional().describe("Name of previously created filesystem snapshot, to use"),
1966
+ const je = h.object({
1967
+ snapshotName: h.string().optional().describe("Name of previously created filesystem snapshot, to use"),
1972
1968
  snapshot: X.optional().describe(
1973
1969
  "Filesystem snapshot creation options JSON to automatically create snapshot"
1974
1970
  ),
1975
- parentPath: p.string().optional().describe(
1971
+ parentPath: h.string().optional().describe(
1976
1972
  "Path relative to snapshot rootDir to browse. Omit to browse the rootDir itself"
1977
1973
  ),
1978
- childsIndexRange: p.tuple([p.number(), p.number()]).optional().describe(
1974
+ childsIndexRange: h.tuple([h.number(), h.number()]).optional().describe(
1979
1975
  "Child index range to show [start, end]. Only use the exact ranges that appeared in previous snapshot results - do not modify, combine, or split them"
1980
1976
  )
1981
1977
  // maxCountTotal: z
@@ -1989,13 +1985,13 @@ const je = p.object({
1989
1985
  // maxCountGroup: z.number().default(10).describe('Maximum items per group'),
1990
1986
  // maxTokensGroup: z.number().default(1000).describe('Maximum tokens per group'),
1991
1987
  });
1992
- async function mr(t, r, s) {
1988
+ async function hr(t, r, s) {
1993
1989
  let o;
1994
1990
  try {
1995
1991
  o = je.parse(t);
1996
- } catch (g) {
1992
+ } catch (p) {
1997
1993
  return {
1998
- error: C(g)
1994
+ error: C(p)
1999
1995
  };
2000
1996
  }
2001
1997
  const {
@@ -2006,13 +2002,13 @@ async function mr(t, r, s) {
2006
2002
  // maxTokensTotal,
2007
2003
  // maxCountGroup,
2008
2004
  // maxTokensGroup,
2009
- } = o, i = 60, u = 1e3, l = 25, c = 900;
2005
+ } = o, i = 60, u = 1e3, c = 25, l = 900;
2010
2006
  if (!s.sessionId)
2011
2007
  return {
2012
2008
  error: "Session ID is required"
2013
2009
  };
2014
2010
  const f = V(s.sessionId);
2015
- let d, h = !1, m = !1;
2011
+ let d, m = !1, g = !1;
2016
2012
  if (e && n)
2017
2013
  return {
2018
2014
  error: "Either snapshotName or snapshot must be provided, not both"
@@ -2023,46 +2019,46 @@ async function mr(t, r, s) {
2023
2019
  error: `Filesystem snapshot "${e}" not found`
2024
2020
  };
2025
2021
  } else if (n) {
2026
- const g = await Ae(
2022
+ const p = await Ae(
2027
2023
  n,
2028
2024
  r,
2029
2025
  s
2030
2026
  );
2031
- if (g.error != null)
2027
+ if (p.error != null)
2032
2028
  return {
2033
- error: g.error
2029
+ error: p.error
2034
2030
  };
2035
- d = g.fsSnapshot, h = g.queryCreated, m = !0;
2031
+ d = p.fsSnapshot, m = p.queryCreated, g = !0;
2036
2032
  } else
2037
2033
  return {
2038
2034
  error: "Either snapshotName or snapshot must be provided"
2039
2035
  };
2040
2036
  try {
2041
- const g = W(o.parentPath), b = qe({
2037
+ const p = W(o.parentPath), y = qe({
2042
2038
  tree: d.tree,
2043
2039
  request: {
2044
- parentNodeId: g,
2040
+ parentNodeId: p,
2045
2041
  childsIndexRange: a,
2046
2042
  limits: {
2047
2043
  maxCountTotal: i,
2048
2044
  maxTokensTotal: u,
2049
- maxCountGroup: l,
2050
- maxTokensGroup: c
2045
+ maxCountGroup: c,
2046
+ maxTokensGroup: l
2051
2047
  }
2052
2048
  },
2053
- indexRangeGroupStrategy: new hr()
2054
- }), y = Ge(b);
2049
+ indexRangeGroupStrategy: new mr()
2050
+ }), w = Ge(y);
2055
2051
  return {
2056
2052
  fsSnapshot: d,
2057
- queryCreated: h,
2058
- snapshotCreated: m,
2059
- parentPath: g,
2053
+ queryCreated: m,
2054
+ snapshotCreated: g,
2055
+ parentPath: p,
2060
2056
  childsIndexRange: a,
2061
- report: y
2057
+ report: w
2062
2058
  };
2063
- } catch (g) {
2059
+ } catch (p) {
2064
2060
  return {
2065
- error: `Failed to browse filesystem snapshot: ${g instanceof Error ? g.message : "Unknown error"}`
2061
+ error: `Failed to browse filesystem snapshot: ${p instanceof Error ? p.message : "Unknown error"}`
2066
2062
  };
2067
2063
  }
2068
2064
  }
@@ -2075,7 +2071,7 @@ function pr(t, r) {
2075
2071
  inputSchema: je.shape
2076
2072
  },
2077
2073
  async (s, o) => {
2078
- const e = await mr(s, r, o);
2074
+ const e = await hr(s, r, o);
2079
2075
  if (e.error != null)
2080
2076
  return `Method: fs-snapshot-browse(${JSON.stringify(s)})
2081
2077
  ❌ Error: ${e.error}`;
@@ -2084,12 +2080,12 @@ function pr(t, r) {
2084
2080
  if (e.queryCreated && (n += `✅ Filesystem snapshot query "${e.fsSnapshot.query.name}" created successfully
2085
2081
  `), e.snapshotCreated && (n += `✅ Filesystem snapshot "${e.fsSnapshot.name}" created successfully
2086
2082
  `), n += `✅ Browsing filesystem snapshot "${e.fsSnapshot.name}":
2087
- `, n += `Root directory: ${e.fsSnapshot.query.rootDir || "./"}
2083
+ `, n += `Root directory (<root>/): ${e.fsSnapshot.query.rootDir || "./"}
2088
2084
  `, n += `Parent path: ${"./" + (e.parentPath ?? "")}
2089
2085
  `, n += `Fields: ${e.fsSnapshot.query.fields.map((a) => a === "dateModified" ? "lastModified" : a).join(" ")}
2090
2086
  `, e.childsIndexRange) {
2091
- const [a, i] = e.childsIndexRange, l = (e.parentPath ? e.fsSnapshot.tree.getNode(e.parentPath) : e.fsSnapshot.tree.root).countChilds;
2092
- n += ` Showing indexes: ${a}-${i} of ${l}
2087
+ const [a, i] = e.childsIndexRange, c = (e.parentPath ? e.fsSnapshot.tree.getNode(e.parentPath) : e.fsSnapshot.tree.root).countChilds;
2088
+ n += ` Showing indexes: ${a}-${i} of ${c}
2093
2089
  `;
2094
2090
  }
2095
2091
  return n += `
@@ -2105,27 +2101,27 @@ function gr(t, r) {
2105
2101
  );
2106
2102
  }
2107
2103
  const J = /* @__PURE__ */ new Map();
2108
- function E(t) {
2104
+ function D(t) {
2109
2105
  return J.has(t) || J.set(t, {
2110
2106
  browsers: /* @__PURE__ */ new Map(),
2111
2107
  domSnapshotQueries: /* @__PURE__ */ new Map()
2112
2108
  }), J.get(t);
2113
2109
  }
2114
- const ee = p.object({
2115
- name: p.string().describe(
2110
+ const ee = h.object({
2111
+ name: h.string().describe(
2116
2112
  "Unique name for the browser. Recommended format: kebab-case-1, kebab-case-2, ..."
2117
2113
  ),
2118
- browserType: p.enum(["chromium", "firefox", "webkit"]).describe("Browser type to launch"),
2119
- muteAudio: p.boolean().optional().describe("Mute audio in the browser"),
2120
- devTools: p.boolean().optional().describe("Open browser with dev tools")
2114
+ browserType: h.enum(["chromium", "firefox", "webkit"]).describe("Browser type to launch"),
2115
+ muteAudio: h.boolean().optional().describe("Mute audio in the browser"),
2116
+ devTools: h.boolean().optional().describe("Open browser with dev tools")
2121
2117
  });
2122
2118
  async function _e(t, r, s) {
2123
2119
  let o;
2124
2120
  try {
2125
2121
  o = ee.parse(t);
2126
- } catch (c) {
2122
+ } catch (l) {
2127
2123
  return {
2128
- error: C(c)
2124
+ error: C(l)
2129
2125
  };
2130
2126
  }
2131
2127
  const { name: e, browserType: n, muteAudio: a, devTools: i } = o;
@@ -2133,16 +2129,16 @@ async function _e(t, r, s) {
2133
2129
  return {
2134
2130
  error: "Session ID is required"
2135
2131
  };
2136
- const u = E(s.sessionId), l = u.browsers.get(e);
2137
- if (l)
2132
+ const u = D(s.sessionId), c = u.browsers.get(e);
2133
+ if (c)
2138
2134
  return {
2139
- error: `Browser "${l.name}" (${l.browserType}) already exists`
2135
+ error: `Browser "${c.name}" (${c.browserType}) already exists`
2140
2136
  };
2141
2137
  try {
2142
2138
  const f = await {
2143
2139
  chromium: gt,
2144
2140
  firefox: pt,
2145
- webkit: mt
2141
+ webkit: ht
2146
2142
  }[n].launch({
2147
2143
  headless: !1,
2148
2144
  devtools: i,
@@ -2154,9 +2150,9 @@ async function _e(t, r, s) {
2154
2150
  contexts: /* @__PURE__ */ new Map()
2155
2151
  };
2156
2152
  return u.browsers.set(e, d), { browserInfo: d };
2157
- } catch (c) {
2153
+ } catch (l) {
2158
2154
  return {
2159
- error: `Failed to create browser: ${c instanceof Error ? c.message : "Unknown error"}`
2155
+ error: `Failed to create browser: ${l instanceof Error ? l.message : "Unknown error"}`
2160
2156
  };
2161
2157
  }
2162
2158
  }
@@ -2175,7 +2171,7 @@ ${e.error != null ? `❌ Error: ${e.error}` : `✅ Browser "${e.browserInfo.name
2175
2171
  }
2176
2172
  );
2177
2173
  }
2178
- const Je = p.object({});
2174
+ const Je = h.object({});
2179
2175
  async function yr(t, r, s) {
2180
2176
  let o;
2181
2177
  try {
@@ -2189,7 +2185,7 @@ async function yr(t, r, s) {
2189
2185
  return {
2190
2186
  error: "Session ID is required"
2191
2187
  };
2192
- const e = E(s.sessionId);
2188
+ const e = D(s.sessionId);
2193
2189
  return {
2194
2190
  browserInfos: Array.from(e.browsers.values())
2195
2191
  };
@@ -2215,18 +2211,18 @@ ${n.length === 0 ? "No browsers found" : `Browsers: ${n.join(", ")}`}`;
2215
2211
  }
2216
2212
  );
2217
2213
  }
2218
- const Ke = p.object({
2219
- names: p.array(p.string()).optional().describe(
2214
+ const Ke = h.object({
2215
+ names: h.array(h.string()).optional().describe(
2220
2216
  "Names of browsers to close. If not specified, closes all browsers"
2221
2217
  )
2222
2218
  });
2223
- async function xr(t, r, s) {
2219
+ async function Sr(t, r, s) {
2224
2220
  let o;
2225
2221
  try {
2226
2222
  o = Ke.parse(t);
2227
- } catch (l) {
2223
+ } catch (c) {
2228
2224
  return {
2229
- error: C(l)
2225
+ error: C(c)
2230
2226
  };
2231
2227
  }
2232
2228
  const { names: e } = o;
@@ -2234,18 +2230,18 @@ async function xr(t, r, s) {
2234
2230
  return {
2235
2231
  error: "Session ID is required"
2236
2232
  };
2237
- const n = E(s.sessionId), a = [], i = [];
2233
+ const n = D(s.sessionId), a = [], i = [];
2238
2234
  let u = [];
2239
- return e ? e.forEach((l) => {
2240
- const c = n.browsers.get(l);
2241
- c ? u.push(c) : i.push(`Browser "${l}" not found`);
2235
+ return e ? e.forEach((c) => {
2236
+ const l = n.browsers.get(c);
2237
+ l ? u.push(l) : i.push(`Browser "${c}" not found`);
2242
2238
  }) : u = Array.from(n.browsers.values()), await Promise.all(
2243
- u.map(async (l) => {
2239
+ u.map(async (c) => {
2244
2240
  try {
2245
- await l.browser.close(), n.browsers.delete(l.name), a.push(l);
2246
- } catch (c) {
2241
+ await c.browser.close(), n.browsers.delete(c.name), a.push(c);
2242
+ } catch (l) {
2247
2243
  i.push(
2248
- `Failed to close browser "${l.name}" (${l.browserType}): ${c instanceof Error ? c.message : "Unknown error"}`
2244
+ `Failed to close browser "${c.name}" (${c.browserType}): ${l instanceof Error ? l.message : "Unknown error"}`
2249
2245
  );
2250
2246
  }
2251
2247
  })
@@ -2254,7 +2250,7 @@ async function xr(t, r, s) {
2254
2250
  ...i.length > 0 && { errors: i }
2255
2251
  };
2256
2252
  }
2257
- function Sr(t, r) {
2253
+ function xr(t, r) {
2258
2254
  t(
2259
2255
  "playwright-browser-close",
2260
2256
  {
@@ -2263,7 +2259,7 @@ function Sr(t, r) {
2263
2259
  inputSchema: Ke.shape
2264
2260
  },
2265
2261
  async (s, o) => {
2266
- const e = await xr(s, r, o);
2262
+ const e = await Sr(s, r, o);
2267
2263
  if (e.error != null)
2268
2264
  return `Method: playwright-browser-close(${JSON.stringify(s)})
2269
2265
  ❌ Error: ${e.error}`;
@@ -2280,53 +2276,53 @@ ${n.join(`
2280
2276
  }
2281
2277
  );
2282
2278
  }
2283
- const te = p.object({
2284
- browserName: p.string().optional().describe("Name of previously created browser, to use"),
2279
+ const te = h.object({
2280
+ browserName: h.string().optional().describe("Name of previously created browser, to use"),
2285
2281
  browser: ee.optional().describe(
2286
2282
  "Browser creation options JSON to automatically create browser"
2287
2283
  ),
2288
- name: p.string().describe(
2284
+ name: h.string().describe(
2289
2285
  "Unique name for the context. Recommended format: kebab-case-1, kebab-case-2, ..."
2290
2286
  ),
2291
- isMobile: p.boolean().optional().describe("Configure for mobile device simulation"),
2292
- hasTouch: p.boolean().optional().describe("Enable touch events"),
2293
- viewport: p.object({
2294
- width: p.number(),
2295
- height: p.number()
2287
+ isMobile: h.boolean().optional().describe("Configure for mobile device simulation"),
2288
+ hasTouch: h.boolean().optional().describe("Enable touch events"),
2289
+ viewport: h.object({
2290
+ width: h.number(),
2291
+ height: h.number()
2296
2292
  }).optional().describe("Viewport size configuration")
2297
2293
  });
2298
2294
  async function We(t, r, s) {
2299
2295
  let o;
2300
2296
  try {
2301
2297
  o = te.parse(t);
2302
- } catch (h) {
2298
+ } catch (m) {
2303
2299
  return {
2304
- error: C(h)
2300
+ error: C(m)
2305
2301
  };
2306
2302
  }
2307
- const { name: e, browserName: n, browser: a, isMobile: i, hasTouch: u, viewport: l } = o;
2303
+ const { name: e, browserName: n, browser: a, isMobile: i, hasTouch: u, viewport: c } = o;
2308
2304
  if (!s.sessionId)
2309
2305
  return {
2310
2306
  error: "Session ID is required"
2311
2307
  };
2312
- const c = E(s.sessionId);
2308
+ const l = D(s.sessionId);
2313
2309
  if (n && a)
2314
2310
  return {
2315
2311
  error: "Either browserName or browser must be provided, not both"
2316
2312
  };
2317
2313
  let f = !1, d;
2318
2314
  if (n) {
2319
- if (d = c.browsers.get(n), !d)
2315
+ if (d = l.browsers.get(n), !d)
2320
2316
  return {
2321
2317
  error: `Browser "${n}" not found`
2322
2318
  };
2323
2319
  } else if (a) {
2324
- const h = await _e(a, r, s);
2325
- if (h.error != null)
2320
+ const m = await _e(a, r, s);
2321
+ if (m.error != null)
2326
2322
  return {
2327
- error: h.error
2323
+ error: m.error
2328
2324
  };
2329
- d = h.browserInfo, f = !0;
2325
+ d = m.browserInfo, f = !0;
2330
2326
  } else
2331
2327
  return {
2332
2328
  error: "Either browserName or browser must be provided"
@@ -2336,24 +2332,24 @@ async function We(t, r, s) {
2336
2332
  error: `Context "${e}" already exists in browser "${d.name}" (${d.browserType})`
2337
2333
  };
2338
2334
  try {
2339
- const h = await d.browser.newContext({
2335
+ const m = await d.browser.newContext({
2340
2336
  isMobile: i,
2341
2337
  hasTouch: u,
2342
- viewport: l
2343
- }), m = {
2338
+ viewport: c
2339
+ }), g = {
2344
2340
  browserInfo: d,
2345
2341
  name: e,
2346
- context: h,
2342
+ context: m,
2347
2343
  pages: /* @__PURE__ */ new Map()
2348
2344
  };
2349
- return d.contexts.set(e, m), {
2345
+ return d.contexts.set(e, g), {
2350
2346
  browserInfoCreated: f,
2351
2347
  browserInfo: d,
2352
- contextInfo: m
2348
+ contextInfo: g
2353
2349
  };
2354
- } catch (h) {
2350
+ } catch (m) {
2355
2351
  return {
2356
- error: `Failed to create context: ${h instanceof Error ? h.message : "Unknown error"} in browser "${d.name}" (${d.browserType})`
2352
+ error: `Failed to create context: ${m instanceof Error ? m.message : "Unknown error"} in browser "${d.name}" (${d.browserType})`
2357
2353
  };
2358
2354
  }
2359
2355
  }
@@ -2377,8 +2373,8 @@ function $r(t, r) {
2377
2373
  }
2378
2374
  );
2379
2375
  }
2380
- const Qe = p.object({
2381
- browserName: p.string().optional().describe(
2376
+ const Qe = h.object({
2377
+ browserName: h.string().optional().describe(
2382
2378
  "Name of browser to list contexts from. If not specified, lists contexts from all browsers"
2383
2379
  )
2384
2380
  });
@@ -2396,7 +2392,7 @@ async function Ir(t, r, s) {
2396
2392
  return {
2397
2393
  error: "Session ID is required"
2398
2394
  };
2399
- const n = E(s.sessionId), a = [];
2395
+ const n = D(s.sessionId), a = [];
2400
2396
  if (e) {
2401
2397
  const i = n.browsers.get(e);
2402
2398
  if (!i)
@@ -2441,11 +2437,11 @@ function Mr(t, r) {
2441
2437
  }
2442
2438
  );
2443
2439
  }
2444
- const He = p.object({
2445
- names: p.array(p.string()).optional().describe(
2440
+ const He = h.object({
2441
+ names: h.array(h.string()).optional().describe(
2446
2442
  "Names of contexts to close. If not specified, closes all contexts"
2447
2443
  ),
2448
- browserName: p.string().optional().describe(
2444
+ browserName: h.string().optional().describe(
2449
2445
  "Name of browser to close contexts from. If not specified, searches all browsers"
2450
2446
  )
2451
2447
  });
@@ -2453,9 +2449,9 @@ async function Tr(t, r, s) {
2453
2449
  let o;
2454
2450
  try {
2455
2451
  o = He.parse(t);
2456
- } catch (c) {
2452
+ } catch (l) {
2457
2453
  return {
2458
- error: C(c)
2454
+ error: C(l)
2459
2455
  };
2460
2456
  }
2461
2457
  const { names: e, browserName: n } = o;
@@ -2463,38 +2459,38 @@ async function Tr(t, r, s) {
2463
2459
  return {
2464
2460
  error: "Session ID is required"
2465
2461
  };
2466
- const a = E(s.sessionId), i = [], u = [];
2467
- let l = [];
2462
+ const a = D(s.sessionId), i = [], u = [];
2463
+ let c = [];
2468
2464
  if (n) {
2469
- const c = a.browsers.get(n);
2470
- if (!c)
2465
+ const l = a.browsers.get(n);
2466
+ if (!l)
2471
2467
  return {
2472
2468
  error: `Browser "${n}" not found`
2473
2469
  };
2474
2470
  e ? e.forEach((f) => {
2475
- const d = c.contexts.get(f);
2476
- d ? l.push(d) : u.push(
2477
- `Context "${f}" not found in browser "${c.name}" (${c.browserType})`
2471
+ const d = l.contexts.get(f);
2472
+ d ? c.push(d) : u.push(
2473
+ `Context "${f}" not found in browser "${l.name}" (${l.browserType})`
2478
2474
  );
2479
- }) : l = Array.from(c.contexts.values());
2475
+ }) : c = Array.from(l.contexts.values());
2480
2476
  } else if (e)
2481
- for (const c of a.browsers.values())
2477
+ for (const l of a.browsers.values())
2482
2478
  e.forEach((f) => {
2483
- const d = c.contexts.get(f);
2484
- d ? l.push(d) : u.push(
2485
- `Context "${f}" not found in browser "${c.name}" (${c.browserType})`
2479
+ const d = l.contexts.get(f);
2480
+ d ? c.push(d) : u.push(
2481
+ `Context "${f}" not found in browser "${l.name}" (${l.browserType})`
2486
2482
  );
2487
2483
  });
2488
2484
  else
2489
- for (const c of a.browsers.values())
2490
- l.push(...Array.from(c.contexts.values()));
2485
+ for (const l of a.browsers.values())
2486
+ c.push(...Array.from(l.contexts.values()));
2491
2487
  return await Promise.all(
2492
- l.map(async (c) => {
2488
+ c.map(async (l) => {
2493
2489
  try {
2494
- await c.context.close(), c.browserInfo.contexts.delete(c.name), i.push(c);
2490
+ await l.context.close(), l.browserInfo.contexts.delete(l.name), i.push(l);
2495
2491
  } catch (f) {
2496
2492
  u.push(
2497
- `Failed to close context "${c.name}" (${c.browserInfo.name}) (${c.browserInfo.browserType}): ${f instanceof Error ? f.message : "Unknown error"}`
2493
+ `Failed to close context "${l.name}" (${l.browserInfo.name}) (${l.browserInfo.browserType}): ${f instanceof Error ? f.message : "Unknown error"}`
2498
2494
  );
2499
2495
  }
2500
2496
  })
@@ -2541,66 +2537,66 @@ function Cr() {
2541
2537
  });
2542
2538
  }
2543
2539
  getOrCreateId(u) {
2544
- let l = this.objectToId.get(u);
2545
- return l == null && (l = ++this.prevId, this.objectToId.set(u, l), this.idToObject.set(l, new WeakRef(u)), this.cleanupRegistry.register(u, l)), l;
2540
+ let c = this.objectToId.get(u);
2541
+ return c == null && (c = ++this.prevId, this.objectToId.set(u, c), this.idToObject.set(c, new WeakRef(u)), this.cleanupRegistry.register(u, c)), c;
2546
2542
  }
2547
2543
  getObject(u) {
2548
- const l = this.idToObject.get(u);
2549
- if (!l)
2544
+ const c = this.idToObject.get(u);
2545
+ if (!c)
2550
2546
  return null;
2551
- const c = l.deref();
2552
- return c ?? (this.idToObject.delete(u), null);
2547
+ const l = c.deref();
2548
+ return l ?? (this.idToObject.delete(u), null);
2553
2549
  }
2554
2550
  }
2555
- function r(i, u, l) {
2556
- let c = null;
2551
+ function r(i, u, c) {
2552
+ let l = null;
2557
2553
  for (let f = 0, d = u.length; f < d; f++) {
2558
- const h = u[f], m = i(h), g = m == null ? null : r(i, m, l), b = l(h, g);
2559
- b != null && (c == null && (c = []), c.push(b));
2554
+ const m = u[f], g = i(m), p = g == null ? null : r(i, g, c), y = c(m, p);
2555
+ y != null && (l == null && (l = []), l.push(y));
2560
2556
  }
2561
- return c;
2557
+ return l;
2562
2558
  }
2563
2559
  function s(i) {
2564
- const { getId: u, getChilds: l, rootNodes: c, createSnapshotNode: f } = i, d = /* @__PURE__ */ new Map(), h = /* @__PURE__ */ new Map(), m = /* @__PURE__ */ new Map(), g = r(
2565
- l,
2560
+ const { getId: u, getChilds: c, rootNodes: l, createSnapshotNode: f } = i, d = /* @__PURE__ */ new Map(), m = /* @__PURE__ */ new Map(), g = /* @__PURE__ */ new Map(), p = r(
2566
2561
  c,
2567
- (y, x) => {
2568
- const I = f(y, x);
2569
- if (y != null && I != null) {
2570
- const S = u(y);
2571
- d.set(S, I), h.set(I, S);
2562
+ l,
2563
+ (w, S) => {
2564
+ const M = f(w, S);
2565
+ if (w != null && M != null) {
2566
+ const I = u(w);
2567
+ d.set(I, M), m.set(M, I);
2572
2568
  }
2573
- return I != null && x != null && m.set(
2574
- h.get(I),
2575
- x.map((S) => h.get(S))
2576
- ), I;
2569
+ return M != null && S != null && g.set(
2570
+ m.get(M),
2571
+ S.map((I) => m.get(I))
2572
+ ), M;
2577
2573
  }
2578
- ), b = f(null, g);
2579
- if (b == null)
2574
+ ), y = f(null, p);
2575
+ if (y == null)
2580
2576
  throw new Error("Impossible behavior: rootNode == null");
2581
- return d.set(null, b), g != null && m.set(
2577
+ return d.set(null, y), p != null && g.set(
2582
2578
  null,
2583
- g.map((y) => h.get(y))
2579
+ p.map((w) => m.get(w))
2584
2580
  ), {
2585
2581
  idToNode: d,
2586
- idToChildIds: m
2582
+ idToChildIds: g
2587
2583
  };
2588
2584
  }
2589
2585
  const o = (i) => i instanceof HTMLElement ? i.childNodes : null;
2590
2586
  function e(i) {
2591
- return function(l, c) {
2592
- const f = c != null && c.length > 0;
2593
- let d = !1, h = null, m = null;
2594
- if (l instanceof HTMLElement) {
2595
- if (h = n.getOrCreateId(l), m = l.tagName.toLowerCase(), d = l.matches(i.cssSelector), !d && !f)
2587
+ return function(c, l) {
2588
+ const f = l != null && l.length > 0;
2589
+ let d = !1, m = null, g = null;
2590
+ if (c instanceof HTMLElement) {
2591
+ if (m = n.getOrCreateId(c), g = c.tagName.toLowerCase(), d = c.matches(i.cssSelector), !d && !f)
2596
2592
  return null;
2597
- } else if (l == null)
2598
- h = null, m = null, d = !1;
2593
+ } else if (c == null)
2594
+ m = null, g = null, d = !1;
2599
2595
  else
2600
2596
  return null;
2601
2597
  return {
2602
- uid: h,
2603
- tagName: m,
2598
+ uid: m,
2599
+ tagName: g,
2604
2600
  isMatched: d
2605
2601
  };
2606
2602
  };
@@ -2609,7 +2605,7 @@ function Cr() {
2609
2605
  function a(i) {
2610
2606
  const u = e(i);
2611
2607
  return s({
2612
- getId: (l) => n.getOrCreateId(l),
2608
+ getId: (c) => n.getOrCreateId(c),
2613
2609
  getChilds: o,
2614
2610
  createSnapshotNode: u,
2615
2611
  rootNodes: [window.document.documentElement]
@@ -2617,12 +2613,12 @@ function Cr() {
2617
2613
  }
2618
2614
  window.__mcp_playwright_tool_tx4byhar35_createDomSnapshotTreeRawDom = a;
2619
2615
  }
2620
- const kr = `(function (){function __name(fn){return fn};${Cr.toString()}; setupPageGlobals();})()`, re = p.object({
2621
- contextName: p.string().optional().describe("Name of previously created context, to use"),
2616
+ const kr = `(function (){function __name(fn){return fn};${Cr.toString()}; setupPageGlobals();})()`, re = h.object({
2617
+ contextName: h.string().optional().describe("Name of previously created context, to use"),
2622
2618
  context: te.optional().describe(
2623
2619
  "Context creation options JSON to automatically create context"
2624
2620
  ),
2625
- name: p.string().describe(
2621
+ name: h.string().describe(
2626
2622
  "Unique name for the page. Recommended format: kebab-case-1, kebab-case-2, ..."
2627
2623
  )
2628
2624
  });
@@ -2640,19 +2636,19 @@ async function Ye(t, r, s) {
2640
2636
  return {
2641
2637
  error: "Session ID is required"
2642
2638
  };
2643
- const i = E(s.sessionId);
2639
+ const i = D(s.sessionId);
2644
2640
  if (n && a)
2645
2641
  return {
2646
2642
  error: "Either contextName or context must be provided, not both"
2647
2643
  };
2648
- let u = !1, l = !1, c;
2644
+ let u = !1, c = !1, l;
2649
2645
  if (n) {
2650
2646
  for (const f of i.browsers.values())
2651
2647
  if (f.contexts.has(n)) {
2652
- c = f.contexts.get(n);
2648
+ l = f.contexts.get(n);
2653
2649
  break;
2654
2650
  }
2655
- if (!c)
2651
+ if (!l)
2656
2652
  return {
2657
2653
  error: `Context "${n}" not found`
2658
2654
  };
@@ -2662,32 +2658,32 @@ async function Ye(t, r, s) {
2662
2658
  return {
2663
2659
  error: f.error
2664
2660
  };
2665
- c = f.contextInfo, u = f.browserInfoCreated, l = !0;
2661
+ l = f.contextInfo, u = f.browserInfoCreated, c = !0;
2666
2662
  } else
2667
2663
  return {
2668
2664
  error: "Either contextName or context must be provided"
2669
2665
  };
2670
- if (c.pages.has(e))
2666
+ if (l.pages.has(e))
2671
2667
  return {
2672
- error: `Page "${e}" already exists in context "${c.name}" in browser "${c.browserInfo.name}" (${c.browserInfo.browserType})`
2668
+ error: `Page "${e}" already exists in context "${l.name}" in browser "${l.browserInfo.name}" (${l.browserInfo.browserType})`
2673
2669
  };
2674
2670
  try {
2675
- const f = await c.context.newPage();
2671
+ const f = await l.context.newPage();
2676
2672
  await f.addInitScript(kr), await f.goto("about:blank");
2677
2673
  const d = {
2678
- contextInfo: c,
2674
+ contextInfo: l,
2679
2675
  name: e,
2680
2676
  page: f,
2681
2677
  domSnapshots: /* @__PURE__ */ new Map()
2682
2678
  };
2683
- return c.pages.set(e, d), {
2679
+ return l.pages.set(e, d), {
2684
2680
  browserInfoCreated: u,
2685
- contextInfoCreated: l,
2681
+ contextInfoCreated: c,
2686
2682
  pageInfo: d
2687
2683
  };
2688
2684
  } catch (f) {
2689
2685
  return {
2690
- error: `Failed to create page: ${f instanceof Error ? f.message : "Unknown error"} in context "${c.name}" in browser "${c.browserInfo.name}" (${c.browserInfo.browserType})`
2686
+ error: `Failed to create page: ${f instanceof Error ? f.message : "Unknown error"} in context "${l.name}" in browser "${l.browserInfo.name}" (${l.browserInfo.browserType})`
2691
2687
  };
2692
2688
  }
2693
2689
  }
@@ -2712,15 +2708,15 @@ function Nr(t, r) {
2712
2708
  }
2713
2709
  );
2714
2710
  }
2715
- const Ve = p.object({
2716
- contextName: p.string().optional().describe(
2711
+ const Ve = h.object({
2712
+ contextName: h.string().optional().describe(
2717
2713
  "Name of context to list pages from. If not specified, lists pages from all contexts"
2718
2714
  ),
2719
- browserName: p.string().optional().describe(
2715
+ browserName: h.string().optional().describe(
2720
2716
  "Name of browser to search in. If not specified, searches all browsers"
2721
2717
  )
2722
2718
  });
2723
- async function Dr(t, r, s) {
2719
+ async function Er(t, r, s) {
2724
2720
  let o;
2725
2721
  try {
2726
2722
  o = Ve.parse(t);
@@ -2734,7 +2730,7 @@ async function Dr(t, r, s) {
2734
2730
  return {
2735
2731
  error: "Session ID is required"
2736
2732
  };
2737
- const a = E(s.sessionId), i = [];
2733
+ const a = D(s.sessionId), i = [];
2738
2734
  if (n) {
2739
2735
  const u = a.browsers.get(n);
2740
2736
  if (!u)
@@ -2742,49 +2738,49 @@ async function Dr(t, r, s) {
2742
2738
  error: `Browser "${n}" not found`
2743
2739
  };
2744
2740
  if (e) {
2745
- const l = u.contexts.get(e);
2746
- if (!l)
2741
+ const c = u.contexts.get(e);
2742
+ if (!c)
2747
2743
  return {
2748
2744
  error: `Context "${e}" not found in browser "${u.name}" (${u.browserType})`
2749
2745
  };
2750
- const c = Array.from(l.pages.values());
2751
- c.length > 0 && i.push({
2752
- contextInfo: l,
2753
- pages: c
2746
+ const l = Array.from(c.pages.values());
2747
+ l.length > 0 && i.push({
2748
+ contextInfo: c,
2749
+ pages: l
2754
2750
  });
2755
2751
  } else
2756
- for (const l of u.contexts.values()) {
2757
- const c = Array.from(l.pages.values());
2758
- c.length > 0 && i.push({
2759
- contextInfo: l,
2760
- pages: c
2752
+ for (const c of u.contexts.values()) {
2753
+ const l = Array.from(c.pages.values());
2754
+ l.length > 0 && i.push({
2755
+ contextInfo: c,
2756
+ pages: l
2761
2757
  });
2762
2758
  }
2763
2759
  } else if (e)
2764
2760
  for (const u of a.browsers.values()) {
2765
- const l = u.contexts.get(e);
2766
- if (l) {
2767
- const c = Array.from(l.pages.values());
2768
- c.length > 0 && i.push({
2769
- contextInfo: l,
2770
- pages: c
2761
+ const c = u.contexts.get(e);
2762
+ if (c) {
2763
+ const l = Array.from(c.pages.values());
2764
+ l.length > 0 && i.push({
2765
+ contextInfo: c,
2766
+ pages: l
2771
2767
  });
2772
2768
  }
2773
2769
  }
2774
2770
  else
2775
2771
  for (const u of a.browsers.values())
2776
- for (const l of u.contexts.values()) {
2777
- const c = Array.from(l.pages.values());
2778
- c.length > 0 && i.push({
2779
- contextInfo: l,
2780
- pages: c
2772
+ for (const c of u.contexts.values()) {
2773
+ const l = Array.from(c.pages.values());
2774
+ l.length > 0 && i.push({
2775
+ contextInfo: c,
2776
+ pages: l
2781
2777
  });
2782
2778
  }
2783
2779
  return {
2784
2780
  pagesByContext: i
2785
2781
  };
2786
2782
  }
2787
- function Er(t, r) {
2783
+ function Dr(t, r) {
2788
2784
  t(
2789
2785
  "playwright-page-list",
2790
2786
  {
@@ -2793,7 +2789,7 @@ function Er(t, r) {
2793
2789
  inputSchema: Ve.shape
2794
2790
  },
2795
2791
  async (s, o) => {
2796
- const e = await Dr(s, r, o);
2792
+ const e = await Er(s, r, o);
2797
2793
  if ("error" in e)
2798
2794
  return `Method: playwright-page-list(${JSON.stringify(s)})
2799
2795
  ❌ Error: ${e.error}`;
@@ -2806,12 +2802,12 @@ function Er(t, r) {
2806
2802
  }
2807
2803
  );
2808
2804
  }
2809
- const Ze = p.object({
2810
- names: p.array(p.string()).optional().describe("Names of pages to close. If not specified, closes all pages"),
2811
- contextName: p.string().optional().describe(
2805
+ const Ze = h.object({
2806
+ names: h.array(h.string()).optional().describe("Names of pages to close. If not specified, closes all pages"),
2807
+ contextName: h.string().optional().describe(
2812
2808
  "Name of context to close pages from. If not specified, searches all contexts"
2813
2809
  ),
2814
- browserName: p.string().optional().describe(
2810
+ browserName: h.string().optional().describe(
2815
2811
  "Name of browser to search in. If not specified, searches all browsers"
2816
2812
  )
2817
2813
  });
@@ -2829,8 +2825,8 @@ async function Fr(t, r, s) {
2829
2825
  return {
2830
2826
  error: "Session ID is required"
2831
2827
  };
2832
- const i = E(s.sessionId), u = [], l = [];
2833
- let c = [];
2828
+ const i = D(s.sessionId), u = [], c = [];
2829
+ let l = [];
2834
2830
  if (a) {
2835
2831
  const f = i.browsers.get(a);
2836
2832
  if (!f)
@@ -2843,54 +2839,54 @@ async function Fr(t, r, s) {
2843
2839
  return {
2844
2840
  error: `Context "${n}" not found in browser "${f.name}" (${f.browserType})`
2845
2841
  };
2846
- e ? e.forEach((h) => {
2847
- const m = d.pages.get(h);
2848
- m ? c.push(m) : l.push(
2849
- `Page "${h}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2842
+ e ? e.forEach((m) => {
2843
+ const g = d.pages.get(m);
2844
+ g ? l.push(g) : c.push(
2845
+ `Page "${m}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2850
2846
  );
2851
- }) : c = Array.from(d.pages.values());
2847
+ }) : l = Array.from(d.pages.values());
2852
2848
  } else
2853
2849
  for (const d of f.contexts.values())
2854
- e ? e.forEach((h) => {
2855
- const m = d.pages.get(h);
2856
- m ? c.push(m) : l.push(
2857
- `Page "${h}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2850
+ e ? e.forEach((m) => {
2851
+ const g = d.pages.get(m);
2852
+ g ? l.push(g) : c.push(
2853
+ `Page "${m}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2858
2854
  );
2859
- }) : c.push(...Array.from(d.pages.values()));
2855
+ }) : l.push(...Array.from(d.pages.values()));
2860
2856
  } else if (n)
2861
2857
  for (const f of i.browsers.values()) {
2862
2858
  const d = f.contexts.get(n);
2863
- d && (e ? e.forEach((h) => {
2864
- const m = d.pages.get(h);
2865
- m ? c.push(m) : l.push(
2866
- `Page "${h}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2859
+ d && (e ? e.forEach((m) => {
2860
+ const g = d.pages.get(m);
2861
+ g ? l.push(g) : c.push(
2862
+ `Page "${m}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2867
2863
  );
2868
- }) : c.push(...Array.from(d.pages.values())));
2864
+ }) : l.push(...Array.from(d.pages.values())));
2869
2865
  }
2870
2866
  else
2871
2867
  for (const f of i.browsers.values())
2872
2868
  for (const d of f.contexts.values())
2873
- e ? e.forEach((h) => {
2874
- const m = d.pages.get(h);
2875
- m ? c.push(m) : l.push(
2876
- `Page "${h}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2869
+ e ? e.forEach((m) => {
2870
+ const g = d.pages.get(m);
2871
+ g ? l.push(g) : c.push(
2872
+ `Page "${m}" not found in context "${d.name}" in browser "${f.name}" (${f.browserType})`
2877
2873
  );
2878
- }) : c.push(...Array.from(d.pages.values()));
2874
+ }) : l.push(...Array.from(d.pages.values()));
2879
2875
  return await Promise.all(
2880
- c.map(async (f) => {
2876
+ l.map(async (f) => {
2881
2877
  try {
2882
2878
  await f.page.close(), f.contextInfo.pages.delete(f.name), u.push(
2883
2879
  `${f.name} (${f.contextInfo.name}) (${f.contextInfo.browserInfo.name}) (${f.contextInfo.browserInfo.browserType})`
2884
2880
  );
2885
2881
  } catch (d) {
2886
- l.push(
2882
+ c.push(
2887
2883
  `Failed to close page "${f.name}" (${f.contextInfo.name}) (${f.contextInfo.browserInfo.name}) (${f.contextInfo.browserInfo.browserType}): ${d instanceof Error ? d.message : "Unknown error"}`
2888
2884
  );
2889
2885
  }
2890
2886
  })
2891
2887
  ), {
2892
2888
  closedPages: u,
2893
- ...l.length > 0 && { errors: l }
2889
+ ...c.length > 0 && { errors: c }
2894
2890
  };
2895
2891
  }
2896
2892
  function Br(t, r) {
@@ -2913,14 +2909,14 @@ ${n.join(`
2913
2909
  }
2914
2910
  );
2915
2911
  }
2916
- const Xe = p.object({
2917
- pageName: p.string().optional().describe("Name of previously created page to navigate"),
2912
+ const Xe = h.object({
2913
+ pageName: h.string().optional().describe("Name of previously created page to navigate"),
2918
2914
  page: re.optional().describe(
2919
2915
  "Page creation options JSON to automatically create page"
2920
2916
  ),
2921
- url: p.string().describe("URL to navigate to"),
2922
- timeout: p.number().describe("Timeout in seconds"),
2923
- waitUntil: p.enum(["load", "domcontentloaded", "networkidle", "commit"]).describe(
2917
+ url: h.string().describe("URL to navigate to"),
2918
+ timeout: h.number().describe("Timeout in seconds"),
2919
+ waitUntil: h.enum(["load", "domcontentloaded", "networkidle", "commit"]).describe(
2924
2920
  `Wait until event:
2925
2921
  - 'domcontentloaded': DOMContentLoaded event is fired
2926
2922
  - 'load': load event is fired
@@ -2932,9 +2928,9 @@ async function Or(t, r, s) {
2932
2928
  let o;
2933
2929
  try {
2934
2930
  o = Xe.parse(t);
2935
- } catch (m) {
2931
+ } catch (g) {
2936
2932
  return {
2937
- error: C(m)
2933
+ error: C(g)
2938
2934
  };
2939
2935
  }
2940
2936
  const { pageName: e, page: n, url: a, timeout: i, waitUntil: u } = o;
@@ -2942,57 +2938,57 @@ async function Or(t, r, s) {
2942
2938
  return {
2943
2939
  error: "Session ID is required"
2944
2940
  };
2945
- const l = E(s.sessionId);
2941
+ const c = D(s.sessionId);
2946
2942
  if (e && n)
2947
2943
  return {
2948
2944
  error: "Either pageName or page must be provided, not both"
2949
2945
  };
2950
- let c = !1, f = !1, d = !1, h;
2946
+ let l = !1, f = !1, d = !1, m;
2951
2947
  if (e) {
2952
- for (const m of l.browsers.values()) {
2953
- for (const g of m.contexts.values())
2954
- if (g.pages.has(e)) {
2955
- h = g.pages.get(e);
2948
+ for (const g of c.browsers.values()) {
2949
+ for (const p of g.contexts.values())
2950
+ if (p.pages.has(e)) {
2951
+ m = p.pages.get(e);
2956
2952
  break;
2957
2953
  }
2958
- if (h) break;
2954
+ if (m) break;
2959
2955
  }
2960
- if (!h)
2956
+ if (!m)
2961
2957
  return {
2962
2958
  error: `Page "${e}" not found`
2963
2959
  };
2964
2960
  } else if (n) {
2965
- const m = await Ye(n, r, s);
2966
- if (m.error != null)
2961
+ const g = await Ye(n, r, s);
2962
+ if (g.error != null)
2967
2963
  return {
2968
- error: m.error
2964
+ error: g.error
2969
2965
  };
2970
- h = m.pageInfo, c = m.browserInfoCreated, f = m.contextInfoCreated, d = !0;
2966
+ m = g.pageInfo, l = g.browserInfoCreated, f = g.contextInfoCreated, d = !0;
2971
2967
  } else
2972
2968
  return {
2973
2969
  error: "Either pageName or page must be provided"
2974
2970
  };
2975
2971
  try {
2976
- const m = await h.page.goto(a, {
2972
+ const g = await m.page.goto(a, {
2977
2973
  timeout: i * 1e3,
2978
2974
  waitUntil: u
2979
2975
  });
2980
- return m ? {
2981
- browserInfoCreated: c,
2976
+ return g ? {
2977
+ browserInfoCreated: l,
2982
2978
  contextInfoCreated: f,
2983
2979
  pageInfoCreated: d,
2984
- pageInfo: h,
2985
- status: m.status()
2980
+ pageInfo: m,
2981
+ status: g.status()
2986
2982
  } : {
2987
- browserInfoCreated: c,
2983
+ browserInfoCreated: l,
2988
2984
  contextInfoCreated: f,
2989
2985
  pageInfoCreated: d,
2990
- pageInfo: h,
2986
+ pageInfo: m,
2991
2987
  status: 200
2992
2988
  };
2993
- } catch (m) {
2989
+ } catch (g) {
2994
2990
  return {
2995
- error: `Failed to navigate to "${a}": ${m instanceof Error ? m.message : "Unknown error"}`
2991
+ error: `Failed to navigate to "${a}": ${g instanceof Error ? g.message : "Unknown error"}`
2996
2992
  };
2997
2993
  }
2998
2994
  }
@@ -3018,11 +3014,11 @@ function Rr(t, r) {
3018
3014
  }
3019
3015
  );
3020
3016
  }
3021
- const se = p.object({
3022
- name: p.string().describe(
3017
+ const se = h.object({
3018
+ name: h.string().describe(
3023
3019
  "Unique name for the DOM snapshot query. Recommended format: kebab-case-1, kebab-case-2, ..."
3024
3020
  ),
3025
- cssSelector: p.string().describe("CSS selector to capture page content")
3021
+ cssSelector: h.string().describe("CSS selector to capture page content")
3026
3022
  });
3027
3023
  async function et(t, r, s) {
3028
3024
  let o;
@@ -3038,7 +3034,7 @@ async function et(t, r, s) {
3038
3034
  return {
3039
3035
  error: "Session ID is required"
3040
3036
  };
3041
- const a = E(s.sessionId);
3037
+ const a = D(s.sessionId);
3042
3038
  if (a.domSnapshotQueries.has(e))
3043
3039
  return {
3044
3040
  error: `DOM snapshot query "${e}" already exists`
@@ -3071,34 +3067,34 @@ function zr(t) {
3071
3067
  return function(s, o) {
3072
3068
  let e, n = 0;
3073
3069
  const a = o ? o.length : 0;
3074
- let i = 1, u = 0, l = 0, c, f;
3070
+ let i = 1, u = 0, c = 0, l, f;
3075
3071
  if (o)
3076
- for (let m = 0; m < o.length; m++) {
3077
- const g = o[m];
3078
- n += g.countMatched, i += g.countTotal, u += g.tokens, l += g.tokensTotal;
3072
+ for (let g = 0; g < o.length; g++) {
3073
+ const p = o[g];
3074
+ n += p.countMatched, i += p.countTotal, u += p.tokens, c += p.tokensTotal;
3079
3075
  }
3080
- s ? (c = s.uid, f = s.tagName, e = s.isMatched, e && (n += 1)) : (c = null, f = null, e = !1);
3076
+ s ? (l = s.uid, f = s.tagName, e = s.isMatched, e && (n += 1)) : (l = null, f = null, e = !1);
3081
3077
  let d;
3082
3078
  f ? d = {
3083
3079
  indent: !0,
3084
- textOpen: `<${f} uid:${c}>`,
3080
+ textOpen: `<${f} uid:${l}>`,
3085
3081
  textClose: `</${f}>`
3086
3082
  } : d = {
3087
3083
  indent: !0,
3088
- textOpen: `<root uid:${c}>`,
3084
+ textOpen: `<root uid:${l}>`,
3089
3085
  textClose: "</root>"
3090
3086
  };
3091
- const h = Ue(d);
3092
- return l += h, {
3093
- uid: c,
3087
+ const m = Ue(d);
3088
+ return c += m, {
3089
+ uid: l,
3094
3090
  tagName: f,
3095
3091
  isMatched: e,
3096
3092
  countMatched: n,
3097
3093
  countChilds: a,
3098
3094
  countTotal: i,
3099
- tokens: h,
3095
+ tokens: m,
3100
3096
  tokensChilds: u,
3101
- tokensTotal: l,
3097
+ tokensTotal: c,
3102
3098
  text: d
3103
3099
  };
3104
3100
  };
@@ -3119,13 +3115,13 @@ function Lr(t, r) {
3119
3115
  });
3120
3116
  return j(e);
3121
3117
  }
3122
- const oe = p.object({
3123
- pageName: p.string().describe("Name of previously created page, to create snapshot from"),
3124
- queryName: p.string().optional().describe("Name of previously created DOM snapshot query, to use"),
3118
+ const oe = h.object({
3119
+ pageName: h.string().describe("Name of previously created page, to create snapshot from"),
3120
+ queryName: h.string().optional().describe("Name of previously created DOM snapshot query, to use"),
3125
3121
  query: se.optional().describe(
3126
3122
  "DOM snapshot query creation options JSON to automatically create query"
3127
3123
  ),
3128
- name: p.string().describe(
3124
+ name: h.string().describe(
3129
3125
  "Unique name for the DOM snapshot. Recommended format: kebab-case-1, kebab-case-2, ..."
3130
3126
  )
3131
3127
  });
@@ -3143,21 +3139,21 @@ async function tt(t, r, s) {
3143
3139
  return {
3144
3140
  error: "Session ID is required"
3145
3141
  };
3146
- const u = E(s.sessionId);
3147
- let l;
3142
+ const u = D(s.sessionId);
3143
+ let c;
3148
3144
  for (const d of u.browsers.values()) {
3149
- for (const h of d.contexts.values())
3150
- if (h.pages.has(e)) {
3151
- l = h.pages.get(e);
3145
+ for (const m of d.contexts.values())
3146
+ if (m.pages.has(e)) {
3147
+ c = m.pages.get(e);
3152
3148
  break;
3153
3149
  }
3154
- if (l) break;
3150
+ if (c) break;
3155
3151
  }
3156
- if (!l)
3152
+ if (!c)
3157
3153
  return {
3158
3154
  error: `Page "${e}" not found`
3159
3155
  };
3160
- if (l.domSnapshots.has(i))
3156
+ if (c.domSnapshots.has(i))
3161
3157
  return {
3162
3158
  error: `DOM snapshot "${i}" already exists in page "${e}"`
3163
3159
  };
@@ -3165,14 +3161,14 @@ async function tt(t, r, s) {
3165
3161
  return {
3166
3162
  error: "Either queryName or query must be provided, not both"
3167
3163
  };
3168
- let c, f = !1;
3164
+ let l, f = !1;
3169
3165
  if (n) {
3170
3166
  const d = u.domSnapshotQueries.get(n);
3171
3167
  if (!d)
3172
3168
  return {
3173
3169
  error: `DOM snapshot query "${n}" not found`
3174
3170
  };
3175
- c = d;
3171
+ l = d;
3176
3172
  } else if (a) {
3177
3173
  const d = await et(
3178
3174
  a,
@@ -3183,34 +3179,34 @@ async function tt(t, r, s) {
3183
3179
  return {
3184
3180
  error: d.error
3185
3181
  };
3186
- c = d.snapshotQuery, f = !0;
3182
+ l = d.snapshotQuery, f = !0;
3187
3183
  } else
3188
3184
  return {
3189
3185
  error: "Either queryName or query must be provided"
3190
3186
  };
3191
3187
  try {
3192
- const d = await l.page.evaluate(
3193
- (b) => {
3194
- const y = window.__mcp_playwright_tool_tx4byhar35_createDomSnapshotTreeRawDom;
3195
- if (!y)
3188
+ const d = await c.page.evaluate(
3189
+ (y) => {
3190
+ const w = window.__mcp_playwright_tool_tx4byhar35_createDomSnapshotTreeRawDom;
3191
+ if (!w)
3196
3192
  throw new Error("DOM snapshot global function not initialized");
3197
- const x = y(b);
3193
+ const S = w(y);
3198
3194
  return {
3199
- idToNode: Array.from(x.idToNode.entries()),
3200
- idToChildIds: Array.from(x.idToChildIds.entries())
3195
+ idToNode: Array.from(S.idToNode.entries()),
3196
+ idToChildIds: Array.from(S.idToChildIds.entries())
3201
3197
  };
3202
3198
  },
3203
- c
3204
- ), h = {
3199
+ l
3200
+ ), m = {
3205
3201
  idToNode: new Map(d.idToNode),
3206
3202
  idToChildIds: new Map(d.idToChildIds)
3207
- }, m = Lr(c, h), g = {
3203
+ }, g = Lr(l, m), p = {
3208
3204
  name: i,
3209
- query: c,
3210
- tree: m
3205
+ query: l,
3206
+ tree: g
3211
3207
  };
3212
- return l.domSnapshots.set(i, g), {
3213
- domSnapshot: g,
3208
+ return c.domSnapshots.set(i, p), {
3209
+ domSnapshot: p,
3214
3210
  queryCreated: f
3215
3211
  };
3216
3212
  } catch (d) {
@@ -3253,13 +3249,13 @@ class Ar {
3253
3249
  tokensGrouped: s.tokens
3254
3250
  } : (r.indexRange[1] = o, r.countGrouped += 1, r.countMatched += s.countMatched, r.tokensGrouped += s.tokens, r);
3255
3251
  }
3256
- const rt = p.object({
3257
- snapshotName: p.string().optional().describe("Name of previously created DOM snapshot, to use"),
3252
+ const rt = h.object({
3253
+ snapshotName: h.string().optional().describe("Name of previously created DOM snapshot, to use"),
3258
3254
  snapshot: oe.optional().describe(
3259
3255
  "DOM snapshot creation options JSON to automatically create snapshot"
3260
3256
  ),
3261
- parentUid: p.number().optional().describe("UID of parent node to browse. Omit to browse the root node"),
3262
- childsIndexRange: p.tuple([p.number(), p.number()]).optional().describe(
3257
+ parentUid: h.number().optional().describe("UID of parent node to browse. Omit to browse the root node"),
3258
+ childsIndexRange: h.tuple([h.number(), h.number()]).optional().describe(
3263
3259
  "Child index range to show [start, end]. Only use the exact ranges that appeared in previous snapshot results - do not modify, combine, or split them"
3264
3260
  )
3265
3261
  // maxCountTotal: z
@@ -3277,9 +3273,9 @@ async function qr(t, r, s) {
3277
3273
  let o;
3278
3274
  try {
3279
3275
  o = rt.parse(t);
3280
- } catch (g) {
3276
+ } catch (p) {
3281
3277
  return {
3282
- error: C(g)
3278
+ error: C(p)
3283
3279
  };
3284
3280
  }
3285
3281
  const {
@@ -3290,23 +3286,23 @@ async function qr(t, r, s) {
3290
3286
  // maxTokensTotal,
3291
3287
  // maxCountGroup,
3292
3288
  // maxTokensGroup,
3293
- } = o, i = 60, u = 1e3, l = 25, c = 900;
3289
+ } = o, i = 60, u = 1e3, c = 25, l = 900;
3294
3290
  if (!s.sessionId)
3295
3291
  return {
3296
3292
  error: "Session ID is required"
3297
3293
  };
3298
- const f = E(s.sessionId);
3294
+ const f = D(s.sessionId);
3299
3295
  if (e && n)
3300
3296
  return {
3301
3297
  error: "Either snapshotName or snapshot must be provided, not both"
3302
3298
  };
3303
- let d, h = !1, m = !1;
3299
+ let d, m = !1, g = !1;
3304
3300
  if (e) {
3305
- for (const g of f.browsers.values()) {
3306
- for (const b of g.contexts.values()) {
3307
- for (const y of b.pages.values())
3308
- if (y.domSnapshots.has(e)) {
3309
- d = y.domSnapshots.get(e);
3301
+ for (const p of f.browsers.values()) {
3302
+ for (const y of p.contexts.values()) {
3303
+ for (const w of y.pages.values())
3304
+ if (w.domSnapshots.has(e)) {
3305
+ d = w.domSnapshots.get(e);
3310
3306
  break;
3311
3307
  }
3312
3308
  if (d != null) break;
@@ -3318,46 +3314,46 @@ async function qr(t, r, s) {
3318
3314
  error: `DOM snapshot "${e}" not found`
3319
3315
  };
3320
3316
  } else if (n) {
3321
- const g = await tt(
3317
+ const p = await tt(
3322
3318
  n,
3323
3319
  r,
3324
3320
  s
3325
3321
  );
3326
- if (g.error != null)
3322
+ if (p.error != null)
3327
3323
  return {
3328
- error: g.error
3324
+ error: p.error
3329
3325
  };
3330
- d = g.domSnapshot, h = g.queryCreated, m = !0;
3326
+ d = p.domSnapshot, m = p.queryCreated, g = !0;
3331
3327
  } else
3332
3328
  return {
3333
3329
  error: "Either snapshotName or snapshot must be provided"
3334
3330
  };
3335
3331
  try {
3336
- const g = o.parentUid, b = qe({
3332
+ const p = o.parentUid, y = qe({
3337
3333
  tree: d.tree,
3338
3334
  request: {
3339
- parentNodeId: g,
3335
+ parentNodeId: p,
3340
3336
  childsIndexRange: a,
3341
3337
  limits: {
3342
3338
  maxCountTotal: i,
3343
3339
  maxTokensTotal: u,
3344
- maxCountGroup: l,
3345
- maxTokensGroup: c
3340
+ maxCountGroup: c,
3341
+ maxTokensGroup: l
3346
3342
  }
3347
3343
  },
3348
3344
  indexRangeGroupStrategy: new Ar()
3349
- }), y = Ge(b);
3345
+ }), w = Ge(y);
3350
3346
  return {
3351
3347
  domSnapshot: d,
3352
- queryCreated: h,
3353
- snapshotCreated: m,
3354
- parentUid: g,
3348
+ queryCreated: m,
3349
+ snapshotCreated: g,
3350
+ parentUid: p,
3355
3351
  childsIndexRange: a,
3356
- report: y
3352
+ report: w
3357
3353
  };
3358
- } catch (g) {
3354
+ } catch (p) {
3359
3355
  return {
3360
- error: `Failed to browse DOM snapshot: ${g instanceof Error ? g.message : "Unknown error"}`
3356
+ error: `Failed to browse DOM snapshot: ${p instanceof Error ? p.message : "Unknown error"}`
3361
3357
  };
3362
3358
  }
3363
3359
  }
@@ -3382,8 +3378,8 @@ function Gr(t, r) {
3382
3378
  `, n += `CSS Selector: ${e.domSnapshot.query.cssSelector}
3383
3379
  `, n += `Parent UID: ${e.parentUid ?? "null (root node)"}
3384
3380
  `, e.childsIndexRange) {
3385
- const [a, i] = e.childsIndexRange, l = (e.parentUid ? e.domSnapshot.tree.getNode(e.parentUid) : e.domSnapshot.tree.root).countChilds;
3386
- n += ` Showing indexes: ${a}-${i} of ${l}
3381
+ const [a, i] = e.childsIndexRange, c = (e.parentUid ? e.domSnapshot.tree.getNode(e.parentUid) : e.domSnapshot.tree.root).countChilds;
3382
+ n += ` Showing indexes: ${a}-${i} of ${c}
3387
3383
  `;
3388
3384
  }
3389
3385
  return n += `
@@ -3392,7 +3388,7 @@ ${e.report}`, n;
3392
3388
  );
3393
3389
  }
3394
3390
  function jr(t, r) {
3395
- r.browserCreate && wr(t, r), r.browserList && br(t, r), r.browserClose && Sr(t, r), r.contextCreate && $r(t, r), r.contextList && Mr(t, r), r.contextClose && vr(t, r), r.pageCreate && Nr(t, r), r.pageList && Er(t, r), r.pageClose && Br(t, r), r.pageGoto && Rr(t, r), r.domSnapshotQueryCreate && Pr(t, r), r.domSnapshotCreate && Ur(t, r), r.domSnapshotBrowse && Gr(t, r), console.log("Playwright manager");
3391
+ r.browserCreate && wr(t, r), r.browserList && br(t, r), r.browserClose && xr(t, r), r.contextCreate && $r(t, r), r.contextList && Mr(t, r), r.contextClose && vr(t, r), r.pageCreate && Nr(t, r), r.pageList && Dr(t, r), r.pageClose && Br(t, r), r.pageGoto && Rr(t, r), r.domSnapshotQueryCreate && Pr(t, r), r.domSnapshotCreate && Ur(t, r), r.domSnapshotBrowse && Gr(t, r), console.log("Playwright manager");
3396
3392
  }
3397
3393
  function _r(t) {
3398
3394
  const { logFilePath: r } = t;
@@ -3449,16 +3445,18 @@ function Qr(t, r) {
3449
3445
  });
3450
3446
  }
3451
3447
  function Hr(t, r) {
3452
- const s = t.address().family, o = t.address().port;
3453
- let e = t.address().address;
3454
- e === "::" ? e = "localhost" : s === "IPv6" && (e = `[${e}]`);
3455
- const n = `http://${s === "IPv6" ? `[${e}]` : e}:${o}`;
3448
+ if (!t.address())
3449
+ throw new Error("Server address is not available. Check your DNS and host configuration.");
3450
+ const o = t.address().family, e = t.address().port;
3451
+ let n = t.address().address;
3452
+ n === "::" ? n = "localhost" : o === "IPv6" && (n = `[${n}]`);
3453
+ const a = `http://${o === "IPv6" ? `[${n}]` : n}:${e}`;
3456
3454
  return `Project Tools - MCP Server Started
3457
3455
 
3458
3456
  Server Name: ${r.name}
3459
3457
  Server Version: ${r.version}
3460
- Server URL: ${n}/mcp
3461
- SSE Endpoint: ${n}/sse
3458
+ Server URL: ${a}/mcp
3459
+ SSE Endpoint: ${a}/sse
3462
3460
 
3463
3461
  Log File: ${T.resolve(r.logFilePath)}`;
3464
3462
  }
@@ -3499,8 +3497,8 @@ async function ps(t) {
3499
3497
  ), e;
3500
3498
  }
3501
3499
  export {
3502
- ms as A,
3503
- hs as S,
3500
+ hs as A,
3501
+ ms as S,
3504
3502
  fs as a,
3505
3503
  ds as b,
3506
3504
  Zt as p,