@unravel-tech/ccusage-pi 18.1.0 → 18.2.2

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 (4) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +1 -0
  3. package/dist/index.js +479 -170
  4. package/package.json +18 -25
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 ryoppippi
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -75,6 +75,7 @@ Useful environment variables:
75
75
 
76
76
  - 📊 **Daily/Monthly/Session Reports**: Same reporting options as ccusage
77
77
  - 💵 **Accurate Cost Calculation**: Uses LiteLLM pricing database
78
+ - 🧠 **Subagent-aware accounting**: Usage totals include both top-level assistant usage and nested subagent usage from `message.details.results[].usage` where `message.toolName == "subagent"`
78
79
  - 📄 **JSON Output**: Export data in structured JSON format with `--json`
79
80
  - 📱 **Compact Mode**: Use `--compact` flag for narrow terminals
80
81
 
package/dist/index.js CHANGED
@@ -2,13 +2,13 @@
2
2
  import { createRequire } from "node:module";
3
3
  import process$1 from "node:process";
4
4
  import { formatWithOptions } from "node:util";
5
- import { homedir } from "node:os";
5
+ import F, { homedir } from "node:os";
6
6
  import * as nativeFs from "node:fs";
7
7
  import fs from "node:fs";
8
8
  import readline from "node:readline";
9
+ import a from "node:fs/promises";
9
10
  import path, { basename, dirname, normalize, posix, relative, resolve, sep } from "node:path";
10
11
  import { fileURLToPath } from "node:url";
11
- import fsPromises from "node:fs/promises";
12
12
  import * as tty from "node:tty";
13
13
  var __create = Object.create;
14
14
  var __defProp = Object.defineProperty;
@@ -18,10 +18,10 @@ var __getProtoOf = Object.getPrototypeOf;
18
18
  var __hasOwnProp = Object.prototype.hasOwnProperty;
19
19
  var __commonJSMin = (cb, mod) => () => (mod || cb((mod = { exports: {} }).exports, mod), mod.exports);
