fleetlens 0.16.6 → 0.16.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.
Files changed (118) hide show
  1. package/app/apps/web/.next/BUILD_ID +1 -1
  2. package/app/apps/web/.next/build-manifest.json +3 -3
  3. package/app/apps/web/.next/prerender-manifest.json +3 -3
  4. package/app/apps/web/.next/server/app/_global-error.html +1 -1
  5. package/app/apps/web/.next/server/app/_global-error.rsc +1 -1
  6. package/app/apps/web/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  7. package/app/apps/web/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  8. package/app/apps/web/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  9. package/app/apps/web/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  10. package/app/apps/web/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  11. package/app/apps/web/.next/server/app/_not-found/page.js.nft.json +1 -1
  12. package/app/apps/web/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  13. package/app/apps/web/.next/server/app/agent/page.js.nft.json +1 -1
  14. package/app/apps/web/.next/server/app/agent/page_client-reference-manifest.js +1 -1
  15. package/app/apps/web/.next/server/app/api/agent/chats/[id]/messages/route.js.nft.json +1 -1
  16. package/app/apps/web/.next/server/app/api/agent/index/route.js.nft.json +1 -1
  17. package/app/apps/web/.next/server/app/api/agent/mcp/route.js.nft.json +1 -1
  18. package/app/apps/web/.next/server/app/api/agent/suggestions/route.js.nft.json +1 -1
  19. package/app/apps/web/.next/server/app/api/ask/route.js.nft.json +1 -1
  20. package/app/apps/web/.next/server/app/api/digest/day/[date]/route.js.nft.json +1 -1
  21. package/app/apps/web/.next/server/app/api/digest/month/[yearMonth]/route.js.nft.json +1 -1
  22. package/app/apps/web/.next/server/app/api/digest/month-index/route.js.nft.json +1 -1
  23. package/app/apps/web/.next/server/app/api/digest/week/[startDate]/route.js.nft.json +1 -1
  24. package/app/apps/web/.next/server/app/api/digest/week-index/route.js.nft.json +1 -1
  25. package/app/apps/web/.next/server/app/api/pdf/[key]/route.js.nft.json +1 -1
  26. package/app/apps/web/.next/server/app/api/projects/open-folder/route.js.nft.json +1 -1
  27. package/app/apps/web/.next/server/app/api/runs/[runId]/route.js.nft.json +1 -1
  28. package/app/apps/web/.next/server/app/api/runs/[runId]/stream/route.js.nft.json +1 -1
  29. package/app/apps/web/.next/server/app/api/settings/credentials/route.js.nft.json +1 -1
  30. package/app/apps/web/.next/server/app/api/settings/route.js.nft.json +1 -1
  31. package/app/apps/web/.next/server/app/changelog/page.js.nft.json +1 -1
  32. package/app/apps/web/.next/server/app/changelog/page_client-reference-manifest.js +1 -1
  33. package/app/apps/web/.next/server/app/day/[date]/page.js.nft.json +1 -1
  34. package/app/apps/web/.next/server/app/day/[date]/page_client-reference-manifest.js +1 -1
  35. package/app/apps/web/.next/server/app/day/page.js.nft.json +1 -1
  36. package/app/apps/web/.next/server/app/day/page_client-reference-manifest.js +1 -1
  37. package/app/apps/web/.next/server/app/digest/[date]/page.js.nft.json +1 -1
  38. package/app/apps/web/.next/server/app/digest/[date]/page_client-reference-manifest.js +1 -1
  39. package/app/apps/web/.next/server/app/digest/page.js.nft.json +1 -1
  40. package/app/apps/web/.next/server/app/digest/page_client-reference-manifest.js +1 -1
  41. package/app/apps/web/.next/server/app/insights/[key]/page.js.nft.json +1 -1
  42. package/app/apps/web/.next/server/app/insights/[key]/page_client-reference-manifest.js +1 -1
  43. package/app/apps/web/.next/server/app/insights/page.js.nft.json +1 -1
  44. package/app/apps/web/.next/server/app/insights/page_client-reference-manifest.js +1 -1
  45. package/app/apps/web/.next/server/app/page.js.nft.json +1 -1
  46. package/app/apps/web/.next/server/app/page_client-reference-manifest.js +1 -1
  47. package/app/apps/web/.next/server/app/parallelism/page.js.nft.json +1 -1
  48. package/app/apps/web/.next/server/app/parallelism/page_client-reference-manifest.js +1 -1
  49. package/app/apps/web/.next/server/app/print/[key]/page.js.nft.json +1 -1
  50. package/app/apps/web/.next/server/app/print/[key]/page_client-reference-manifest.js +1 -1
  51. package/app/apps/web/.next/server/app/projects/[slug]/page.js.nft.json +1 -1
  52. package/app/apps/web/.next/server/app/projects/[slug]/page_client-reference-manifest.js +1 -1
  53. package/app/apps/web/.next/server/app/projects/page.js.nft.json +1 -1
  54. package/app/apps/web/.next/server/app/projects/page_client-reference-manifest.js +1 -1
  55. package/app/apps/web/.next/server/app/runs/page.js.nft.json +1 -1
  56. package/app/apps/web/.next/server/app/runs/page_client-reference-manifest.js +1 -1
  57. package/app/apps/web/.next/server/app/sessions/[id]/page.js.nft.json +1 -1
  58. package/app/apps/web/.next/server/app/sessions/[id]/page_client-reference-manifest.js +1 -1
  59. package/app/apps/web/.next/server/app/sessions/page.js.nft.json +1 -1
  60. package/app/apps/web/.next/server/app/sessions/page_client-reference-manifest.js +1 -1
  61. package/app/apps/web/.next/server/app/settings/page.js.nft.json +1 -1
  62. package/app/apps/web/.next/server/app/settings/page_client-reference-manifest.js +1 -1
  63. package/app/apps/web/.next/server/app/team/onboarding/page.js.nft.json +1 -1
  64. package/app/apps/web/.next/server/app/team/onboarding/page_client-reference-manifest.js +1 -1
  65. package/app/apps/web/.next/server/app/team/page.js.nft.json +1 -1
  66. package/app/apps/web/.next/server/app/team/page_client-reference-manifest.js +1 -1
  67. package/app/apps/web/.next/server/app/usage/page.js.nft.json +1 -1
  68. package/app/apps/web/.next/server/app/usage/page_client-reference-manifest.js +1 -1
  69. package/app/apps/web/.next/server/chunks/node_modules_next_dist_esm_build_templates_app-route_0sr4wr_.js +1 -1
  70. package/app/apps/web/.next/server/chunks/packages_parser_dist_06d9se1._.js +1 -1
  71. package/app/apps/web/.next/server/chunks/packages_parser_dist_10ihc3~._.js +1 -1
  72. package/app/apps/web/.next/server/chunks/ssr/[root-of-the-server]__0-zxvif._.js +1 -1
  73. package/app/apps/web/.next/server/chunks/ssr/[root-of-the-server]__01wj6p0._.js +1 -1
  74. package/app/apps/web/.next/server/chunks/ssr/[root-of-the-server]__0f3q8gt._.js +1 -1
  75. package/app/apps/web/.next/server/chunks/ssr/[root-of-the-server]__0ygwqfa._.js +1 -1
  76. package/app/apps/web/.next/server/chunks/ssr/[root-of-the-server]__0z0wa91._.js +1 -1
  77. package/app/apps/web/.next/server/chunks/ssr/[root-of-the-server]__12s3gv9._.js +1 -1
  78. package/app/apps/web/.next/server/chunks/ssr/_0k8yioi._.js +1 -1
  79. package/app/apps/web/.next/server/chunks/ssr/apps_web_0epqfet._.js +1 -1
  80. package/app/apps/web/.next/server/chunks/ssr/apps_web_0~aj0~u._.js +1 -1
  81. package/app/apps/web/.next/server/chunks/ssr/apps_web_components_0x014hn._.js +1 -1
  82. package/app/apps/web/.next/server/chunks/ssr/apps_web_components_usage-charts-dashboard_tsx_0bgr_uv._.js +1 -1
  83. package/app/apps/web/.next/server/chunks/ssr/apps_web_lib_changelog_ts_0n7_p1d._.js +1 -1
  84. package/app/apps/web/.next/server/chunks/ssr/apps_web_lib_changelog_ts_0nb5_-s._.js +1 -1
  85. package/app/apps/web/.next/server/chunks/ssr/packages_parser_dist_0mx_509._.js +1 -1
  86. package/app/apps/web/.next/server/middleware-build-manifest.js +3 -3
  87. package/app/apps/web/.next/server/middleware-manifest.json +5 -5
  88. package/app/apps/web/.next/server/pages/500.html +1 -1
  89. package/app/apps/web/.next/server/server-reference-manifest.js +1 -1
  90. package/app/apps/web/.next/server/server-reference-manifest.json +1 -1
  91. package/app/apps/web/.next/static/chunks/01ky0t_.38u4u.js +14 -0
  92. package/app/apps/web/.next/static/chunks/0d~6j~aj2vr1t.js +1 -0
  93. package/app/apps/web/.next/static/chunks/{0-z49mtd-zwgv.js → 0~opjw4gew2-w.js} +1 -1
  94. package/app/apps/web/app/settings/page.tsx +1 -1
  95. package/app/apps/web/app/usage/page.tsx +178 -13
  96. package/app/apps/web/components/menubar-install-banner.tsx +1 -1
  97. package/app/apps/web/components/menubar-install.tsx +1 -1
  98. package/app/apps/web/components/usage-chart-range.tsx +9 -3
  99. package/app/apps/web/components/usage-chart.tsx +9 -3
  100. package/app/apps/web/components/usage-charts-dashboard.tsx +10 -3
  101. package/app/apps/web/lib/changelog-data.generated.ts +1 -1
  102. package/app/apps/web/lib/format.test.ts +10 -0
  103. package/app/apps/web/lib/format.ts +6 -4
  104. package/app/apps/web/lib/usage-data.ts +11 -0
  105. package/app/apps/web/lib/usage-display.test.ts +79 -0
  106. package/app/apps/web/lib/usage-display.ts +59 -0
  107. package/app/apps/web/package.json +1 -1
  108. package/app/apps/web/tsconfig.tsbuildinfo +1 -1
  109. package/dist/daemon-worker.js +994 -328
  110. package/dist/index.js +1085 -413
  111. package/menubar/FleetlensMenubar.app/Contents/Info.plist +2 -2
  112. package/menubar/FleetlensMenubar.app/Contents/MacOS/FleetlensMenubar +0 -0
  113. package/package.json +1 -1
  114. package/app/apps/web/.next/static/chunks/0rrcj195v1nd..js +0 -1
  115. package/app/apps/web/.next/static/chunks/1350ox0.qybjo.js +0 -14
  116. /package/app/apps/web/.next/static/{8slBxbEObd72azKwDvtmy → yxbgwGc3dXx7HY0GSHJeG}/_buildManifest.js +0 -0
  117. /package/app/apps/web/.next/static/{8slBxbEObd72azKwDvtmy → yxbgwGc3dXx7HY0GSHJeG}/_clientMiddlewareManifest.js +0 -0
  118. /package/app/apps/web/.next/static/{8slBxbEObd72azKwDvtmy → yxbgwGc3dXx7HY0GSHJeG}/_ssgManifest.js +0 -0
