@ken-jo/agent-connector 0.1.0

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 (203) hide show
  1. package/LICENSE +202 -0
  2. package/NOTICE +6 -0
  3. package/README.md +348 -0
  4. package/dist/amp-QSFH2V7Y.js +217 -0
  5. package/dist/amp-QSFH2V7Y.js.map +1 -0
  6. package/dist/amp-TULUPXXL.js +237 -0
  7. package/dist/amp-TULUPXXL.js.map +1 -0
  8. package/dist/antigravity-CX2YLSY7.js +17 -0
  9. package/dist/antigravity-CX2YLSY7.js.map +1 -0
  10. package/dist/antigravity-STHZWMP3.js +171 -0
  11. package/dist/antigravity-STHZWMP3.js.map +1 -0
  12. package/dist/antigravity-cli-P6HADOAO.js +121 -0
  13. package/dist/antigravity-cli-P6HADOAO.js.map +1 -0
  14. package/dist/antigravity-cli-YQDFVV4U.js +86 -0
  15. package/dist/antigravity-cli-YQDFVV4U.js.map +1 -0
  16. package/dist/chunk-54EMKTTX.js +191 -0
  17. package/dist/chunk-54EMKTTX.js.map +1 -0
  18. package/dist/chunk-7L6ITC4T.js +54 -0
  19. package/dist/chunk-7L6ITC4T.js.map +1 -0
  20. package/dist/chunk-7MSDGHJW.js +316 -0
  21. package/dist/chunk-7MSDGHJW.js.map +1 -0
  22. package/dist/chunk-BCHWFTV4.js +196 -0
  23. package/dist/chunk-BCHWFTV4.js.map +1 -0
  24. package/dist/chunk-DBQMX75U.js +36 -0
  25. package/dist/chunk-DBQMX75U.js.map +1 -0
  26. package/dist/chunk-EXLS7BSI.js +29 -0
  27. package/dist/chunk-EXLS7BSI.js.map +1 -0
  28. package/dist/chunk-JNM3TPLX.js +593 -0
  29. package/dist/chunk-JNM3TPLX.js.map +1 -0
  30. package/dist/chunk-JWNT5KW7.js +197 -0
  31. package/dist/chunk-JWNT5KW7.js.map +1 -0
  32. package/dist/chunk-KHO5WNTP.js +30 -0
  33. package/dist/chunk-KHO5WNTP.js.map +1 -0
  34. package/dist/chunk-LTT56GI3.js +155 -0
  35. package/dist/chunk-LTT56GI3.js.map +1 -0
  36. package/dist/chunk-MEH7GC7R.js +111 -0
  37. package/dist/chunk-MEH7GC7R.js.map +1 -0
  38. package/dist/chunk-MQPNU2CY.js +64 -0
  39. package/dist/chunk-MQPNU2CY.js.map +1 -0
  40. package/dist/chunk-OPXAP3AC.js +12 -0
  41. package/dist/chunk-OPXAP3AC.js.map +1 -0
  42. package/dist/chunk-RK6VBLXP.js +50 -0
  43. package/dist/chunk-RK6VBLXP.js.map +1 -0
  44. package/dist/chunk-TIIP3RG2.js +420 -0
  45. package/dist/chunk-TIIP3RG2.js.map +1 -0
  46. package/dist/chunk-TRKWUNO4.js +702 -0
  47. package/dist/chunk-TRKWUNO4.js.map +1 -0
  48. package/dist/chunk-TRQKHP7D.js +93 -0
  49. package/dist/chunk-TRQKHP7D.js.map +1 -0
  50. package/dist/chunk-WCETQWWK.js +59 -0
  51. package/dist/chunk-WCETQWWK.js.map +1 -0
  52. package/dist/chunk-WV63X7IK.js +357 -0
  53. package/dist/chunk-WV63X7IK.js.map +1 -0
  54. package/dist/chunk-XD7MY6HB.js +343 -0
  55. package/dist/chunk-XD7MY6HB.js.map +1 -0
  56. package/dist/chunk-XNAM7F35.js +276 -0
  57. package/dist/chunk-XNAM7F35.js.map +1 -0
  58. package/dist/chunk-XUCWLJY5.js +238 -0
  59. package/dist/chunk-XUCWLJY5.js.map +1 -0
  60. package/dist/chunk-YNZU6PAV.js +800 -0
  61. package/dist/chunk-YNZU6PAV.js.map +1 -0
  62. package/dist/chunk-YT43MUSJ.js +146 -0
  63. package/dist/chunk-YT43MUSJ.js.map +1 -0
  64. package/dist/claude-code-HKDV7T32.js +637 -0
  65. package/dist/claude-code-HKDV7T32.js.map +1 -0
  66. package/dist/claude-code-W74MNTAC.js +652 -0
  67. package/dist/claude-code-W74MNTAC.js.map +1 -0
  68. package/dist/cli/sdk.d.ts +54 -0
  69. package/dist/cli/sdk.js +82 -0
  70. package/dist/cli/sdk.js.map +1 -0
  71. package/dist/cli.d.ts +2 -0
  72. package/dist/cli.js +15 -0
  73. package/dist/cli.js.map +1 -0
  74. package/dist/codebuff-3PMZJJHP.js +307 -0
  75. package/dist/codebuff-3PMZJJHP.js.map +1 -0
  76. package/dist/codebuff-QX57FJDN.js +220 -0
  77. package/dist/codebuff-QX57FJDN.js.map +1 -0
  78. package/dist/codex-JFQTS6LU.js +593 -0
  79. package/dist/codex-JFQTS6LU.js.map +1 -0
  80. package/dist/codex-Q3ATRRX3.js +364 -0
  81. package/dist/codex-Q3ATRRX3.js.map +1 -0
  82. package/dist/copilot-cli-MTCGHZ2T.js +622 -0
  83. package/dist/copilot-cli-MTCGHZ2T.js.map +1 -0
  84. package/dist/copilot-cli-SJGIXVSD.js +369 -0
  85. package/dist/copilot-cli-SJGIXVSD.js.map +1 -0
  86. package/dist/crush-I7PK3FGI.js +360 -0
  87. package/dist/crush-I7PK3FGI.js.map +1 -0
  88. package/dist/crush-LN5QFFR2.js +183 -0
  89. package/dist/crush-LN5QFFR2.js.map +1 -0
  90. package/dist/cursor-4TMXKJOZ.js +603 -0
  91. package/dist/cursor-4TMXKJOZ.js.map +1 -0
  92. package/dist/cursor-QZ6MTO74.js +194 -0
  93. package/dist/cursor-QZ6MTO74.js.map +1 -0
  94. package/dist/detect-WIAGVYS4.js +68 -0
  95. package/dist/detect-WIAGVYS4.js.map +1 -0
  96. package/dist/doctor-EZW2K4NI.js +372 -0
  97. package/dist/doctor-EZW2K4NI.js.map +1 -0
  98. package/dist/droid-KN6VRMMT.js +424 -0
  99. package/dist/droid-KN6VRMMT.js.map +1 -0
  100. package/dist/droid-W5WF5XEX.js +224 -0
  101. package/dist/droid-W5WF5XEX.js.map +1 -0
  102. package/dist/gemini-cli-CIRW37TU.js +369 -0
  103. package/dist/gemini-cli-CIRW37TU.js.map +1 -0
  104. package/dist/gemini-cli-Y35FFK4M.js +705 -0
  105. package/dist/gemini-cli-Y35FFK4M.js.map +1 -0
  106. package/dist/goose-A3M5GODH.js +212 -0
  107. package/dist/goose-A3M5GODH.js.map +1 -0
  108. package/dist/goose-ZTGTSUFJ.js +480 -0
  109. package/dist/goose-ZTGTSUFJ.js.map +1 -0
  110. package/dist/hermes-H2KV44GK.js +470 -0
  111. package/dist/hermes-H2KV44GK.js.map +1 -0
  112. package/dist/hermes-ZYLMOFLZ.js +196 -0
  113. package/dist/hermes-ZYLMOFLZ.js.map +1 -0
  114. package/dist/hook-YVDILAMZ.js +75 -0
  115. package/dist/hook-YVDILAMZ.js.map +1 -0
  116. package/dist/index.d.ts +22 -0
  117. package/dist/index.js +10 -0
  118. package/dist/index.js.map +1 -0
  119. package/dist/install-HQRYZOQ2.js +60 -0
  120. package/dist/install-HQRYZOQ2.js.map +1 -0
  121. package/dist/jetbrains-copilot-HWA3DMH7.js +633 -0
  122. package/dist/jetbrains-copilot-HWA3DMH7.js.map +1 -0
  123. package/dist/kilo-NSWAVP6P.js +235 -0
  124. package/dist/kilo-NSWAVP6P.js.map +1 -0
  125. package/dist/kilo-QXJRCSLT.js +384 -0
  126. package/dist/kilo-QXJRCSLT.js.map +1 -0
  127. package/dist/kilo-cli-EAQTHXUW.js +587 -0
  128. package/dist/kilo-cli-EAQTHXUW.js.map +1 -0
  129. package/dist/kilo-cli-EVBKUODA.js +160 -0
  130. package/dist/kilo-cli-EVBKUODA.js.map +1 -0
  131. package/dist/kimi-EI3UM3ZV.js +155 -0
  132. package/dist/kimi-EI3UM3ZV.js.map +1 -0
  133. package/dist/kimi-GQ7VXNYT.js +423 -0
  134. package/dist/kimi-GQ7VXNYT.js.map +1 -0
  135. package/dist/kiro-UCLSLBW2.js +217 -0
  136. package/dist/kiro-UCLSLBW2.js.map +1 -0
  137. package/dist/kiro-VQTT6LO2.js +451 -0
  138. package/dist/kiro-VQTT6LO2.js.map +1 -0
  139. package/dist/leaderboard-K6ON3SWW.js +137 -0
  140. package/dist/leaderboard-K6ON3SWW.js.map +1 -0
  141. package/dist/mux-T2TV4CIQ.js +211 -0
  142. package/dist/mux-T2TV4CIQ.js.map +1 -0
  143. package/dist/mux-ZMLVAXOO.js +96 -0
  144. package/dist/mux-ZMLVAXOO.js.map +1 -0
  145. package/dist/omp-PB4VDKS6.js +586 -0
  146. package/dist/omp-PB4VDKS6.js.map +1 -0
  147. package/dist/openclaw-ETN2M63O.js +751 -0
  148. package/dist/openclaw-ETN2M63O.js.map +1 -0
  149. package/dist/openclaw-IYA7ASL6.js +150 -0
  150. package/dist/openclaw-IYA7ASL6.js.map +1 -0
  151. package/dist/opencode-FZ33JKUZ.js +734 -0
  152. package/dist/opencode-FZ33JKUZ.js.map +1 -0
  153. package/dist/opencode-HWT3RSMN.js +216 -0
  154. package/dist/opencode-HWT3RSMN.js.map +1 -0
  155. package/dist/package-DLOVE2E4.js +1132 -0
  156. package/dist/package-DLOVE2E4.js.map +1 -0
  157. package/dist/pi-CIU2QHT4.js +208 -0
  158. package/dist/pi-CIU2QHT4.js.map +1 -0
  159. package/dist/pi-UFX2OYFV.js +139 -0
  160. package/dist/pi-UFX2OYFV.js.map +1 -0
  161. package/dist/qwen-code-5POCNU6P.js +573 -0
  162. package/dist/qwen-code-5POCNU6P.js.map +1 -0
  163. package/dist/qwen-code-W7NUCDEN.js +134 -0
  164. package/dist/qwen-code-W7NUCDEN.js.map +1 -0
  165. package/dist/roo-code-IOIUXRDE.js +242 -0
  166. package/dist/roo-code-IOIUXRDE.js.map +1 -0
  167. package/dist/roo-code-ZLKH4A7N.js +229 -0
  168. package/dist/roo-code-ZLKH4A7N.js.map +1 -0
  169. package/dist/runtime/index.d.ts +157 -0
  170. package/dist/runtime/index.js +20 -0
  171. package/dist/runtime/index.js.map +1 -0
  172. package/dist/serve-HVWWY4B6.js +65 -0
  173. package/dist/serve-HVWWY4B6.js.map +1 -0
  174. package/dist/status-FE7TECZD.js +128 -0
  175. package/dist/status-FE7TECZD.js.map +1 -0
  176. package/dist/synthetic-UKR6SMGS.js +178 -0
  177. package/dist/synthetic-UKR6SMGS.js.map +1 -0
  178. package/dist/telemetry-36GESKQQ.js +349 -0
  179. package/dist/telemetry-36GESKQQ.js.map +1 -0
  180. package/dist/trae-JSNDZFKL.js +204 -0
  181. package/dist/trae-JSNDZFKL.js.map +1 -0
  182. package/dist/trae-PA26DPBW.js +157 -0
  183. package/dist/trae-PA26DPBW.js.map +1 -0
  184. package/dist/types-CYUB1OTr.d.ts +427 -0
  185. package/dist/uninstall-IGCKNOSF.js +72 -0
  186. package/dist/uninstall-IGCKNOSF.js.map +1 -0
  187. package/dist/upgrade-JV2VK242.js +104 -0
  188. package/dist/upgrade-JV2VK242.js.map +1 -0
  189. package/dist/usage-6ER6EMEY.js +324 -0
  190. package/dist/usage-6ER6EMEY.js.map +1 -0
  191. package/dist/usage-event-JKBI6XCF.js +48 -0
  192. package/dist/usage-event-JKBI6XCF.js.map +1 -0
  193. package/dist/vscode-copilot-CK3NO54M.js +715 -0
  194. package/dist/vscode-copilot-CK3NO54M.js.map +1 -0
  195. package/dist/warp-JNQA7PBU.js +126 -0
  196. package/dist/warp-JNQA7PBU.js.map +1 -0
  197. package/dist/warp-QNVDXOG4.js +199 -0
  198. package/dist/warp-QNVDXOG4.js.map +1 -0
  199. package/dist/zed-NNNX5MNT.js +272 -0
  200. package/dist/zed-NNNX5MNT.js.map +1 -0
  201. package/dist/zed-VRJKWYUR.js +209 -0
  202. package/dist/zed-VRJKWYUR.js.map +1 -0
  203. package/package.json +79 -0