20
20
  var __copyProps = (to, from, except, desc) => {
21
- if (from && typeof from === "object" || typeof from === "function") for (var keys = __getOwnPropNames(from), i$1 = 0, n$1 = keys.length, key; i$1 < n$1; i$1++) {
21
+ if (from && typeof from === "object" || typeof from === "function") for (var keys = __getOwnPropNames(from), i$1 = 0, n$2 = keys.length, key; i$1 < n$2; i$1++) {
22
22
  key = keys[i$1];
23
23
  if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, {
24
- get: ((k) => from[k]).bind(null, key),
24
+ get: ((k$1) => from[k$1]).bind(null, key),
25
25
  enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable
26
26
  });
27
27
  }
@@ -896,7 +896,7 @@ async function executeCommand(cmd, ctx, name$1) {
896
896
  await resolved.run(ctx);
897
897
  }
898
898
  var name = "@unravel-tech/ccusage-pi";
899
- var version = "18.1.0";
899
+ var version = "18.2.1";
900
900
  var description = "Pi-agent usage tracking - unified Claude Max usage across Claude Code and pi-agent";
901
901
  var require_debug = /* @__PURE__ */ __commonJSMin(((exports, module) => {
902
902
  let messages = [];
@@ -910,8 +910,8 @@ var require_debug = /* @__PURE__ */ __commonJSMin(((exports, module) => {
910
910
  debug$3.reset = () => {
911
911
  messages = [];
912
912
  };
913
- debug$3.setDebugLevel = (v) => {
914
- level = v;
913
+ debug$3.setDebugLevel = (v$1) => {
914
+ level = v$1;
915
915
  };
916
916
  debug$3.warn = (msg) => debug$3(msg, debug$3.WARN);
917
917
  debug$3.info = (msg) => debug$3(msg, debug$3.INFO);
@@ -1656,16 +1656,16 @@ var require_zalgo = /* @__PURE__ */ __commonJSMin(((exports, module) => {
1656
1656
  function heComes(text$1, options$1) {
1657
1657
  var result = "";
1658
1658
  var counts;
1659
- var l$1;
1659
+ var l$2;
1660
1660
  options$1 = options$1 || {};
1661
1661
  options$1["up"] = typeof options$1["up"] !== "undefined" ? options$1["up"] : true;
1662
1662
  options$1["mid"] = typeof options$1["mid"] !== "undefined" ? options$1["mid"] : true;
1663
1663
  options$1["down"] = typeof options$1["down"] !== "undefined" ? options$1["down"] : true;
1664
1664
  options$1["size"] = typeof options$1["size"] !== "undefined" ? options$1["size"] : "maxi";
1665
1665
  text$1 = text$1.split("");
1666
- for (l$1 in text$1) {
1667
- if (isChar(l$1)) continue;
1668
- result = result + text$1[l$1];
1666
+ for (l$2 in text$1) {
1667
+ if (isChar(l$2)) continue;
1668
+ result = result + text$1[l$2];
1669
1669
  counts = {
1670
1670
  "up": 0,
1671
1671
  "down": 0,
@@ -1693,8 +1693,8 @@ var require_zalgo = /* @__PURE__ */ __commonJSMin(((exports, module) => {
1693
1693
  "mid",
1694
1694
  "down"
1695
1695
  ];
1696
- for (var d in arr) {
1697
- var index = arr[d];
1696
+ for (var d$1 in arr) {
1697
+ var index = arr[d$1];
1698
1698
  for (var i$1 = 0; i$1 <= counts[index]; i$1++) if (options$1[index]) result = result + soul[index][randomNumber(soul[index].length)];
1699
1699
  }
1700
1700
  }
@@ -1956,13 +1956,13 @@ var require_cell = /* @__PURE__ */ __commonJSMin(((exports, module) => {
1956
1956
  }
1957
1957
  init(tableOptions) {
1958
1958
  let x = this.x;
1959
- let y$1 = this.y;
1959
+ let y$2 = this.y;
1960
1960
  this.widths = tableOptions.colWidths.slice(x, x + this.colSpan);
1961
- this.heights = tableOptions.rowHeights.slice(y$1, y$1 + this.rowSpan);
1961
+ this.heights = tableOptions.rowHeights.slice(y$2, y$2 + this.rowSpan);
1962
1962
  this.width = this.widths.reduce(sumPlusOne, -1);
1963
1963
  this.height = this.heights.reduce(sumPlusOne, -1);
1964
1964
  this.hAlign = this.options.hAlign || tableOptions.colAligns[x];
1965
- this.vAlign = this.options.vAlign || tableOptions.rowAligns[y$1];
1965
+ this.vAlign = this.options.vAlign || tableOptions.rowAligns[y$2];
1966
1966
  this.drawRight = x + this.colSpan == tableOptions.colWidths.length;
1967
1967
  }
1968
1968
  draw(lineNum, spanningCell) {
@@ -2082,9 +2082,9 @@ var require_cell = /* @__PURE__ */ __commonJSMin(((exports, module) => {
2082
2082
  this.originalCell = originalCell;
2083
2083
  }
2084
2084
  init(tableOptions) {
2085
- let y$1 = this.y;
2085
+ let y$2 = this.y;
2086
2086
  let originalY = this.originalCell.y;
2087
- this.cellOffset = y$1 - originalY;
2087
+ this.cellOffset = y$2 - originalY;
2088
2088
  this.offset = findDimension(tableOptions.rowHeights, originalY, this.cellOffset);
2089
2089
  }
2090
2090
  draw(lineNum) {
@@ -2096,7 +2096,7 @@ var require_cell = /* @__PURE__ */ __commonJSMin(((exports, module) => {
2096
2096
  mergeTableOptions() {}
2097
2097
  };
2098
2098
  function firstDefined(...args) {
2099
- return args.filter((v) => v !== void 0 && v !== null).shift();
2099
+ return args.filter((v$1) => v$1 !== void 0 && v$1 !== null).shift();
2100
2100
  }
2101
2101
  function setOption(objA, objB, nameB, targetObj) {
2102
2102
  let nameA = nameB.split("-");
@@ -2111,8 +2111,8 @@ var require_cell = /* @__PURE__ */ __commonJSMin(((exports, module) => {
2111
2111
  for (let i$1 = 1; i$1 < span; i$1++) ret += 1 + dimensionTable[startingIndex + i$1];
2112
2112
  return ret;
2113
2113
  }
2114
- function sumPlusOne(a$1, b$1) {
2115
- return a$1 + b$1 + 1;
2114
+ function sumPlusOne(a$2, b$1) {
2115
+ return a$2 + b$1 + 1;
2116
2116
  }
2117
2117
  let CHAR_NAMES = [
2118
2118
  "top",
@@ -2185,20 +2185,20 @@ var require_layout_manager = /* @__PURE__ */ __commonJSMin(((exports, module) =>
2185
2185
  let xConflict = !(xMin1 > cell2.x - 1 + (cell2.colSpan || 1) || xMin2 > xMax1);
2186
2186
  return yConflict && xConflict;
2187
2187
  }
2188
- function conflictExists(rows, x, y$1) {
2189
- let i_max = Math.min(rows.length - 1, y$1);
2188
+ function conflictExists(rows, x, y$2) {
2189
+ let i_max = Math.min(rows.length - 1, y$2);
2190
2190
  let cell = {
2191
2191
  x,
2192
- y: y$1
2192
+ y: y$2
2193
2193
  };
2194
2194
  for (let i$1 = 0; i$1 <= i_max; i$1++) {
2195
2195
  let row = rows[i$1];
2196
- for (let j = 0; j < row.length; j++) if (cellsConflict(cell, row[j])) return true;
2196
+ for (let j$1 = 0; j$1 < row.length; j$1++) if (cellsConflict(cell, row[j$1])) return true;
2197
2197
  }
2198
2198
  return false;
2199
2199
  }
2200
- function allBlank(rows, y$1, xMin, xMax) {
2201
- for (let x = xMin; x < xMax; x++) if (conflictExists(rows, x, y$1)) return false;
2200
+ function allBlank(rows, y$2, xMin, xMax) {
2201
+ for (let x = xMin; x < xMax; x++) if (conflictExists(rows, x, y$2)) return false;
2202
2202
  return true;
2203
2203
  }
2204
2204
  function addRowSpanCells(table) {
@@ -2219,9 +2219,9 @@ var require_layout_manager = /* @__PURE__ */ __commonJSMin(((exports, module) =>
2219
2219
  let cellColumns = cellRows[rowIndex];
2220
2220
  for (let columnIndex = 0; columnIndex < cellColumns.length; columnIndex++) {
2221
2221
  let cell = cellColumns[columnIndex];
2222
- for (let k = 1; k < cell.colSpan; k++) {
2222
+ for (let k$1 = 1; k$1 < cell.colSpan; k$1++) {
2223
2223
  let colSpanCell = new ColSpanCell();
2224
- colSpanCell.x = cell.x + k;
2224
+ colSpanCell.x = cell.x + k$1;
2225
2225
  colSpanCell.y = cell.y;
2226
2226
  cellColumns.splice(columnIndex + 1, 0, colSpanCell);
2227
2227
  }
@@ -2237,19 +2237,19 @@ var require_layout_manager = /* @__PURE__ */ __commonJSMin(((exports, module) =>
2237
2237
  let h_max = maxHeight(table);
2238
2238
  let w_max = maxWidth(table);
2239
2239
  debug$1(`Max rows: ${h_max}; Max cols: ${w_max}`);
2240
- for (let y$1 = 0; y$1 < h_max; y$1++) for (let x = 0; x < w_max; x++) if (!conflictExists(table, x, y$1)) {
2240
+ for (let y$2 = 0; y$2 < h_max; y$2++) for (let x = 0; x < w_max; x++) if (!conflictExists(table, x, y$2)) {
2241
2241
  let opts = {
2242
2242
  x,
2243
- y: y$1,
2243
+ y: y$2,
2244
2244
  colSpan: 1,
2245
2245
  rowSpan: 1
2246
2246
  };
2247
2247
  x++;
2248
- while (x < w_max && !conflictExists(table, x, y$1)) {
2248
+ while (x < w_max && !conflictExists(table, x, y$2)) {
2249
2249
  opts.colSpan++;
2250
2250
  x++;
2251
2251
  }
2252
- let y2 = y$1 + 1;
2252
+ let y2 = y$2 + 1;
2253
2253
  while (y2 < h_max && allBlank(table, y2, opts.x, opts.x + opts.colSpan)) {
2254
2254
  opts.rowSpan++;
2255
2255
  y2++;
@@ -2258,7 +2258,7 @@ var require_layout_manager = /* @__PURE__ */ __commonJSMin(((exports, module) =>
2258
2258
  cell.x = opts.x;
2259
2259
  cell.y = opts.y;
2260
2260
  warn(`Missing cell at ${cell.y}-${cell.x}.`);
2261
- insertCell(cell, table[y$1]);
2261
+ insertCell(cell, table[y$2]);
2262
2262
  }
2263
2263
  }
2264
2264
  function generateCells(rows) {
@@ -2308,8 +2308,8 @@ var require_layout_manager = /* @__PURE__ */ __commonJSMin(((exports, module) =>
2308
2308
  vals.forEach(function(val, index) {
2309
2309
  if (typeof val === "number") result[index] = val;
2310
2310
  });
2311
- for (let k = spanners.length - 1; k >= 0; k--) {
2312
- let cell = spanners[k];
2311
+ for (let k$1 = spanners.length - 1; k$1 >= 0; k$1--) {
2312
+ let cell = spanners[k$1];
2313
2313
  let span = cell[colSpan];
2314
2314
  let col = cell[x];
2315
2315
  let existingWidth = result[col];
@@ -2336,7 +2336,7 @@ var require_layout_manager = /* @__PURE__ */ __commonJSMin(((exports, module) =>
2336
2336
  }
2337
2337
  }
2338
2338
  Object.assign(vals, result, auto);
2339
- for (let j = 0; j < vals.length; j++) vals[j] = Math.max(forcedMin, vals[j] || 0);
2339
+ for (let j$1 = 0; j$1 < vals.length; j$1++) vals[j$1] = Math.max(forcedMin, vals[j$1] || 0);
2340
2340
  };
2341
2341
  }
2342
2342
  }));
@@ -2373,13 +2373,13 @@ var require_table = /* @__PURE__ */ __commonJSMin(((exports, module) => {
2373
2373
  }
2374
2374
  }
2375
2375
  toString() {
2376
- let array = this;
2376
+ let array$1 = this;
2377
2377
  let headersPresent = this.options.head && this.options.head.length;
2378
2378
  if (headersPresent) {
2379
- array = [this.options.head];
2380
- if (this.length) array.push.apply(array, this);
2379
+ array$1 = [this.options.head];
2380
+ if (this.length) array$1.push.apply(array$1, this);
2381
2381
  } else this.options.style.head = [];
2382
- let cells = tableLayout.makeTableLayout(array);
2382
+ let cells = tableLayout.makeTableLayout(array$1);
2383
2383
  cells.forEach(function(row) {
2384
2384
  row.forEach(function(cell) {
2385
2385
  cell.mergeTableOptions(this.options, cells);
@@ -2440,50 +2440,50 @@ var import_picocolors = /* @__PURE__ */ __toESM((/* @__PURE__ */ __commonJSMin((
2440
2440
  return result + string$1.substring(cursor);
2441
2441
  };
2442
2442
  let createColors$1 = (enabled = isColorSupported$1) => {
2443
- let f$1 = enabled ? formatter : () => String;
2443
+ let f$2 = enabled ? formatter : () => String;
2444
2444
  return {
2445
2445
  isColorSupported: enabled,
2446
- reset: f$1("\x1B[0m", "\x1B[0m"),
2447
- bold: f$1("\x1B[1m", "\x1B[22m", "\x1B[22m\x1B[1m"),
2448
- dim: f$1("\x1B[2m", "\x1B[22m", "\x1B[22m\x1B[2m"),
2449
- italic: f$1("\x1B[3m", "\x1B[23m"),
2450
- underline: f$1("\x1B[4m", "\x1B[24m"),
2451
- inverse: f$1("\x1B[7m", "\x1B[27m"),
2452
- hidden: f$1("\x1B[8m", "\x1B[28m"),
2453
- strikethrough: f$1("\x1B[9m", "\x1B[29m"),
2454
- black: f$1("\x1B[30m", "\x1B[39m"),
2455
- red: f$1("\x1B[31m", "\x1B[39m"),
2456
- green: f$1("\x1B[32m", "\x1B[39m"),
2457
- yellow: f$1("\x1B[33m", "\x1B[39m"),
2458
- blue: f$1("\x1B[34m", "\x1B[39m"),
2459
- magenta: f$1("\x1B[35m", "\x1B[39m"),
2460
- cyan: f$1("\x1B[36m", "\x1B[39m"),
2461
- white: f$1("\x1B[37m", "\x1B[39m"),
2462
- gray: f$1("\x1B[90m", "\x1B[39m"),
2463
- bgBlack: f$1("\x1B[40m", "\x1B[49m"),
2464
- bgRed: f$1("\x1B[41m", "\x1B[49m"),
2465
- bgGreen: f$1("\x1B[42m", "\x1B[49m"),
2466
- bgYellow: f$1("\x1B[43m", "\x1B[49m"),
2467
- bgBlue: f$1("\x1B[44m", "\x1B[49m"),
2468
- bgMagenta: f$1("\x1B[45m", "\x1B[49m"),
2469
- bgCyan: f$1("\x1B[46m", "\x1B[49m"),
2470
- bgWhite: f$1("\x1B[47m", "\x1B[49m"),
2471
- blackBright: f$1("\x1B[90m", "\x1B[39m"),
2472
- redBright: f$1("\x1B[91m", "\x1B[39m"),
2473
- greenBright: f$1("\x1B[92m", "\x1B[39m"),
2474
- yellowBright: f$1("\x1B[93m", "\x1B[39m"),
2475
- blueBright: f$1("\x1B[94m", "\x1B[39m"),
2476
- magentaBright: f$1("\x1B[95m", "\x1B[39m"),
2477
- cyanBright: f$1("\x1B[96m", "\x1B[39m"),
2478
- whiteBright: f$1("\x1B[97m", "\x1B[39m"),
2479
- bgBlackBright: f$1("\x1B[100m", "\x1B[49m"),
2480
- bgRedBright: f$1("\x1B[101m", "\x1B[49m"),
2481
- bgGreenBright: f$1("\x1B[102m", "\x1B[49m"),
2482
- bgYellowBright: f$1("\x1B[103m", "\x1B[49m"),
2483
- bgBlueBright: f$1("\x1B[104m", "\x1B[49m"),
2484
- bgMagentaBright: f$1("\x1B[105m", "\x1B[49m"),
2485
- bgCyanBright: f$1("\x1B[106m", "\x1B[49m"),
2486
- bgWhiteBright: f$1("\x1B[107m", "\x1B[49m")
2446
+ reset: f$2("\x1B[0m", "\x1B[0m"),
2447
+ bold: f$2("\x1B[1m", "\x1B[22m", "\x1B[22m\x1B[1m"),
2448
+ dim: f$2("\x1B[2m", "\x1B[22m", "\x1B[22m\x1B[2m"),
2449
+ italic: f$2("\x1B[3m", "\x1B[23m"),
2450
+ underline: f$2("\x1B[4m", "\x1B[24m"),
2451
+ inverse: f$2("\x1B[7m", "\x1B[27m"),
2452
+ hidden: f$2("\x1B[8m", "\x1B[28m"),
2453
+ strikethrough: f$2("\x1B[9m", "\x1B[29m"),
2454
+ black: f$2("\x1B[30m", "\x1B[39m"),
2455
+ red: f$2("\x1B[31m", "\x1B[39m"),
2456
+ green: f$2("\x1B[32m", "\x1B[39m"),
2457
+ yellow: f$2("\x1B[33m", "\x1B[39m"),
2458
+ blue: f$2("\x1B[34m", "\x1B[39m"),
2459
+ magenta: f$2("\x1B[35m", "\x1B[39m"),
2460
+ cyan: f$2("\x1B[36m", "\x1B[39m"),
2461
+ white: f$2("\x1B[37m", "\x1B[39m"),
2462
+ gray: f$2("\x1B[90m", "\x1B[39m"),
2463
+ bgBlack: f$2("\x1B[40m", "\x1B[49m"),
2464
+ bgRed: f$2("\x1B[41m", "\x1B[49m"),
2465
+ bgGreen: f$2("\x1B[42m", "\x1B[49m"),
2466
+ bgYellow: f$2("\x1B[43m", "\x1B[49m"),
2467
+ bgBlue: f$2("\x1B[44m", "\x1B[49m"),
2468
+ bgMagenta: f$2("\x1B[45m", "\x1B[49m"),
2469
+ bgCyan: f$2("\x1B[46m", "\x1B[49m"),
2470
+ bgWhite: f$2("\x1B[47m", "\x1B[49m"),
2471
+ blackBright: f$2("\x1B[90m", "\x1B[39m"),
2472
+ redBright: f$2("\x1B[91m", "\x1B[39m"),
2473
+ greenBright: f$2("\x1B[92m", "\x1B[39m"),
2474
+ yellowBright: f$2("\x1B[93m", "\x1B[39m"),
2475
+ blueBright: f$2("\x1B[94m", "\x1B[39m"),
2476
+ magentaBright: f$2("\x1B[95m", "\x1B[39m"),
2477
+ cyanBright: f$2("\x1B[96m", "\x1B[39m"),
2478
+ whiteBright: f$2("\x1B[97m", "\x1B[39m"),
2479
+ bgBlackBright: f$2("\x1B[100m", "\x1B[49m"),
2480
+ bgRedBright: f$2("\x1B[101m", "\x1B[49m"),
2481
+ bgGreenBright: f$2("\x1B[102m", "\x1B[49m"),
2482
+ bgYellowBright: f$2("\x1B[103m", "\x1B[49m"),
2483
+ bgBlueBright: f$2("\x1B[104m", "\x1B[49m"),
2484
+ bgMagentaBright: f$2("\x1B[105m", "\x1B[49m"),
2485
+ bgCyanBright: f$2("\x1B[106m", "\x1B[49m"),
2486
+ bgWhiteBright: f$2("\x1B[107m", "\x1B[49m")
2487
2487
  };
2488
2488
  };
2489
2489
  module.exports = createColors$1();
@@ -2805,6 +2805,130 @@ function addEmptySeparatorRow(table, columnCount) {
2805
2805
  const emptyRow = Array.from({ length: columnCount }, () => "");
2806
2806
  table.push(emptyRow);
2807
2807
  }
2808
+ var d = Object.defineProperty;
2809
+ var n$1 = (s$1, t$1) => d(s$1, "name", {
2810
+ value: t$1,
2811
+ configurable: !0
2812
+ });
2813
+ typeof Symbol.asyncDispose != "symbol" && Object.defineProperty(Symbol, "asyncDispose", {
2814
+ configurable: !1,
2815
+ enumerable: !1,
2816
+ writable: !1,
2817
+ value: Symbol.for("asyncDispose")
2818
+ });
2819
+ var P = class {
2820
+ static {
2821
+ n$1(this, "FsFixture");
2822
+ }
2823
+ path;
2824
+ constructor(t$1) {
2825
+ this.path = t$1;
2826
+ }
2827
+ getPath(...t$1) {
2828
+ return path.join(this.path, ...t$1);
2829
+ }
2830
+ exists(t$1 = "") {
2831
+ return a.access(this.getPath(t$1)).then(() => !0, () => !1);
2832
+ }
2833
+ rm(t$1 = "") {
2834
+ return a.rm(this.getPath(t$1), {
2835
+ recursive: !0,
2836
+ force: !0
2837
+ });
2838
+ }
2839
+ cp(t$1, r$1, i$1) {
2840
+ return r$1 ? r$1.endsWith(path.sep) && (r$1 += path.basename(t$1)) : r$1 = path.basename(t$1), a.cp(t$1, this.getPath(r$1), i$1);
2841
+ }
2842
+ mkdir(t$1) {
2843
+ return a.mkdir(this.getPath(t$1), { recursive: !0 });
2844
+ }
2845
+ writeFile(t$1, r$1) {
2846
+ return a.writeFile(this.getPath(t$1), r$1);
2847
+ }
2848
+ writeJson(t$1, r$1) {
2849
+ return this.writeFile(t$1, JSON.stringify(r$1, null, 2));
2850
+ }
2851
+ readFile(t$1, r$1) {
2852
+ return a.readFile(this.getPath(t$1), r$1);
2853
+ }
2854
+ async [Symbol.asyncDispose]() {
2855
+ await this.rm();
2856
+ }
2857
+ };
2858
+ const v = fs.realpathSync(F.tmpdir()), D$1 = `fs-fixture-${Date.now()}-${process.pid}`;
2859
+ let m = 0;
2860
+ const j = n$1(() => (m += 1, m), "getId");
2861
+ var u$1 = class {
2862
+ static {
2863
+ n$1(this, "Path");
2864
+ }
2865
+ path;
2866
+ constructor(t$1) {
2867
+ this.path = t$1;
2868
+ }
2869
+ };
2870
+ var f$1 = class extends u$1 {
2871
+ static {
2872
+ n$1(this, "Directory");
2873
+ }
2874
+ };
2875
+ var y$1 = class extends u$1 {
2876
+ static {
2877
+ n$1(this, "File");
2878
+ }
2879
+ content;
2880
+ constructor(t$1, r$1) {
2881
+ super(t$1), this.content = r$1;
2882
+ }
2883
+ };
2884
+ var l$1 = class {
2885
+ static {
2886
+ n$1(this, "Symlink");
2887
+ }
2888
+ target;
2889
+ type;
2890
+ path;
2891
+ constructor(t$1, r$1) {
2892
+ this.target = t$1, this.type = r$1;
2893
+ }
2894
+ };
2895
+ const w = n$1((s$1, t$1, r$1) => {
2896
+ const i$1 = [];
2897
+ for (const p$1 in s$1) {
2898
+ if (!Object.hasOwn(s$1, p$1)) continue;
2899
+ const e = path.join(t$1, p$1);
2900
+ let o$1 = s$1[p$1];
2901
+ if (typeof o$1 == "function") {
2902
+ const g$1 = Object.assign(Object.create(r$1), { filePath: e }), h = o$1(g$1);
2903
+ if (h instanceof l$1) {
2904
+ h.path = e, i$1.push(h);
2905
+ continue;
2906
+ } else o$1 = h;
2907
+ }
2908
+ typeof o$1 == "string" ? i$1.push(new y$1(e, o$1)) : i$1.push(new f$1(e), ...w(o$1, e, r$1));
2909
+ }
2910
+ return i$1;
2911
+ }, "flattenFileTree");
2912
+ n$1(async (s$1, t$1) => {
2913
+ const r$1 = t$1?.tempDir ? path.resolve(t$1.tempDir) : v, i$1 = path.join(r$1, `${D$1}-${j()}/`);
2914
+ if (await a.mkdir(i$1, { recursive: !0 }), s$1) {
2915
+ if (typeof s$1 == "string") await a.cp(s$1, i$1, {
2916
+ recursive: !0,
2917
+ filter: t$1?.templateFilter
2918
+ });
2919
+ else if (typeof s$1 == "object") {
2920
+ const p$1 = {
2921
+ fixturePath: i$1,
2922
+ getPath: n$1((...e) => path.join(i$1, ...e), "getPath"),
2923
+ symlink: n$1((e, o$1) => new l$1(e, o$1), "symlink")
2924
+ };
2925
+ await Promise.all(w(s$1, i$1, p$1).map(async (e) => {
2926
+ e instanceof f$1 ? await a.mkdir(e.path, { recursive: !0 }) : e instanceof l$1 ? (await a.mkdir(path.dirname(e.path), { recursive: !0 }), await a.symlink(e.target, e.path, e.type)) : e instanceof y$1 && (await a.mkdir(path.dirname(e.path), { recursive: !0 }), await a.writeFile(e.path, e.content));
2927
+ }));
2928
+ }
2929
+ }
2930
+ return new P(i$1);
2931
+ }, "createFixture");
2808
2932
  var __require = /* @__PURE__ */ createRequire(import.meta.url);
2809
2933
  function cleanPath(path$1) {
2810
2934
  let normalized = normalize(path$1);
@@ -3729,9 +3853,9 @@ var require_scan = /* @__PURE__ */ __commonJSMin(((exports, module) => {
3729
3853
  if (opts.parts === true || opts.tokens === true) {
3730
3854
  let prevIndex;
3731
3855
  for (let idx = 0; idx < slashes.length; idx++) {
3732
- const n$1 = prevIndex ? prevIndex + 1 : start;
3856
+ const n$2 = prevIndex ? prevIndex + 1 : start;
3733
3857
  const i$1 = slashes[idx];
3734
- const value = input.slice(n$1, i$1);
3858
+ const value = input.slice(n$2, i$1);
3735
3859
  if (opts.tokens) {
3736
3860
  if (idx === 0 && start !== 0) {
3737
3861
  tokens[idx].isPrefix = true;
@@ -3770,7 +3894,7 @@ var require_parse = /* @__PURE__ */ __commonJSMin(((exports, module) => {
3770
3894
  try {
3771
3895
  new RegExp(value);
3772
3896
  } catch (ex) {
3773
- return args.map((v) => utils$2.escapeRegex(v)).join("..");
3897
+ return args.map((v$1) => utils$2.escapeRegex(v$1)).join("..");
3774
3898
  }
3775
3899
  return value;
3776
3900
  };
@@ -3827,7 +3951,7 @@ var require_parse = /* @__PURE__ */ __commonJSMin(((exports, module) => {
3827
3951
  let prev = bos;
3828
3952
  let value;
3829
3953
  const eos = () => state.index === len - 1;
3830
- const peek = state.peek = (n$1 = 1) => input[state.index + n$1];
3954
+ const peek = state.peek = (n$2 = 1) => input[state.index + n$2];
3831
3955
  const advance = state.advance = () => input[++state.index] || "";
3832
3956
  const remaining = () => input.slice(state.index + 1);
3833
3957
  const consume = (value$1 = "", num = 0) => {
@@ -3928,10 +4052,10 @@ var require_parse = /* @__PURE__ */ __commonJSMin(((exports, module) => {
3928
4052
  };
3929
4053
  if (opts.fastpaths !== false && !/(^[*!]|[/()[\]{}"])/.test(input)) {
3930
4054
  let backslashes = false;
3931
- let output = input.replace(REGEX_SPECIAL_CHARS_BACKREF, (m, esc, chars, first, rest, index) => {
4055
+ let output = input.replace(REGEX_SPECIAL_CHARS_BACKREF, (m$1, esc, chars, first, rest, index) => {
3932
4056
  if (first === "\\") {
3933
4057
  backslashes = true;
3934
- return m;
4058
+ return m$1;
3935
4059
  }
3936
4060
  if (first === "?") {
3937
4061
  if (esc) return esc + first + (rest ? QMARK$1.repeat(rest.length) : "");
@@ -3943,11 +4067,11 @@ var require_parse = /* @__PURE__ */ __commonJSMin(((exports, module) => {
3943
4067
  if (esc) return esc + first + (rest ? star : "");
3944
4068
  return star;
3945
4069
  }
3946
- return esc ? m : `\\${m}`;
4070
+ return esc ? m$1 : `\\${m$1}`;
3947
4071
  });
3948
4072
  if (backslashes === true) if (opts.unescape === true) output = output.replace(/\\/g, "");
3949
- else output = output.replace(/\\+/g, (m) => {
3950
- return m.length % 2 === 0 ? "\\\\" : m ? "\\" : "";
4073
+ else output = output.replace(/\\+/g, (m$1) => {
4074
+ return m$1.length % 2 === 0 ? "\\\\" : m$1 ? "\\" : "";
3951
4075
  });
3952
4076
  if (output === input && opts.contains === true) {
3953
4077
  state.output = input;
@@ -4685,7 +4809,7 @@ function getPartialMatcher(patterns, options = {}) {
4685
4809
  patternsParts[i$1] = parts;
4686
4810
  const partsCount = parts.length;
4687
4811
  const partMatchers = Array(partsCount);
4688
- for (let j = 0; j < partsCount; j++) partMatchers[j] = (0, import_picomatch.default)(parts[j], options);
4812
+ for (let j$1 = 0; j$1 < partsCount; j$1++) partMatchers[j$1] = (0, import_picomatch.default)(parts[j$1], options);
4689
4813
  matchers[i$1] = partMatchers;
4690
4814
  }
4691
4815
  return (input) => {
@@ -4696,15 +4820,15 @@ function getPartialMatcher(patterns, options = {}) {
4696
4820
  const matcher = matchers[i$1];
4697
4821
  const inputPatternCount = inputParts.length;
4698
4822
  const minParts = Math.min(inputPatternCount, patternParts.length);
4699
- let j = 0;
4700
- while (j < minParts) {
4701
- const part = patternParts[j];
4823
+ let j$1 = 0;
4824
+ while (j$1 < minParts) {
4825
+ const part = patternParts[j$1];
4702
4826
  if (part.includes("/")) return true;
4703
- if (!matcher[j](inputParts[j])) break;
4827
+ if (!matcher[j$1](inputParts[j$1])) break;
4704
4828
  if (globstarEnabled && part === "**") return true;
4705
- j++;
4829
+ j$1++;
4706
4830
  }
4707
- if (j === inputPatternCount) return true;
4831
+ if (j$1 === inputPatternCount) return true;
4708
4832
  }
4709
4833
  return false;
4710
4834
  };
@@ -4773,17 +4897,17 @@ function normalizePattern(pattern, expandDirectories, cwd, props, isIgnore) {
4773
4897
  const parentDirectoryMatch = PARENT_DIRECTORY.exec(result);
4774
4898
  const parts = splitPattern(result);
4775
4899
  if (parentDirectoryMatch === null || parentDirectoryMatch === void 0 ? void 0 : parentDirectoryMatch[0]) {
4776
- const n$1 = (parentDirectoryMatch[0].length + 1) / 3;
4900
+ const n$2 = (parentDirectoryMatch[0].length + 1) / 3;
4777
4901
  let i$1 = 0;
4778
4902
  const cwdParts = escapedCwd.split("/");
4779
- while (i$1 < n$1 && parts[i$1 + n$1] === cwdParts[cwdParts.length + i$1 - n$1]) {
4780
- result = result.slice(0, (n$1 - i$1 - 1) * 3) + result.slice((n$1 - i$1) * 3 + parts[i$1 + n$1].length + 1) || ".";
4903
+ while (i$1 < n$2 && parts[i$1 + n$2] === cwdParts[cwdParts.length + i$1 - n$2]) {
4904
+ result = result.slice(0, (n$2 - i$1 - 1) * 3) + result.slice((n$2 - i$1) * 3 + parts[i$1 + n$2].length + 1) || ".";
4781
4905
  i$1++;
4782
4906
  }
4783
4907
  const potentialRoot = posix.join(cwd, parentDirectoryMatch[0].slice(i$1 * 3));
4784
4908
  if (!potentialRoot.startsWith(".") && props.root.length > potentialRoot.length) {
4785
4909
  props.root = potentialRoot;
4786
- props.depthOffset = -n$1 + i$1;
4910
+ props.depthOffset = -n$2 + i$1;
4787
4911
  }
4788
4912
  }
4789
4913
  if (!isIgnore && props.depthOffset >= 0) {
@@ -5005,6 +5129,10 @@ function _getStandardProps(context) {
5005
5129
  };
5006
5130
  }
5007
5131
  /* @__NO_SIDE_EFFECTS__ */
5132
+ function _isValidObjectKey(object2, key) {
5133
+ return Object.hasOwn(object2, key) && key !== "__proto__" && key !== "prototype" && key !== "constructor";
5134
+ }
5135
+ /* @__NO_SIDE_EFFECTS__ */
5008
5136
  function brand(name$1) {
5009
5137
  return {
5010
5138
  kind: "transformation",
@@ -5042,6 +5170,54 @@ function getDefault(schema, dataset, config2) {
5042
5170
  return typeof schema.default === "function" ? schema.default(dataset, config2) : schema.default;
5043
5171
  }
5044
5172
  /* @__NO_SIDE_EFFECTS__ */
5173
+ function array(item, message2) {
5174
+ return {
5175
+ kind: "schema",
5176
+ type: "array",
5177
+ reference: array,
5178
+ expects: "Array",
5179
+ async: false,
5180
+ item,
5181
+ message: message2,
5182
+ get "~standard"() {
5183
+ return /* @__PURE__ */ _getStandardProps(this);
5184
+ },
5185
+ "~run"(dataset, config2) {
5186
+ const input = dataset.value;
5187
+ if (Array.isArray(input)) {
5188
+ dataset.typed = true;
5189
+ dataset.value = [];
5190
+ for (let key = 0; key < input.length; key++) {
5191
+ const value2 = input[key];
5192
+ const itemDataset = this.item["~run"]({ value: value2 }, config2);
5193
+ if (itemDataset.issues) {
5194
+ const pathItem = {
5195
+ type: "array",
5196
+ origin: "value",
5197
+ input,
5198
+ key,
5199
+ value: value2
5200
+ };
5201
+ for (const issue of itemDataset.issues) {
5202
+ if (issue.path) issue.path.unshift(pathItem);
5203
+ else issue.path = [pathItem];
5204
+ dataset.issues?.push(issue);
5205
+ }
5206
+ if (!dataset.issues) dataset.issues = itemDataset.issues;
5207
+ if (config2.abortEarly) {
5208
+ dataset.typed = false;
5209
+ break;
5210
+ }
5211
+ }
5212
+ if (!itemDataset.typed) dataset.typed = false;
5213
+ dataset.value.push(itemDataset.value);
5214
+ }
5215
+ } else _addIssue(this, "type", dataset, config2);
5216
+ return dataset;
5217
+ }
5218
+ };
5219
+ }
5220
+ /* @__NO_SIDE_EFFECTS__ */
5045
5221
  function number(message2) {
5046
5222
  return {
5047
5223
  kind: "schema",
@@ -5151,6 +5327,74 @@ function optional(wrapped, default_) {
5151
5327
  };
5152
5328
  }
5153
5329
  /* @__NO_SIDE_EFFECTS__ */
5330
+ function record(key, value2, message2) {
5331
+ return {
5332
+ kind: "schema",
5333
+ type: "record",
5334
+ reference: record,
5335
+ expects: "Object",
5336
+ async: false,
5337
+ key,
5338
+ value: value2,
5339
+ message: message2,
5340
+ get "~standard"() {
5341
+ return /* @__PURE__ */ _getStandardProps(this);
5342
+ },
5343
+ "~run"(dataset, config2) {
5344
+ const input = dataset.value;
5345
+ if (input && typeof input === "object") {
5346
+ dataset.typed = true;
5347
+ dataset.value = {};
5348
+ for (const entryKey in input) if (/* @__PURE__ */ _isValidObjectKey(input, entryKey)) {
5349
+ const entryValue = input[entryKey];
5350
+ const keyDataset = this.key["~run"]({ value: entryKey }, config2);
5351
+ if (keyDataset.issues) {
5352
+ const pathItem = {
5353
+ type: "object",
5354
+ origin: "key",
5355
+ input,
5356
+ key: entryKey,
5357
+ value: entryValue
5358
+ };
5359
+ for (const issue of keyDataset.issues) {
5360
+ issue.path = [pathItem];
5361
+ dataset.issues?.push(issue);
5362
+ }
5363
+ if (!dataset.issues) dataset.issues = keyDataset.issues;
5364
+ if (config2.abortEarly) {
5365
+ dataset.typed = false;
5366
+ break;
5367
+ }
5368
+ }
5369
+ const valueDataset = this.value["~run"]({ value: entryValue }, config2);
5370
+ if (valueDataset.issues) {
5371
+ const pathItem = {
5372
+ type: "object",
5373
+ origin: "value",
5374
+ input,
5375
+ key: entryKey,
5376
+ value: entryValue
5377
+ };
5378
+ for (const issue of valueDataset.issues) {
5379
+ if (issue.path) issue.path.unshift(pathItem);
5380
+ else issue.path = [pathItem];
5381
+ dataset.issues?.push(issue);
5382
+ }
5383
+ if (!dataset.issues) dataset.issues = valueDataset.issues;
5384
+ if (config2.abortEarly) {
5385
+ dataset.typed = false;
5386
+ break;
5387
+ }
5388
+ }
5389
+ if (!keyDataset.typed || !valueDataset.typed) dataset.typed = false;
5390
+ if (keyDataset.typed) dataset.value[keyDataset.value] = valueDataset.value;
5391
+ }
5392
+ } else _addIssue(this, "type", dataset, config2);
5393
+ return dataset;
5394
+ }
5395
+ };
5396
+ }
5397
+ /* @__NO_SIDE_EFFECTS__ */
5154
5398
  function string(message2) {
5155
5399
  return {
5156
5400
  kind: "schema",
@@ -5170,6 +5414,23 @@ function string(message2) {
5170
5414
  };
5171
5415
  }
5172
5416
  /* @__NO_SIDE_EFFECTS__ */
5417
+ function unknown() {
5418
+ return {
5419
+ kind: "schema",
5420
+ type: "unknown",
5421
+ reference: unknown,
5422
+ expects: "unknown",
5423
+ async: false,
5424
+ get "~standard"() {
5425
+ return /* @__PURE__ */ _getStandardProps(this);
5426
+ },
5427
+ "~run"(dataset) {
5428
+ dataset.typed = true;
5429
+ return dataset;
5430
+ }
5431
+ };
5432
+ }
5433
+ /* @__NO_SIDE_EFFECTS__ */
5173
5434
  function pipe(...pipe2) {
5174
5435
  return {
5175
5436
  ...pipe2[0],
@@ -5202,7 +5463,7 @@ function safeParse(schema, input, config2) {
5202
5463
  async function isType(fsStatType, statsMethodName, filePath) {
5203
5464
  if (typeof filePath !== "string") throw new TypeError(`Expected a string, got ${typeof filePath}`);
5204
5465
  try {
5205
- return (await fsPromises[fsStatType](filePath))[statsMethodName]();
5466
+ return (await a[fsStatType](filePath))[statsMethodName]();
5206
5467
  } catch (error) {
5207
5468
  if (error.code === "ENOENT") return false;
5208
5469
  throw error;
@@ -5240,12 +5501,72 @@ const piAgentMessageSchema = /* @__PURE__ */ object({
5240
5501
  cacheWrite: /* @__PURE__ */ optional(/* @__PURE__ */ number()),
5241
5502
  totalTokens: /* @__PURE__ */ optional(/* @__PURE__ */ number()),
5242
5503
  cost: /* @__PURE__ */ optional(/* @__PURE__ */ object({ total: /* @__PURE__ */ optional(/* @__PURE__ */ number()) }))
5243
- }))
5504
+ })),
5505
+ toolName: /* @__PURE__ */ optional(/* @__PURE__ */ string()),
5506
+ details: /* @__PURE__ */ optional(/* @__PURE__ */ object({ results: /* @__PURE__ */ optional(/* @__PURE__ */ array(/* @__PURE__ */ object({
5507
+ usage: /* @__PURE__ */ optional(/* @__PURE__ */ record(/* @__PURE__ */ string(), /* @__PURE__ */ unknown())),
5508
+ model: /* @__PURE__ */ optional(/* @__PURE__ */ string())
5509
+ }))) }))
5244
5510
  })
5245
5511
  });
5512
+ const TOP_LEVEL_MODEL_PREFIX = "[pi]";
5513
+ const SUBAGENT_MODEL_PREFIX = "[pi-subagent]";
5514
+ function createModelName(model, usageSource) {
5515
+ return usageSource === "subagent" ? `${SUBAGENT_MODEL_PREFIX} ${model}` : `${TOP_LEVEL_MODEL_PREFIX} ${model}`;
5516
+ }
5517
+ function createUsageEntry(usage, model, usageSource = "assistant") {
5518
+ const totalTokens = usage.totalTokens ?? usage.input + usage.output + (usage.cacheRead ?? 0) + (usage.cacheWrite ?? 0);
5519
+ return {
5520
+ usage: {
5521
+ input_tokens: usage.input,
5522
+ output_tokens: usage.output,
5523
+ cache_creation_input_tokens: usage.cacheWrite ?? 0,
5524
+ cache_read_input_tokens: usage.cacheRead ?? 0
5525
+ },
5526
+ model: model != null ? createModelName(model, usageSource) : void 0,
5527
+ costUSD: usage.cost?.total,
5528
+ totalTokens
5529
+ };
5530
+ }
5246
5531
  function isPiAgentUsageEntry(data) {
5247
5532
  return (data.type == null || data.type === "message") && data.message?.role === "assistant" && data.message?.usage != null && typeof data.message.usage.input === "number" && typeof data.message.usage.output === "number";
5248
5533
  }
5534
+ function extractPiAgentSubagentUsageEntries(data) {
5535
+ const toolResults = data.message?.details?.results;
5536
+ if (data.message?.toolName !== "subagent" || !Array.isArray(toolResults)) return [];
5537
+ const entries = [];
5538
+ for (const result of toolResults) {
5539
+ const usage = result?.usage;
5540
+ if (usage == null || typeof usage !== "object" || Array.isArray(usage)) continue;
5541
+ const usageRecord = usage;
5542
+ const input = usageRecord.input;
5543
+ const output = usageRecord.output;
5544
+ if (typeof input !== "number" || typeof output !== "number") continue;
5545
+ const cacheRead = usageRecord.cacheRead;
5546
+ const cacheWrite = usageRecord.cacheWrite;
5547
+ const totalTokens = usageRecord.totalTokens;
5548
+ const rawCost = usageRecord.cost;
5549
+ let normalizedCost;
5550
+ if (rawCost != null && typeof rawCost === "object" && !Array.isArray(rawCost)) {
5551
+ const rawCostRecord = rawCost;
5552
+ if (typeof rawCostRecord.total === "number") normalizedCost = { total: rawCostRecord.total };
5553
+ }
5554
+ const normalizedUsage = {
5555
+ input,
5556
+ output,
5557
+ cacheRead: typeof cacheRead === "number" ? cacheRead : void 0,
5558
+ cacheWrite: typeof cacheWrite === "number" ? cacheWrite : void 0,
5559
+ totalTokens: typeof totalTokens === "number" ? totalTokens : void 0,
5560
+ cost: normalizedCost
5561
+ };
5562
+ entries.push(createUsageEntry(normalizedUsage, result.model ?? data.message?.model, "subagent"));
5563
+ }
5564
+ return entries;
5565
+ }
5566
+ function transformPiAgentUsage(data) {
5567
+ if (isPiAgentUsageEntry(data)) return createUsageEntry(data.message.usage, data.message?.model);
5568
+ return extractPiAgentSubagentUsageEntries(data)[0] ?? null;
5569
+ }
5249
5570
  function extractPiAgentSessionId(filePath) {
5250
5571
  const filename = path.basename(filePath, ".jsonl");
5251
5572
  const idx = filename.indexOf("_");
@@ -5271,31 +5592,17 @@ function getPiAgentPaths(customPath) {
5271
5592
  if (isDirectorySync(defaultPath)) return [defaultPath];
5272
5593
  return [];
5273
5594
  }
5274
- function transformPiAgentUsage(data) {
5275
- if (!isPiAgentUsageEntry(data)) return null;
5276
- const usage = data.message.usage;
5277
- const totalTokens = usage.totalTokens ?? usage.input + usage.output + (usage.cacheRead ?? 0) + (usage.cacheWrite ?? 0);
5278
- return {
5279
- usage: {
5280
- input_tokens: usage.input,
5281
- output_tokens: usage.output,
5282
- cache_creation_input_tokens: usage.cacheWrite ?? 0,
5283
- cache_read_input_tokens: usage.cacheRead ?? 0
5284
- },
5285
- model: data.message.model != null ? `[pi] ${data.message.model}` : void 0,
5286
- costUSD: usage.cost?.total,
5287
- totalTokens
5288
- };
5289
- }
5290
5595
  async function processJSONLFileByLine(filePath, processor) {
5291
5596
  const fileStream = fs.createReadStream(filePath, { encoding: "utf-8" });
5292
5597
  const rl = readline.createInterface({
5293
5598
  input: fileStream,
5294
5599
  crlfDelay: Infinity
5295
5600
  });
5601
+ let lineIndex = 0;
5296
5602
  for await (const line of rl) {
5297
5603
  const trimmedLine = line.trim();
5298
- if (trimmedLine !== "") await processor(trimmedLine);
5604
+ if (trimmedLine !== "") await processor(trimmedLine, lineIndex);
5605
+ lineIndex += 1;
5299
5606
  }
5300
5607
  }
5301
5608
  async function globPiAgentFiles(paths) {
@@ -5338,27 +5645,29 @@ async function loadPiAgentData(options) {
5338
5645
  for (const file of files) {
5339
5646
  const project = extractPiAgentProject(file);
5340
5647
  const sessionId = extractPiAgentSessionId(file);
5341
- await processJSONLFileByLine(file, (line) => {
5648
+ await processJSONLFileByLine(file, (line, lineIndex) => {
5342
5649
  try {
5343
5650
  const result = /* @__PURE__ */ safeParse(piAgentMessageSchema, JSON.parse(line));
5344
5651
  if (!result.success) return;
5345
5652
  const data = result.output;
5346
- const transformed = transformPiAgentUsage(data);
5347
- if (transformed == null) return;
5348
- const hash = `pi:${data.timestamp}:${transformed.totalTokens}`;
5349
- if (processedHashes.has(hash)) return;
5350
- processedHashes.add(hash);
5351
- entries.push({
5352
- timestamp: data.timestamp,
5353
- model: transformed.model,
5354
- inputTokens: transformed.usage.input_tokens,
5355
- outputTokens: transformed.usage.output_tokens,
5356
- cacheCreationTokens: transformed.usage.cache_creation_input_tokens,
5357
- cacheReadTokens: transformed.usage.cache_read_input_tokens,
5358
- cost: transformed.costUSD ?? 0,
5359
- project,
5360
- sessionId
5361
- });
5653
+ const usageEntries = [...isPiAgentUsageEntry(data) ? [transformPiAgentUsage(data)] : [], ...extractPiAgentSubagentUsageEntries(data)].filter((entry) => entry != null);
5654
+ for (const [resultIndex, transformed] of usageEntries.entries()) {
5655
+ if (transformed == null) continue;
5656
+ const hash = `pi:${file}:${lineIndex}:${resultIndex}`;
5657
+ if (processedHashes.has(hash)) continue;
5658
+ processedHashes.add(hash);
5659
+ entries.push({
5660
+ timestamp: data.timestamp,
5661
+ model: transformed.model,
5662
+ inputTokens: transformed.usage.input_tokens,
5663
+ outputTokens: transformed.usage.output_tokens,
5664
+ cacheCreationTokens: transformed.usage.cache_creation_input_tokens,
5665
+ cacheReadTokens: transformed.usage.cache_read_input_tokens,
5666
+ cost: transformed.costUSD ?? 0,
5667
+ project,
5668
+ sessionId
5669
+ });
5670
+ }
5362
5671
  } catch {}
5363
5672
  });
5364
5673
  }
@@ -5436,7 +5745,7 @@ async function loadPiAgentDailyData(options) {
5436
5745
  });
5437
5746
  }
5438
5747
  const order = options?.order ?? "desc";
5439
- results.sort((a$1, b$1) => order === "asc" ? a$1.date.localeCompare(b$1.date) : b$1.date.localeCompare(a$1.date));
5748
+ results.sort((a$2, b$1) => order === "asc" ? a$2.date.localeCompare(b$1.date) : b$1.date.localeCompare(a$2.date));
5440
5749
  return results;
5441
5750
  }
5442
5751
  async function loadPiAgentSessionData(options) {
@@ -5470,7 +5779,7 @@ async function loadPiAgentSessionData(options) {
5470
5779
  });
5471
5780
  }
5472
5781
  const order = options?.order ?? "desc";
5473
- results.sort((a$1, b$1) => order === "asc" ? a$1.lastActivity.localeCompare(b$1.lastActivity) : b$1.lastActivity.localeCompare(a$1.lastActivity));
5782
+ results.sort((a$2, b$1) => order === "asc" ? a$2.lastActivity.localeCompare(b$1.lastActivity) : b$1.lastActivity.localeCompare(a$2.lastActivity));
5474
5783
  return results;
5475
5784
  }
5476
5785
  async function loadPiAgentMonthlyData(options) {
@@ -5498,7 +5807,7 @@ async function loadPiAgentMonthlyData(options) {
5498
5807
  });
5499
5808
  }
5500
5809
  const order = options?.order ?? "desc";
5501
- results.sort((a$1, b$1) => order === "asc" ? a$1.month.localeCompare(b$1.month) : b$1.month.localeCompare(a$1.month));
5810
+ results.sort((a$2, b$1) => order === "asc" ? a$2.month.localeCompare(b$1.month) : b$1.month.localeCompare(a$2.month));
5502
5811
  return results;
5503
5812
  }
5504
5813
  const LogLevels = {
@@ -5801,7 +6110,7 @@ function createConsola(options = {}) {
5801
6110
  }
5802
6111
  function parseStack(stack, message) {
5803
6112
  const cwd = process.cwd() + sep;
5804
- return stack.split("\n").splice(message.split("\n").length).map((l$1) => l$1.trim().replace("file://", "").replace(cwd, ""));
6113
+ return stack.split("\n").splice(message.split("\n").length).map((l$2) => l$2.trim().replace("file://", "").replace(cwd, ""));
5805
6114
  }
5806
6115
  function writeStream(data, stream) {
5807
6116
  return (stream.__write || stream.write).call(stream, data);
@@ -5842,7 +6151,7 @@ ${indent}`);
5842
6151
  bracket(logObj.tag),
5843
6152
  logObj.title && logObj.title,
5844
6153
  ...message.split("\n")
5845
- ].filter(Boolean).map((l$1) => " > " + l$1).join("\n") + "\n";
6154
+ ].filter(Boolean).map((l$2) => " > " + l$2).join("\n") + "\n";
5846
6155
  return this.filterAndJoin([
5847
6156
  bracket(logObj.type),
5848
6157
  bracket(logObj.tag),
@@ -6174,10 +6483,10 @@ l.name;
6174
6483
  function n(e) {
6175
6484
  return e ? e !== "false" : false;
6176
6485
  }
6177
- const I = globalThis.process?.platform || "", T = n(o.CI) || l.ci !== false, a = n(globalThis.process?.stdout && globalThis.process?.stdout.isTTY), g = n(o.DEBUG), R = t === "test" || n(o.TEST);
6486
+ const I = globalThis.process?.platform || "", T = n(o.CI) || l.ci !== false, a$1 = n(globalThis.process?.stdout && globalThis.process?.stdout.isTTY), g = n(o.DEBUG), R = t === "test" || n(o.TEST);
6178
6487
  n(o.MINIMAL);
6179
6488
  const A = /^win/i.test(I);
6180
- !n(o.NO_COLOR) && (n(o.FORCE_COLOR) || (a || A) && o.TERM);
6489
+ !n(o.NO_COLOR) && (n(o.FORCE_COLOR) || (a$1 || A) && o.TERM);
6181
6490
  const C = (globalThis.process?.versions?.node || "").replace(/^v/, "") || null;
6182
6491
  Number(C?.split(".")[0]);
6183
6492
  const y = globalThis.process || Object.create(null), _ = { versions: {} };
@@ -6186,7 +6495,7 @@ new Proxy(y, { get(e, s$1) {
6186
6495
  if (s$1 in e) return e[s$1];
6187
6496
  if (s$1 in _) return _[s$1];
6188
6497
  } });
6189
- const c = globalThis.process?.release?.name === "node", O = !!globalThis.Bun || !!globalThis.process?.versions?.bun, D = !!globalThis.Deno, L = !!globalThis.fastly, S = !!globalThis.Netlify, u = !!globalThis.EdgeRuntime, N = globalThis.navigator?.userAgent === "Cloudflare-Workers", F = [
6498
+ const c = globalThis.process?.release?.name === "node", O = !!globalThis.Bun || !!globalThis.process?.versions?.bun, D = !!globalThis.Deno, L = !!globalThis.fastly, S = !!globalThis.Netlify, u = !!globalThis.EdgeRuntime, N = globalThis.navigator?.userAgent === "Cloudflare-Workers", F$1 = [
6190
6499
  [S, "netlify"],
6191
6500
  [u, "edge-light"],
6192
6501
  [N, "workerd"],
@@ -6196,7 +6505,7 @@ const c = globalThis.process?.release?.name === "node", O = !!globalThis.Bun ||
6196
6505
  [c, "node"]
6197
6506
  ];
6198
6507
  function G() {
6199
- const e = F.find((s$1) => s$1[0]);
6508
+ const e = F$1.find((s$1) => s$1[0]);
6200
6509
  if (e) return { name: e[1] };
6201
6510
  }
6202
6511
  G()?.name;
@@ -6294,7 +6603,7 @@ var FancyReporter = class extends BasicReporter {
6294
6603
  formatStack(stack, message, opts) {
6295
6604
  const indent = " ".repeat((opts?.errorLevel || 0) + 1);
6296
6605
  return `
6297
- ${indent}` + parseStack(stack, message).map((line) => " " + line.replace(/^at +/, (m) => colors.gray(m)).replace(/\((.+)\)/, (_$1, m) => `(${colors.cyan(m)})`)).join(`
6606
+ ${indent}` + parseStack(stack, message).map((line) => " " + line.replace(/^at +/, (m$1) => colors.gray(m$1)).replace(/\((.+)\)/, (_$1, m$1) => `(${colors.cyan(m$1)})`)).join(`
6298
6607
  ${indent}`);
6299
6608
  }
6300
6609
  formatType(logObj, isBadge, opts) {
@@ -6328,7 +6637,7 @@ ${indent}`);
6328
6637
  }
6329
6638
  };
6330
6639
  function characterFormat(str) {
6331
- return str.replace(/`([^`]+)`/gm, (_$1, m) => colors.cyan(m)).replace(/\s+_([^_]+)_\s+/gm, (_$1, m) => ` ${colors.underline(m)} `);
6640
+ return str.replace(/`([^`]+)`/gm, (_$1, m$1) => colors.cyan(m$1)).replace(/\s+_([^_]+)_\s+/gm, (_$1, m$1) => ` ${colors.underline(m$1)} `);
6332
6641
  }
6333
6642
  function getColor(color = "white") {
6334
6643
  return colors[color] || colors.white;
@@ -6344,7 +6653,7 @@ function createConsola$1(options = {}) {
6344
6653
  defaults: { level: level$1 },
6345
6654
  stdout: process.stdout,
6346
6655
  stderr: process.stderr,
6347
- prompt: (...args) => import("./prompt-B5khkcyF.js").then((m) => m.prompt(...args)),
6656
+ prompt: (...args) => import("./prompt-B5khkcyF.js").then((m$1) => m$1.prompt(...args)),
6348
6657
  reporters: options.reporters || [options.fancy ?? !(T || R) ? new FancyReporter() : new BasicReporter()],
6349
6658
  ...options
6350
6659
  });
@@ -6435,12 +6744,12 @@ const dailyCommand = define({
6435
6744
  totalTokens: 0,
6436
6745
  totalCost: 0
6437
6746
  };
6438
- for (const d of piData) {
6439
- totals.inputTokens += d.inputTokens;
6440
- totals.outputTokens += d.outputTokens;
6441
- totals.cacheCreationTokens += d.cacheCreationTokens;
6442
- totals.cacheReadTokens += d.cacheReadTokens;
6443
- totals.totalCost += d.totalCost;
6747
+ for (const d$1 of piData) {
6748
+ totals.inputTokens += d$1.inputTokens;
6749
+ totals.outputTokens += d$1.outputTokens;
6750
+ totals.cacheCreationTokens += d$1.cacheCreationTokens;
6751
+ totals.cacheReadTokens += d$1.cacheReadTokens;
6752
+ totals.totalCost += d$1.totalCost;
6444
6753
  }
6445
6754
  totals.totalTokens = totals.inputTokens + totals.outputTokens + totals.cacheCreationTokens + totals.cacheReadTokens;
6446
6755
  if (ctx.values.json) log(JSON.stringify({
@@ -6547,12 +6856,12 @@ const monthlyCommand = define({
6547
6856
  totalTokens: 0,
6548
6857
  totalCost: 0
6549
6858
  };
6550
- for (const d of piData) {
6551
- totals.inputTokens += d.inputTokens;
6552
- totals.outputTokens += d.outputTokens;
6553
- totals.cacheCreationTokens += d.cacheCreationTokens;
6554
- totals.cacheReadTokens += d.cacheReadTokens;
6555
- totals.totalCost += d.totalCost;
6859
+ for (const d$1 of piData) {
6860
+ totals.inputTokens += d$1.inputTokens;
6861
+ totals.outputTokens += d$1.outputTokens;
6862
+ totals.cacheCreationTokens += d$1.cacheCreationTokens;
6863
+ totals.cacheReadTokens += d$1.cacheReadTokens;
6864
+ totals.totalCost += d$1.totalCost;
6556
6865
  }
6557
6866
  totals.totalTokens = totals.inputTokens + totals.outputTokens + totals.cacheCreationTokens + totals.cacheReadTokens;
6558
6867
  if (ctx.values.json) log(JSON.stringify({
@@ -6657,13 +6966,13 @@ const sessionCommand = define({
6657
6966
  process$1.exit(0);
6658
6967
  }
6659
6968
  const totals = createEmptyTotals();
6660
- for (const d of piData) {
6661
- totals.inputTokens += d.inputTokens;
6662
- totals.outputTokens += d.outputTokens;
6663
- totals.cacheCreationTokens += d.cacheCreationTokens;
6664
- totals.cacheReadTokens += d.cacheReadTokens;
6665
- totals.totalTokens += d.inputTokens + d.outputTokens + d.cacheCreationTokens + d.cacheReadTokens;
6666
- totals.totalCost += d.totalCost;
6969
+ for (const d$1 of piData) {
6970
+ totals.inputTokens += d$1.inputTokens;
6971
+ totals.outputTokens += d$1.outputTokens;
6972
+ totals.cacheCreationTokens += d$1.cacheCreationTokens;
6973
+ totals.cacheReadTokens += d$1.cacheReadTokens;
6974
+ totals.totalTokens += d$1.inputTokens + d$1.outputTokens + d$1.cacheCreationTokens + d$1.cacheReadTokens;
6975
+ totals.totalCost += d$1.totalCost;
6667
6976
  }
6668
6977
  if (ctx.values.json) log(JSON.stringify({
6669
6978
  sessions: piData,
package/package.json CHANGED
@@ -1,46 +1,39 @@
1
1
  {
2
2
  "name": "@unravel-tech/ccusage-pi",
3
- "type": "module",
4
- "version": "18.1.0",
3
+ "version": "18.2.2",
5
4
  "description": "Pi-agent usage tracking - unified Claude Max usage across Claude Code and pi-agent",
5
+ "homepage": "https://github.com/ryoppippi/ccusage#readme",
6
+ "bugs": {
7
+ "url": "https://github.com/ryoppippi/ccusage/issues"
8
+ },
9
+ "license": "MIT",
6
10
  "author": "ryoppippi",
7
11
  "contributors": [
8
12
  "nicobailon"
9
13
  ],
10
- "license": "MIT",
11
- "funding": "https://github.com/ryoppippi/ccusage?sponsor=1",
12
- "homepage": "https://github.com/ryoppippi/ccusage#readme",
13
14
  "repository": {
14
15
  "type": "git",
15
16
  "url": "git+https://github.com/ryoppippi/ccusage.git",
16
17
  "directory": "apps/pi"
17
18
  },
18
- "bugs": {
19
- "url": "https://github.com/ryoppippi/ccusage/issues"
20
- },
21
- "exports": {
22
- ".": "./src/index.ts",
23
- "./package.json": "./package.json"
24
- },
25
- "main": "./dist/index.js",
26
- "module": "./dist/index.js",
27
- "types": "./dist/index.d.ts",
19
+ "funding": "https://github.com/ryoppippi/ccusage?sponsor=1",
28
20
  "bin": {
29
21
  "ccusage-pi": "./dist/index.js"
30
22
  },
31
23
  "files": [
32
- "README.md",
33
- "dist"
24
+ "dist",
25
+ "README.md"
34
26
  ],
27
+ "type": "module",
28
+ "main": "./dist/index.js",
29
+ "module": "./dist/index.js",
30
+ "types": "./dist/index.d.ts",
31
+ "exports": {
32
+ ".": "./dist/index.js",
33
+ "./package.json": "./package.json"
34
+ },
35
35
  "publishConfig": {
36
- "access": "public",
37
- "bin": {
38
- "ccusage-pi": "./dist/index.js"
39
- },
40
- "exports": {
41
- ".": "./dist/index.js",
42
- "./package.json": "./package.json"
43
- }
36
+ "access": "public"
44
37
  },
45
38
  "engines": {
46
39
  "node": ">=20.19.4"