package/dist/index.js CHANGED
@@ -675,7 +675,7 @@ function getAgentMetadata(kind) {
675
675
  function isAgentKind(s) {
676
676
  return typeof s === "string" && KNOWN_AGENT_KINDS.has(s);
677
677
  }
678
- var CLAUDE_CODE_METADATA, CODEX_METADATA, GEMINI_METADATA, ANTIGRAVITY_METADATA, COWORK_METADATA, ZAI_METADATA, GROK_METADATA, agentMetadata, KNOWN_AGENT_KINDS;
678
+ var CLAUDE_CODE_METADATA, CODEX_METADATA, COPILOT_METADATA, GEMINI_METADATA, ANTIGRAVITY_METADATA, COWORK_METADATA, ZAI_METADATA, GROK_METADATA, agentMetadata, KNOWN_AGENT_KINDS;
679
679
  var init_agent_metadata = __esm({
680
680
  "../parser/dist/agent-metadata.js"() {
681
681
  "use strict";
@@ -693,6 +693,13 @@ var init_agent_metadata = __esm({
693
693
  accentColor: "rgb(16, 163, 127)",
694
694
  iconChar: "\u25C6"
695
695
  };
696
+ COPILOT_METADATA = {
697
+ kind: "copilot",
698
+ displayName: "GitHub Copilot CLI",
699
+ shortLabel: "Copilot",
700
+ accentColor: "rgb(137, 87, 229)",
701
+ iconChar: "\u221E"
702
+ };
696
703
  GEMINI_METADATA = {
697
704
  kind: "gemini",
698
705
  displayName: "Gemini CLI",
@@ -732,6 +739,7 @@ var init_agent_metadata = __esm({
732
739
  agentMetadata = [
733
740
  CLAUDE_CODE_METADATA,
734
741
  CODEX_METADATA,
742
+ COPILOT_METADATA,
735
743
  GEMINI_METADATA,
736
744
  ANTIGRAVITY_METADATA,
737
745
  COWORK_METADATA,
@@ -1593,11 +1601,11 @@ function defaultBranch(commonDir) {
1593
1601
  }
1594
1602
  return void 0;
1595
1603
  }
1596
- function readGitFolder(path10) {
1597
- if (!existsSync(path10))
1604
+ function readGitFolder(path11) {
1605
+ if (!existsSync(path11))
1598
1606
  return { exists: false, isWorktree: false };
1599
1607
  try {
1600
- const git = nearestDotGit(realpathOrSelf(path10));
1608
+ const git = nearestDotGit(realpathOrSelf(path11));
1601
1609
  if (!git)
1602
1610
  return { exists: true, isWorktree: false };
1603
1611
  const projectRoot = projectRootFromCommonDir(git.commonDir);
@@ -3379,24 +3387,442 @@ var init_codex = __esm({
3379
3387
  }
3380
3388
  });
3381
3389
 
3382
- // ../parser/dist/gemini.js
3390
+ // ../parser/dist/copilot.js
3383
3391
  import { promises as fs3 } from "node:fs";
3384
3392
  import os3 from "node:os";
3385
3393
  import path3 from "node:path";
3386
- async function safeReaddir2(p) {
3387
- return fs3.readdir(p).catch(() => []);
3394
+ function recordOf(value) {
3395
+ return typeof value === "object" && value !== null ? value : void 0;
3396
+ }
3397
+ function stringOf(value) {
3398
+ return typeof value === "string" ? value : void 0;
3399
+ }
3400
+ function numberOf2(value) {
3401
+ return typeof value === "number" && Number.isFinite(value) ? value : void 0;
3402
+ }
3403
+ function emptyUsage2() {
3404
+ return { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 };
3405
+ }
3406
+ function previewOf2(value) {
3407
+ const text = typeof value === "string" ? value : JSON.stringify(value ?? "");
3408
+ return text.replace(/\s+/g, " ").trim().slice(0, 200);
3409
+ }
3410
+ function tokenCount(details, key) {
3411
+ return numberOf2(recordOf(details?.[key])?.tokenCount);
3412
+ }
3413
+ function syntheticProjectDir(cwd) {
3414
+ return cwd ? cwd.replace(/^\//, "-").replace(/\//g, "-") : "(unknown)";
3388
3415
  }
3389
3416
  async function listSessionFiles(root) {
3417
+ const entries2 = await fs3.readdir(root, { withFileTypes: true }).catch(() => []);
3418
+ const out = [];
3419
+ for (const entry of entries2) {
3420
+ if (!entry.isDirectory())
3421
+ continue;
3422
+ const filePath = path3.join(root, entry.name, "events.jsonl");
3423
+ const stat = await fs3.stat(filePath).catch(() => null);
3424
+ if (!stat?.isFile())
3425
+ continue;
3426
+ out.push({
3427
+ filePath,
3428
+ sessionId: entry.name,
3429
+ mtimeMs: stat.mtimeMs,
3430
+ sizeBytes: stat.size
3431
+ });
3432
+ }
3433
+ return out;
3434
+ }
3435
+ async function readJsonl2(filePath) {
3436
+ const raw = await fs3.readFile(filePath, "utf8");
3437
+ const out = [];
3438
+ for (const line of raw.split("\n")) {
3439
+ const trimmed = line.trim();
3440
+ if (!trimmed)
3441
+ continue;
3442
+ try {
3443
+ out.push(JSON.parse(trimmed));
3444
+ } catch {
3445
+ }
3446
+ }
3447
+ return out;
3448
+ }
3449
+ function computeActiveSegments3(timestamps) {
3450
+ const sorted = [...new Set(timestamps)].sort((a, b) => a - b);
3451
+ if (sorted.length === 0)
3452
+ return [];
3453
+ const segments = [];
3454
+ let start2 = sorted[0];
3455
+ let end = start2;
3456
+ for (let i = 1; i < sorted.length; i++) {
3457
+ const next = sorted[i];
3458
+ if (next - end > IDLE_GAP_MS2) {
3459
+ segments.push({ startMs: start2, endMs: end });
3460
+ start2 = next;
3461
+ }
3462
+ end = next;
3463
+ }
3464
+ segments.push({ startMs: start2, endMs: end });
3465
+ return segments;
3466
+ }
3467
+ function parseSession(file, lines) {
3468
+ const records = lines.map(recordOf).filter((line) => line !== void 0);
3469
+ const executionCallIds = /* @__PURE__ */ new Set();
3470
+ for (const record of records) {
3471
+ if (record.type !== "tool.execution_start")
3472
+ continue;
3473
+ const callId = stringOf(recordOf(record.data)?.toolCallId);
3474
+ if (callId)
3475
+ executionCallIds.add(callId);
3476
+ }
3477
+ const events = [];
3478
+ const timestamps = [];
3479
+ const totalUsage = emptyUsage2();
3480
+ let firstMs;
3481
+ let lastMs;
3482
+ let cwd;
3483
+ let repository;
3484
+ let gitBranch;
3485
+ let model;
3486
+ let firstUserPreview;
3487
+ let lastUserPreview;
3488
+ let lastAgentPreview;
3489
+ let toolCallCount = 0;
3490
+ let turnCount = 0;
3491
+ let observedOutput = 0;
3492
+ let sawShutdown = false;
3493
+ let linesAdded;
3494
+ let linesRemoved;
3495
+ let filesEdited;
3496
+ let idx = 0;
3497
+ function push(event) {
3498
+ events.push({ index: idx++, ...event });
3499
+ }
3500
+ for (const obj of records) {
3501
+ const type = stringOf(obj.type) ?? "";
3502
+ const data = recordOf(obj.data) ?? {};
3503
+ const timestamp = stringOf(obj.timestamp);
3504
+ if (timestamp) {
3505
+ const ms = Date.parse(timestamp);
3506
+ if (Number.isFinite(ms)) {
3507
+ timestamps.push(ms);
3508
+ firstMs = firstMs === void 0 ? ms : Math.min(firstMs, ms);
3509
+ lastMs = lastMs === void 0 ? ms : Math.max(lastMs, ms);
3510
+ }
3511
+ }
3512
+ if (type === "session.start") {
3513
+ const context = recordOf(data.context);
3514
+ cwd = stringOf(context?.cwd) ?? cwd;
3515
+ repository = stringOf(context?.repository) ?? repository;
3516
+ gitBranch = stringOf(context?.branch) ?? gitBranch;
3517
+ push({
3518
+ timestamp,
3519
+ role: "meta",
3520
+ rawType: type,
3521
+ preview: "Copilot session started",
3522
+ blocks: [],
3523
+ raw: obj
3524
+ });
3525
+ continue;
3526
+ }
3527
+ if (type === "session.model_change") {
3528
+ const selected = stringOf(data.newModel);
3529
+ if (selected && selected !== "auto")
3530
+ model = selected;
3531
+ } else if (type === "session.auto_mode_resolved") {
3532
+ model = stringOf(data.chosenModel) ?? model;
3533
+ } else if (type === "assistant.turn_start" || type === "assistant.message") {
3534
+ model = stringOf(data.model) ?? model;
3535
+ }
3536
+ if (type === "system.message") {
3537
+ push({
3538
+ timestamp,
3539
+ role: "system",
3540
+ rawType: type,
3541
+ preview: "Copilot system instructions",
3542
+ blocks: [],
3543
+ raw: obj
3544
+ });
3545
+ continue;
3546
+ }
3547
+ if (type === "user.message") {
3548
+ const text = stringOf(data.content) ?? "";
3549
+ const preview = previewOf2(text);
3550
+ if (text && !isFrameworkInjectedUserInput(text)) {
3551
+ firstUserPreview ??= preview;
3552
+ lastUserPreview = preview;
3553
+ turnCount += 1;
3554
+ }
3555
+ push({
3556
+ timestamp,
3557
+ role: "user",
3558
+ rawType: type,
3559
+ preview,
3560
+ blocks: text ? [{ type: "text", text }] : [],
3561
+ raw: obj
3562
+ });
3563
+ continue;
3564
+ }
3565
+ if (type === "assistant.message") {
3566
+ const text = stringOf(data.content) ?? "";
3567
+ const outputTokens = numberOf2(data.outputTokens) ?? 0;
3568
+ observedOutput += outputTokens;
3569
+ if (text) {
3570
+ const preview = previewOf2(text);
3571
+ lastAgentPreview = preview;
3572
+ push({
3573
+ timestamp,
3574
+ role: "agent",
3575
+ rawType: type,
3576
+ messageId: stringOf(data.messageId),
3577
+ preview,
3578
+ blocks: [{ type: "text", text }],
3579
+ model,
3580
+ raw: obj
3581
+ });
3582
+ }
3583
+ const requests = Array.isArray(data.toolRequests) ? data.toolRequests : [];
3584
+ for (const requestValue of requests) {
3585
+ const request = recordOf(requestValue);
3586
+ if (!request)
3587
+ continue;
3588
+ const callId = stringOf(request.toolCallId);
3589
+ if (callId && executionCallIds.has(callId))
3590
+ continue;
3591
+ const name = stringOf(request.name) ?? "(unknown)";
3592
+ const input = recordOf(request.arguments) ?? request.arguments ?? null;
3593
+ toolCallCount += 1;
3594
+ push({
3595
+ timestamp,
3596
+ role: "tool-call",
3597
+ rawType: "assistant.message/tool_request",
3598
+ preview: `${name}(${previewOf2(input).slice(0, 80)})`,
3599
+ blocks: [{ type: "tool_use", id: callId ?? `copilot-${idx}`, name, input }],
3600
+ toolName: name,
3601
+ toolUseId: callId,
3602
+ model,
3603
+ raw: obj
3604
+ });
3605
+ }
3606
+ continue;
3607
+ }
3608
+ if (type === "tool.execution_start") {
3609
+ const callId = stringOf(data.toolCallId);
3610
+ const name = stringOf(data.toolName) ?? "(unknown)";
3611
+ const input = data.arguments ?? null;
3612
+ toolCallCount += 1;
3613
+ push({
3614
+ timestamp,
3615
+ role: "tool-call",
3616
+ rawType: type,
3617
+ preview: `${name}(${previewOf2(input).slice(0, 80)})`,
3618
+ blocks: [{ type: "tool_use", id: callId ?? `copilot-${idx}`, name, input }],
3619
+ toolName: name,
3620
+ toolUseId: callId,
3621
+ model: stringOf(data.model) ?? model,
3622
+ raw: obj
3623
+ });
3624
+ continue;
3625
+ }
3626
+ if (type === "tool.execution_complete") {
3627
+ const callId = stringOf(data.toolCallId);
3628
+ const resultRecord = recordOf(data.result);
3629
+ const result = resultRecord && "content" in resultRecord ? resultRecord.content : data.result;
3630
+ const success = data.success !== false;
3631
+ push({
3632
+ timestamp,
3633
+ role: "tool-result",
3634
+ rawType: type,
3635
+ preview: previewOf2(result),
3636
+ blocks: [{ type: "tool_result", tool_use_id: callId ?? "", content: result, is_error: !success }],
3637
+ toolUseId: callId,
3638
+ toolResult: data.result,
3639
+ raw: obj
3640
+ });
3641
+ continue;
3642
+ }
3643
+ if (type === "assistant.reasoning") {
3644
+ const text = stringOf(data.content) ?? "";
3645
+ push({
3646
+ timestamp,
3647
+ role: "agent-thinking",
3648
+ rawType: type,
3649
+ preview: previewOf2(text),
3650
+ blocks: text ? [{ type: "thinking", thinking: text }] : [],
3651
+ model,
3652
+ raw: obj
3653
+ });
3654
+ continue;
3655
+ }
3656
+ if (type === "session.shutdown") {
3657
+ sawShutdown = true;
3658
+ model = stringOf(data.currentModel) ?? model;
3659
+ const details = recordOf(data.tokenDetails);
3660
+ totalUsage.input = tokenCount(details, "input") ?? totalUsage.input;
3661
+ totalUsage.output = tokenCount(details, "output") ?? observedOutput;
3662
+ totalUsage.cacheRead = tokenCount(details, "cache_read") ?? totalUsage.cacheRead;
3663
+ totalUsage.cacheWrite = tokenCount(details, "cache_write") ?? totalUsage.cacheWrite;
3664
+ const changes = recordOf(data.codeChanges);
3665
+ linesAdded = numberOf2(changes?.linesAdded);
3666
+ linesRemoved = numberOf2(changes?.linesRemoved);
3667
+ const modified = changes?.filesModified;
3668
+ filesEdited = Array.isArray(modified) ? modified.length : void 0;
3669
+ }
3670
+ push({
3671
+ timestamp,
3672
+ role: "meta",
3673
+ rawType: type,
3674
+ preview: "",
3675
+ blocks: [],
3676
+ raw: obj
3677
+ });
3678
+ }
3679
+ if (totalUsage.output === 0)
3680
+ totalUsage.output = observedOutput;
3681
+ if (totalUsage.input || totalUsage.output || totalUsage.cacheRead || totalUsage.cacheWrite) {
3682
+ const usageEvent = [...events].reverse().find((event) => event.role === "agent" || event.role === "agent-thinking" || event.role === "tool-call");
3683
+ if (usageEvent) {
3684
+ usageEvent.messageId = `copilot-${file.sessionId}-total`;
3685
+ usageEvent.usage = { ...totalUsage };
3686
+ }
3687
+ }
3688
+ const firstTimestamp = firstMs === void 0 ? void 0 : new Date(firstMs).toISOString();
3689
+ const lastTimestamp = lastMs === void 0 ? void 0 : new Date(lastMs).toISOString();
3690
+ if (firstMs !== void 0) {
3691
+ let previousMs;
3692
+ for (const event of events) {
3693
+ if (!event.timestamp)
3694
+ continue;
3695
+ const ms = Date.parse(event.timestamp);
3696
+ if (!Number.isFinite(ms))
3697
+ continue;
3698
+ event.tOffsetMs = Math.max(0, ms - firstMs);
3699
+ if (previousMs !== void 0)
3700
+ event.gapMs = Math.max(0, ms - previousMs);
3701
+ previousMs = ms;
3702
+ }
3703
+ }
3704
+ const activeSegments = computeActiveSegments3(timestamps);
3705
+ const airTimeMs = activeSegments.reduce((sum, segment) => sum + segment.endMs - segment.startMs, 0);
3706
+ const project = cwd ? resolveProjectIdentity(cwd) : void 0;
3707
+ const repoName = project?.repoName ?? repository?.split("/").filter(Boolean).at(-1);
3708
+ const meta = {
3709
+ agent: "copilot",
3710
+ id: file.sessionId,
3711
+ filePath: file.filePath,
3712
+ projectName: project?.projectName ?? cwd ?? "(unknown)",
3713
+ worktreeName: project?.worktreeName,
3714
+ repoName,
3715
+ projectDir: syntheticProjectDir(cwd),
3716
+ sessionId: file.sessionId,
3717
+ firstTimestamp,
3718
+ lastTimestamp,
3719
+ lastActivityMs: file.mtimeMs,
3720
+ durationMs: firstMs !== void 0 && lastMs !== void 0 ? lastMs - firstMs : void 0,
3721
+ eventCount: events.length,
3722
+ model,
3723
+ cwd,
3724
+ gitBranch,
3725
+ totalUsage,
3726
+ status: sawShutdown || Date.now() - file.mtimeMs > IDLE_GAP_MS2 ? "idle" : "running",
3727
+ firstUserPreview,
3728
+ lastUserPreview,
3729
+ lastAgentPreview,
3730
+ toolCallCount,
3731
+ turnCount,
3732
+ linesAdded,
3733
+ linesRemoved,
3734
+ filesEdited,
3735
+ airTimeMs,
3736
+ activeSegments
3737
+ };
3738
+ return { meta, events };
3739
+ }
3740
+ function clearCopilotCaches() {
3741
+ metaCache3.clear();
3742
+ detailCache3.clear();
3743
+ }
3744
+ async function scanCopilot(root) {
3745
+ const files = await listSessionFiles(root);
3746
+ const out = [];
3747
+ for (const file of files) {
3748
+ const cached = metaCache3.get(file.filePath);
3749
+ if (cached && cached.mtimeMs === file.mtimeMs && cached.sizeBytes === file.sizeBytes) {
3750
+ out.push({ file, meta: cached.meta });
3751
+ continue;
3752
+ }
3753
+ try {
3754
+ const lines = await readJsonl2(file.filePath);
3755
+ const { meta } = parseSession(file, lines);
3756
+ metaCache3.set(file.filePath, { meta, mtimeMs: file.mtimeMs, sizeBytes: file.sizeBytes });
3757
+ out.push({ file, meta });
3758
+ } catch {
3759
+ }
3760
+ }
3761
+ return out;
3762
+ }
3763
+ async function listCopilotSessions(opts = {}) {
3764
+ const root = opts.root ?? DEFAULT_COPILOT_ROOT;
3765
+ const sessions = (await scanCopilot(root)).map((entry) => entry.meta);
3766
+ sessions.sort((a, b) => (b.firstTimestamp ?? "").localeCompare(a.firstTimestamp ?? ""));
3767
+ return opts.limit === void 0 ? sessions : sessions.slice(0, opts.limit);
3768
+ }
3769
+ async function getCopilotSession(id, opts = {}) {
3770
+ const root = opts.root ?? DEFAULT_COPILOT_ROOT;
3771
+ const entry = (await scanCopilot(root)).find((candidate) => candidate.meta.id === id);
3772
+ if (!entry)
3773
+ return null;
3774
+ const cached = detailCache3.get(entry.file.filePath);
3775
+ if (cached && cached.mtimeMs === entry.file.mtimeMs && cached.sizeBytes === entry.file.sizeBytes) {
3776
+ return cached.detail;
3777
+ }
3778
+ const lines = await readJsonl2(entry.file.filePath);
3779
+ const { meta, events } = parseSession(entry.file, lines);
3780
+ const detail = { ...meta, events };
3781
+ detailCache3.set(entry.file.filePath, {
3782
+ detail,
3783
+ mtimeMs: entry.file.mtimeMs,
3784
+ sizeBytes: entry.file.sizeBytes
3785
+ });
3786
+ return detail;
3787
+ }
3788
+ function copilotSessionLocalDay(meta) {
3789
+ if (!meta.firstTimestamp)
3790
+ return void 0;
3791
+ const ms = Date.parse(meta.firstTimestamp);
3792
+ return Number.isFinite(ms) ? toLocalDay(ms) : void 0;
3793
+ }
3794
+ var DEFAULT_COPILOT_ROOT, IDLE_GAP_MS2, metaCache3, detailCache3;
3795
+ var init_copilot = __esm({
3796
+ "../parser/dist/copilot.js"() {
3797
+ "use strict";
3798
+ init_analytics();
3799
+ init_git_project();
3800
+ init_user_input();
3801
+ DEFAULT_COPILOT_ROOT = path3.join(os3.homedir(), ".copilot", "session-state");
3802
+ IDLE_GAP_MS2 = 3 * 60 * 1e3;
3803
+ metaCache3 = /* @__PURE__ */ new Map();
3804
+ detailCache3 = /* @__PURE__ */ new Map();
3805
+ }
3806
+ });
3807
+
3808
+ // ../parser/dist/gemini.js
3809
+ import { promises as fs4 } from "node:fs";
3810
+ import os4 from "node:os";
3811
+ import path4 from "node:path";
3812
+ async function safeReaddir2(p) {
3813
+ return fs4.readdir(p).catch(() => []);
3814
+ }
3815
+ async function listSessionFiles2(root) {
3390
3816
  const out = [];
3391
3817
  const slugs = await safeReaddir2(root);
3392
3818
  for (const slug of slugs) {
3393
- const chatsDir = path3.join(root, slug, "chats");
3819
+ const chatsDir = path4.join(root, slug, "chats");
3394
3820
  const entries2 = await safeReaddir2(chatsDir);
3395
3821
  for (const entry of entries2) {
3396
3822
  if (!SESSION_FILE_RE.test(entry))
3397
3823
  continue;
3398
- const full = path3.join(chatsDir, entry);
3399
- const stat = await fs3.stat(full).catch(() => null);
3824
+ const full = path4.join(chatsDir, entry);
3825
+ const stat = await fs4.stat(full).catch(() => null);
3400
3826
  if (!stat || !stat.isFile())
3401
3827
  continue;
3402
3828
  const filenameId = entry.replace(/\.(jsonl|json)$/, "").split("-").pop() ?? entry;
@@ -3413,13 +3839,13 @@ async function listSessionFiles(root) {
3413
3839
  return out;
3414
3840
  }
3415
3841
  async function loadSlugToCwd() {
3416
- const stat = await fs3.stat(GEMINI_PROJECTS_FILE).catch(() => null);
3842
+ const stat = await fs4.stat(GEMINI_PROJECTS_FILE).catch(() => null);
3417
3843
  if (!stat)
3418
3844
  return /* @__PURE__ */ new Map();
3419
3845
  if (projectsCache && projectsCache.mtimeMs === stat.mtimeMs) {
3420
3846
  return projectsCache.slugToCwd;
3421
3847
  }
3422
- const raw = await fs3.readFile(GEMINI_PROJECTS_FILE, "utf8").catch(() => "");
3848
+ const raw = await fs4.readFile(GEMINI_PROJECTS_FILE, "utf8").catch(() => "");
3423
3849
  let parsed;
3424
3850
  try {
3425
3851
  parsed = JSON.parse(raw);
@@ -3444,7 +3870,7 @@ function isMessageRecord(o) {
3444
3870
  return !!o && typeof o === "object" && typeof o.id === "string" && typeof o.type === "string";
3445
3871
  }
3446
3872
  async function readAndReplay(file) {
3447
- const raw = await fs3.readFile(file.filePath, "utf8");
3873
+ const raw = await fs4.readFile(file.filePath, "utf8");
3448
3874
  if (file.format === "legacy-json") {
3449
3875
  let blob;
3450
3876
  try {
@@ -3519,10 +3945,10 @@ async function readAndReplay(file) {
3519
3945
  }
3520
3946
  return { meta, messages };
3521
3947
  }
3522
- function emptyUsage2() {
3948
+ function emptyUsage3() {
3523
3949
  return { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 };
3524
3950
  }
3525
- function previewOf2(text) {
3951
+ function previewOf3(text) {
3526
3952
  return text.replace(/\s+/g, " ").trim().slice(0, 200);
3527
3953
  }
3528
3954
  function flattenContent(c) {
@@ -3561,12 +3987,12 @@ function flattenContent(c) {
3561
3987
  function truncate3(s, n) {
3562
3988
  return s.length <= n ? s : s.slice(0, n - 1) + "\u2026";
3563
3989
  }
3564
- async function parseSession(file) {
3990
+ async function parseSession2(file) {
3565
3991
  const { meta: metaRec, messages } = await readAndReplay(file);
3566
3992
  const slugToCwd = await loadSlugToCwd();
3567
3993
  const cwd = slugToCwd.get(file.slug);
3568
3994
  const events = [];
3569
- const totalUsage = emptyUsage2();
3995
+ const totalUsage = emptyUsage3();
3570
3996
  let firstTimestamp;
3571
3997
  let lastTimestamp;
3572
3998
  let model;
@@ -3592,7 +4018,7 @@ async function parseSession(file) {
3592
4018
  const ts = msg.timestamp;
3593
4019
  if (msg.type === "user") {
3594
4020
  const text = flattenContent(msg.displayContent ?? msg.content);
3595
- const preview = previewOf2(text);
4021
+ const preview = previewOf3(text);
3596
4022
  const isHidden = isFrameworkInjectedUserInput(text);
3597
4023
  if (text && !isHidden) {
3598
4024
  if (!firstUserPreview)
@@ -3616,7 +4042,7 @@ async function parseSession(file) {
3616
4042
  if (typeof msg.model === "string")
3617
4043
  model = msg.model;
3618
4044
  const text = flattenContent(msg.content);
3619
- const preview = previewOf2(text);
4045
+ const preview = previewOf3(text);
3620
4046
  if (text)
3621
4047
  lastAgentPreview = preview;
3622
4048
  let usage2;
@@ -3642,7 +4068,7 @@ async function parseSession(file) {
3642
4068
  timestamp: th.timestamp ?? ts,
3643
4069
  role: "agent-thinking",
3644
4070
  rawType: "gemini/thought",
3645
- preview: previewOf2(thText),
4071
+ preview: previewOf3(thText),
3646
4072
  blocks: [{ type: "thinking", thinking: thText }],
3647
4073
  model,
3648
4074
  raw: th
@@ -3699,7 +4125,7 @@ async function parseSession(file) {
3699
4125
  timestamp: tc.timestamp ?? ts,
3700
4126
  role: "tool-result",
3701
4127
  rawType: "gemini/tool_result",
3702
- preview: previewOf2(resultText),
4128
+ preview: previewOf3(resultText),
3703
4129
  blocks: [
3704
4130
  {
3705
4131
  type: "tool_result",
@@ -3723,7 +4149,7 @@ async function parseSession(file) {
3723
4149
  timestamp: ts,
3724
4150
  role: "meta",
3725
4151
  rawType: `gemini/${msg.type}`,
3726
- preview: previewOf2(text),
4152
+ preview: previewOf3(text),
3727
4153
  blocks: text ? [{ type: "text", text }] : [],
3728
4154
  raw: msg
3729
4155
  });
@@ -3745,7 +4171,7 @@ async function parseSession(file) {
3745
4171
  prevMs = ms;
3746
4172
  }
3747
4173
  }
3748
- const activeSegments = computeActiveSegments3(tsMs);
4174
+ const activeSegments = computeActiveSegments4(tsMs);
3749
4175
  const airTimeMs = activeSegments.reduce((acc, s) => acc + (s.endMs - s.startMs), 0);
3750
4176
  const durationMs = firstTimestamp && lastTimestamp ? Date.parse(lastTimestamp) - Date.parse(firstTimestamp) : void 0;
3751
4177
  const sessionId = metaRec.sessionId ?? file.filenameId;
@@ -3779,7 +4205,7 @@ async function parseSession(file) {
3779
4205
  };
3780
4206
  return { meta, events };
3781
4207
  }
3782
- function computeActiveSegments3(tsMs) {
4208
+ function computeActiveSegments4(tsMs) {
3783
4209
  if (tsMs.length === 0)
3784
4210
  return [];
3785
4211
  const sorted = [...tsMs].sort((a, b) => a - b);
@@ -3787,7 +4213,7 @@ function computeActiveSegments3(tsMs) {
3787
4213
  let segStart = sorted[0];
3788
4214
  let segEnd = sorted[0];
3789
4215
  for (let i = 1; i < sorted.length; i++) {
3790
- if (sorted[i] - segEnd > IDLE_GAP_MS2) {
4216
+ if (sorted[i] - segEnd > IDLE_GAP_MS3) {
3791
4217
  out.push({ startMs: segStart, endMs: segEnd });
3792
4218
  segStart = sorted[i];
3793
4219
  }
@@ -3797,23 +4223,23 @@ function computeActiveSegments3(tsMs) {
3797
4223
  return out;
3798
4224
  }
3799
4225
  function clearGeminiCaches() {
3800
- metaCache3.clear();
3801
- detailCache3.clear();
4226
+ metaCache4.clear();
4227
+ detailCache4.clear();
3802
4228
  projectsCache = null;
3803
4229
  }
3804
4230
  async function listGeminiSessions(opts = {}) {
3805
4231
  const root = opts.root ?? DEFAULT_GEMINI_ROOT;
3806
- const files = await listSessionFiles(root);
4232
+ const files = await listSessionFiles2(root);
3807
4233
  const out = [];
3808
4234
  for (const file of files) {
3809
- const cached = metaCache3.get(file.filePath);
4235
+ const cached = metaCache4.get(file.filePath);
3810
4236
  if (cached && cached.mtimeMs === file.mtimeMs && cached.sizeBytes === file.sizeBytes) {
3811
4237
  out.push(cached.meta);
3812
4238
  continue;
3813
4239
  }
3814
4240
  try {
3815
- const { meta } = await parseSession(file);
3816
- metaCache3.set(file.filePath, {
4241
+ const { meta } = await parseSession2(file);
4242
+ metaCache4.set(file.filePath, {
3817
4243
  meta,
3818
4244
  mtimeMs: file.mtimeMs,
3819
4245
  sizeBytes: file.sizeBytes
@@ -3829,7 +4255,7 @@ async function listGeminiSessions(opts = {}) {
3829
4255
  }
3830
4256
  async function getGeminiSession(id, opts = {}) {
3831
4257
  const root = opts.root ?? DEFAULT_GEMINI_ROOT;
3832
- const files = await listSessionFiles(root);
4258
+ const files = await listSessionFiles2(root);
3833
4259
  let chosen;
3834
4260
  for (const file of files) {
3835
4261
  if (file.filenameId === id || id.startsWith(file.filenameId)) {
@@ -3839,7 +4265,7 @@ async function getGeminiSession(id, opts = {}) {
3839
4265
  }
3840
4266
  if (!chosen) {
3841
4267
  for (const file of files) {
3842
- const { meta: meta2 } = await parseSession(file).catch(() => ({ meta: { id: "" } }));
4268
+ const { meta: meta2 } = await parseSession2(file).catch(() => ({ meta: { id: "" } }));
3843
4269
  if (meta2.id === id) {
3844
4270
  chosen = file;
3845
4271
  break;
@@ -3848,13 +4274,13 @@ async function getGeminiSession(id, opts = {}) {
3848
4274
  }
3849
4275
  if (!chosen)
3850
4276
  return null;
3851
- const cached = detailCache3.get(chosen.filePath);
4277
+ const cached = detailCache4.get(chosen.filePath);
3852
4278
  if (cached && cached.mtimeMs === chosen.mtimeMs && cached.sizeBytes === chosen.sizeBytes) {
3853
4279
  return cached.detail;
3854
4280
  }
3855
- const { meta, events } = await parseSession(chosen);
4281
+ const { meta, events } = await parseSession2(chosen);
3856
4282
  const detail = { ...meta, events };
3857
- detailCache3.set(chosen.filePath, {
4283
+ detailCache4.set(chosen.filePath, {
3858
4284
  detail,
3859
4285
  mtimeMs: chosen.mtimeMs,
3860
4286
  sizeBytes: chosen.sizeBytes
@@ -3867,39 +4293,39 @@ function geminiSessionLocalDay(meta) {
3867
4293
  const ms = Date.parse(meta.firstTimestamp);
3868
4294
  return Number.isFinite(ms) ? toLocalDay(ms) : void 0;
3869
4295
  }
3870
- var DEFAULT_GEMINI_ROOT, GEMINI_PROJECTS_FILE, SESSION_FILE_RE, IDLE_GAP_MS2, projectsCache, metaCache3, detailCache3;
4296
+ var DEFAULT_GEMINI_ROOT, GEMINI_PROJECTS_FILE, SESSION_FILE_RE, IDLE_GAP_MS3, projectsCache, metaCache4, detailCache4;
3871
4297
  var init_gemini = __esm({
3872
4298
  "../parser/dist/gemini.js"() {
3873
4299
  "use strict";
3874
4300
  init_analytics();
3875
4301
  init_git_project();
3876
4302
  init_user_input();
3877
- DEFAULT_GEMINI_ROOT = path3.join(os3.homedir(), ".gemini", "tmp");
3878
- GEMINI_PROJECTS_FILE = path3.join(os3.homedir(), ".gemini", "projects.json");
4303
+ DEFAULT_GEMINI_ROOT = path4.join(os4.homedir(), ".gemini", "tmp");
4304
+ GEMINI_PROJECTS_FILE = path4.join(os4.homedir(), ".gemini", "projects.json");
3879
4305
  SESSION_FILE_RE = /^session-.+\.(jsonl|json)$/;
3880
- IDLE_GAP_MS2 = 3 * 60 * 1e3;
4306
+ IDLE_GAP_MS3 = 3 * 60 * 1e3;
3881
4307
  projectsCache = null;
3882
- metaCache3 = /* @__PURE__ */ new Map();
3883
- detailCache3 = /* @__PURE__ */ new Map();
4308
+ metaCache4 = /* @__PURE__ */ new Map();
4309
+ detailCache4 = /* @__PURE__ */ new Map();
3884
4310
  }
3885
4311
  });
3886
4312
 
3887
4313
  // ../parser/dist/antigravity.js
3888
- import { promises as fs4 } from "node:fs";
3889
- import os4 from "node:os";
3890
- import path4 from "node:path";
4314
+ import { promises as fs5 } from "node:fs";
4315
+ import os5 from "node:os";
4316
+ import path5 from "node:path";
3891
4317
  async function safeReaddir3(p) {
3892
- return fs4.readdir(p).catch(() => []);
4318
+ return fs5.readdir(p).catch(() => []);
3893
4319
  }
3894
4320
  async function loadSlugToCwd2(root) {
3895
- const historyFile = path4.join(root, "history.jsonl");
3896
- const stat = await fs4.stat(historyFile).catch(() => null);
4321
+ const historyFile = path5.join(root, "history.jsonl");
4322
+ const stat = await fs5.stat(historyFile).catch(() => null);
3897
4323
  if (!stat)
3898
4324
  return /* @__PURE__ */ new Map();
3899
4325
  if (historyCache && historyCache.mtimeMs === stat.mtimeMs) {
3900
4326
  return historyCache.slugToCwd;
3901
4327
  }
3902
- const raw = await fs4.readFile(historyFile, "utf8").catch(() => "");
4328
+ const raw = await fs5.readFile(historyFile, "utf8").catch(() => "");
3903
4329
  const slugToCwd = /* @__PURE__ */ new Map();
3904
4330
  for (const line of raw.split("\n")) {
3905
4331
  const trimmed = line.trim();
@@ -3916,14 +4342,14 @@ async function loadSlugToCwd2(root) {
3916
4342
  historyCache = { mtimeMs: stat.mtimeMs, slugToCwd };
3917
4343
  return slugToCwd;
3918
4344
  }
3919
- async function listSessionFiles2(root) {
4345
+ async function listSessionFiles3(root) {
3920
4346
  const slugToCwd = await loadSlugToCwd2(root);
3921
4347
  const out = [];
3922
- const brainDir = path4.join(root, "brain");
4348
+ const brainDir = path5.join(root, "brain");
3923
4349
  const entries2 = await safeReaddir3(brainDir);
3924
4350
  for (const entry of entries2) {
3925
- const transcriptPath = path4.join(brainDir, entry, ".system_generated", "logs", "transcript.jsonl");
3926
- const stat = await fs4.stat(transcriptPath).catch(() => null);
4351
+ const transcriptPath = path5.join(brainDir, entry, ".system_generated", "logs", "transcript.jsonl");
4352
+ const stat = await fs5.stat(transcriptPath).catch(() => null);
3927
4353
  if (stat && stat.isFile()) {
3928
4354
  out.push({
3929
4355
  filePath: transcriptPath,
@@ -3936,19 +4362,19 @@ async function listSessionFiles2(root) {
3936
4362
  }
3937
4363
  return out;
3938
4364
  }
3939
- function emptyUsage3() {
4365
+ function emptyUsage4() {
3940
4366
  return { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 };
3941
4367
  }
3942
- function previewOf3(text) {
4368
+ function previewOf4(text) {
3943
4369
  return text.replace(/\s+/g, " ").trim().slice(0, 200);
3944
4370
  }
3945
4371
  function truncate4(s, n) {
3946
4372
  return s.length <= n ? s : s.slice(0, n - 1) + "\u2026";
3947
4373
  }
3948
- async function parseSession2(file) {
3949
- const raw = await fs4.readFile(file.filePath, "utf8");
4374
+ async function parseSession3(file) {
4375
+ const raw = await fs5.readFile(file.filePath, "utf8");
3950
4376
  const events = [];
3951
- const totalUsage = emptyUsage3();
4377
+ const totalUsage = emptyUsage4();
3952
4378
  let firstTimestamp;
3953
4379
  let lastTimestamp;
3954
4380
  let model;
@@ -4020,7 +4446,7 @@ async function parseSession2(file) {
4020
4446
  if (requestMatch) {
4021
4447
  text2 = requestMatch[1].trim();
4022
4448
  }
4023
- const preview = previewOf3(text2);
4449
+ const preview = previewOf4(text2);
4024
4450
  const isHidden = isFrameworkInjectedUserInput(text2);
4025
4451
  if (text2 && !isHidden) {
4026
4452
  if (!firstUserPreview)
@@ -4049,14 +4475,14 @@ async function parseSession2(file) {
4049
4475
  timestamp: ts,
4050
4476
  role: "agent-thinking",
4051
4477
  rawType: "antigravity/thought",
4052
- preview: previewOf3(thinking),
4478
+ preview: previewOf4(thinking),
4053
4479
  blocks: [{ type: "thinking", thinking }],
4054
4480
  model,
4055
4481
  raw: eventObj
4056
4482
  });
4057
4483
  }
4058
4484
  if (content) {
4059
- const preview = previewOf3(content);
4485
+ const preview = previewOf4(content);
4060
4486
  lastAgentPreview = preview;
4061
4487
  pushEvent({
4062
4488
  index: idx++,
@@ -4102,7 +4528,7 @@ async function parseSession2(file) {
4102
4528
  timestamp: ts,
4103
4529
  role: "tool-result",
4104
4530
  rawType: "antigravity/tool_result",
4105
- preview: previewOf3(contentStr),
4531
+ preview: previewOf4(contentStr),
4106
4532
  blocks: [{
4107
4533
  type: "tool_result",
4108
4534
  tool_use_id: toolUseId,
@@ -4121,7 +4547,7 @@ async function parseSession2(file) {
4121
4547
  timestamp: ts,
4122
4548
  role: "meta",
4123
4549
  rawType: `antigravity/${eventObj.type?.toLowerCase() || "unknown"}`,
4124
- preview: previewOf3(text),
4550
+ preview: previewOf4(text),
4125
4551
  blocks: text ? [{ type: "text", text }] : [],
4126
4552
  raw: eventObj
4127
4553
  });
@@ -4141,7 +4567,7 @@ async function parseSession2(file) {
4141
4567
  prevMs = ms;
4142
4568
  }
4143
4569
  }
4144
- const activeSegments = computeActiveSegments4(tsMs);
4570
+ const activeSegments = computeActiveSegments5(tsMs);
4145
4571
  const airTimeMs = activeSegments.reduce((acc, s) => acc + (s.endMs - s.startMs), 0);
4146
4572
  const durationMs = firstTimestamp && lastTimestamp ? Date.parse(lastTimestamp) - Date.parse(firstTimestamp) : void 0;
4147
4573
  const sessionId = file.conversationId;
@@ -4176,7 +4602,7 @@ async function parseSession2(file) {
4176
4602
  };
4177
4603
  return { meta, events };
4178
4604
  }
4179
- function computeActiveSegments4(tsMs) {
4605
+ function computeActiveSegments5(tsMs) {
4180
4606
  if (tsMs.length === 0)
4181
4607
  return [];
4182
4608
  const sorted = [...tsMs].sort((a, b) => a - b);
@@ -4184,7 +4610,7 @@ function computeActiveSegments4(tsMs) {
4184
4610
  let segStart = sorted[0];
4185
4611
  let segEnd = sorted[0];
4186
4612
  for (let i = 1; i < sorted.length; i++) {
4187
- if (sorted[i] - segEnd > IDLE_GAP_MS3) {
4613
+ if (sorted[i] - segEnd > IDLE_GAP_MS4) {
4188
4614
  out.push({ startMs: segStart, endMs: segEnd });
4189
4615
  segStart = sorted[i];
4190
4616
  }
@@ -4194,23 +4620,23 @@ function computeActiveSegments4(tsMs) {
4194
4620
  return out;
4195
4621
  }
4196
4622
  function clearAntigravityCaches() {
4197
- metaCache4.clear();
4198
- detailCache4.clear();
4623
+ metaCache5.clear();
4624
+ detailCache5.clear();
4199
4625
  historyCache = null;
4200
4626
  }
4201
4627
  async function listAntigravitySessions(opts = {}) {
4202
4628
  const root = opts.root ?? DEFAULT_ANTIGRAVITY_ROOT;
4203
- const files = await listSessionFiles2(root);
4629
+ const files = await listSessionFiles3(root);
4204
4630
  const out = [];
4205
4631
  for (const file of files) {
4206
- const cached = metaCache4.get(file.filePath);
4632
+ const cached = metaCache5.get(file.filePath);
4207
4633
  if (cached && cached.mtimeMs === file.mtimeMs && cached.sizeBytes === file.sizeBytes && cached.cwd === file.cwd) {
4208
4634
  out.push(cached.meta);
4209
4635
  continue;
4210
4636
  }
4211
4637
  try {
4212
- const { meta } = await parseSession2(file);
4213
- metaCache4.set(file.filePath, {
4638
+ const { meta } = await parseSession3(file);
4639
+ metaCache5.set(file.filePath, {
4214
4640
  meta,
4215
4641
  mtimeMs: file.mtimeMs,
4216
4642
  sizeBytes: file.sizeBytes,
@@ -4227,7 +4653,7 @@ async function listAntigravitySessions(opts = {}) {
4227
4653
  }
4228
4654
  async function getAntigravitySession(id, opts = {}) {
4229
4655
  const root = opts.root ?? DEFAULT_ANTIGRAVITY_ROOT;
4230
- const files = await listSessionFiles2(root);
4656
+ const files = await listSessionFiles3(root);
4231
4657
  let chosen;
4232
4658
  for (const file of files) {
4233
4659
  if (file.conversationId === id) {
@@ -4237,13 +4663,13 @@ async function getAntigravitySession(id, opts = {}) {
4237
4663
  }
4238
4664
  if (!chosen)
4239
4665
  return null;
4240
- const cached = detailCache4.get(chosen.filePath);
4666
+ const cached = detailCache5.get(chosen.filePath);
4241
4667
  if (cached && cached.mtimeMs === chosen.mtimeMs && cached.sizeBytes === chosen.sizeBytes && cached.cwd === chosen.cwd) {
4242
4668
  return cached.detail;
4243
4669
  }
4244
- const { meta, events } = await parseSession2(chosen);
4670
+ const { meta, events } = await parseSession3(chosen);
4245
4671
  const detail = { ...meta, events };
4246
- detailCache4.set(chosen.filePath, {
4672
+ detailCache5.set(chosen.filePath, {
4247
4673
  detail,
4248
4674
  mtimeMs: chosen.mtimeMs,
4249
4675
  sizeBytes: chosen.sizeBytes,
@@ -4257,61 +4683,61 @@ function antigravitySessionLocalDay(meta) {
4257
4683
  const ms = Date.parse(meta.firstTimestamp);
4258
4684
  return Number.isFinite(ms) ? toLocalDay(ms) : void 0;
4259
4685
  }
4260
- var DEFAULT_ANTIGRAVITY_ROOT, IDLE_GAP_MS3, historyCache, metaCache4, detailCache4;
4686
+ var DEFAULT_ANTIGRAVITY_ROOT, IDLE_GAP_MS4, historyCache, metaCache5, detailCache5;
4261
4687
  var init_antigravity = __esm({
4262
4688
  "../parser/dist/antigravity.js"() {
4263
4689
  "use strict";
4264
4690
  init_analytics();
4265
4691
  init_git_project();
4266
4692
  init_user_input();
4267
- DEFAULT_ANTIGRAVITY_ROOT = path4.join(os4.homedir(), ".gemini", "antigravity-cli");
4268
- IDLE_GAP_MS3 = 3 * 60 * 1e3;
4693
+ DEFAULT_ANTIGRAVITY_ROOT = path5.join(os5.homedir(), ".gemini", "antigravity-cli");
4694
+ IDLE_GAP_MS4 = 3 * 60 * 1e3;
4269
4695
  historyCache = null;
4270
- metaCache4 = /* @__PURE__ */ new Map();
4271
- detailCache4 = /* @__PURE__ */ new Map();
4696
+ metaCache5 = /* @__PURE__ */ new Map();
4697
+ detailCache5 = /* @__PURE__ */ new Map();
4272
4698
  }
4273
4699
  });
4274
4700
 
4275
4701
  // ../parser/dist/cowork.js
4276
- import { promises as fs5 } from "node:fs";
4277
- import os5 from "node:os";
4278
- import path5 from "node:path";
4702
+ import { promises as fs6 } from "node:fs";
4703
+ import os6 from "node:os";
4704
+ import path6 from "node:path";
4279
4705
  function defaultCoworkRoot() {
4280
- const home = os5.homedir();
4706
+ const home = os6.homedir();
4281
4707
  if (process.platform === "darwin") {
4282
- return path5.join(home, "Library", "Application Support", "Claude", "local-agent-mode-sessions");
4708
+ return path6.join(home, "Library", "Application Support", "Claude", "local-agent-mode-sessions");
4283
4709
  }
4284
4710
  if (process.platform === "win32") {
4285
- const appData = process.env.APPDATA ?? path5.join(home, "AppData", "Roaming");
4286
- return path5.join(appData, "Claude", "local-agent-mode-sessions");
4711
+ const appData = process.env.APPDATA ?? path6.join(home, "AppData", "Roaming");
4712
+ return path6.join(appData, "Claude", "local-agent-mode-sessions");
4287
4713
  }
4288
- return path5.join(home, ".config", "Claude", "local-agent-mode-sessions");
4714
+ return path6.join(home, ".config", "Claude", "local-agent-mode-sessions");
4289
4715
  }
4290
4716
  async function safeReaddir4(p) {
4291
- return fs5.readdir(p).catch(() => []);
4717
+ return fs6.readdir(p).catch(() => []);
4292
4718
  }
4293
4719
  async function statMs(p) {
4294
- const s = await fs5.stat(p).catch(() => null);
4720
+ const s = await fs6.stat(p).catch(() => null);
4295
4721
  return s ? s.mtimeMs : 0;
4296
4722
  }
4297
- async function listSessionFiles3(root) {
4723
+ async function listSessionFiles4(root) {
4298
4724
  const out = [];
4299
4725
  const accounts = await safeReaddir4(root);
4300
4726
  for (const accountId of accounts) {
4301
- const accountDir = path5.join(root, accountId);
4727
+ const accountDir = path6.join(root, accountId);
4302
4728
  const workspaces = await safeReaddir4(accountDir);
4303
4729
  for (const workspaceId of workspaces) {
4304
- const workspaceDir = path5.join(accountDir, workspaceId);
4305
- const spacesMtimeMs = await statMs(path5.join(workspaceDir, "spaces.json"));
4730
+ const workspaceDir = path6.join(accountDir, workspaceId);
4731
+ const spacesMtimeMs = await statMs(path6.join(workspaceDir, "spaces.json"));
4306
4732
  const entries2 = await safeReaddir4(workspaceDir);
4307
4733
  for (const entry of entries2) {
4308
4734
  if (!SESSION_ID_RE.test(entry))
4309
4735
  continue;
4310
- const auditPath = path5.join(workspaceDir, entry, "audit.jsonl");
4311
- const auditStat = await fs5.stat(auditPath).catch(() => null);
4736
+ const auditPath = path6.join(workspaceDir, entry, "audit.jsonl");
4737
+ const auditStat = await fs6.stat(auditPath).catch(() => null);
4312
4738
  if (!auditStat || !auditStat.isFile() || auditStat.size === 0)
4313
4739
  continue;
4314
- const metaPath = path5.join(workspaceDir, `${entry}.json`);
4740
+ const metaPath = path6.join(workspaceDir, `${entry}.json`);
4315
4741
  const metaMtimeMs = await statMs(metaPath);
4316
4742
  out.push({
4317
4743
  sessionId: entry,
@@ -4329,14 +4755,14 @@ async function listSessionFiles3(root) {
4329
4755
  return out;
4330
4756
  }
4331
4757
  async function loadSpacesForWorkspace(workspaceDir) {
4332
- const spacesPath = path5.join(workspaceDir, "spaces.json");
4333
- const stat = await fs5.stat(spacesPath).catch(() => null);
4758
+ const spacesPath = path6.join(workspaceDir, "spaces.json");
4759
+ const stat = await fs6.stat(spacesPath).catch(() => null);
4334
4760
  if (!stat)
4335
4761
  return /* @__PURE__ */ new Map();
4336
4762
  const cached = spacesCache.get(workspaceDir);
4337
4763
  if (cached && cached.mtimeMs === stat.mtimeMs)
4338
4764
  return cached.spaceIdToPath;
4339
- const raw = await fs5.readFile(spacesPath, "utf8").catch(() => "");
4765
+ const raw = await fs6.readFile(spacesPath, "utf8").catch(() => "");
4340
4766
  const out = /* @__PURE__ */ new Map();
4341
4767
  try {
4342
4768
  const parsed = JSON.parse(raw);
@@ -4354,7 +4780,7 @@ async function loadSpacesForWorkspace(workspaceDir) {
4354
4780
  return out;
4355
4781
  }
4356
4782
  async function readCoworkMeta(metaPath) {
4357
- const raw = await fs5.readFile(metaPath, "utf8").catch(() => "");
4783
+ const raw = await fs6.readFile(metaPath, "utf8").catch(() => "");
4358
4784
  if (!raw)
4359
4785
  return {};
4360
4786
  try {
@@ -4390,8 +4816,8 @@ function resolveProject(meta, spaceIdToPath) {
4390
4816
  cwd: projectPath
4391
4817
  };
4392
4818
  }
4393
- async function readJsonl2(filePath) {
4394
- const raw = await fs5.readFile(filePath, "utf8");
4819
+ async function readJsonl3(filePath) {
4820
+ const raw = await fs6.readFile(filePath, "utf8");
4395
4821
  const out = [];
4396
4822
  for (const line of raw.split("\n")) {
4397
4823
  const trimmed = line.trim();
@@ -4527,7 +4953,7 @@ function buildCoworkSubagents(subagentGroups, allLines, sessionStartMs) {
4527
4953
  }
4528
4954
  async function parseCoworkSession(file) {
4529
4955
  const [lines, coworkMeta, spaceIdToPath] = await Promise.all([
4530
- readJsonl2(file.auditPath),
4956
+ readJsonl3(file.auditPath),
4531
4957
  readCoworkMeta(file.metaPath),
4532
4958
  loadSpacesForWorkspace(file.workspaceDir)
4533
4959
  ]);
@@ -4562,24 +4988,24 @@ function cacheKeyMatches(a, b) {
4562
4988
  return a.auditMtimeMs === b.auditMtimeMs && a.auditSize === b.auditSize && a.metaMtimeMs === b.metaMtimeMs && a.spacesMtimeMs === b.spacesMtimeMs;
4563
4989
  }
4564
4990
  function clearCoworkCaches() {
4565
- metaCache5.clear();
4566
- detailCache5.clear();
4991
+ metaCache6.clear();
4992
+ detailCache6.clear();
4567
4993
  spacesCache.clear();
4568
4994
  }
4569
4995
  async function listCoworkSessions(opts = {}) {
4570
4996
  const root = opts.root ?? DEFAULT_COWORK_ROOT;
4571
- const files = await listSessionFiles3(root);
4997
+ const files = await listSessionFiles4(root);
4572
4998
  const out = [];
4573
4999
  for (const file of files) {
4574
5000
  const key = cacheKeyFor(file);
4575
- const cached = metaCache5.get(file.auditPath);
5001
+ const cached = metaCache6.get(file.auditPath);
4576
5002
  if (cached && cacheKeyMatches(cached.key, key)) {
4577
5003
  out.push(cached.meta);
4578
5004
  continue;
4579
5005
  }
4580
5006
  try {
4581
5007
  const { meta } = await parseCoworkSession(file);
4582
- metaCache5.set(file.auditPath, { meta, key });
5008
+ metaCache6.set(file.auditPath, { meta, key });
4583
5009
  out.push(meta);
4584
5010
  } catch {
4585
5011
  }
@@ -4591,12 +5017,12 @@ async function listCoworkSessions(opts = {}) {
4591
5017
  }
4592
5018
  async function getCoworkSession(id, opts = {}) {
4593
5019
  const root = opts.root ?? DEFAULT_COWORK_ROOT;
4594
- const files = await listSessionFiles3(root);
5020
+ const files = await listSessionFiles4(root);
4595
5021
  const file = files.find((f) => f.sessionId === id);
4596
5022
  if (!file)
4597
5023
  return null;
4598
5024
  const key = cacheKeyFor(file);
4599
- const cached = detailCache5.get(file.auditPath);
5025
+ const cached = detailCache6.get(file.auditPath);
4600
5026
  if (cached && cacheKeyMatches(cached.key, key))
4601
5027
  return cached.detail;
4602
5028
  const { meta, events, subagents } = await parseCoworkSession(file);
@@ -4605,10 +5031,10 @@ async function getCoworkSession(id, opts = {}) {
4605
5031
  events,
4606
5032
  ...subagents.length ? { subagents } : {}
4607
5033
  };
4608
- detailCache5.set(file.auditPath, { detail, key });
5034
+ detailCache6.set(file.auditPath, { detail, key });
4609
5035
  return detail;
4610
5036
  }
4611
- var DEFAULT_COWORK_ROOT, SESSION_ID_RE, spacesCache, metaCache5, detailCache5;
5037
+ var DEFAULT_COWORK_ROOT, SESSION_ID_RE, spacesCache, metaCache6, detailCache6;
4612
5038
  var init_cowork = __esm({
4613
5039
  "../parser/dist/cowork.js"() {
4614
5040
  "use strict";
@@ -4618,24 +5044,24 @@ var init_cowork = __esm({
4618
5044
  DEFAULT_COWORK_ROOT = defaultCoworkRoot();
4619
5045
  SESSION_ID_RE = /^local_[0-9a-f-]+$/;
4620
5046
  spacesCache = /* @__PURE__ */ new Map();
4621
- metaCache5 = /* @__PURE__ */ new Map();
4622
- detailCache5 = /* @__PURE__ */ new Map();
5047
+ metaCache6 = /* @__PURE__ */ new Map();
5048
+ detailCache6 = /* @__PURE__ */ new Map();
4623
5049
  }
4624
5050
  });
4625
5051
 
4626
5052
  // ../parser/dist/grok.js
4627
- import { promises as fs6 } from "node:fs";
4628
- import os6 from "node:os";
4629
- import path6 from "node:path";
5053
+ import { promises as fs7 } from "node:fs";
5054
+ import os7 from "node:os";
5055
+ import path7 from "node:path";
4630
5056
  function resolveDefaultGrokRoot() {
4631
- const home = process.env.GROK_HOME || path6.join(os6.homedir(), ".grok");
4632
- return path6.join(home, "sessions");
5057
+ const home = process.env.GROK_HOME || path7.join(os7.homedir(), ".grok");
5058
+ return path7.join(home, "sessions");
4633
5059
  }
4634
5060
  async function safeReaddir5(p) {
4635
- return fs6.readdir(p).catch(() => []);
5061
+ return fs7.readdir(p).catch(() => []);
4636
5062
  }
4637
5063
  async function safeReadJson(p) {
4638
- const raw = await fs6.readFile(p, "utf8").catch(() => null);
5064
+ const raw = await fs7.readFile(p, "utf8").catch(() => null);
4639
5065
  if (raw == null)
4640
5066
  return null;
4641
5067
  try {
@@ -4645,8 +5071,8 @@ async function safeReadJson(p) {
4645
5071
  }
4646
5072
  }
4647
5073
  async function resolveEncodedCwd(groupDir, encoded) {
4648
- const cwdFile = path6.join(groupDir, ".cwd");
4649
- const fromFile = await fs6.readFile(cwdFile, "utf8").catch(() => null);
5074
+ const cwdFile = path7.join(groupDir, ".cwd");
5075
+ const fromFile = await fs7.readFile(cwdFile, "utf8").catch(() => null);
4650
5076
  if (fromFile && fromFile.trim())
4651
5077
  return fromFile.trim();
4652
5078
  try {
@@ -4661,8 +5087,8 @@ async function listSessionDirs(root) {
4661
5087
  for (const group of groups) {
4662
5088
  if (group === "session_search.sqlite" || group.startsWith("."))
4663
5089
  continue;
4664
- const groupDir = path6.join(root, group);
4665
- const groupStat = await fs6.stat(groupDir).catch(() => null);
5090
+ const groupDir = path7.join(root, group);
5091
+ const groupStat = await fs7.stat(groupDir).catch(() => null);
4666
5092
  if (!groupStat?.isDirectory())
4667
5093
  continue;
4668
5094
  const decodedCwd = await resolveEncodedCwd(groupDir, group);
@@ -4670,14 +5096,14 @@ async function listSessionDirs(root) {
4670
5096
  for (const entry of entries2) {
4671
5097
  if (entry === "prompt_history.jsonl" || entry.startsWith("."))
4672
5098
  continue;
4673
- const dirPath = path6.join(groupDir, entry);
4674
- const summaryPath = path6.join(dirPath, "summary.json");
4675
- const updatesPath = path6.join(dirPath, "updates.jsonl");
4676
- const signalsCandidate = path6.join(dirPath, "signals.json");
5099
+ const dirPath = path7.join(groupDir, entry);
5100
+ const summaryPath = path7.join(dirPath, "summary.json");
5101
+ const updatesPath = path7.join(dirPath, "updates.jsonl");
5102
+ const signalsCandidate = path7.join(dirPath, "signals.json");
4677
5103
  const [summaryStat, updatesStat, signalsStat] = await Promise.all([
4678
- fs6.stat(summaryPath).catch(() => null),
4679
- fs6.stat(updatesPath).catch(() => null),
4680
- fs6.stat(signalsCandidate).catch(() => null)
5104
+ fs7.stat(summaryPath).catch(() => null),
5105
+ fs7.stat(updatesPath).catch(() => null),
5106
+ fs7.stat(signalsCandidate).catch(() => null)
4681
5107
  ]);
4682
5108
  if (!summaryStat?.isFile())
4683
5109
  continue;
@@ -4698,10 +5124,10 @@ async function listSessionDirs(root) {
4698
5124
  }
4699
5125
  return out;
4700
5126
  }
4701
- function emptyUsage4() {
5127
+ function emptyUsage5() {
4702
5128
  return { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 };
4703
5129
  }
4704
- function previewOf4(text) {
5130
+ function previewOf5(text) {
4705
5131
  return text.replace(/\s+/g, " ").trim().slice(0, 200);
4706
5132
  }
4707
5133
  function truncate5(s, n) {
@@ -4815,7 +5241,7 @@ function lineTimestampIso(line) {
4815
5241
  }
4816
5242
  return void 0;
4817
5243
  }
4818
- function computeActiveSegments5(tsMs) {
5244
+ function computeActiveSegments6(tsMs) {
4819
5245
  if (tsMs.length === 0)
4820
5246
  return [];
4821
5247
  const sorted = [...tsMs].sort((a, b) => a - b);
@@ -4824,7 +5250,7 @@ function computeActiveSegments5(tsMs) {
4824
5250
  let segEnd = sorted[0];
4825
5251
  for (let i = 1; i < sorted.length; i++) {
4826
5252
  const t = sorted[i];
4827
- if (t - segEnd > IDLE_GAP_MS4) {
5253
+ if (t - segEnd > IDLE_GAP_MS5) {
4828
5254
  out.push({ startMs: segStart, endMs: segEnd });
4829
5255
  segStart = t;
4830
5256
  }
@@ -4833,17 +5259,17 @@ function computeActiveSegments5(tsMs) {
4833
5259
  out.push({ startMs: segStart, endMs: segEnd });
4834
5260
  return out;
4835
5261
  }
4836
- async function parseSession3(dir) {
5262
+ async function parseSession4(dir) {
4837
5263
  const [summary, signals, updatesRaw] = await Promise.all([
4838
5264
  safeReadJson(dir.summaryPath),
4839
5265
  dir.signalsPath ? safeReadJson(dir.signalsPath) : Promise.resolve(null),
4840
- fs6.readFile(dir.updatesPath, "utf8").catch(() => "")
5266
+ fs7.readFile(dir.updatesPath, "utf8").catch(() => "")
4841
5267
  ]);
4842
5268
  const sessionId = summary?.info?.id ?? dir.sessionId;
4843
5269
  const cwd = summary?.info?.cwd ?? dir.decodedCwd;
4844
5270
  let model = summary?.current_model_id ?? signals?.primaryModelId ?? signals?.modelsUsed?.[0];
4845
5271
  const events = [];
4846
- const totalUsage = emptyUsage4();
5272
+ const totalUsage = emptyUsage5();
4847
5273
  if (signals?.contextTokensUsed && signals.contextTokensUsed > 0) {
4848
5274
  totalUsage.input = signals.contextTokensUsed;
4849
5275
  }
@@ -4877,7 +5303,7 @@ async function parseSession3(dir) {
4877
5303
  if (!buf)
4878
5304
  return;
4879
5305
  const text = buf.texts.join("");
4880
- const preview = previewOf4(text);
5306
+ const preview = previewOf5(text);
4881
5307
  if (buf.kind === "user") {
4882
5308
  const isHidden = !text || isFrameworkInjectedUserInput(text);
4883
5309
  if (text && !isHidden) {
@@ -5037,7 +5463,7 @@ async function parseSession3(dir) {
5037
5463
  timestamp: ts,
5038
5464
  role: "tool-result",
5039
5465
  rawType: "grok/tool_result",
5040
- preview: previewOf4(resultText),
5466
+ preview: previewOf5(resultText),
5041
5467
  blocks: [
5042
5468
  {
5043
5469
  type: "tool_result",
@@ -5086,7 +5512,7 @@ async function parseSession3(dir) {
5086
5512
  prevMs = ms;
5087
5513
  }
5088
5514
  }
5089
- const activeSegments = computeActiveSegments5(tsMs);
5515
+ const activeSegments = computeActiveSegments6(tsMs);
5090
5516
  const airTimeMs = activeSegments.reduce((acc, s) => acc + (s.endMs - s.startMs), 0);
5091
5517
  const durationMs = firstTimestamp && lastTimestamp ? Date.parse(lastTimestamp) - Date.parse(firstTimestamp) : void 0;
5092
5518
  const project = cwd ? resolveProjectIdentity(cwd) : void 0;
@@ -5095,7 +5521,7 @@ async function parseSession3(dir) {
5095
5521
  if (!firstUserPreview) {
5096
5522
  const title = summary?.generated_title || summary?.session_summary;
5097
5523
  if (title)
5098
- firstUserPreview = previewOf4(title);
5524
+ firstUserPreview = previewOf5(title);
5099
5525
  }
5100
5526
  const spawnedAgentCount = await countSubagentChildren(dir.dirPath);
5101
5527
  const meta = {
@@ -5132,38 +5558,38 @@ async function parseSession3(dir) {
5132
5558
  return { meta, events, sessionKind: summary?.session_kind };
5133
5559
  }
5134
5560
  async function countSubagentChildren(dirPath) {
5135
- const subRoot = path6.join(dirPath, "subagents");
5561
+ const subRoot = path7.join(dirPath, "subagents");
5136
5562
  const entries2 = await safeReaddir5(subRoot);
5137
5563
  let n = 0;
5138
5564
  for (const e of entries2) {
5139
- const st = await fs6.stat(path6.join(subRoot, e)).catch(() => null);
5565
+ const st = await fs7.stat(path7.join(subRoot, e)).catch(() => null);
5140
5566
  if (st?.isDirectory())
5141
5567
  n += 1;
5142
5568
  }
5143
5569
  return n;
5144
5570
  }
5145
5571
  async function loadGrokSubagents(parentDir, parentStartMs) {
5146
- const subRoot = path6.join(parentDir.dirPath, "subagents");
5572
+ const subRoot = path7.join(parentDir.dirPath, "subagents");
5147
5573
  const entries2 = await safeReaddir5(subRoot);
5148
- const groupDir = path6.dirname(parentDir.dirPath);
5574
+ const groupDir = path7.dirname(parentDir.dirPath);
5149
5575
  const runs2 = [];
5150
5576
  for (const entry of entries2) {
5151
- const metaPath = path6.join(subRoot, entry, "meta.json");
5577
+ const metaPath = path7.join(subRoot, entry, "meta.json");
5152
5578
  const meta = await safeReadJson(metaPath);
5153
5579
  if (!meta)
5154
5580
  continue;
5155
5581
  const childId = meta.child_session_id ?? meta.subagent_id ?? entry;
5156
- const childDir = path6.join(groupDir, childId);
5582
+ const childDir = path7.join(groupDir, childId);
5157
5583
  const [childSummary, childSignals] = await Promise.all([
5158
- safeReadJson(path6.join(childDir, "summary.json")),
5159
- safeReadJson(path6.join(childDir, "signals.json"))
5584
+ safeReadJson(path7.join(childDir, "summary.json")),
5585
+ safeReadJson(path7.join(childDir, "signals.json"))
5160
5586
  ]);
5161
5587
  const startMs = childSummary?.created_at ? Date.parse(childSummary.created_at) : void 0;
5162
5588
  const endIso = childSummary?.last_active_at ?? childSummary?.updated_at;
5163
5589
  const endMs = endIso ? Date.parse(endIso) : void 0;
5164
5590
  const startOk = startMs !== void 0 && Number.isFinite(startMs) ? startMs : void 0;
5165
5591
  const endOk = endMs !== void 0 && Number.isFinite(endMs) ? endMs : void 0;
5166
- const usage2 = emptyUsage4();
5592
+ const usage2 = emptyUsage5();
5167
5593
  if (childSignals?.contextTokensUsed)
5168
5594
  usage2.input = childSignals.contextTokensUsed;
5169
5595
  runs2.push({
@@ -5186,8 +5612,8 @@ async function loadGrokSubagents(parentDir, parentStartMs) {
5186
5612
  return runs2;
5187
5613
  }
5188
5614
  function clearGrokCaches() {
5189
- metaCache6.clear();
5190
- detailCache6.clear();
5615
+ metaCache7.clear();
5616
+ detailCache7.clear();
5191
5617
  }
5192
5618
  async function listGrokSessions(opts = {}) {
5193
5619
  const root = opts.root ?? resolveDefaultGrokRoot();
@@ -5197,16 +5623,16 @@ async function listGrokSessions(opts = {}) {
5197
5623
  const summaryPeek = await safeReadJson(dir.summaryPath);
5198
5624
  if (summaryPeek?.session_kind === "subagent")
5199
5625
  continue;
5200
- const cached = metaCache6.get(dir.dirPath);
5626
+ const cached = metaCache7.get(dir.dirPath);
5201
5627
  if (cached && cached.mtimeMs === dir.mtimeMs && cached.sizeBytes === dir.sizeBytes) {
5202
5628
  out.push(cached.meta);
5203
5629
  continue;
5204
5630
  }
5205
5631
  try {
5206
- const { meta, sessionKind } = await parseSession3(dir);
5632
+ const { meta, sessionKind } = await parseSession4(dir);
5207
5633
  if (sessionKind === "subagent")
5208
5634
  continue;
5209
- metaCache6.set(dir.dirPath, {
5635
+ metaCache7.set(dir.dirPath, {
5210
5636
  meta,
5211
5637
  mtimeMs: dir.mtimeMs,
5212
5638
  sizeBytes: dir.sizeBytes
@@ -5227,10 +5653,10 @@ async function getGrokSession(id, opts = {}) {
5227
5653
  if (!chosen) {
5228
5654
  for (const dir of dirs) {
5229
5655
  try {
5230
- const { meta: meta2, events: events2 } = await parseSession3(dir);
5656
+ const { meta: meta2, events: events2 } = await parseSession4(dir);
5231
5657
  if (meta2.id === id) {
5232
5658
  const detail2 = { ...meta2, events: events2 };
5233
- detailCache6.set(dir.dirPath, {
5659
+ detailCache7.set(dir.dirPath, {
5234
5660
  detail: detail2,
5235
5661
  mtimeMs: dir.mtimeMs,
5236
5662
  sizeBytes: dir.sizeBytes
@@ -5242,11 +5668,11 @@ async function getGrokSession(id, opts = {}) {
5242
5668
  }
5243
5669
  return null;
5244
5670
  }
5245
- const cached = detailCache6.get(chosen.dirPath);
5671
+ const cached = detailCache7.get(chosen.dirPath);
5246
5672
  if (cached && cached.mtimeMs === chosen.mtimeMs && cached.sizeBytes === chosen.sizeBytes) {
5247
5673
  return cached.detail;
5248
5674
  }
5249
- const { meta, events } = await parseSession3(chosen);
5675
+ const { meta, events } = await parseSession4(chosen);
5250
5676
  const parentStartMs = meta.firstTimestamp ? Date.parse(meta.firstTimestamp) : void 0;
5251
5677
  const subagents = await loadGrokSubagents(chosen, parentStartMs !== void 0 && Number.isFinite(parentStartMs) ? parentStartMs : void 0);
5252
5678
  const detail = {
@@ -5254,12 +5680,12 @@ async function getGrokSession(id, opts = {}) {
5254
5680
  events,
5255
5681
  ...subagents.length > 0 ? { subagents, spawnedAgentCount: subagents.length } : {}
5256
5682
  };
5257
- detailCache6.set(chosen.dirPath, {
5683
+ detailCache7.set(chosen.dirPath, {
5258
5684
  detail,
5259
5685
  mtimeMs: chosen.mtimeMs,
5260
5686
  sizeBytes: chosen.sizeBytes
5261
5687
  });
5262
- metaCache6.set(chosen.dirPath, {
5688
+ metaCache7.set(chosen.dirPath, {
5263
5689
  meta: {
5264
5690
  ...meta,
5265
5691
  ...subagents.length > 0 ? { spawnedAgentCount: subagents.length } : {}
@@ -5275,17 +5701,17 @@ function grokSessionLocalDay(meta) {
5275
5701
  const ms = Date.parse(meta.firstTimestamp);
5276
5702
  return Number.isFinite(ms) ? toLocalDay(ms) : void 0;
5277
5703
  }
5278
- var DEFAULT_GROK_ROOT, IDLE_GAP_MS4, metaCache6, detailCache6;
5704
+ var DEFAULT_GROK_ROOT, IDLE_GAP_MS5, metaCache7, detailCache7;
5279
5705
  var init_grok = __esm({
5280
5706
  "../parser/dist/grok.js"() {
5281
5707
  "use strict";
5282
5708
  init_analytics();
5283
5709
  init_git_project();
5284
5710
  init_user_input();
5285
- DEFAULT_GROK_ROOT = path6.join(os6.homedir(), ".grok", "sessions");
5286
- IDLE_GAP_MS4 = 3 * 60 * 1e3;
5287
- metaCache6 = /* @__PURE__ */ new Map();
5288
- detailCache6 = /* @__PURE__ */ new Map();
5711
+ DEFAULT_GROK_ROOT = path7.join(os7.homedir(), ".grok", "sessions");
5712
+ IDLE_GAP_MS5 = 3 * 60 * 1e3;
5713
+ metaCache7 = /* @__PURE__ */ new Map();
5714
+ detailCache7 = /* @__PURE__ */ new Map();
5289
5715
  }
5290
5716
  });
5291
5717
 
@@ -5346,6 +5772,7 @@ var fs_exports = {};
5346
5772
  __export(fs_exports, {
5347
5773
  DEFAULT_ANTIGRAVITY_ROOT: () => DEFAULT_ANTIGRAVITY_ROOT,
5348
5774
  DEFAULT_CODEX_ROOT: () => DEFAULT_CODEX_ROOT,
5775
+ DEFAULT_COPILOT_ROOT: () => DEFAULT_COPILOT_ROOT,
5349
5776
  DEFAULT_COWORK_ROOT: () => DEFAULT_COWORK_ROOT,
5350
5777
  DEFAULT_GEMINI_ROOT: () => DEFAULT_GEMINI_ROOT,
5351
5778
  DEFAULT_GROK_ROOT: () => DEFAULT_GROK_ROOT,
@@ -5362,6 +5789,7 @@ __export(fs_exports, {
5362
5789
  clearGrokCaches: () => clearGrokCaches,
5363
5790
  clearTeamConfig: () => clearTeamConfig,
5364
5791
  codexSessionLocalDay: () => codexSessionLocalDay,
5792
+ copilotSessionLocalDay: () => copilotSessionLocalDay,
5365
5793
  decodeProjectName: () => decodeProjectName,
5366
5794
  findTeamLead: () => findTeamLead,
5367
5795
  geminiSessionLocalDay: () => geminiSessionLocalDay,
@@ -5369,6 +5797,7 @@ __export(fs_exports, {
5369
5797
  getAntigravitySession: () => getAntigravitySession,
5370
5798
  getAnySession: () => getAnySession,
5371
5799
  getCodexSession: () => getCodexSession,
5800
+ getCopilotSession: () => getCopilotSession,
5372
5801
  getCoworkSession: () => getCoworkSession,
5373
5802
  getGeminiSession: () => getGeminiSession,
5374
5803
  getGrokSession: () => getGrokSession,
@@ -5380,6 +5809,7 @@ __export(fs_exports, {
5380
5809
  listAllSessions: () => listAllSessions,
5381
5810
  listAntigravitySessions: () => listAntigravitySessions,
5382
5811
  listCodexSessions: () => listCodexSessions,
5812
+ listCopilotSessions: () => listCopilotSessions,
5383
5813
  listCoworkSessions: () => listCoworkSessions,
5384
5814
  listGeminiSessions: () => listGeminiSessions,
5385
5815
  listGrokSessions: () => listGrokSessions,
@@ -5402,14 +5832,14 @@ __export(fs_exports, {
5402
5832
  walkJsonlFiles: () => walkJsonlFiles,
5403
5833
  writeTeamConfig: () => writeTeamConfig
5404
5834
  });
5405
- import { promises as fs7, existsSync as existsSync2, readFileSync as readFileSync4, writeFileSync as writeFileSync3, appendFileSync, mkdirSync as mkdirSync3 } from "node:fs";
5406
- import os7 from "node:os";
5407
- import path7 from "node:path";
5835
+ import { promises as fs8, existsSync as existsSync2, readFileSync as readFileSync4, writeFileSync as writeFileSync3, appendFileSync, mkdirSync as mkdirSync3 } from "node:fs";
5836
+ import os8 from "node:os";
5837
+ import path8 from "node:path";
5408
5838
  function cclensHome() {
5409
- return process.env.CCLENS_HOME || path7.join(os7.homedir(), ".cclens");
5839
+ return process.env.CCLENS_HOME || path8.join(os8.homedir(), ".cclens");
5410
5840
  }
5411
5841
  function cclensPath(...parts) {
5412
- return path7.join(cclensHome(), ...parts);
5842
+ return path8.join(cclensHome(), ...parts);
5413
5843
  }
5414
5844
  function cacheStats() {
5415
5845
  return claudeCodeCacheStats();
@@ -5417,6 +5847,7 @@ function cacheStats() {
5417
5847
  function clearCaches() {
5418
5848
  clearClaudeCodeCaches();
5419
5849
  clearCodexCaches();
5850
+ clearCopilotCaches();
5420
5851
  clearGeminiCaches();
5421
5852
  clearAntigravityCaches();
5422
5853
  clearCoworkCaches();
@@ -5451,7 +5882,7 @@ function usageLogPath() {
5451
5882
  }
5452
5883
  function appendUsageSnapshot(snapshot) {
5453
5884
  const p = usageLogPath();
5454
- mkdirSync3(path7.dirname(p), { recursive: true });
5885
+ mkdirSync3(path8.dirname(p), { recursive: true });
5455
5886
  appendFileSync(p, JSON.stringify(snapshot) + "\n", "utf8");
5456
5887
  }
5457
5888
  function pruneUsageAgent(agent) {
@@ -5467,13 +5898,13 @@ function pruneUsageAgent(agent) {
5467
5898
  return true;
5468
5899
  }
5469
5900
  });
5470
- mkdirSync3(path7.dirname(p), { recursive: true });
5901
+ mkdirSync3(path8.dirname(p), { recursive: true });
5471
5902
  writeFileSync3(p, kept.join("\n") + (kept.length ? "\n" : ""), "utf8");
5472
5903
  }
5473
5904
  async function loadUsageByDay(start2, end) {
5474
5905
  let raw;
5475
5906
  try {
5476
- raw = await fs7.readFile(usageLogPath(), "utf8");
5907
+ raw = await fs8.readFile(usageLogPath(), "utf8");
5477
5908
  } catch {
5478
5909
  return { by_day: [] };
5479
5910
  }
@@ -5518,7 +5949,7 @@ async function loadUsageByDay(start2, end) {
5518
5949
  async function loadCalibrationSnapshots() {
5519
5950
  let raw;
5520
5951
  try {
5521
- raw = await fs7.readFile(usageLogPath(), "utf8");
5952
+ raw = await fs8.readFile(usageLogPath(), "utf8");
5522
5953
  } catch {
5523
5954
  return [];
5524
5955
  }
@@ -5682,7 +6113,7 @@ async function loadCalibrationCurve(tier = "pro-max-20x", root = DEFAULT_ROOT, g
5682
6113
  ]);
5683
6114
  return buildCalibrationCurve(events, snapshots, tier, granularityMin);
5684
6115
  }
5685
- var codexSource, geminiSource, antigravitySource, coworkSource, grokSource, agentSources;
6116
+ var codexSource, copilotSource, geminiSource, antigravitySource, coworkSource, grokSource, agentSources;
5686
6117
  var init_fs = __esm({
5687
6118
  "../parser/dist/fs.js"() {
5688
6119
  "use strict";
@@ -5691,6 +6122,7 @@ var init_fs = __esm({
5691
6122
  init_calibration();
5692
6123
  init_claude_code();
5693
6124
  init_codex();
6125
+ init_copilot();
5694
6126
  init_gemini();
5695
6127
  init_antigravity();
5696
6128
  init_cowork();
@@ -5698,6 +6130,7 @@ var init_fs = __esm({
5698
6130
  init_claude_code();
5699
6131
  init_git_project();
5700
6132
  init_codex();
6133
+ init_copilot();
5701
6134
  init_gemini();
5702
6135
  init_antigravity();
5703
6136
  init_cowork();
@@ -5714,6 +6147,16 @@ var init_fs = __esm({
5714
6147
  return getCodexSession(id);
5715
6148
  }
5716
6149
  };
6150
+ copilotSource = {
6151
+ ...COPILOT_METADATA,
6152
+ defaultRoot: DEFAULT_COPILOT_ROOT,
6153
+ async listSessions(opts) {
6154
+ return listCopilotSessions(opts);
6155
+ },
6156
+ async getSession(id, opts) {
6157
+ return getCopilotSession(id, opts);
6158
+ }
6159
+ };
5717
6160
  geminiSource = {
5718
6161
  ...GEMINI_METADATA,
5719
6162
  defaultRoot: DEFAULT_GEMINI_ROOT,
@@ -5758,6 +6201,7 @@ var init_fs = __esm({
5758
6201
  agentSources = [
5759
6202
  claudeCodeSource,
5760
6203
  codexSource,
6204
+ copilotSource,
5761
6205
  geminiSource,
5762
6206
  antigravitySource,
5763
6207
  coworkSource,
@@ -5797,9 +6241,9 @@ function onDiskVersion() {
5797
6241
  try {
5798
6242
  const here = dirname3(fileURLToPath(import.meta.url));
5799
6243
  const pkg = JSON.parse(readFileSync5(join3(here, "..", "package.json"), "utf8"));
5800
- return pkg.version ?? "0.16.6";
6244
+ return pkg.version ?? "0.16.8";
5801
6245
  } catch {
5802
- return "0.16.6";
6246
+ return "0.16.8";
5803
6247
  }
5804
6248
  }
5805
6249
  function getServerStatus() {
@@ -5811,7 +6255,7 @@ function getServerStatus() {
5811
6255
  return { running: false };
5812
6256
  }
5813
6257
  function isServerStale(status2) {
5814
- return status2.running === true && status2.version !== "0.16.6";
6258
+ return status2.running === true && status2.version !== "0.16.8";
5815
6259
  }
5816
6260
  async function ensureCurrentServer(opts = {}) {
5817
6261
  const status2 = getServerStatus();
@@ -6250,9 +6694,9 @@ Installed: ${PACKAGE_NAME}@${verify.installedVersion} at ${verify.installedPath
6250
6694
  console.warn(
6251
6695
  ` \u2022 reinstall in the correct Node env: 'npm install -g ${PACKAGE_NAME}@latest'`
6252
6696
  );
6253
- } else if (verify.installedVersion !== "0.16.6") {
6697
+ } else if (verify.installedVersion !== "0.16.8") {
6254
6698
  console.log(
6255
- ` \u2192 This process is still running ${"0.16.6"}. Next invocation will use ${verify.installedVersion}.`
6699
+ ` \u2192 This process is still running ${"0.16.8"}. Next invocation will use ${verify.installedVersion}.`
6256
6700
  );
6257
6701
  }
6258
6702
  }
@@ -6287,14 +6731,14 @@ async function getUpdateAvailability() {
6287
6731
  if (isDevMode()) return null;
6288
6732
  const latest = await fetchLatestVersion();
6289
6733
  if (latest === null) return {
6290
- current: "0.16.6",
6734
+ current: "0.16.8",
6291
6735
  latest: null,
6292
6736
  updateAvailable: false
6293
6737
  };
6294
6738
  return {
6295
- current: "0.16.6",
6739
+ current: "0.16.8",
6296
6740
  latest,
6297
- updateAvailable: shouldUpdate("0.16.6", latest)
6741
+ updateAvailable: shouldUpdate("0.16.8", latest)
6298
6742
  };
6299
6743
  }
6300
6744
  async function checkForUpdate() {
@@ -6384,7 +6828,7 @@ async function restartServices(state) {
6384
6828
  }
6385
6829
  async function forceUpdate() {
6386
6830
  const latest = await fetchLatestVersion();
6387
- const current = "0.16.6";
6831
+ const current = "0.16.8";
6388
6832
  if (latest === null) {
6389
6833
  console.error("Could not reach npm registry. Check your network.");
6390
6834
  process.exit(1);
@@ -6797,7 +7241,7 @@ async function status() {
6797
7241
  console.log(`Server: running on ${url} (PID ${server.pid}, v${ver})`);
6798
7242
  if (isServerStale(server)) {
6799
7243
  console.log(
6800
- ` \u26A0 serving stale ${ver} (CLI is ${"0.16.6"}) \u2014 run 'fleetlens start' to restart on the current version`
7244
+ ` \u26A0 serving stale ${ver} (CLI is ${"0.16.8"}) \u2014 run 'fleetlens start' to restart on the current version`
6801
7245
  );
6802
7246
  }
6803
7247
  } else {
@@ -6836,7 +7280,7 @@ async function web(args2) {
6836
7280
  const open = args2.includes("--open");
6837
7281
  const positional = args2.filter((a) => !a.startsWith("--"));
6838
7282
  const rawPath = positional[0] ?? "";
6839
- const path10 = rawPath.startsWith("/") ? rawPath : rawPath ? `/${rawPath}` : "";
7283
+ const path11 = rawPath.startsWith("/") ? rawPath : rawPath ? `/${rawPath}` : "";
6840
7284
  let result;
6841
7285
  try {
6842
7286
  result = await ensureCurrentServer({});
@@ -6844,7 +7288,7 @@ async function web(args2) {
6844
7288
  console.error(`Failed to start: ${err.message}`);
6845
7289
  process.exit(1);
6846
7290
  }
6847
- const url = `http://localhost:${result.port}${path10}`;
7291
+ const url = `http://localhost:${result.port}${path11}`;
6848
7292
  if (result.restarted) {
6849
7293
  console.log(`fleetlens restarted on http://localhost:${result.port} (PID ${result.pid}) \u2014 replaced stale ${result.previousVersion ?? "unknown"} server`);
6850
7294
  }
@@ -6905,9 +7349,9 @@ function readFromCredentialsFile() {
6905
7349
  join7(homedir4(), ".claude", ".credentials.json"),
6906
7350
  join7(homedir4(), ".config", "claude", "credentials.json")
6907
7351
  ];
6908
- for (const path10 of candidates) {
7352
+ for (const path11 of candidates) {
6909
7353
  try {
6910
- const blob = readFileSync10(path10, "utf8");
7354
+ const blob = readFileSync10(path11, "utf8");
6911
7355
  const creds = extractCredentials(blob);
6912
7356
  if (creds) return creds;
6913
7357
  } catch {
@@ -7031,13 +7475,13 @@ var init_api = __esm({
7031
7475
 
7032
7476
  // src/usage/grok.ts
7033
7477
  import { existsSync as existsSync8, readFileSync as readFileSync11 } from "node:fs";
7034
- import os8 from "node:os";
7035
- import path8 from "node:path";
7478
+ import os9 from "node:os";
7479
+ import path9 from "node:path";
7036
7480
  function grokHome() {
7037
- return process.env.GROK_HOME || path8.join(os8.homedir(), ".grok");
7481
+ return process.env.GROK_HOME || path9.join(os9.homedir(), ".grok");
7038
7482
  }
7039
7483
  function authPath() {
7040
- return path8.join(grokHome(), "auth.json");
7484
+ return path9.join(grokHome(), "auth.json");
7041
7485
  }
7042
7486
  function loadAuthEntry() {
7043
7487
  const p = authPath();
@@ -7253,15 +7697,15 @@ import {
7253
7697
  readFileSync as readFileSync12,
7254
7698
  writeFileSync as writeFileSync6
7255
7699
  } from "node:fs";
7256
- import os9 from "node:os";
7257
- import path9 from "node:path";
7700
+ import os10 from "node:os";
7701
+ import path10 from "node:path";
7258
7702
  function codexHome() {
7259
7703
  const env = process.env.CODEX_HOME?.trim();
7260
7704
  if (env) return env;
7261
- return path9.join(os9.homedir(), ".codex");
7705
+ return path10.join(os10.homedir(), ".codex");
7262
7706
  }
7263
7707
  function authPath2() {
7264
- return path9.join(codexHome(), "auth.json");
7708
+ return path10.join(codexHome(), "auth.json");
7265
7709
  }
7266
7710
  function loadAuth() {
7267
7711
  const p = authPath2();
@@ -7376,7 +7820,7 @@ function authHeaders2(accessToken, accountId) {
7376
7820
  }
7377
7821
  return headers;
7378
7822
  }
7379
- function numberOf2(v) {
7823
+ function numberOf3(v) {
7380
7824
  if (typeof v === "number" && Number.isFinite(v)) return v;
7381
7825
  if (typeof v === "string" && v.trim()) {
7382
7826
  const n = Number(v);
@@ -7386,21 +7830,21 @@ function numberOf2(v) {
7386
7830
  }
7387
7831
  function windowSeconds(raw) {
7388
7832
  if (!raw) return void 0;
7389
- const sec = numberOf2(raw.limit_window_seconds);
7833
+ const sec = numberOf3(raw.limit_window_seconds);
7390
7834
  if (sec !== void 0) return sec;
7391
- const minutes = numberOf2(raw.window_minutes);
7835
+ const minutes = numberOf3(raw.window_minutes);
7392
7836
  if (minutes !== void 0) return minutes * 60;
7393
7837
  return void 0;
7394
7838
  }
7395
7839
  function normalizeWindow2(raw, headerPercent, nowMs) {
7396
- const used = numberOf2(raw?.used_percent) ?? headerPercent;
7840
+ const used = numberOf3(raw?.used_percent) ?? headerPercent;
7397
7841
  if (used === void 0) return null;
7398
7842
  let resetsAt = null;
7399
- const resetUnix = numberOf2(raw?.reset_at) ?? numberOf2(raw?.resets_at);
7843
+ const resetUnix = numberOf3(raw?.reset_at) ?? numberOf3(raw?.resets_at);
7400
7844
  if (resetUnix !== void 0) {
7401
7845
  resetsAt = new Date(resetUnix * 1e3).toISOString();
7402
7846
  } else {
7403
- const after = numberOf2(raw?.reset_after_seconds);
7847
+ const after = numberOf3(raw?.reset_after_seconds);
7404
7848
  if (after !== void 0) {
7405
7849
  resetsAt = new Date(nowMs + after * 1e3).toISOString();
7406
7850
  }
@@ -7416,8 +7860,8 @@ function parseCodexWhamUsage(body, headers = {}, nowMs = Date.now()) {
7416
7860
  }
7417
7861
  const b = body;
7418
7862
  const rateLimit = b.rate_limit && typeof b.rate_limit === "object" ? b.rate_limit : {};
7419
- const headerPrimary = numberOf2(headers["x-codex-primary-used-percent"]);
7420
- const headerSecondary = numberOf2(headers["x-codex-secondary-used-percent"]);
7863
+ const headerPrimary = numberOf3(headers["x-codex-primary-used-percent"]);
7864
+ const headerSecondary = numberOf3(headers["x-codex-secondary-used-percent"]);
7421
7865
  const primary = rateLimit.primary_window && typeof rateLimit.primary_window === "object" ? rateLimit.primary_window : null;
7422
7866
  const secondary = rateLimit.secondary_window && typeof rateLimit.secondary_window === "object" ? rateLimit.secondary_window : null;
7423
7867
  const candidates = [
@@ -7533,6 +7977,214 @@ var init_codex2 = __esm({
7533
7977
  }
7534
7978
  });
7535
7979
 
7980
+ // src/usage/copilot.ts
7981
+ import { spawn as spawn3 } from "node:child_process";
7982
+ import { existsSync as existsSync10 } from "node:fs";
7983
+ import { dirname as dirname8, join as join8 } from "node:path";
7984
+ function recordOf2(value) {
7985
+ return typeof value === "object" && value !== null ? value : void 0;
7986
+ }
7987
+ function numberOf4(value) {
7988
+ return typeof value === "number" && Number.isFinite(value) ? value : void 0;
7989
+ }
7990
+ function clampPercent(value) {
7991
+ return Math.min(100, Math.max(0, value));
7992
+ }
7993
+ function nextCopilotMonthlyReset(nowMs = Date.now()) {
7994
+ const now = new Date(nowMs);
7995
+ return new Date(Date.UTC(now.getUTCFullYear(), now.getUTCMonth() + 1, 1)).toISOString();
7996
+ }
7997
+ function quotaResetDate(value, nowMs) {
7998
+ const parsed = typeof value === "string" ? Date.parse(value) : Number.NaN;
7999
+ return Number.isFinite(parsed) && parsed > nowMs + 6e4 ? new Date(parsed).toISOString() : nextCopilotMonthlyReset(nowMs);
8000
+ }
8001
+ function parseCopilotQuota(body, nowMs = Date.now()) {
8002
+ const root = recordOf2(body);
8003
+ const snapshots = recordOf2(root?.quotaSnapshots);
8004
+ if (!snapshots) {
8005
+ throw new CopilotApiError("Copilot quota response missing quotaSnapshots", "parse");
8006
+ }
8007
+ const chat = recordOf2(snapshots.chat);
8008
+ const legacy = recordOf2(snapshots.premium_interactions);
8009
+ const chatLimit = numberOf4(chat?.entitlementRequests);
8010
+ const quota = chat && (chatLimit !== void 0 && chatLimit > 0 || chat.isUnlimitedEntitlement === true) ? chat : legacy;
8011
+ if (!quota) {
8012
+ throw new CopilotApiError("Copilot quota response has no chat allowance", "parse");
8013
+ }
8014
+ const unlimited = quota.isUnlimitedEntitlement === true;
8015
+ const remainingPercent = numberOf4(quota.remainingPercentage);
8016
+ const utilization = unlimited ? null : remainingPercent === void 0 ? null : clampPercent(100 - remainingPercent);
8017
+ const limit = numberOf4(quota.entitlementRequests) ?? null;
8018
+ const used = numberOf4(quota.usedRequests) ?? null;
8019
+ const unit = quota.tokenBasedBilling === true ? "ai-credits" : "premium-requests";
8020
+ return {
8021
+ captured_at: new Date(nowMs).toISOString(),
8022
+ agent: "copilot",
8023
+ five_hour: { utilization: null, resets_at: null },
8024
+ seven_day: { utilization: null, resets_at: null },
8025
+ monthly: {
8026
+ utilization,
8027
+ resets_at: quotaResetDate(quota.resetDate, nowMs)
8028
+ },
8029
+ monthly_quota: {
8030
+ used,
8031
+ limit,
8032
+ remaining: used !== null && limit !== null ? Math.max(0, limit - used) : null,
8033
+ unit,
8034
+ unlimited
8035
+ },
8036
+ seven_day_opus: null,
8037
+ seven_day_sonnet: null,
8038
+ seven_day_oauth_apps: null,
8039
+ seven_day_cowork: null,
8040
+ extra_usage: null,
8041
+ plan_type: unit === "ai-credits" ? "AI credits" : "premium requests"
8042
+ };
8043
+ }
8044
+ function rpcFrame(message) {
8045
+ const body = Buffer.from(JSON.stringify(message), "utf8");
8046
+ return Buffer.concat([
8047
+ Buffer.from(`Content-Length: ${body.length}\r
8048
+ \r
8049
+ `, "ascii"),
8050
+ body
8051
+ ]);
8052
+ }
8053
+ function resolveCopilotCliPath() {
8054
+ const configured = process.env.COPILOT_CLI_PATH?.trim();
8055
+ if (configured) return configured;
8056
+ const sibling = join8(dirname8(process.execPath), process.platform === "win32" ? "copilot.cmd" : "copilot");
8057
+ return existsSync10(sibling) ? sibling : process.platform === "win32" ? "copilot.cmd" : "copilot";
8058
+ }
8059
+ async function requestQuota(child) {
8060
+ const decoder = new ContentLengthDecoder();
8061
+ const pending = /* @__PURE__ */ new Map();
8062
+ let nextId = 1;
8063
+ const rejectAll = (error) => {
8064
+ for (const waiter of pending.values()) waiter.reject(error);
8065
+ pending.clear();
8066
+ };
8067
+ child.stdout.on("data", (chunk2) => {
8068
+ try {
8069
+ for (const value of decoder.push(chunk2)) {
8070
+ const message = recordOf2(value);
8071
+ const id = numberOf4(message?.id);
8072
+ if (id === void 0) continue;
8073
+ const waiter = pending.get(id);
8074
+ if (!waiter) continue;
8075
+ pending.delete(id);
8076
+ const rpcError = recordOf2(message?.error);
8077
+ if (rpcError) {
8078
+ waiter.reject(new CopilotApiError(
8079
+ typeof rpcError.message === "string" ? rpcError.message : "Copilot RPC request failed",
8080
+ "protocol"
8081
+ ));
8082
+ } else {
8083
+ waiter.resolve(message?.result);
8084
+ }
8085
+ }
8086
+ } catch (error) {
8087
+ rejectAll(error);
8088
+ }
8089
+ });
8090
+ const exited = new Promise((_, reject) => {
8091
+ child.once("error", (error) => {
8092
+ reject(new CopilotApiError(
8093
+ error.message,
8094
+ error.code === "ENOENT" ? "no_cli" : "protocol"
8095
+ ));
8096
+ });
8097
+ child.once("exit", (code) => {
8098
+ reject(new CopilotApiError(`Copilot RPC exited before responding (code ${code ?? "unknown"})`, "protocol"));
8099
+ });
8100
+ });
8101
+ const request = (method, params = {}) => {
8102
+ const id = nextId++;
8103
+ const response = new Promise((resolve4, reject) => {
8104
+ pending.set(id, { resolve: resolve4, reject });
8105
+ child.stdin.write(rpcFrame({ jsonrpc: "2.0", id, method, params }));
8106
+ });
8107
+ return Promise.race([response, exited]);
8108
+ };
8109
+ await request("connect", {});
8110
+ return request("account.getQuota", {});
8111
+ }
8112
+ async function fetchCopilotUsage() {
8113
+ const cliPath = resolveCopilotCliPath();
8114
+ const child = spawn3(cliPath, ["--headless", "--no-auto-update", "--stdio", "--log-level", "none"], {
8115
+ cwd: process.cwd(),
8116
+ env: process.env,
8117
+ stdio: ["pipe", "pipe", "pipe"],
8118
+ windowsHide: true,
8119
+ shell: process.platform === "win32"
8120
+ });
8121
+ let stderr = "";
8122
+ child.stderr.on("data", (chunk2) => {
8123
+ stderr = (stderr + chunk2.toString("utf8")).slice(-2e3);
8124
+ });
8125
+ const timeout = new Promise((_, reject) => {
8126
+ const handle = setTimeout(() => {
8127
+ reject(new CopilotApiError("Timed out reading Copilot quota", "timeout"));
8128
+ }, RPC_TIMEOUT_MS);
8129
+ handle.unref();
8130
+ });
8131
+ try {
8132
+ const body = await Promise.race([requestQuota(child), timeout]);
8133
+ return parseCopilotQuota(body);
8134
+ } catch (error) {
8135
+ if (error instanceof CopilotApiError) {
8136
+ const message = `${error.message} ${stderr}`.toLowerCase();
8137
+ if (message.includes("not logged") || message.includes("authentication")) {
8138
+ throw new CopilotApiError("Copilot not logged in. Run `copilot login`.", "no_auth");
8139
+ }
8140
+ throw error;
8141
+ }
8142
+ throw new CopilotApiError(error.message, "protocol");
8143
+ } finally {
8144
+ child.kill();
8145
+ }
8146
+ }
8147
+ var RPC_TIMEOUT_MS, CopilotApiError, ContentLengthDecoder;
8148
+ var init_copilot2 = __esm({
8149
+ "src/usage/copilot.ts"() {
8150
+ "use strict";
8151
+ RPC_TIMEOUT_MS = 1e4;
8152
+ CopilotApiError = class extends Error {
8153
+ constructor(message, code) {
8154
+ super(message);
8155
+ this.code = code;
8156
+ }
8157
+ };
8158
+ ContentLengthDecoder = class {
8159
+ buffer = Buffer.alloc(0);
8160
+ push(chunk2) {
8161
+ this.buffer = Buffer.concat([this.buffer, chunk2]);
8162
+ const messages = [];
8163
+ while (true) {
8164
+ const headerEnd = this.buffer.indexOf("\r\n\r\n");
8165
+ if (headerEnd === -1) break;
8166
+ const header = this.buffer.subarray(0, headerEnd).toString("ascii");
8167
+ const match = header.match(/(?:^|\r\n)Content-Length:\s*(\d+)/i);
8168
+ if (!match) {
8169
+ throw new CopilotApiError("Copilot RPC response missing Content-Length", "protocol");
8170
+ }
8171
+ const length = Number(match[1]);
8172
+ const bodyStart = headerEnd + 4;
8173
+ if (this.buffer.length < bodyStart + length) break;
8174
+ const body = this.buffer.subarray(bodyStart, bodyStart + length).toString("utf8");
8175
+ this.buffer = this.buffer.subarray(bodyStart + length);
8176
+ try {
8177
+ messages.push(JSON.parse(body));
8178
+ } catch {
8179
+ throw new CopilotApiError("Copilot RPC returned invalid JSON", "protocol");
8180
+ }
8181
+ }
8182
+ return messages;
8183
+ }
8184
+ };
8185
+ }
8186
+ });
8187
+
7536
8188
  // src/usage/format.ts
7537
8189
  function formatUsage(snapshot) {
7538
8190
  const rows = [
@@ -7872,6 +8524,51 @@ var usage_exports = {};
7872
8524
  __export(usage_exports, {
7873
8525
  usage: () => usage
7874
8526
  });
8527
+ async function saveAuxiliarySnapshots() {
8528
+ let saved = 0;
8529
+ for (const source of agentSources) {
8530
+ if (source.kind === "claude-code" || !source.usagePoller) continue;
8531
+ try {
8532
+ const partial = await source.usagePoller();
8533
+ if (!partial) continue;
8534
+ appendSnapshot(USAGE_LOG2, {
8535
+ ...partial,
8536
+ seven_day_opus: null,
8537
+ seven_day_sonnet: null,
8538
+ seven_day_oauth_apps: null,
8539
+ seven_day_cowork: null,
8540
+ extra_usage: null
8541
+ });
8542
+ saved += 1;
8543
+ } catch {
8544
+ }
8545
+ }
8546
+ try {
8547
+ appendSnapshot(USAGE_LOG2, await fetchCodexUsage());
8548
+ saved += 1;
8549
+ } catch (err) {
8550
+ if (!(err instanceof CodexApiError) || err.code !== "no_auth" && err.code !== "api_key_only") {
8551
+ console.warn(`codex usage: ${err.message}`);
8552
+ }
8553
+ }
8554
+ try {
8555
+ appendSnapshot(USAGE_LOG2, await fetchCopilotUsage());
8556
+ saved += 1;
8557
+ } catch (err) {
8558
+ if (!(err instanceof CopilotApiError) || err.code !== "no_cli" && err.code !== "no_auth") {
8559
+ console.warn(`copilot usage: ${err.message}`);
8560
+ }
8561
+ }
8562
+ try {
8563
+ appendSnapshot(USAGE_LOG2, await fetchGrokUsage());
8564
+ saved += 1;
8565
+ } catch (err) {
8566
+ if (!(err instanceof GrokApiError) || err.code !== "no_auth" && err.code !== "not_weekly") {
8567
+ console.warn(`grok usage: ${err.message}`);
8568
+ }
8569
+ }
8570
+ return saved;
8571
+ }
7875
8572
  async function usage(args2) {
7876
8573
  if (args2.includes("--help") || args2.includes("-h")) {
7877
8574
  console.log(`fleetlens usage \u2014 plan utilization snapshot
@@ -7888,54 +8585,27 @@ Usage:
7888
8585
  return;
7889
8586
  }
7890
8587
  const save = args2.includes("--save");
8588
+ let snapshot;
7891
8589
  try {
7892
- const snapshot = await fetchUsage();
8590
+ snapshot = await fetchUsage();
7893
8591
  if (save) appendSnapshot(USAGE_LOG2, snapshot);
7894
8592
  process.stdout.write(formatUsage(snapshot));
7895
- if (save) {
7896
- for (const source of agentSources) {
7897
- if (source.kind === "claude-code" || !source.usagePoller) continue;
7898
- try {
7899
- const partial = await source.usagePoller();
7900
- if (!partial) continue;
7901
- appendSnapshot(USAGE_LOG2, {
7902
- ...partial,
7903
- seven_day_opus: null,
7904
- seven_day_sonnet: null,
7905
- seven_day_oauth_apps: null,
7906
- seven_day_cowork: null,
7907
- extra_usage: null
7908
- });
7909
- } catch {
7910
- }
7911
- }
7912
- try {
7913
- appendSnapshot(USAGE_LOG2, await fetchCodexUsage());
7914
- } catch (err) {
7915
- if (err instanceof CodexApiError && (err.code === "no_auth" || err.code === "api_key_only")) {
7916
- } else {
7917
- console.warn(
7918
- `codex usage: ${err.message}`
7919
- );
7920
- }
7921
- }
7922
- try {
7923
- appendSnapshot(USAGE_LOG2, await fetchGrokUsage());
7924
- } catch (err) {
7925
- if (err instanceof GrokApiError && err.code === "no_auth") {
7926
- } else {
7927
- console.warn(`grok usage: ${err.message}`);
7928
- }
7929
- }
7930
- }
7931
- process.stdout.write("\n (tip: run with --history for the daily token/cost table)\n");
7932
8593
  } catch (err) {
7933
- if (err instanceof UsageApiError) {
8594
+ if (!save || !(err instanceof UsageApiError)) {
8595
+ if (!(err instanceof UsageApiError)) throw err;
7934
8596
  console.error(`Error: ${err.message}`);
7935
- process.exit(1);
8597
+ process.exitCode = 1;
8598
+ return;
7936
8599
  }
7937
- throw err;
8600
+ const saved = await saveAuxiliarySnapshots();
8601
+ if (saved === 0) {
8602
+ console.error(`Error: ${err.message}`);
8603
+ process.exitCode = 1;
8604
+ }
8605
+ return;
7938
8606
  }
8607
+ if (save) await saveAuxiliarySnapshots();
8608
+ process.stdout.write("\n (tip: run with --history for the daily token/cost table)\n");
7939
8609
  }
7940
8610
  var USAGE_LOG2;
7941
8611
  var init_usage = __esm({
@@ -7944,6 +8614,7 @@ var init_usage = __esm({
7944
8614
  init_api();
7945
8615
  init_grok2();
7946
8616
  init_codex2();
8617
+ init_copilot2();
7947
8618
  init_format();
7948
8619
  init_storage();
7949
8620
  init_fs();
@@ -8438,6 +9109,7 @@ __export(dist_exports, {
8438
9109
  ANTIGRAVITY_METADATA: () => ANTIGRAVITY_METADATA,
8439
9110
  CLAUDE_CODE_METADATA: () => CLAUDE_CODE_METADATA,
8440
9111
  CODEX_METADATA: () => CODEX_METADATA,
9112
+ COPILOT_METADATA: () => COPILOT_METADATA,
8441
9113
  COWORK_METADATA: () => COWORK_METADATA,
8442
9114
  GEMINI_METADATA: () => GEMINI_METADATA,
8443
9115
  GROK_METADATA: () => GROK_METADATA,
@@ -8854,7 +9526,7 @@ function closeTurn(t, closed, cwd) {
8854
9526
  let active = 0;
8855
9527
  for (let i = 1; i < ts.length; i++) {
8856
9528
  const dt = ts[i] - ts[i - 1];
8857
- if (dt < IDLE_GAP_MS5)
9529
+ if (dt < IDLE_GAP_MS6)
8858
9530
  active += dt;
8859
9531
  }
8860
9532
  closed.push({
@@ -9051,7 +9723,7 @@ function aggregateDay(dayEvents, _sessionFallbackProject) {
9051
9723
  let activeMs2 = 0;
9052
9724
  for (let i = 1; i < tsSorted.length; i++) {
9053
9725
  const dt = tsSorted[i] - tsSorted[i - 1];
9054
- if (dt < IDLE_GAP_MS5)
9726
+ if (dt < IDLE_GAP_MS6)
9055
9727
  activeMs2 += dt;
9056
9728
  }
9057
9729
  const tsSortedStrings = dayEvents.map((e) => e.timestamp).filter((t) => !!t).sort();
@@ -9238,7 +9910,7 @@ function buildEntries(sessionDetail) {
9238
9910
  entries2.sort((a, b) => a.local_day.localeCompare(b.local_day));
9239
9911
  return entries2;
9240
9912
  }
9241
- var IDLE_GAP_MS5, INTERRUPT_RE2, PR_TITLE_RE, BASH_CHAIN_SPLIT_RE, SHELL_NOISE, IMAGE_BLOCK_RE;
9913
+ var IDLE_GAP_MS6, INTERRUPT_RE2, PR_TITLE_RE, BASH_CHAIN_SPLIT_RE, SHELL_NOISE, IMAGE_BLOCK_RE;
9242
9914
  var init_build = __esm({
9243
9915
  "../entries/dist/build.js"() {
9244
9916
  "use strict";
@@ -9246,7 +9918,7 @@ var init_build = __esm({
9246
9918
  init_types();
9247
9919
  init_signals();
9248
9920
  init_trivial();
9249
- IDLE_GAP_MS5 = 3 * 60 * 1e3;
9921
+ IDLE_GAP_MS6 = 3 * 60 * 1e3;
9250
9922
  INTERRUPT_RE2 = /\[request interrupted|interrupted by user/i;
9251
9923
  PR_TITLE_RE = /--title\s+["']([^"']+)["']/;
9252
9924
  BASH_CHAIN_SPLIT_RE = /\|\||&&|;|\|/;
@@ -9275,11 +9947,11 @@ var init_dist2 = __esm({
9275
9947
  });
9276
9948
 
9277
9949
  // ../entries/dist/digest-fs.js
9278
- import { readFileSync as readFileSync13, readdirSync, writeFileSync as writeFileSync7, renameSync as renameSync2, chmodSync, mkdirSync as mkdirSync6, existsSync as existsSync10 } from "node:fs";
9279
- import { dirname as dirname8, join as join8 } from "node:path";
9280
- function parseDigestFile(path10, expectedVersion) {
9950
+ import { readFileSync as readFileSync13, readdirSync, writeFileSync as writeFileSync7, renameSync as renameSync2, chmodSync, mkdirSync as mkdirSync6, existsSync as existsSync11 } from "node:fs";
9951
+ import { dirname as dirname9, join as join9 } from "node:path";
9952
+ function parseDigestFile(path11, expectedVersion) {
9281
9953
  try {
9282
- const parsed = JSON.parse(readFileSync13(path10, "utf8"));
9954
+ const parsed = JSON.parse(readFileSync13(path11, "utf8"));
9283
9955
  if (!parsed || typeof parsed !== "object")
9284
9956
  return null;
9285
9957
  if (parsed.version !== expectedVersion)
@@ -9298,24 +9970,24 @@ function digestsDir() {
9298
9970
  digestsDirCached = envOverride ?? cclensPath("digests");
9299
9971
  return digestsDirCached;
9300
9972
  }
9301
- function __setDigestsDirForTest(path10) {
9302
- digestsDirCached = path10;
9303
- mkdirSync6(join8(path10, "day"), { recursive: true });
9304
- mkdirSync6(join8(path10, "week"), { recursive: true });
9305
- mkdirSync6(join8(path10, "month"), { recursive: true });
9973
+ function __setDigestsDirForTest(path11) {
9974
+ digestsDirCached = path11;
9975
+ mkdirSync6(join9(path11, "day"), { recursive: true });
9976
+ mkdirSync6(join9(path11, "week"), { recursive: true });
9977
+ mkdirSync6(join9(path11, "month"), { recursive: true });
9306
9978
  }
9307
9979
  function dayDigestPath(date) {
9308
- return join8(digestsDir(), "day", `${date}.json`);
9980
+ return join9(digestsDir(), "day", `${date}.json`);
9309
9981
  }
9310
9982
  function weekDigestPath(monday) {
9311
- return join8(digestsDir(), "week", `${monday}.json`);
9983
+ return join9(digestsDir(), "week", `${monday}.json`);
9312
9984
  }
9313
9985
  function monthDigestPath(yearMonth) {
9314
- return join8(digestsDir(), "month", `${yearMonth}.json`);
9986
+ return join9(digestsDir(), "month", `${yearMonth}.json`);
9315
9987
  }
9316
9988
  function writeDayDigest(digest2) {
9317
9989
  const final = dayDigestPath(digest2.key);
9318
- mkdirSync6(dirname8(final), { recursive: true });
9990
+ mkdirSync6(dirname9(final), { recursive: true });
9319
9991
  const tmp = `${final}.tmp`;
9320
9992
  writeFileSync7(tmp, JSON.stringify(digest2, null, 2), "utf8");
9321
9993
  if (process.platform !== "win32") {
@@ -9328,7 +10000,7 @@ function writeDayDigest(digest2) {
9328
10000
  }
9329
10001
  function readDayDigest(date) {
9330
10002
  const p = dayDigestPath(date);
9331
- if (!existsSync10(p))
10003
+ if (!existsSync11(p))
9332
10004
  return null;
9333
10005
  return parseDigestFile(p, CURRENT_DAY_DIGEST_SCHEMA_VERSION);
9334
10006
  }
@@ -9351,7 +10023,7 @@ function __clearTodayCacheForTest() {
9351
10023
  }
9352
10024
  function writeWeekDigest(digest2) {
9353
10025
  const final = weekDigestPath(digest2.key);
9354
- mkdirSync6(dirname8(final), { recursive: true });
10026
+ mkdirSync6(dirname9(final), { recursive: true });
9355
10027
  const tmp = `${final}.tmp`;
9356
10028
  writeFileSync7(tmp, JSON.stringify(digest2, null, 2), "utf8");
9357
10029
  if (process.platform !== "win32") {
@@ -9364,13 +10036,13 @@ function writeWeekDigest(digest2) {
9364
10036
  }
9365
10037
  function readWeekDigest(monday) {
9366
10038
  const p = weekDigestPath(monday);
9367
- if (!existsSync10(p))
10039
+ if (!existsSync11(p))
9368
10040
  return null;
9369
10041
  return parseDigestFile(p, CURRENT_WEEK_DIGEST_SCHEMA_VERSION);
9370
10042
  }
9371
10043
  function listWeekDigestKeys() {
9372
- const dir = join8(digestsDir(), "week");
9373
- if (!existsSync10(dir))
10044
+ const dir = join9(digestsDir(), "week");
10045
+ if (!existsSync11(dir))
9374
10046
  return [];
9375
10047
  return readdirSync(dir).filter((f) => f.endsWith(".json")).map((f) => f.slice(0, -".json".length)).filter((k) => /^\d{4}-\d{2}-\d{2}$/.test(k));
9376
10048
  }
@@ -9388,7 +10060,7 @@ function setCurrentWeekDigestInCache(monday, digest2, nowMs) {
9388
10060
  }
9389
10061
  function writeMonthDigest(digest2) {
9390
10062
  const final = monthDigestPath(digest2.key);
9391
- mkdirSync6(dirname8(final), { recursive: true });
10063
+ mkdirSync6(dirname9(final), { recursive: true });
9392
10064
  const tmp = `${final}.tmp`;
9393
10065
  writeFileSync7(tmp, JSON.stringify(digest2, null, 2), "utf8");
9394
10066
  if (process.platform !== "win32") {
@@ -9401,13 +10073,13 @@ function writeMonthDigest(digest2) {
9401
10073
  }
9402
10074
  function readMonthDigest(yearMonth) {
9403
10075
  const p = monthDigestPath(yearMonth);
9404
- if (!existsSync10(p))
10076
+ if (!existsSync11(p))
9405
10077
  return null;
9406
10078
  return parseDigestFile(p, CURRENT_MONTH_DIGEST_SCHEMA_VERSION);
9407
10079
  }
9408
10080
  function listMonthDigestKeys() {
9409
- const dir = join8(digestsDir(), "month");
9410
- if (!existsSync10(dir))
10081
+ const dir = join9(digestsDir(), "month");
10082
+ if (!existsSync11(dir))
9411
10083
  return [];
9412
10084
  return readdirSync(dir).filter((f) => f.endsWith(".json")).map((f) => f.slice(0, -".json".length)).filter((k) => /^\d{4}-\d{2}$/.test(k));
9413
10085
  }
@@ -9469,9 +10141,9 @@ __export(fs_exports2, {
9469
10141
  writeMonthDigest: () => writeMonthDigest,
9470
10142
  writeWeekDigest: () => writeWeekDigest
9471
10143
  });
9472
- import { readFileSync as readFileSync14, readdirSync as readdirSync2, writeFileSync as writeFileSync8, mkdirSync as mkdirSync7, renameSync as renameSync3, existsSync as existsSync11 } from "node:fs";
10144
+ import { readFileSync as readFileSync14, readdirSync as readdirSync2, writeFileSync as writeFileSync8, mkdirSync as mkdirSync7, renameSync as renameSync3, existsSync as existsSync12 } from "node:fs";
9473
10145
  import { randomBytes } from "node:crypto";
9474
- import { join as join9 } from "node:path";
10146
+ import { join as join10 } from "node:path";
9475
10147
  function entriesDir() {
9476
10148
  if (entriesDirCached)
9477
10149
  return entriesDirCached;
@@ -9479,12 +10151,12 @@ function entriesDir() {
9479
10151
  entriesDirCached = envOverride ?? cclensPath("entries");
9480
10152
  return entriesDirCached;
9481
10153
  }
9482
- function __setEntriesDirForTest(path10) {
9483
- entriesDirCached = path10;
9484
- mkdirSync7(path10, { recursive: true });
10154
+ function __setEntriesDirForTest(path11) {
10155
+ entriesDirCached = path11;
10156
+ mkdirSync7(path11, { recursive: true });
9485
10157
  }
9486
10158
  function pathFor(sessionId, localDay2) {
9487
- return join9(entriesDir(), `${entryKey(sessionId, localDay2)}.json`);
10159
+ return join10(entriesDir(), `${entryKey(sessionId, localDay2)}.json`);
9488
10160
  }
9489
10161
  function tmpPathFor(final) {
9490
10162
  return `${final}.tmp.${process.pid}.${randomBytes(4).toString("hex")}`;
@@ -9528,17 +10200,17 @@ function writeEntryPreservingEnrichment(fresh) {
9528
10200
  }
9529
10201
  function readEntry(sessionId, localDay2) {
9530
10202
  const p = pathFor(sessionId, localDay2);
9531
- if (!existsSync11(p))
10203
+ if (!existsSync12(p))
9532
10204
  return null;
9533
10205
  const raw = readFileSync14(p, "utf8");
9534
10206
  return JSON.parse(raw);
9535
10207
  }
9536
10208
  function entryExists(sessionId, localDay2) {
9537
- return existsSync11(pathFor(sessionId, localDay2));
10209
+ return existsSync12(pathFor(sessionId, localDay2));
9538
10210
  }
9539
10211
  function listEntryKeys() {
9540
10212
  const dir = entriesDir();
9541
- if (!existsSync11(dir))
10213
+ if (!existsSync12(dir))
9542
10214
  return [];
9543
10215
  return readdirSync2(dir).filter((f) => f.endsWith(".json")).map((f) => f.slice(0, -".json".length));
9544
10216
  }
@@ -10020,8 +10692,8 @@ var init_parseUtil = __esm({
10020
10692
  init_errors();
10021
10693
  init_en();
10022
10694
  makeIssue = (params) => {
10023
- const { data, path: path10, errorMaps, issueData } = params;
10024
- const fullPath = [...path10, ...issueData.path || []];
10695
+ const { data, path: path11, errorMaps, issueData } = params;
10696
+ const fullPath = [...path11, ...issueData.path || []];
10025
10697
  const fullIssue = {
10026
10698
  ...issueData,
10027
10699
  path: fullPath
@@ -10329,11 +11001,11 @@ var init_types3 = __esm({
10329
11001
  init_parseUtil();
10330
11002
  init_util();
10331
11003
  ParseInputLazyPath = class {
10332
- constructor(parent, value, path10, key) {
11004
+ constructor(parent, value, path11, key) {
10333
11005
  this._cachedPath = [];
10334
11006
  this.parent = parent;
10335
11007
  this.data = value;
10336
- this._path = path10;
11008
+ this._path = path11;
10337
11009
  this._key = key;
10338
11010
  }
10339
11011
  get path() {
@@ -13817,8 +14489,8 @@ RESPOND WITH ONLY VALID JSON (no prose, no code fence):
13817
14489
  });
13818
14490
 
13819
14491
  // ../entries/dist/tmux-runner.js
13820
- import { mkdirSync as mkdirSync8, writeFileSync as writeFileSync9, existsSync as existsSync12, readdirSync as readdirSync3, realpathSync as realpathSync5, readFileSync as readFileSync15, unlinkSync as unlinkSync3, renameSync as renameSync4 } from "node:fs";
13821
- import { join as join10 } from "node:path";
14492
+ import { mkdirSync as mkdirSync8, writeFileSync as writeFileSync9, existsSync as existsSync13, readdirSync as readdirSync3, realpathSync as realpathSync5, readFileSync as readFileSync15, unlinkSync as unlinkSync3, renameSync as renameSync4 } from "node:fs";
14493
+ import { join as join11 } from "node:path";
13822
14494
  import { homedir as homedir5 } from "node:os";
13823
14495
  import { spawnSync as spawnSync2 } from "node:child_process";
13824
14496
  function which(bin) {
@@ -13835,13 +14507,13 @@ function tmuxRunnerAvailable() {
13835
14507
  return { ok: true };
13836
14508
  }
13837
14509
  function runtimeCwd() {
13838
- const dir = join10(homedir5(), ".cclens", "runtime");
13839
- if (!existsSync12(dir))
14510
+ const dir = join11(homedir5(), ".cclens", "runtime");
14511
+ if (!existsSync13(dir))
13840
14512
  mkdirSync8(dir, { recursive: true });
13841
14513
  return realpathSync5(dir);
13842
14514
  }
13843
14515
  function ensureRuntimeCwdTrusted(cwd) {
13844
- const cfgPath = join10(homedir5(), ".claude.json");
14516
+ const cfgPath = join11(homedir5(), ".claude.json");
13845
14517
  let cfg;
13846
14518
  try {
13847
14519
  cfg = JSON.parse(readFileSync15(cfgPath, "utf8"));
@@ -13886,9 +14558,9 @@ async function runClaudeUnderTmuxImpl(args2) {
13886
14558
  ensureRuntimeCwdTrusted(cwd);
13887
14559
  const runId = `${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
13888
14560
  const sessionName = `cclens-${runId}`;
13889
- const systemFile = join10(cwd, `system-${runId}.txt`);
13890
- const userFile = join10(cwd, `user-${runId}.txt`);
13891
- const wrapper = join10(cwd, `run-${runId}.sh`);
14561
+ const systemFile = join11(cwd, `system-${runId}.txt`);
14562
+ const userFile = join11(cwd, `user-${runId}.txt`);
14563
+ const wrapper = join11(cwd, `run-${runId}.sh`);
13892
14564
  writeFileSync9(systemFile, args2.systemPrompt);
13893
14565
  writeFileSync9(userFile, args2.reminder ? `${args2.userPrompt}
13894
14566
 
@@ -13907,10 +14579,10 @@ exec ${shellEscape(claudeBin)} \\
13907
14579
  "$USR"
13908
14580
  `, { mode: 493 });
13909
14581
  const existingBefore = snapshotAllTranscripts();
13910
- const spawn4 = spawnSync2(tmuxBin, ["new-session", "-d", "-s", sessionName, "-x", "140", "-y", "50", "-c", cwd, wrapper], { encoding: "utf8" });
13911
- if (spawn4.status !== 0) {
14582
+ const spawn5 = spawnSync2(tmuxBin, ["new-session", "-d", "-s", sessionName, "-x", "140", "-y", "50", "-c", cwd, wrapper], { encoding: "utf8" });
14583
+ if (spawn5.status !== 0) {
13912
14584
  cleanup(cwd, runId, tmuxBin, sessionName);
13913
- throw new TmuxRunError(`tmux new-session failed: ${spawn4.stderr.trim()}`);
14585
+ throw new TmuxRunError(`tmux new-session failed: ${spawn5.stderr.trim()}`);
13914
14586
  }
13915
14587
  const onAbort = () => {
13916
14588
  try {
@@ -13977,7 +14649,7 @@ function snapshotAllTranscripts() {
13977
14649
  return out;
13978
14650
  }
13979
14651
  for (const sub of subs) {
13980
- const dir = join10(root, sub);
14652
+ const dir = join11(root, sub);
13981
14653
  let files;
13982
14654
  try {
13983
14655
  files = readdirSync3(dir);
@@ -13986,15 +14658,15 @@ function snapshotAllTranscripts() {
13986
14658
  }
13987
14659
  for (const f of files) {
13988
14660
  if (f.endsWith(".jsonl"))
13989
- out.add(join10(dir, f));
14661
+ out.add(join11(dir, f));
13990
14662
  }
13991
14663
  }
13992
14664
  return out;
13993
14665
  }
13994
- function readJsonlCwd(path10, maxLines = 8) {
14666
+ function readJsonlCwd(path11, maxLines = 8) {
13995
14667
  let raw;
13996
14668
  try {
13997
- raw = readFileSync15(path10, "utf8");
14669
+ raw = readFileSync15(path11, "utf8");
13998
14670
  } catch {
13999
14671
  return void 0;
14000
14672
  }
@@ -14027,7 +14699,7 @@ async function discoverTranscript(targetCwd, existingBefore, startMs, timeoutMs,
14027
14699
  subs = [];
14028
14700
  }
14029
14701
  for (const sub of subs) {
14030
- const dir = join10(root, sub);
14702
+ const dir = join11(root, sub);
14031
14703
  let files;
14032
14704
  try {
14033
14705
  files = readdirSync3(dir);
@@ -14037,7 +14709,7 @@ async function discoverTranscript(targetCwd, existingBefore, startMs, timeoutMs,
14037
14709
  for (const f of files) {
14038
14710
  if (!f.endsWith(".jsonl"))
14039
14711
  continue;
14040
- const full = join10(dir, f);
14712
+ const full = join11(dir, f);
14041
14713
  if (existingBefore.has(full))
14042
14714
  continue;
14043
14715
  if (readJsonlCwd(full) === targetCwd)
@@ -14048,10 +14720,10 @@ async function discoverTranscript(targetCwd, existingBefore, startMs, timeoutMs,
14048
14720
  }
14049
14721
  throw new TmuxRunError(`timeout waiting for claude to create the session transcript (cwd: ${targetCwd})`);
14050
14722
  }
14051
- function parseTranscript2(path10, defaultModel) {
14723
+ function parseTranscript2(path11, defaultModel) {
14052
14724
  let raw;
14053
14725
  try {
14054
- raw = readFileSync15(path10, "utf8");
14726
+ raw = readFileSync15(path11, "utf8");
14055
14727
  } catch {
14056
14728
  return { assembled: "", inputTokens: 0, outputTokens: 0, modelUsed: defaultModel, done: false };
14057
14729
  }
@@ -14111,7 +14783,7 @@ function cleanup(cwd, runId, tmuxBin, sessionName, transcriptPath) {
14111
14783
  }
14112
14784
  for (const f of [`system-${runId}.txt`, `user-${runId}.txt`, `run-${runId}.sh`]) {
14113
14785
  try {
14114
- unlinkSync3(join10(cwd, f));
14786
+ unlinkSync3(join11(cwd, f));
14115
14787
  } catch {
14116
14788
  }
14117
14789
  }
@@ -14139,17 +14811,17 @@ var init_tmux_runner = __esm({
14139
14811
  }
14140
14812
  };
14141
14813
  mutex = Promise.resolve();
14142
- PROJECTS_ROOT = () => join10(homedir5(), ".claude", "projects");
14814
+ PROJECTS_ROOT = () => join11(homedir5(), ".claude", "projects");
14143
14815
  }
14144
14816
  });
14145
14817
 
14146
14818
  // ../entries/dist/llm-runner.js
14147
- import { spawn as spawn3 } from "node:child_process";
14148
- import { mkdirSync as mkdirSync9, appendFileSync as appendFileSync3, writeFileSync as writeFileSync10, existsSync as existsSync13 } from "node:fs";
14149
- import { join as join11 } from "node:path";
14819
+ import { spawn as spawn4 } from "node:child_process";
14820
+ import { mkdirSync as mkdirSync9, appendFileSync as appendFileSync3, writeFileSync as writeFileSync10, existsSync as existsSync14 } from "node:fs";
14821
+ import { join as join12 } from "node:path";
14150
14822
  import { randomUUID } from "node:crypto";
14151
14823
  function ensureRunsDir() {
14152
- if (!existsSync13(RUNS_DIR)) {
14824
+ if (!existsSync14(RUNS_DIR)) {
14153
14825
  try {
14154
14826
  mkdirSync9(RUNS_DIR, { recursive: true });
14155
14827
  } catch {
@@ -14178,17 +14850,17 @@ function newRunId(kind) {
14178
14850
  return `${ts}_${kind}_${short}`;
14179
14851
  }
14180
14852
  function tracePath(runId) {
14181
- return join11(RUNS_DIR, `${runId}.jsonl`);
14853
+ return join12(RUNS_DIR, `${runId}.jsonl`);
14182
14854
  }
14183
- function safeAppend(path10, line) {
14855
+ function safeAppend(path11, line) {
14184
14856
  try {
14185
- appendFileSync3(path10, line);
14857
+ appendFileSync3(path11, line);
14186
14858
  } catch {
14187
14859
  }
14188
14860
  }
14189
- function safeWrite(path10, line) {
14861
+ function safeWrite(path11, line) {
14190
14862
  try {
14191
- writeFileSync10(path10, line);
14863
+ writeFileSync10(path11, line);
14192
14864
  } catch {
14193
14865
  }
14194
14866
  }
@@ -14321,7 +14993,7 @@ function runClaudePrintMode(args2) {
14321
14993
  "--append-system-prompt",
14322
14994
  args2.systemPrompt
14323
14995
  ];
14324
- const proc = spawn3("claude", claudeArgs, { stdio: ["pipe", "pipe", "pipe"], env: { ...process.env } });
14996
+ const proc = spawn4("claude", claudeArgs, { stdio: ["pipe", "pipe", "pipe"], env: { ...process.env } });
14325
14997
  safeAppend(trace, JSON.stringify({ _meta: { type: "spawned", run_id: runId, pid: proc.pid } }) + "\n");
14326
14998
  const stdinPayload = args2.reminder ? `${args2.userPrompt}
14327
14999
 
@@ -14594,25 +15266,25 @@ var init_enrich2 = __esm({
14594
15266
  });
14595
15267
 
14596
15268
  // ../entries/dist/budget.js
14597
- import { appendFileSync as appendFileSync4, readFileSync as readFileSync16, existsSync as existsSync14, mkdirSync as mkdirSync10 } from "node:fs";
14598
- import { dirname as dirname9 } from "node:path";
15269
+ import { appendFileSync as appendFileSync4, readFileSync as readFileSync16, existsSync as existsSync15, mkdirSync as mkdirSync10 } from "node:fs";
15270
+ import { dirname as dirname10 } from "node:path";
14599
15271
  function spendPath() {
14600
15272
  if (spendPathCached)
14601
15273
  return spendPathCached;
14602
15274
  spendPathCached = cclensPath("llm-spend.jsonl");
14603
15275
  return spendPathCached;
14604
15276
  }
14605
- function __setSpendPathForTest(path10) {
14606
- spendPathCached = path10;
15277
+ function __setSpendPathForTest(path11) {
15278
+ spendPathCached = path11;
14607
15279
  }
14608
15280
  function appendSpend(record) {
14609
15281
  const p = spendPath();
14610
- mkdirSync10(dirname9(p), { recursive: true });
15282
+ mkdirSync10(dirname10(p), { recursive: true });
14611
15283
  appendFileSync4(p, JSON.stringify(record) + "\n", { encoding: "utf8" });
14612
15284
  }
14613
15285
  function monthToDateSpend(now = /* @__PURE__ */ new Date()) {
14614
15286
  const p = spendPath();
14615
- if (!existsSync14(p))
15287
+ if (!existsSync15(p))
14616
15288
  return 0;
14617
15289
  const year = now.getUTCFullYear();
14618
15290
  const month2 = now.getUTCMonth();
@@ -14646,15 +15318,15 @@ var init_budget = __esm({
14646
15318
  });
14647
15319
 
14648
15320
  // ../entries/dist/pipeline-lock.js
14649
- import { writeFileSync as writeFileSync11, unlinkSync as unlinkSync4, existsSync as existsSync15, readFileSync as readFileSync17, statSync as statSync3 } from "node:fs";
15321
+ import { writeFileSync as writeFileSync11, unlinkSync as unlinkSync4, existsSync as existsSync16, readFileSync as readFileSync17, statSync as statSync3 } from "node:fs";
14650
15322
  function lockPath() {
14651
15323
  if (lockPathCached)
14652
15324
  return lockPathCached;
14653
15325
  lockPathCached = cclensPath("llm-interactive.lock");
14654
15326
  return lockPathCached;
14655
15327
  }
14656
- function __setInteractiveLockPathForTest(path10) {
14657
- lockPathCached = path10;
15328
+ function __setInteractiveLockPathForTest(path11) {
15329
+ lockPathCached = path11;
14658
15330
  }
14659
15331
  function touchLock() {
14660
15332
  writeFileSync11(lockPath(), String(process.pid), "utf8");
@@ -14691,7 +15363,7 @@ function pidAlive(pid) {
14691
15363
  }
14692
15364
  function interactiveLockFresh(nowMs) {
14693
15365
  const p = lockPath();
14694
- if (!existsSync15(p))
15366
+ if (!existsSync16(p))
14695
15367
  return false;
14696
15368
  try {
14697
15369
  const mtime = statSync3(p).mtimeMs;
@@ -14803,16 +15475,16 @@ var init_queue = __esm({
14803
15475
  });
14804
15476
 
14805
15477
  // ../entries/dist/settings.js
14806
- import { readFileSync as readFileSync18, writeFileSync as writeFileSync12, renameSync as renameSync5, chmodSync as chmodSync2, mkdirSync as mkdirSync11, existsSync as existsSync16 } from "node:fs";
14807
- import { dirname as dirname10 } from "node:path";
15478
+ import { readFileSync as readFileSync18, writeFileSync as writeFileSync12, renameSync as renameSync5, chmodSync as chmodSync2, mkdirSync as mkdirSync11, existsSync as existsSync17 } from "node:fs";
15479
+ import { dirname as dirname11 } from "node:path";
14808
15480
  function settingsPath() {
14809
15481
  if (settingsPathCached)
14810
15482
  return settingsPathCached;
14811
15483
  settingsPathCached = cclensPath("settings.json");
14812
15484
  return settingsPathCached;
14813
15485
  }
14814
- function __setSettingsPathForTest(path10) {
14815
- settingsPathCached = path10;
15486
+ function __setSettingsPathForTest(path11) {
15487
+ settingsPathCached = path11;
14816
15488
  }
14817
15489
  function toDisk(s) {
14818
15490
  return {
@@ -14839,7 +15511,7 @@ function fromDisk(d) {
14839
15511
  }
14840
15512
  function readSettings() {
14841
15513
  const p = settingsPath();
14842
- if (!existsSync16(p))
15514
+ if (!existsSync17(p))
14843
15515
  return DEFAULT_SETTINGS;
14844
15516
  try {
14845
15517
  const raw = readFileSync18(p, "utf8");
@@ -14850,7 +15522,7 @@ function readSettings() {
14850
15522
  }
14851
15523
  function writeSettings(s) {
14852
15524
  const p = settingsPath();
14853
- mkdirSync11(dirname10(p), { recursive: true });
15525
+ mkdirSync11(dirname11(p), { recursive: true });
14854
15526
  const tmp = `${p}.tmp`;
14855
15527
  writeFileSync12(tmp, JSON.stringify(toDisk(s), null, 2), { encoding: "utf8" });
14856
15528
  if (process.platform !== "win32") {
@@ -16915,7 +17587,7 @@ function activeMs(timestamps) {
16915
17587
  let active = 0;
16916
17588
  for (let i = 1; i < ts.length; i++) {
16917
17589
  const dt = ts[i] - ts[i - 1];
16918
- if (dt < IDLE_GAP_MS6)
17590
+ if (dt < IDLE_GAP_MS7)
16919
17591
  active += dt;
16920
17592
  }
16921
17593
  return active;
@@ -17086,7 +17758,7 @@ function buildSessionSlice(entry, events, daySignature) {
17086
17758
  let intEnd = sortedTs[0];
17087
17759
  for (let i = 1; i < sortedTs.length; i++) {
17088
17760
  const dt = sortedTs[i] - intEnd;
17089
- if (dt >= IDLE_GAP_MS6) {
17761
+ if (dt >= IDLE_GAP_MS7) {
17090
17762
  intervals.push({
17091
17763
  start_min: fmtMin(intStart - sliceStartMs),
17092
17764
  end_min: fmtMin(intEnd - sliceStartMs)
@@ -17483,14 +18155,14 @@ async function generateTopSession(slice, opts = {}) {
17483
18155
  void lastModel;
17484
18156
  }
17485
18157
  }
17486
- var IDLE_GAP_MS6, LONG_AUTONOMOUS_MIN, N_USER, N_FIRST_AGENT, N_LAST_AGENT, N_USER_TURN1, N_SUBAGENT, SHELL_NOISE2, INTERRUPT_RE3, PR_TITLE_RE2, PinResponseSchema, TopSessionResponseSchema, SYSTEM_PROMPT5, TOP_SESSION_SYSTEM_PROMPT, DEFAULT_MODEL5, defaultCallLLMTopSession, validateTopSession;
18158
+ var IDLE_GAP_MS7, LONG_AUTONOMOUS_MIN, N_USER, N_FIRST_AGENT, N_LAST_AGENT, N_USER_TURN1, N_SUBAGENT, SHELL_NOISE2, INTERRUPT_RE3, PR_TITLE_RE2, PinResponseSchema, TopSessionResponseSchema, SYSTEM_PROMPT5, TOP_SESSION_SYSTEM_PROMPT, DEFAULT_MODEL5, defaultCallLLMTopSession, validateTopSession;
17487
18159
  var init_top_sessions = __esm({
17488
18160
  "../entries/dist/top-sessions.js"() {
17489
18161
  "use strict";
17490
18162
  init_zod();
17491
18163
  init_signals();
17492
18164
  init_llm_runner();
17493
- IDLE_GAP_MS6 = 3 * 60 * 1e3;
18165
+ IDLE_GAP_MS7 = 3 * 60 * 1e3;
17494
18166
  LONG_AUTONOMOUS_MIN = 20;
17495
18167
  N_USER = 150;
17496
18168
  N_FIRST_AGENT = 150;
@@ -18032,8 +18704,8 @@ var init_digest_month_pipeline = __esm({
18032
18704
  });
18033
18705
 
18034
18706
  // ../entries/dist/credentials.js
18035
- import { writeFileSync as writeFileSync13, readFileSync as readFileSync19, renameSync as renameSync6, chmodSync as chmodSync3, mkdirSync as mkdirSync12, existsSync as existsSync17, unlinkSync as unlinkSync5 } from "node:fs";
18036
- import { dirname as dirname11 } from "node:path";
18707
+ import { writeFileSync as writeFileSync13, readFileSync as readFileSync19, renameSync as renameSync6, chmodSync as chmodSync3, mkdirSync as mkdirSync12, existsSync as existsSync18, unlinkSync as unlinkSync5 } from "node:fs";
18708
+ import { dirname as dirname12 } from "node:path";
18037
18709
  async function fetchZaiUsage(candidate) {
18038
18710
  const key = candidate.trim();
18039
18711
  if (!key)
@@ -18103,7 +18775,7 @@ function credentialsPath() {
18103
18775
  }
18104
18776
  function readCredentials() {
18105
18777
  const p = credentialsPath();
18106
- if (!existsSync17(p))
18778
+ if (!existsSync18(p))
18107
18779
  return {};
18108
18780
  try {
18109
18781
  const raw = readFileSync19(p, "utf8");
@@ -18129,7 +18801,7 @@ function writeZaiKey(apiKey) {
18129
18801
  const store = readCredentials();
18130
18802
  store.zai = { ...store.zai ?? {}, apiKey };
18131
18803
  const p = credentialsPath();
18132
- mkdirSync12(dirname11(p), { recursive: true });
18804
+ mkdirSync12(dirname12(p), { recursive: true });
18133
18805
  const tmp = `${p}.tmp`;
18134
18806
  writeFileSync13(tmp, JSON.stringify(store, null, 2), { encoding: "utf8" });
18135
18807
  if (process.platform !== "win32") {
@@ -18736,9 +19408,9 @@ var menubar_exports = {};
18736
19408
  __export(menubar_exports, {
18737
19409
  menubar: () => menubar
18738
19410
  });
18739
- import { existsSync as existsSync18, mkdirSync as mkdirSync13, cpSync, rmSync as rmSync2, readdirSync as readdirSync4, writeFileSync as writeFileSync14, realpathSync as realpathSync6 } from "node:fs";
19411
+ import { existsSync as existsSync19, mkdirSync as mkdirSync13, cpSync, rmSync as rmSync2, readdirSync as readdirSync4, writeFileSync as writeFileSync14, realpathSync as realpathSync6 } from "node:fs";
18740
19412
  import { homedir as homedir6 } from "node:os";
18741
- import { join as join12, dirname as dirname12 } from "node:path";
19413
+ import { join as join13, dirname as dirname13 } from "node:path";
18742
19414
  import { fileURLToPath as fileURLToPath3 } from "node:url";
18743
19415
  import { execFile as execFile2 } from "node:child_process";
18744
19416
  import { promisify as promisify2 } from "node:util";
@@ -18746,8 +19418,8 @@ function isMac2() {
18746
19418
  return process.platform === "darwin";
18747
19419
  }
18748
19420
  function bundledAppPath() {
18749
- const here = dirname12(fileURLToPath3(import.meta.url));
18750
- return join12(here, "..", "menubar", APP_BUNDLE);
19421
+ const here = dirname13(fileURLToPath3(import.meta.url));
19422
+ return join13(here, "..", "menubar", APP_BUNDLE);
18751
19423
  }
18752
19424
  function resolveScriptPath2() {
18753
19425
  const argv1 = process.argv[1] ?? "";
@@ -18768,7 +19440,7 @@ function writeCliLaunchFile() {
18768
19440
  }
18769
19441
  }
18770
19442
  function installedAppPath() {
18771
- return join12(homedir6(), "Applications", APP_BUNDLE);
19443
+ return join13(homedir6(), "Applications", APP_BUNDLE);
18772
19444
  }
18773
19445
  async function isRunning() {
18774
19446
  try {
@@ -18778,8 +19450,8 @@ async function isRunning() {
18778
19450
  return false;
18779
19451
  }
18780
19452
  }
18781
- async function launchApp(path10) {
18782
- await execFileAsync2("open", ["-a", path10]);
19453
+ async function launchApp(path11) {
19454
+ await execFileAsync2("open", ["-a", path11]);
18783
19455
  }
18784
19456
  async function quitApp() {
18785
19457
  await execFileAsync2("osascript", ["-e", `tell application "${BUNDLE_EXEC}" to quit`]).catch(
@@ -18800,14 +19472,14 @@ async function installMenubar(opts) {
18800
19472
  return;
18801
19473
  }
18802
19474
  const src = bundledAppPath();
18803
- if (!existsSync18(src)) {
19475
+ if (!existsSync19(src)) {
18804
19476
  console.error(
18805
19477
  `Bundled widget not found at ${src}.
18806
19478
  This install was probably built without the menubar artifact. Run \`node apps/menubar/build-app.sh && cp -R apps/menubar/dist/FleetlensMenubar.app packages/cli/menubar/\` and rebuild.`
18807
19479
  );
18808
19480
  process.exit(1);
18809
19481
  }
18810
- const destDir = join12(homedir6(), "Applications");
19482
+ const destDir = join13(homedir6(), "Applications");
18811
19483
  mkdirSync13(destDir, { recursive: true });
18812
19484
  const dest = installedAppPath();
18813
19485
  if (await isRunning()) {
@@ -18842,7 +19514,7 @@ async function uninstallMenubar() {
18842
19514
  await new Promise((r) => setTimeout(r, 300));
18843
19515
  }
18844
19516
  const dest = installedAppPath();
18845
- if (existsSync18(dest)) {
19517
+ if (existsSync19(dest)) {
18846
19518
  rmSync2(dest, { recursive: true, force: true });
18847
19519
  console.log(`Removed ${dest}`);
18848
19520
  } else {
@@ -18856,7 +19528,7 @@ async function openMenubar() {
18856
19528
  return;
18857
19529
  }
18858
19530
  const dest = installedAppPath();
18859
- if (!existsSync18(dest)) {
19531
+ if (!existsSync19(dest)) {
18860
19532
  console.log("Widget not installed yet. Run `fleetlens menubar install` first.");
18861
19533
  return;
18862
19534
  }
@@ -18873,15 +19545,15 @@ async function statusMenubar() {
18873
19545
  return;
18874
19546
  }
18875
19547
  const dest = installedAppPath();
18876
- const installed = existsSync18(dest);
19548
+ const installed = existsSync19(dest);
18877
19549
  const running = await isRunning();
18878
- const bundled = existsSync18(bundledAppPath());
19550
+ const bundled = existsSync19(bundledAppPath());
18879
19551
  console.log(`Menu bar widget: ${installed ? "installed" : "not installed"}${installed ? ` (${dest})` : ""}`);
18880
19552
  console.log(`Running: ${running ? "yes" : "no"}`);
18881
19553
  console.log(`Bundled in CLI: ${bundled ? "yes" : "no \u2014 this build ships without the widget"}`);
18882
19554
  if (installed) {
18883
19555
  try {
18884
- const apps = readdirSync4(join12(homedir6(), "Applications"));
19556
+ const apps = readdirSync4(join13(homedir6(), "Applications"));
18885
19557
  const ours = apps.find((a) => a === APP_BUNDLE);
18886
19558
  console.log(`App bundle: ${ours ? "present in ~/Applications" : "missing"}`);
18887
19559
  } catch {
@@ -18965,7 +19637,7 @@ var init_config = __esm({
18965
19637
 
18966
19638
  // src/perception/build-entries.ts
18967
19639
  import { statSync as statSync4, readFileSync as readFileSync20 } from "node:fs";
18968
- import { basename as basename2, dirname as dirname13 } from "node:path";
19640
+ import { basename as basename2, dirname as dirname14 } from "node:path";
18969
19641
  function decodeProjectDirName(projectDir) {
18970
19642
  if (projectDir.startsWith("-")) {
18971
19643
  return "/" + projectDir.slice(1).replace(/-/g, "/");
@@ -18985,7 +19657,7 @@ function buildEntriesForFile(filePath) {
18985
19657
  if (rawLines.length === 0) return null;
18986
19658
  const { meta, events } = parseTranscript(rawLines);
18987
19659
  const fileName = basename2(filePath);
18988
- const projectDir = basename2(dirname13(filePath));
19660
+ const projectDir = basename2(dirname14(filePath));
18989
19661
  const sessionId = fileName.replace(/\.jsonl$/, "");
18990
19662
  const sd = {
18991
19663
  ...meta,
@@ -19239,7 +19911,7 @@ function buildIngestPayload(inputs) {
19239
19911
  return {
19240
19912
  ingestId: randomUUID2(),
19241
19913
  observedAt: (/* @__PURE__ */ new Date()).toISOString(),
19242
- cliVersion: "0.16.6",
19914
+ cliVersion: "0.16.8",
19243
19915
  ...richRollup || inputs.enrichedExtras || inputs.artifactSignals ? { schemaVersion: RICH_ROLLUP_SCHEMA_VERSION } : {},
19244
19916
  ...inputs.rollup ? { dailyRollup: inputs.rollup } : {},
19245
19917
  ...richRollup ? { richRollup } : {},
@@ -19280,8 +19952,8 @@ var init_push = __esm({
19280
19952
  });
19281
19953
 
19282
19954
  // src/team/git-remote.ts
19283
- import { existsSync as existsSync19, readFileSync as readFileSync21, statSync as statSync5 } from "node:fs";
19284
- import { dirname as dirname14, isAbsolute as isAbsolute2, join as join13, resolve as resolve2 } from "node:path";
19955
+ import { existsSync as existsSync20, readFileSync as readFileSync21, statSync as statSync5 } from "node:fs";
19956
+ import { dirname as dirname15, isAbsolute as isAbsolute2, join as join14, resolve as resolve2 } from "node:path";
19285
19957
  function parseGithubRemote(url) {
19286
19958
  const m = url.trim().match(GITHUB_URL_RE);
19287
19959
  return m ? `${m[1]}/${m[2]}`.toLowerCase() : null;
@@ -19301,19 +19973,19 @@ function originUrl2(configText) {
19301
19973
  return null;
19302
19974
  }
19303
19975
  function gitConfigPathFor(dir) {
19304
- const dotGit = join13(dir, ".git");
19976
+ const dotGit = join14(dir, ".git");
19305
19977
  const st = statSync5(dotGit, { throwIfNoEntry: false });
19306
19978
  if (!st) return null;
19307
- if (st.isDirectory()) return join13(dotGit, "config");
19979
+ if (st.isDirectory()) return join14(dotGit, "config");
19308
19980
  const m = readFileSync21(dotGit, "utf8").match(/^gitdir:\s*(.+)\s*$/m);
19309
19981
  if (!m) return null;
19310
19982
  const gd = isAbsolute2(m[1]) ? m[1] : resolve2(dir, m[1]);
19311
- const commondirFile = join13(gd, "commondir");
19312
- if (existsSync19(commondirFile)) {
19983
+ const commondirFile = join14(gd, "commondir");
19984
+ if (existsSync20(commondirFile)) {
19313
19985
  const common = readFileSync21(commondirFile, "utf8").trim();
19314
- return join13(isAbsolute2(common) ? common : resolve2(gd, common), "config");
19986
+ return join14(isAbsolute2(common) ? common : resolve2(gd, common), "config");
19315
19987
  }
19316
- return join13(gd, "config");
19988
+ return join14(gd, "config");
19317
19989
  }
19318
19990
  function createRepoResolver() {
19319
19991
  const cache = /* @__PURE__ */ new Map();
@@ -19323,14 +19995,14 @@ function createRepoResolver() {
19323
19995
  if (hit !== void 0) return hit;
19324
19996
  let repo = null;
19325
19997
  try {
19326
- for (let d = dir; ; d = dirname14(d)) {
19998
+ for (let d = dir; ; d = dirname15(d)) {
19327
19999
  const config = gitConfigPathFor(d);
19328
- if (config && existsSync19(config)) {
20000
+ if (config && existsSync20(config)) {
19329
20001
  const url = originUrl2(readFileSync21(config, "utf8"));
19330
20002
  repo = url ? parseGithubRemote(url) : null;
19331
20003
  break;
19332
20004
  }
19333
- if (d === dirname14(d)) break;
20005
+ if (d === dirname15(d)) break;
19334
20006
  }
19335
20007
  } catch {
19336
20008
  repo = null;
@@ -19349,9 +20021,9 @@ var init_git_remote = __esm({
19349
20021
 
19350
20022
  // src/team/queue.ts
19351
20023
  import { readFileSync as readFileSync22, writeFileSync as writeFileSync15, appendFileSync as appendFileSync5, statSync as statSync6, mkdirSync as mkdirSync14 } from "node:fs";
19352
- import { dirname as dirname15 } from "node:path";
20024
+ import { dirname as dirname16 } from "node:path";
19353
20025
  function enqueuePayload(payload, queuePath = QUEUE_PATH) {
19354
- mkdirSync14(dirname15(queuePath), { recursive: true });
20026
+ mkdirSync14(dirname16(queuePath), { recursive: true });
19355
20027
  const entry = { payload, enqueuedAt: (/* @__PURE__ */ new Date()).toISOString() };
19356
20028
  appendFileSync5(queuePath, JSON.stringify(entry) + "\n", "utf8");
19357
20029
  try {
@@ -19405,8 +20077,8 @@ var init_queue2 = __esm({
19405
20077
  });
19406
20078
 
19407
20079
  // src/usage/profile.ts
19408
- import { existsSync as existsSync20, mkdirSync as mkdirSync15, readFileSync as readFileSync23, writeFileSync as writeFileSync16 } from "node:fs";
19409
- import { dirname as dirname16 } from "node:path";
20080
+ import { existsSync as existsSync21, mkdirSync as mkdirSync15, readFileSync as readFileSync23, writeFileSync as writeFileSync16 } from "node:fs";
20081
+ import { dirname as dirname17 } from "node:path";
19410
20082
  function mapRateLimitTier(rateLimitTier) {
19411
20083
  switch (rateLimitTier) {
19412
20084
  case "default_claude_pro":
@@ -19446,7 +20118,7 @@ async function fetchProfile(nowMs = Date.now()) {
19446
20118
  };
19447
20119
  }
19448
20120
  function readCachedProfile(cachePath) {
19449
- if (!existsSync20(cachePath)) return null;
20121
+ if (!existsSync21(cachePath)) return null;
19450
20122
  try {
19451
20123
  const raw = JSON.parse(readFileSync23(cachePath, "utf8"));
19452
20124
  if (typeof raw.fetchedAtMs !== "number" || !raw.profile) return null;
@@ -19456,7 +20128,7 @@ function readCachedProfile(cachePath) {
19456
20128
  }
19457
20129
  }
19458
20130
  function writeCachedProfile(cachePath, profile, nowMs = Date.now()) {
19459
- mkdirSync15(dirname16(cachePath), { recursive: true });
20131
+ mkdirSync15(dirname17(cachePath), { recursive: true });
19460
20132
  writeFileSync16(
19461
20133
  cachePath,
19462
20134
  JSON.stringify({ fetchedAtMs: nowMs, profile }, null, 2),
@@ -19670,11 +20342,11 @@ var init_sync_log = __esm({
19670
20342
 
19671
20343
  // src/team/last-push.ts
19672
20344
  import { writeFileSync as writeFileSync17, unlinkSync as unlinkSync6, mkdirSync as mkdirSync16 } from "node:fs";
19673
- import { join as join14 } from "node:path";
20345
+ import { join as join15 } from "node:path";
19674
20346
  function write(record, dir) {
19675
20347
  const d = dir ?? cclensHome();
19676
20348
  mkdirSync16(d, { recursive: true });
19677
- writeFileSync17(join14(d, LAST_PUSH_FILE), JSON.stringify(record, null, 2), { mode: 384 });
20349
+ writeFileSync17(join15(d, LAST_PUSH_FILE), JSON.stringify(record, null, 2), { mode: 384 });
19678
20350
  }
19679
20351
  function writeLastPushSuccess(payload, dir) {
19680
20352
  write({ pushedAt: (/* @__PURE__ */ new Date()).toISOString(), ok: true, payload }, dir);
@@ -19685,7 +20357,7 @@ function writeLastPushFailure(payload, error, dir) {
19685
20357
  function clearLastPush(dir) {
19686
20358
  const d = dir ?? cclensHome();
19687
20359
  try {
19688
- unlinkSync6(join14(d, LAST_PUSH_FILE));
20360
+ unlinkSync6(join15(d, LAST_PUSH_FILE));
19689
20361
  } catch {
19690
20362
  }
19691
20363
  }
@@ -19705,25 +20377,25 @@ __export(file_probe_exports, {
19705
20377
  probeArtifactSignals: () => probeArtifactSignals
19706
20378
  });
19707
20379
  import { createHash } from "node:crypto";
19708
- import { existsSync as existsSync21, readdirSync as readdirSync5, statSync as statSync7 } from "node:fs";
20380
+ import { existsSync as existsSync22, readdirSync as readdirSync5, statSync as statSync7 } from "node:fs";
19709
20381
  import { homedir as homedir7 } from "node:os";
19710
- import { join as join15, relative, resolve as resolve3, sep } from "node:path";
20382
+ import { join as join16, relative, resolve as resolve3, sep } from "node:path";
19711
20383
  import { execFileSync as execFileSync3 } from "node:child_process";
19712
20384
  function pathHash(relPath) {
19713
20385
  return createHash("sha256").update(relPath.split(sep).join("/")).digest("hex").slice(0, 32);
19714
20386
  }
19715
20387
  function defaultScanRoots(extraRoots = []) {
19716
20388
  const roots = [];
19717
- const home = join15(homedir7(), ".claude");
19718
- if (existsSync21(home)) roots.push({ root: home, label: "user" });
20389
+ const home = join16(homedir7(), ".claude");
20390
+ if (existsSync22(home)) roots.push({ root: home, label: "user" });
19719
20391
  for (const e of extraRoots) {
19720
20392
  const r = resolve3(e, ".claude");
19721
- if (existsSync21(r) && r !== home) roots.push({ root: r, label: "project" });
20393
+ if (existsSync22(r) && r !== home) roots.push({ root: r, label: "project" });
19722
20394
  }
19723
20395
  return roots;
19724
20396
  }
19725
20397
  function listMarkdownFiles(dir) {
19726
- if (!existsSync21(dir)) return [];
20398
+ if (!existsSync22(dir)) return [];
19727
20399
  const out = [];
19728
20400
  let entries2;
19729
20401
  try {
@@ -19733,7 +20405,7 @@ function listMarkdownFiles(dir) {
19733
20405
  }
19734
20406
  for (const name of entries2) {
19735
20407
  if (name.startsWith(".")) continue;
19736
- const full = join15(dir, name);
20408
+ const full = join16(dir, name);
19737
20409
  let stat;
19738
20410
  try {
19739
20411
  stat = statSync7(full);
@@ -19753,7 +20425,7 @@ function firstSeenDateOf(file) {
19753
20425
  const out = execFileSync3(
19754
20426
  "git",
19755
20427
  ["log", "--diff-filter=A", "--follow", "--format=%cs", "--", file],
19756
- { encoding: "utf8", stdio: ["ignore", "pipe", "ignore"], cwd: dirname17(file) }
20428
+ { encoding: "utf8", stdio: ["ignore", "pipe", "ignore"], cwd: dirname18(file) }
19757
20429
  ).trim().split("\n").filter(Boolean);
19758
20430
  if (out.length > 0) return out[out.length - 1];
19759
20431
  } catch {
@@ -19765,7 +20437,7 @@ function firstSeenDateOf(file) {
19765
20437
  return todayLocal();
19766
20438
  }
19767
20439
  }
19768
- function dirname17(p) {
20440
+ function dirname18(p) {
19769
20441
  const i = p.lastIndexOf(sep);
19770
20442
  return i < 0 ? "." : p.slice(0, i);
19771
20443
  }
@@ -19792,8 +20464,8 @@ function todayLocal() {
19792
20464
  function scanAuthored(roots, subdir, day2) {
19793
20465
  const out = [];
19794
20466
  for (const r of roots) {
19795
- const dir = join15(r.root, subdir);
19796
- if (!existsSync21(dir)) continue;
20467
+ const dir = join16(r.root, subdir);
20468
+ if (!existsSync22(dir)) continue;
19797
20469
  for (const f of listMarkdownFiles(dir)) {
19798
20470
  const firstSeen = firstSeenDateOf(f);
19799
20471
  if (firstSeen !== day2) continue;
@@ -19806,8 +20478,8 @@ function scanAuthored(roots, subdir, day2) {
19806
20478
  function scanEdited(roots, day2) {
19807
20479
  const out = [];
19808
20480
  for (const r of roots) {
19809
- const dir = join15(r.root, "skills");
19810
- if (!existsSync21(dir)) continue;
20481
+ const dir = join16(r.root, "skills");
20482
+ if (!existsSync22(dir)) continue;
19811
20483
  for (const f of listMarkdownFiles(dir)) {
19812
20484
  const firstSeen = firstSeenDateOf(f);
19813
20485
  if (firstSeen === day2) continue;
@@ -19830,16 +20502,16 @@ function claudemdLineDelta(extraRoots, authorEmail, day2) {
19830
20502
  const candidates = [];
19831
20503
  for (const e of extraRoots) {
19832
20504
  const f = resolve3(e, "CLAUDE.md");
19833
- if (existsSync21(f)) candidates.push(f);
20505
+ if (existsSync22(f)) candidates.push(f);
19834
20506
  }
19835
- const homeClaudeMd = join15(homedir7(), "CLAUDE.md");
19836
- if (existsSync21(homeClaudeMd)) candidates.push(homeClaudeMd);
20507
+ const homeClaudeMd = join16(homedir7(), "CLAUDE.md");
20508
+ if (existsSync22(homeClaudeMd)) candidates.push(homeClaudeMd);
19837
20509
  for (const file of candidates) {
19838
20510
  try {
19839
20511
  const out = execFileSync3(
19840
20512
  "git",
19841
20513
  ["log", "--numstat", "--format=COMMIT %cs %ae", "--", file],
19842
- { encoding: "utf8", stdio: ["ignore", "pipe", "ignore"], cwd: dirname17(file) }
20514
+ { encoding: "utf8", stdio: ["ignore", "pipe", "ignore"], cwd: dirname18(file) }
19843
20515
  );
19844
20516
  let currentDate = "";
19845
20517
  let currentEmail = "";
@@ -20855,8 +21527,8 @@ __export(runs_exports, {
20855
21527
  runs: () => runs
20856
21528
  });
20857
21529
  import { execSync as execSync2 } from "node:child_process";
20858
- import { existsSync as existsSync22, readFileSync as readFileSync26, readdirSync as readdirSync6, statSync as statSync8 } from "node:fs";
20859
- import { join as join16 } from "node:path";
21530
+ import { existsSync as existsSync23, readFileSync as readFileSync26, readdirSync as readdirSync6, statSync as statSync8 } from "node:fs";
21531
+ import { join as join17 } from "node:path";
20860
21532
  async function runs(args2) {
20861
21533
  const json = args2.includes("--json");
20862
21534
  const watch = args2.includes("--watch");
@@ -20940,7 +21612,7 @@ function listActiveRuns() {
20940
21612
  return runs2.sort((a, b) => a.elapsed_s - b.elapsed_s);
20941
21613
  }
20942
21614
  function readSpend(sinceMs) {
20943
- if (!existsSync22(SPEND_PATH)) return [];
21615
+ if (!existsSync23(SPEND_PATH)) return [];
20944
21616
  const lines = readFileSync26(SPEND_PATH, "utf-8").split("\n").filter((l) => l.trim());
20945
21617
  const out = [];
20946
21618
  for (const line of lines) {
@@ -21062,23 +21734,23 @@ function ageLabel(ms) {
21062
21734
  return `${Math.floor(ms / 864e5)}d`;
21063
21735
  }
21064
21736
  function listTraceFiles() {
21065
- if (!existsSync22(RUNS_DIR2)) return [];
21737
+ if (!existsSync23(RUNS_DIR2)) return [];
21066
21738
  const entries2 = readdirSync6(RUNS_DIR2).filter((f) => f.endsWith(".jsonl"));
21067
21739
  return entries2.map((f) => {
21068
- const path10 = join16(RUNS_DIR2, f);
21069
- const st = statSync8(path10);
21070
- return { runId: f.replace(/\.jsonl$/, ""), path: path10, mtimeMs: st.mtimeMs };
21740
+ const path11 = join17(RUNS_DIR2, f);
21741
+ const st = statSync8(path11);
21742
+ return { runId: f.replace(/\.jsonl$/, ""), path: path11, mtimeMs: st.mtimeMs };
21071
21743
  }).sort((a, b) => b.mtimeMs - a.mtimeMs);
21072
21744
  }
21073
21745
  function resolveRunId(arg) {
21074
- if (!existsSync22(RUNS_DIR2)) return null;
21746
+ if (!existsSync23(RUNS_DIR2)) return null;
21075
21747
  if (arg === "latest") {
21076
21748
  const all2 = listTraceFiles();
21077
21749
  if (all2.length === 0) return null;
21078
21750
  return { runId: all2[0].runId, path: all2[0].path };
21079
21751
  }
21080
- const exact = join16(RUNS_DIR2, `${arg}.jsonl`);
21081
- if (existsSync22(exact)) return { runId: arg, path: exact };
21752
+ const exact = join17(RUNS_DIR2, `${arg}.jsonl`);
21753
+ if (existsSync23(exact)) return { runId: arg, path: exact };
21082
21754
  const all = listTraceFiles();
21083
21755
  const matches = all.filter((r) => r.runId.includes(arg));
21084
21756
  if (matches.length === 1) return { runId: matches[0].runId, path: matches[0].path };
@@ -21089,8 +21761,8 @@ function resolveRunId(arg) {
21089
21761
  }
21090
21762
  return null;
21091
21763
  }
21092
- function readTrace(path10) {
21093
- return readFileSync26(path10, "utf-8").split("\n").filter((l) => l.trim()).map((l) => {
21764
+ function readTrace(path11) {
21765
+ return readFileSync26(path11, "utf-8").split("\n").filter((l) => l.trim()).map((l) => {
21094
21766
  try {
21095
21767
  return JSON.parse(l);
21096
21768
  } catch {
@@ -21102,7 +21774,7 @@ async function inspect(arg, follow, json) {
21102
21774
  const r = resolveRunId(arg);
21103
21775
  if (!r) {
21104
21776
  console.error(`run not found: ${arg}`);
21105
- if (existsSync22(RUNS_DIR2)) {
21777
+ if (existsSync23(RUNS_DIR2)) {
21106
21778
  const all = listTraceFiles().slice(0, 5);
21107
21779
  if (all.length > 0) {
21108
21780
  console.error(`
@@ -21282,7 +21954,7 @@ async function main() {
21282
21954
  case "version":
21283
21955
  case "--version":
21284
21956
  case "-v":
21285
- console.log(`fleetlens ${"0.16.6"}`);
21957
+ console.log(`fleetlens ${"0.16.8"}`);
21286
21958
  break;
21287
21959
  case "help":
21288
21960
  case "--help":