@@ -0,0 +1,324 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ formatHostLeaderboard,
4
+ hostLeaderboard,
5
+ scanUsage
6
+ } from "./chunk-WV63X7IK.js";
7
+ import {
8
+ aggregateBy,
9
+ sumTokens
10
+ } from "./chunk-XD7MY6HB.js";
11
+ import {
12
+ fail,
13
+ print
14
+ } from "./chunk-54EMKTTX.js";
15
+
16
+ // src/cli/commands/usage.ts
17
+ import { writeFileSync } from "fs";
18
+ import { parseArgs } from "util";
19
+
20
+ // src/usage/report.ts
21
+ var KEY_HEADER = {
22
+ platform: "PLATFORM",
23
+ project: "PROJECT",
24
+ session: "SESSION",
25
+ model: "MODEL",
26
+ day: "DAY"
27
+ };
28
+ function fmtInt(n) {
29
+ return n.toLocaleString("en-US");
30
+ }
31
+ function padRight(s, width) {
32
+ return s.length >= width ? s : s + " ".repeat(width - s.length);
33
+ }
34
+ function padLeft(s, width) {
35
+ return s.length >= width ? s : " ".repeat(width - s.length) + s;
36
+ }
37
+ function formatUsageReport(rows, by, skipped = []) {
38
+ const keyHeader = KEY_HEADER[by];
39
+ const headers = [
40
+ keyHeader,
41
+ "IN",
42
+ "OUT",
43
+ "CACHE_R",
44
+ "CACHE_W",
45
+ "REASON",
46
+ "TOTAL",
47
+ "SESS",
48
+ "CONF"
49
+ ];
50
+ const sorted = [...rows].sort((a, b) => b.total - a.total || b.lastTs - a.lastTs);
51
+ const dataRows = sorted.map((r) => [
52
+ r.key,
53
+ fmtInt(r.tokens.input),
54
+ fmtInt(r.tokens.output),
55
+ fmtInt(r.tokens.cacheRead),
56
+ fmtInt(r.tokens.cacheWrite),
57
+ fmtInt(r.tokens.reasoning),
58
+ fmtInt(r.total),
59
+ fmtInt(r.sessions),
60
+ r.confidence
61
+ ]);
62
+ const totals = sorted.reduce(
63
+ (acc, r) => {
64
+ acc.input += r.tokens.input;
65
+ acc.output += r.tokens.output;
66
+ acc.cacheRead += r.tokens.cacheRead;
67
+ acc.cacheWrite += r.tokens.cacheWrite;
68
+ acc.reasoning += r.tokens.reasoning;
69
+ acc.total += r.total;
70
+ acc.sessions += r.sessions;
71
+ return acc;
72
+ },
73
+ { input: 0, output: 0, cacheRead: 0, cacheWrite: 0, reasoning: 0, total: 0, sessions: 0 }
74
+ );
75
+ const totalRow = [
76
+ "TOTAL",
77
+ fmtInt(totals.input),
78
+ fmtInt(totals.output),
79
+ fmtInt(totals.cacheRead),
80
+ fmtInt(totals.cacheWrite),
81
+ fmtInt(totals.reasoning),
82
+ fmtInt(totals.total),
83
+ fmtInt(totals.sessions),
84
+ ""
85
+ ];
86
+ const widths = headers.map((h, col) => {
87
+ let w = h.length;
88
+ for (const row of dataRows) w = Math.max(w, (row[col] ?? "").length);
89
+ w = Math.max(w, (totalRow[col] ?? "").length);
90
+ return w;
91
+ });
92
+ const renderRow = (cells) => cells.map((c, col) => col === 0 ? padRight(c, widths[col] ?? 0) : padLeft(c, widths[col] ?? 0)).join(" ").trimEnd();
93
+ const ruleWidth = widths.reduce((a, b) => a + b, 0) + 2 * (widths.length - 1);
94
+ const rule = "-".repeat(ruleWidth);
95
+ const lines = [];
96
+ lines.push(renderRow(headers));
97
+ lines.push(rule);
98
+ if (dataRows.length === 0) {
99
+ lines.push("(no host usage found)");
100
+ } else {
101
+ for (const row of dataRows) lines.push(renderRow(row));
102
+ }
103
+ lines.push(rule);
104
+ lines.push(renderRow(totalRow));
105
+ const hasEstimate = sorted.some((r) => r.confidence === "host-estimated");
106
+ if (hasEstimate) {
107
+ lines.push("");
108
+ lines.push(
109
+ "note: host-estimated rows are derived (e.g. char/4 or cost-only), not exact host-reported token counts."
110
+ );
111
+ }
112
+ if (skipped.length > 0) {
113
+ lines.push("");
114
+ lines.push("skipped:");
115
+ for (const s of skipped) lines.push(` - ${s.platformId}: ${s.reason}`);
116
+ }
117
+ return lines.join("\n");
118
+ }
119
+ var CSV_COLUMNS = [
120
+ "platformId",
121
+ "modelId",
122
+ "providerId",
123
+ "sessionId",
124
+ "projectKey",
125
+ "projectLabel",
126
+ "input",
127
+ "output",
128
+ "cacheRead",
129
+ "cacheWrite",
130
+ "reasoning",
131
+ "total",
132
+ "cost",
133
+ "ts",
134
+ "messageCount",
135
+ "confidence",
136
+ "agent"
137
+ ];
138
+ function csvCell(value) {
139
+ if (value === void 0 || value === null) return "";
140
+ const s = String(value);
141
+ if (/[",\n\r]/.test(s)) return `"${s.replace(/"/g, '""')}"`;
142
+ return s;
143
+ }
144
+ function recordRow(r) {
145
+ return [
146
+ r.platformId,
147
+ r.modelId,
148
+ r.providerId,
149
+ r.sessionId,
150
+ r.projectKey,
151
+ r.projectLabel,
152
+ r.tokens.input,
153
+ r.tokens.output,
154
+ r.tokens.cacheRead,
155
+ r.tokens.cacheWrite,
156
+ r.tokens.reasoning,
157
+ sumTokens(r.tokens),
158
+ r.cost,
159
+ r.ts,
160
+ r.messageCount,
161
+ r.confidence,
162
+ r.agent
163
+ ];
164
+ }
165
+ function usageToCSV(records) {
166
+ const lines = [];
167
+ lines.push(CSV_COLUMNS.join(","));
168
+ for (const r of records) {
169
+ lines.push(recordRow(r).map(csvCell).join(","));
170
+ }
171
+ return lines.join("\r\n");
172
+ }
173
+ function usageToJSON(records) {
174
+ return JSON.stringify(records, null, 2);
175
+ }
176
+
177
+ // src/cli/commands/usage.ts
178
+ function parseSince(since) {
179
+ if (since == null || since.trim() === "") return void 0;
180
+ const m = since.trim().match(/^(\d+)\s*([smhd])$/i);
181
+ if (!m || !m[1] || !m[2]) return null;
182
+ const n = Number(m[1]);
183
+ const unitMs = {
184
+ s: 1e3,
185
+ m: 6e4,
186
+ h: 36e5,
187
+ d: 864e5
188
+ };
189
+ const factor = unitMs[m[2].toLowerCase()];
190
+ if (factor == null) return null;
191
+ return Date.now() - n * factor;
192
+ }
193
+ var GROUP_BY_VALUES = /* @__PURE__ */ new Set([
194
+ "platform",
195
+ "project",
196
+ "session",
197
+ "model",
198
+ "day"
199
+ ]);
200
+ function buildScanOpts(since, platform) {
201
+ const sinceMs = parseSince(since);
202
+ if (sinceMs === null) return null;
203
+ const opts = {};
204
+ if (sinceMs !== void 0) opts.sinceMs = sinceMs;
205
+ if (platform && platform.trim() !== "") opts.platforms = [platform.trim()];
206
+ return opts;
207
+ }
208
+ async function runReport(argv) {
209
+ const { values } = parseArgs({
210
+ args: argv,
211
+ options: {
212
+ by: { type: "string", default: "platform" },
213
+ since: { type: "string" },
214
+ platform: { type: "string" },
215
+ json: { type: "boolean", default: false }
216
+ },
217
+ allowPositionals: false
218
+ });
219
+ const by = values.by;
220
+ if (!GROUP_BY_VALUES.has(by ?? "")) {
221
+ return fail(`invalid --by "${by}" (use platform|project|session|model|day)`);
222
+ }
223
+ const dimension = by;
224
+ const scanOpts = buildScanOpts(values.since, values.platform);
225
+ if (scanOpts === null) {
226
+ return fail(`invalid --since "${values.since}" (use forms like 30s, 15m, 24h, 7d)`);
227
+ }
228
+ const { records, skipped } = await scanUsage(scanOpts);
229
+ const rows = aggregateBy(records, dimension);
230
+ if (values.json) {
231
+ print(JSON.stringify({ by: dimension, rows, skipped }, null, 2));
232
+ } else {
233
+ print(formatUsageReport(rows, dimension, skipped));
234
+ }
235
+ return 0;
236
+ }
237
+ async function runExport(argv) {
238
+ const { values } = parseArgs({
239
+ args: argv,
240
+ options: {
241
+ format: { type: "string", default: "json" },
242
+ out: { type: "string" },
243
+ since: { type: "string" },
244
+ platform: { type: "string" }
245
+ },
246
+ allowPositionals: false
247
+ });
248
+ const format = values.format;
249
+ if (format !== "csv" && format !== "json") {
250
+ return fail(`invalid --format "${format}" (use csv|json)`);
251
+ }
252
+ const scanOpts = buildScanOpts(values.since, values.platform);
253
+ if (scanOpts === null) {
254
+ return fail(`invalid --since "${values.since}" (use forms like 30s, 15m, 24h, 7d)`);
255
+ }
256
+ const { records } = await scanUsage(scanOpts);
257
+ const serialized = format === "csv" ? usageToCSV(records) : usageToJSON(records);
258
+ if (values.out && values.out.trim() !== "") {
259
+ writeFileSync(values.out, serialized, "utf8");
260
+ print(`wrote ${format.toUpperCase()} export \u2192 ${values.out}`);
261
+ } else {
262
+ print(serialized);
263
+ }
264
+ return 0;
265
+ }
266
+ async function runLeaderboard(argv) {
267
+ const { values } = parseArgs({
268
+ args: argv,
269
+ options: {
270
+ by: { type: "string", default: "platform" },
271
+ since: { type: "string" },
272
+ platform: { type: "string" },
273
+ json: { type: "boolean", default: false }
274
+ },
275
+ allowPositionals: false
276
+ });
277
+ const by = values.by;
278
+ if (by !== "platform" && by !== "model") {
279
+ return fail(`invalid --by "${by}" (use platform|model)`);
280
+ }
281
+ const scanOpts = buildScanOpts(values.since, values.platform);
282
+ if (scanOpts === null) {
283
+ return fail(`invalid --since "${values.since}" (use forms like 30s, 15m, 24h, 7d)`);
284
+ }
285
+ const lbOpts = {
286
+ by
287
+ };
288
+ if (scanOpts.sinceMs !== void 0) lbOpts.sinceMs = scanOpts.sinceMs;
289
+ if (scanOpts.platforms !== void 0) lbOpts.platforms = scanOpts.platforms;
290
+ const result = await hostLeaderboard(lbOpts);
291
+ if (values.json) {
292
+ print(JSON.stringify({ by: result.by, rows: result.rows, skipped: result.skipped }, null, 2));
293
+ } else {
294
+ print(formatHostLeaderboard(result));
295
+ }
296
+ return 0;
297
+ }
298
+ async function run(argv) {
299
+ const sub = argv[0];
300
+ const rest = argv.slice(1);
301
+ switch (sub) {
302
+ case "report":
303
+ return runReport(rest);
304
+ case "export":
305
+ return runExport(rest);
306
+ case "leaderboard":
307
+ return runLeaderboard(rest);
308
+ case void 0:
309
+ case "--help":
310
+ case "-h":
311
+ print("usage: agent-connector usage <report|export|leaderboard> [flags]");
312
+ print(" report --by platform|project|session|model|day --since 7d --platform <id> --json");
313
+ print(" export --format csv|json --out <file> --since 7d --platform <id>");
314
+ print(" leaderboard --by platform|model --since 7d --platform <id> --json");
315
+ return sub === void 0 ? 1 : 0;
316
+ default:
317
+ return fail(`unknown usage subcommand "${sub}" (use report|export|leaderboard)`);
318
+ }
319
+ }
320
+ export {
321
+ parseSince,
322
+ run
323
+ };
324
+ //# sourceMappingURL=usage-6ER6EMEY.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/cli/commands/usage.ts","../src/usage/report.ts"],"sourcesContent":["/**\n * cli/commands/usage — inspect HOST-native token usage parsed from each agent\n * CLI's own session logs/DBs (the read-only complement to `telemetry`, which\n * measures the MCP server's own bytes — the two are NOT summed: they measure\n * different things).\n *\n * Subcommands:\n * report --by platform|project|session|model|day (default platform)\n * --since 7d|24h|… --platform <id> [--json]\n * → scanUsage → aggregateBy → formatUsageReport (prints skip notes).\n * export --format csv|json (default json) --out <file>\n * --since 7d --platform <id>\n * → deduped UsageRecord[] to CSV/JSON.\n *\n * Usage rows are aggregate counts only (never raw prompts/results) and the layer\n * is strictly read-only — it parses host logs, it never writes host config.\n */\n\nimport { writeFileSync } from \"node:fs\";\nimport { parseArgs } from \"node:util\";\n\nimport type { PlatformId } from \"../../core/types.js\";\nimport type { UsageGroupBy } from \"../../usage/types.js\";\nimport { aggregateBy } from \"../../usage/aggregate.js\";\nimport { formatUsageReport, usageToCSV, usageToJSON } from \"../../usage/report.js\";\nimport { formatHostLeaderboard, hostLeaderboard } from \"../../usage/leaderboard.js\";\nimport { scanUsage } from \"../../usage/scan.js\";\nimport { fail, print } from \"../app.js\";\n\n/**\n * Parse a relative duration (`Ns`/`Nm`/`Nh`/`Nd`) to a lower-bound epoch ms.\n * Returns undefined for empty input and null for a malformed one. (Mirrors\n * telemetry.ts parseSince — kept local so the two commands stay decoupled.)\n */\nexport function parseSince(since: string | undefined): number | null | undefined {\n if (since == null || since.trim() === \"\") return undefined;\n const m = since.trim().match(/^(\\d+)\\s*([smhd])$/i);\n if (!m || !m[1] || !m[2]) return null;\n const n = Number(m[1]);\n const unitMs: Record<string, number> = {\n s: 1000,\n m: 60_000,\n h: 3_600_000,\n d: 86_400_000,\n };\n const factor = unitMs[m[2].toLowerCase()];\n if (factor == null) return null;\n return Date.now() - n * factor;\n}\n\nconst GROUP_BY_VALUES: ReadonlySet<string> = new Set([\n \"platform\",\n \"project\",\n \"session\",\n \"model\",\n \"day\",\n]);\n\n/** Build the scan options shared by report/export from --since / --platform. */\nfunction buildScanOpts(\n since: string | undefined,\n platform: string | undefined,\n): { sinceMs?: number; platforms?: PlatformId[] } | null {\n const sinceMs = parseSince(since);\n if (sinceMs === null) return null;\n const opts: { sinceMs?: number; platforms?: PlatformId[] } = {};\n if (sinceMs !== undefined) opts.sinceMs = sinceMs;\n if (platform && platform.trim() !== \"\") opts.platforms = [platform.trim() as PlatformId];\n return opts;\n}\n\nasync function runReport(argv: string[]): Promise<number> {\n const { values } = parseArgs({\n args: argv,\n options: {\n by: { type: \"string\", default: \"platform\" },\n since: { type: \"string\" },\n platform: { type: \"string\" },\n json: { type: \"boolean\", default: false },\n },\n allowPositionals: false,\n });\n\n const by = values.by;\n if (!GROUP_BY_VALUES.has(by ?? \"\")) {\n return fail(`invalid --by \"${by}\" (use platform|project|session|model|day)`);\n }\n const dimension = by as UsageGroupBy;\n\n const scanOpts = buildScanOpts(values.since, values.platform);\n if (scanOpts === null) {\n return fail(`invalid --since \"${values.since}\" (use forms like 30s, 15m, 24h, 7d)`);\n }\n\n const { records, skipped } = await scanUsage(scanOpts);\n const rows = aggregateBy(records, dimension);\n\n if (values.json) {\n print(JSON.stringify({ by: dimension, rows, skipped }, null, 2));\n } else {\n print(formatUsageReport(rows, dimension, skipped));\n }\n return 0;\n}\n\nasync function runExport(argv: string[]): Promise<number> {\n const { values } = parseArgs({\n args: argv,\n options: {\n format: { type: \"string\", default: \"json\" },\n out: { type: \"string\" },\n since: { type: \"string\" },\n platform: { type: \"string\" },\n },\n allowPositionals: false,\n });\n\n const format = values.format;\n if (format !== \"csv\" && format !== \"json\") {\n return fail(`invalid --format \"${format}\" (use csv|json)`);\n }\n\n const scanOpts = buildScanOpts(values.since, values.platform);\n if (scanOpts === null) {\n return fail(`invalid --since \"${values.since}\" (use forms like 30s, 15m, 24h, 7d)`);\n }\n\n const { records } = await scanUsage(scanOpts);\n const serialized = format === \"csv\" ? usageToCSV(records) : usageToJSON(records);\n\n if (values.out && values.out.trim() !== \"\") {\n writeFileSync(values.out, serialized, \"utf8\");\n print(`wrote ${format.toUpperCase()} export → ${values.out}`);\n } else {\n print(serialized);\n }\n return 0;\n}\n\n/**\n * `usage leaderboard` — the HOST / USER leaderboard: rank host usage by platform\n * (--by platform, the default \"which CLI/host spent the most\") or by model\n * (--by model). Honors --since / --platform; notes synced/host-estimated rows.\n */\nasync function runLeaderboard(argv: string[]): Promise<number> {\n const { values } = parseArgs({\n args: argv,\n options: {\n by: { type: \"string\", default: \"platform\" },\n since: { type: \"string\" },\n platform: { type: \"string\" },\n json: { type: \"boolean\", default: false },\n },\n allowPositionals: false,\n });\n\n const by = values.by;\n if (by !== \"platform\" && by !== \"model\") {\n return fail(`invalid --by \"${by}\" (use platform|model)`);\n }\n\n const scanOpts = buildScanOpts(values.since, values.platform);\n if (scanOpts === null) {\n return fail(`invalid --since \"${values.since}\" (use forms like 30s, 15m, 24h, 7d)`);\n }\n\n const lbOpts: { by: \"platform\" | \"model\"; sinceMs?: number; platforms?: PlatformId[] } = {\n by,\n };\n if (scanOpts.sinceMs !== undefined) lbOpts.sinceMs = scanOpts.sinceMs;\n if (scanOpts.platforms !== undefined) lbOpts.platforms = scanOpts.platforms;\n\n const result = await hostLeaderboard(lbOpts);\n\n if (values.json) {\n print(JSON.stringify({ by: result.by, rows: result.rows, skipped: result.skipped }, null, 2));\n } else {\n print(formatHostLeaderboard(result));\n }\n return 0;\n}\n\nexport async function run(argv: string[]): Promise<number> {\n const sub = argv[0];\n const rest = argv.slice(1);\n\n switch (sub) {\n case \"report\":\n return runReport(rest);\n case \"export\":\n return runExport(rest);\n case \"leaderboard\":\n return runLeaderboard(rest);\n case undefined:\n case \"--help\":\n case \"-h\":\n print(\"usage: agent-connector usage <report|export|leaderboard> [flags]\");\n print(\" report --by platform|project|session|model|day --since 7d --platform <id> --json\");\n print(\" export --format csv|json --out <file> --since 7d --platform <id>\");\n print(\" leaderboard --by platform|model --since 7d --platform <id> --json\");\n return sub === undefined ? 1 : 0;\n default:\n return fail(`unknown usage subcommand \"${sub}\" (use report|export|leaderboard)`);\n }\n}\n","/**\n * usage/report — CLI-facing formatting for host usage rollups and exports.\n *\n * Pure functions, mirroring telemetry/report.ts: an aligned text table with a\n * TOTAL footer and an honesty legend, plus CSV/JSON serializers for raw records.\n * Confidence is surfaced verbatim so a host-estimated row is never read as exact\n * host-reported usage; a footer note also explains synced-but-uncached platforms.\n */\n\nimport type {\n UsageGroupBy,\n UsageRecord,\n UsageSummary,\n} from \"./types.js\";\nimport type { SkippedPlatform } from \"./scan.js\";\nimport { sumTokens } from \"./aggregate.js\";\n\n/** Human label for the leading KEY column, per grouping dimension. */\nconst KEY_HEADER: Record<UsageGroupBy, string> = {\n platform: \"PLATFORM\",\n project: \"PROJECT\",\n session: \"SESSION\",\n model: \"MODEL\",\n day: \"DAY\",\n};\n\n/** Compact integer formatting with thousands separators. */\nfunction fmtInt(n: number): string {\n return n.toLocaleString(\"en-US\");\n}\n\n/** Right-pad (left-aligned columns). */\nfunction padRight(s: string, width: number): string {\n return s.length >= width ? s : s + \" \".repeat(width - s.length);\n}\n\n/** Left-pad (right-aligned numeric columns). */\nfunction padLeft(s: string, width: number): string {\n return s.length >= width ? s : \" \".repeat(width - s.length) + s;\n}\n\n/**\n * Render an aligned table of usage rows (already aggregated). Columns:\n * KEY | IN | OUT | CACHE_R | CACHE_W | REASON | TOTAL | SESS | CONF\n * with a TOTAL footer (worst confidence across rows) and an honesty legend.\n * Optionally appends notes for platforms the scan skipped.\n */\nexport function formatUsageReport(\n rows: UsageSummary[],\n by: UsageGroupBy,\n skipped: SkippedPlatform[] = [],\n): string {\n const keyHeader = KEY_HEADER[by];\n const headers = [\n keyHeader,\n \"IN\",\n \"OUT\",\n \"CACHE_R\",\n \"CACHE_W\",\n \"REASON\",\n \"TOTAL\",\n \"SESS\",\n \"CONF\",\n ];\n\n const sorted = [...rows].sort((a, b) => b.total - a.total || b.lastTs - a.lastTs);\n\n const dataRows = sorted.map((r) => [\n r.key,\n fmtInt(r.tokens.input),\n fmtInt(r.tokens.output),\n fmtInt(r.tokens.cacheRead),\n fmtInt(r.tokens.cacheWrite),\n fmtInt(r.tokens.reasoning),\n fmtInt(r.total),\n fmtInt(r.sessions),\n r.confidence,\n ]);\n\n // Totals + worst confidence across all rows.\n const totals = sorted.reduce(\n (acc, r) => {\n acc.input += r.tokens.input;\n acc.output += r.tokens.output;\n acc.cacheRead += r.tokens.cacheRead;\n acc.cacheWrite += r.tokens.cacheWrite;\n acc.reasoning += r.tokens.reasoning;\n acc.total += r.total;\n acc.sessions += r.sessions;\n return acc;\n },\n { input: 0, output: 0, cacheRead: 0, cacheWrite: 0, reasoning: 0, total: 0, sessions: 0 },\n );\n const totalRow = [\n \"TOTAL\",\n fmtInt(totals.input),\n fmtInt(totals.output),\n fmtInt(totals.cacheRead),\n fmtInt(totals.cacheWrite),\n fmtInt(totals.reasoning),\n fmtInt(totals.total),\n fmtInt(totals.sessions),\n \"\",\n ];\n\n const widths = headers.map((h, col) => {\n let w = h.length;\n for (const row of dataRows) w = Math.max(w, (row[col] ?? \"\").length);\n w = Math.max(w, (totalRow[col] ?? \"\").length);\n return w;\n });\n\n const renderRow = (cells: string[]): string =>\n cells\n .map((c, col) => (col === 0 ? padRight(c, widths[col] ?? 0) : padLeft(c, widths[col] ?? 0)))\n .join(\" \")\n .trimEnd();\n\n const ruleWidth = widths.reduce((a, b) => a + b, 0) + 2 * (widths.length - 1);\n const rule = \"-\".repeat(ruleWidth);\n\n const lines: string[] = [];\n lines.push(renderRow(headers));\n lines.push(rule);\n if (dataRows.length === 0) {\n lines.push(\"(no host usage found)\");\n } else {\n for (const row of dataRows) lines.push(renderRow(row));\n }\n lines.push(rule);\n lines.push(renderRow(totalRow));\n\n // Honesty legend — estimated rows and skipped synced platforms.\n const hasEstimate = sorted.some((r) => r.confidence === \"host-estimated\");\n if (hasEstimate) {\n lines.push(\"\");\n lines.push(\n \"note: host-estimated rows are derived (e.g. char/4 or cost-only), \" +\n \"not exact host-reported token counts.\",\n );\n }\n if (skipped.length > 0) {\n lines.push(\"\");\n lines.push(\"skipped:\");\n for (const s of skipped) lines.push(` - ${s.platformId}: ${s.reason}`);\n }\n\n return lines.join(\"\\n\");\n}\n\n// ─────────────────────────────────────────────────────────────────────────\n// Exports (raw deduped records)\n// ─────────────────────────────────────────────────────────────────────────\n\n/** Ordered CSV columns (flattening the token breakdown into separate fields). */\nconst CSV_COLUMNS = [\n \"platformId\",\n \"modelId\",\n \"providerId\",\n \"sessionId\",\n \"projectKey\",\n \"projectLabel\",\n \"input\",\n \"output\",\n \"cacheRead\",\n \"cacheWrite\",\n \"reasoning\",\n \"total\",\n \"cost\",\n \"ts\",\n \"messageCount\",\n \"confidence\",\n \"agent\",\n] as const;\n\n/** RFC-4180-ish escaping: quote a cell holding a comma, quote, or newline. */\nfunction csvCell(value: unknown): string {\n if (value === undefined || value === null) return \"\";\n const s = String(value);\n if (/[\",\\n\\r]/.test(s)) return `\"${s.replace(/\"/g, '\"\"')}\"`;\n return s;\n}\n\n/** Flatten one record into the CSV column order. */\nfunction recordRow(r: UsageRecord): unknown[] {\n return [\n r.platformId,\n r.modelId,\n r.providerId,\n r.sessionId,\n r.projectKey,\n r.projectLabel,\n r.tokens.input,\n r.tokens.output,\n r.tokens.cacheRead,\n r.tokens.cacheWrite,\n r.tokens.reasoning,\n sumTokens(r.tokens),\n r.cost,\n r.ts,\n r.messageCount,\n r.confidence,\n r.agent,\n ];\n}\n\n/** Serialize raw records to CSV (header + one CRLF-terminated line per record). */\nexport function usageToCSV(records: UsageRecord[]): string {\n const lines: string[] = [];\n lines.push(CSV_COLUMNS.join(\",\"));\n for (const r of records) {\n lines.push(recordRow(r).map(csvCell).join(\",\"));\n }\n return lines.join(\"\\r\\n\");\n}\n\n/** Serialize raw records to a pretty-printed JSON array string. */\nexport function usageToJSON(records: UsageRecord[]): string {\n return JSON.stringify(records, null, 2);\n}\n"],"mappings":"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","names":[]}
@@ -0,0 +1,48 @@
1
+ #!/usr/bin/env node
2
+ import {
3
+ runUsageEvent
4
+ } from "./chunk-YNZU6PAV.js";
5
+ import "./chunk-BCHWFTV4.js";
6
+ import "./chunk-KHO5WNTP.js";
7
+ import "./chunk-WCETQWWK.js";
8
+ import "./chunk-XUCWLJY5.js";
9
+ import "./chunk-LTT56GI3.js";
10
+ import "./chunk-XNAM7F35.js";
11
+ import "./chunk-MEH7GC7R.js";
12
+ import "./chunk-TRQKHP7D.js";
13
+
14
+ // src/cli/commands/usage-event.ts
15
+ import { parseArgs } from "util";
16
+ async function readAll(stream) {
17
+ const chunks = [];
18
+ for await (const chunk of stream) {
19
+ chunks.push(typeof chunk === "string" ? Buffer.from(chunk) : chunk);
20
+ }
21
+ return Buffer.concat(chunks).toString("utf8");
22
+ }
23
+ async function run(argv) {
24
+ let platformId = "";
25
+ let connectorId = "";
26
+ try {
27
+ const { values, positionals } = parseArgs({
28
+ args: argv,
29
+ options: { connector: { type: "string" } },
30
+ allowPositionals: true,
31
+ strict: false
32
+ });
33
+ platformId = positionals[0] ?? "";
34
+ connectorId = typeof values.connector === "string" ? values.connector : "";
35
+ } catch {
36
+ return 0;
37
+ }
38
+ const stdin = await readAll(process.stdin).catch(() => "");
39
+ if (platformId === "" || connectorId === "") {
40
+ return 0;
41
+ }
42
+ const result = await runUsageEvent({ platformId, connectorId, stdin });
43
+ return result.exitCode;
44
+ }
45
+ export {
46
+ run
47
+ };
48
+ //# sourceMappingURL=usage-event-JKBI6XCF.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/cli/commands/usage-event.ts"],"sourcesContent":["/**\n * cli/commands/usage-event — the HIDDEN host-native turn-usage entrypoint (4a).\n *\n * agent-connector usage-event <platform> --connector <id>\n *\n * An OPT-IN AfterModel / PostInvocation hook (installed by the Gemini / Antigravity\n * adapters only when host-native usage is enabled) points here. It reads the ENTIRE\n * host payload from stdin, hands it to {@link runUsageEvent}, and ALWAYS exits 0 —\n * a host-native usage hook must never block a model turn. Hidden (not in the help\n * text) and intentionally a peer of `hook` so it mirrors the same plumbing.\n *\n * Fail-open is the contract: runUsageEvent never throws; on any parse/store error\n * it records nothing and we still exit 0.\n */\n\nimport { parseArgs } from \"node:util\";\n\nimport { runUsageEvent } from \"../../runtime/index.js\";\n\n/** Read all of a readable stream to a UTF-8 string. */\nasync function readAll(stream: NodeJS.ReadStream): Promise<string> {\n const chunks: Buffer[] = [];\n for await (const chunk of stream) {\n chunks.push(typeof chunk === \"string\" ? Buffer.from(chunk) : chunk);\n }\n return Buffer.concat(chunks).toString(\"utf8\");\n}\n\nexport async function run(argv: string[]): Promise<number> {\n // strict:false so a future flag from a newer install can never make this throw\n // and surface a non-zero exit into the host's model turn.\n let platformId = \"\";\n let connectorId = \"\";\n try {\n const { values, positionals } = parseArgs({\n args: argv,\n options: { connector: { type: \"string\" } },\n allowPositionals: true,\n strict: false,\n });\n platformId = positionals[0] ?? \"\";\n connectorId = typeof values.connector === \"string\" ? values.connector : \"\";\n } catch {\n // A malformed invocation must still fail-open (record nothing, exit 0).\n return 0;\n }\n\n // Drain stdin regardless — a host expects the hook command to consume its\n // payload. A missing platform/connector simply records nothing.\n const stdin = await readAll(process.stdin).catch(() => \"\");\n\n if (platformId === \"\" || connectorId === \"\") {\n return 0;\n }\n\n const result = await runUsageEvent({ platformId, connectorId, stdin });\n return result.exitCode;\n}\n"],"mappings":";;;;;;;;;;;;;;AAeA,SAAS,iBAAiB;AAK1B,eAAe,QAAQ,QAA4C;AACjE,QAAM,SAAmB,CAAC;AAC1B,mBAAiB,SAAS,QAAQ;AAChC,WAAO,KAAK,OAAO,UAAU,WAAW,OAAO,KAAK,KAAK,IAAI,KAAK;AAAA,EACpE;AACA,SAAO,OAAO,OAAO,MAAM,EAAE,SAAS,MAAM;AAC9C;AAEA,eAAsB,IAAI,MAAiC;AAGzD,MAAI,aAAa;AACjB,MAAI,cAAc;AAClB,MAAI;AACF,UAAM,EAAE,QAAQ,YAAY,IAAI,UAAU;AAAA,MACxC,MAAM;AAAA,MACN,SAAS,EAAE,WAAW,EAAE,MAAM,SAAS,EAAE;AAAA,MACzC,kBAAkB;AAAA,MAClB,QAAQ;AAAA,IACV,CAAC;AACD,iBAAa,YAAY,CAAC,KAAK;AAC/B,kBAAc,OAAO,OAAO,cAAc,WAAW,OAAO,YAAY;AAAA,EAC1E,QAAQ;AAEN,WAAO;AAAA,EACT;AAIA,QAAM,QAAQ,MAAM,QAAQ,QAAQ,KAAK,EAAE,MAAM,MAAM,EAAE;AAEzD,MAAI,eAAe,MAAM,gBAAgB,IAAI;AAC3C,WAAO;AAAA,EACT;AAEA,QAAM,SAAS,MAAM,cAAc,EAAE,YAAY,aAAa,MAAM,CAAC;AACrE,SAAO,OAAO;AAChB;","names":[]}