ccc-notifier 0.7.0 → 0.9.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.
- package/README.md +1 -1
- package/dist/{budget-O4VAP6RB.js → budget-KLRUKU6V.js} +1 -1
- package/dist/{chunk-JLDI4D5E.js → chunk-2XOKH54N.js} +1 -1
- package/dist/{chunk-O2E4VTDR.js → chunk-6GWPAYJQ.js} +161 -63
- package/dist/{chunk-OCKZZVOG.js → chunk-GAOGTALW.js} +9 -1
- package/dist/{chunk-XG73C6CC.js → chunk-OHTPBABH.js} +5 -2
- package/dist/{chunk-6BXD6HU5.js → chunk-SKX5EMST.js} +52 -10
- package/dist/{chunk-X7U63BZG.js → chunk-XT3KWNWI.js} +1 -1
- package/dist/{chunk-V4IS4FXH.js → chunk-XXXGWLTS.js} +33 -8
- package/dist/cli.js +14 -14
- package/dist/{dashboard-64XHDUVT.js → dashboard-GR3OMZW5.js} +2 -2
- package/dist/{reset-cursors-5CCM6MQL.js → reset-cursors-UVQXFN5Y.js} +3 -0
- package/dist/{scan-UB6ORRZK.js → scan-YIU6CG3E.js} +14 -7
- package/dist/{setup-VLMW433R.js → setup-H52OFFBQ.js} +3 -3
- package/dist/{sweep-DVOV4XIZ.js → sweep-2GHO4U5C.js} +6 -4
- package/dist/{track-P6A5WDJZ.js → track-GTQOULBP.js} +6 -6
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -19,7 +19,7 @@ in 1.2k(cache 40%) / out 480 · 📁 my-app · 今日: $1.85
|
|
|
19
19
|
|
|
20
20
|
- Claude Codeの応答完了ごとに、USD・JPYの概算をOS通知またはSlackへ送ります
|
|
21
21
|
- プロンプトと概算をローカルへ保存し、あとから検索・集計できます
|
|
22
|
-
- 日・週・月の推移やモデル別・プロジェクト別の内訳をHTML
|
|
22
|
+
- 日・週・月の推移やモデル別・プロジェクト別の内訳をHTMLダッシュボードで確認できます。金額とあわせて**トークン使用量**も表示し、推移チャートは金額/トークンの軸切替つきです
|
|
23
23
|
- 月予算を設定し、今月の使用率を確認できます
|
|
24
24
|
- 通知を一時停止しても、履歴の記録は続けられます
|
|
25
25
|
- Codex CLIも任意で追加し、Claude Codeと同じダッシュボードで確認できます
|
|
@@ -18,7 +18,7 @@ import {
|
|
|
18
18
|
formatTokens,
|
|
19
19
|
formatUSD,
|
|
20
20
|
modelDisplayName
|
|
21
|
-
} from "./chunk-
|
|
21
|
+
} from "./chunk-OHTPBABH.js";
|
|
22
22
|
import {
|
|
23
23
|
paths,
|
|
24
24
|
readConfig,
|
|
@@ -217,7 +217,20 @@ function turnBySlot(rec, map) {
|
|
|
217
217
|
return bs;
|
|
218
218
|
}
|
|
219
219
|
function emptyTotals() {
|
|
220
|
-
return { usd: 0, jpy: 0, turns: 0 };
|
|
220
|
+
return { usd: 0, jpy: 0, turns: 0, tin: 0, tout: 0, tcache: 0 };
|
|
221
|
+
}
|
|
222
|
+
function turnTokenTotals(rec) {
|
|
223
|
+
let tin = 0;
|
|
224
|
+
let tout = 0;
|
|
225
|
+
let tcache = 0;
|
|
226
|
+
for (const b of [rec.tokens, rec.sidechainTokens, rec.subagents?.tokens]) {
|
|
227
|
+
if (!b) continue;
|
|
228
|
+
const cache = b.cacheRead + b.cacheWrite5m + b.cacheWrite1h;
|
|
229
|
+
tin += b.input + cache;
|
|
230
|
+
tcache += cache;
|
|
231
|
+
tout += b.output;
|
|
232
|
+
}
|
|
233
|
+
return { tin, tout, tcache };
|
|
221
234
|
}
|
|
222
235
|
function buildTurnEmbed(rec, map) {
|
|
223
236
|
const raw = String(rec.prompt ?? "");
|
|
@@ -225,7 +238,7 @@ function buildTurnEmbed(rec, map) {
|
|
|
225
238
|
const primary = rec.models[0] ?? "unknown";
|
|
226
239
|
const extra = rec.models.length > 1 ? ` +${rec.models.length - 1}` : "";
|
|
227
240
|
const saMark = rec.subagents ? " +SA" : "";
|
|
228
|
-
const codexActivityMark = rec.source === "codex" && rec.subagentActivity ? " +SA(\
|
|
241
|
+
const codexActivityMark = rec.source === "codex" && rec.subagentActivity ? " +SA(\u691C\u51FA)" : "";
|
|
229
242
|
let sa = null;
|
|
230
243
|
if (rec.subagents) {
|
|
231
244
|
const saModels = Object.keys(rec.subagents.costByModel).map((m) => modelDisplayName(m));
|
|
@@ -235,6 +248,12 @@ function buildTurnEmbed(rec, map) {
|
|
|
235
248
|
models: saModels.join(", "),
|
|
236
249
|
apiCalls: rec.subagents.apiCalls
|
|
237
250
|
};
|
|
251
|
+
const b = rec.subagents.tokens;
|
|
252
|
+
const cache = b.cacheRead + b.cacheWrite5m + b.cacheWrite1h;
|
|
253
|
+
const total = b.input + b.output + cache;
|
|
254
|
+
if (total > 0) {
|
|
255
|
+
sa.tok = `\u8A08 ${formatTokens(total)} tokens(cache ${Math.round(cache / total * 100)}%)`;
|
|
256
|
+
}
|
|
238
257
|
}
|
|
239
258
|
const ms = Date.parse(rec.ts);
|
|
240
259
|
const out = {
|
|
@@ -252,7 +271,11 @@ function buildTurnEmbed(rec, map) {
|
|
|
252
271
|
bs: turnBySlot(rec, map),
|
|
253
272
|
pr: text,
|
|
254
273
|
tr: truncated,
|
|
255
|
-
sa
|
|
274
|
+
sa,
|
|
275
|
+
tk: (() => {
|
|
276
|
+
const t = turnTokenTotals(rec);
|
|
277
|
+
return [t.tin, t.tout, t.tcache];
|
|
278
|
+
})()
|
|
256
279
|
};
|
|
257
280
|
if (rec.source === "codex") out.sc = "codex";
|
|
258
281
|
if (rec.source === "codex" && rec.subagentActivity) {
|
|
@@ -275,28 +298,29 @@ function computeKpis(turns) {
|
|
|
275
298
|
const week = emptyTotals();
|
|
276
299
|
const month = emptyTotals();
|
|
277
300
|
const all = emptyTotals();
|
|
301
|
+
const add = (t, usd, jpy, tk) => {
|
|
302
|
+
t.usd += usd;
|
|
303
|
+
t.jpy += jpy;
|
|
304
|
+
t.turns += 1;
|
|
305
|
+
t.tin += tk.tin;
|
|
306
|
+
t.tout += tk.tout;
|
|
307
|
+
t.tcache += tk.tcache;
|
|
308
|
+
};
|
|
278
309
|
for (const rec of turns) {
|
|
279
310
|
const usd = turnTotalUSD(rec);
|
|
280
311
|
const jpy = turnTotalJPY(rec);
|
|
281
|
-
|
|
282
|
-
all
|
|
283
|
-
all.turns += 1;
|
|
312
|
+
const tk = turnTokenTotals(rec);
|
|
313
|
+
add(all, usd, jpy, tk);
|
|
284
314
|
const dt = new Date(rec.ts);
|
|
285
315
|
if (Number.isNaN(dt.getTime())) continue;
|
|
286
316
|
if (dt.getFullYear() === y && dt.getMonth() === mo && dt.getDate() === d) {
|
|
287
|
-
today
|
|
288
|
-
today.jpy += jpy;
|
|
289
|
-
today.turns += 1;
|
|
317
|
+
add(today, usd, jpy, tk);
|
|
290
318
|
}
|
|
291
319
|
if (dt.getTime() >= weekCutoff) {
|
|
292
|
-
week
|
|
293
|
-
week.jpy += jpy;
|
|
294
|
-
week.turns += 1;
|
|
320
|
+
add(week, usd, jpy, tk);
|
|
295
321
|
}
|
|
296
322
|
if (dt.getFullYear() === y && dt.getMonth() === mo) {
|
|
297
|
-
month
|
|
298
|
-
month.jpy += jpy;
|
|
299
|
-
month.turns += 1;
|
|
323
|
+
add(month, usd, jpy, tk);
|
|
300
324
|
}
|
|
301
325
|
}
|
|
302
326
|
return { today, week, month, all };
|
|
@@ -354,9 +378,11 @@ section.card > .note{color:var(--muted); font-size:12px; margin:0 0 14px;}
|
|
|
354
378
|
.sel-label b{color:var(--ink); font-weight:640;}
|
|
355
379
|
|
|
356
380
|
.legend{display:flex; flex-wrap:wrap; gap:8px 18px; margin:2px 0 14px;}
|
|
381
|
+
.legend[hidden]{display:none;}
|
|
357
382
|
.legend-item{display:inline-flex; align-items:center; gap:7px; font-size:13px; color:var(--ink2);}
|
|
358
383
|
.swatch{display:inline-block; width:11px; height:11px; border-radius:3px; flex:0 0 auto;}
|
|
359
384
|
.k1{background:var(--s1);} .k2{background:var(--s2);} .k3{background:var(--s3);} .k4{background:var(--s4);}
|
|
385
|
+
.ktin{background:var(--s1);} .ktcache{background:var(--sother);} .ktout{background:var(--s3);}
|
|
360
386
|
.k5{background:var(--s5);} .k6{background:var(--s6);} .k7{background:var(--s7);} .k8{background:var(--s8);} .kother{background:var(--sother);}
|
|
361
387
|
|
|
362
388
|
.budget-bar{height:12px; background:var(--plane); border:1px solid var(--border); border-radius:7px; overflow:hidden; margin:12px 0;}
|
|
@@ -374,6 +400,7 @@ section.card > .note{color:var(--muted); font-size:12px; margin:0 0 14px;}
|
|
|
374
400
|
.chart-scroll{overflow-x:auto;}
|
|
375
401
|
.seg.s1{fill:var(--s1);} .seg.s2{fill:var(--s2);} .seg.s3{fill:var(--s3);} .seg.s4{fill:var(--s4);}
|
|
376
402
|
.seg.s5{fill:var(--s5);} .seg.s6{fill:var(--s6);} .seg.s7{fill:var(--s7);} .seg.s8{fill:var(--s8);} .seg.sother{fill:var(--sother);}
|
|
403
|
+
.seg.tin{fill:var(--s1);} .seg.tcache{fill:var(--sother);} .seg.tout{fill:var(--s3);}
|
|
377
404
|
.seg.dim{opacity:0.28;}
|
|
378
405
|
.grid-line{stroke:var(--grid); stroke-width:1;}
|
|
379
406
|
.axis-line{stroke:var(--axis); stroke-width:1;}
|
|
@@ -463,6 +490,13 @@ var APP_JS = `<script>
|
|
|
463
490
|
if(v >= 1) return '\xA5' + Math.round(v).toLocaleString('en-US');
|
|
464
491
|
return '\xA5' + (Math.round(v * 10) / 10);
|
|
465
492
|
}
|
|
493
|
+
function formatTok(n){
|
|
494
|
+
var v = n || 0;
|
|
495
|
+
if(v < 1000) return String(v);
|
|
496
|
+
if(v < 1e6) return (v / 1000).toFixed(1) + 'k';
|
|
497
|
+
if(v < 1e9) return (v / 1e6).toFixed(1) + 'M';
|
|
498
|
+
return (v / 1e9).toFixed(1) + 'B';
|
|
499
|
+
}
|
|
466
500
|
|
|
467
501
|
// ---- \u65E5\u4ED8/\u30D0\u30B1\u30C3\u30C8(\u30ED\u30FC\u30AB\u30EBTZ)----
|
|
468
502
|
function pad(n){ return (n < 10 ? '0' : '') + n; }
|
|
@@ -500,6 +534,9 @@ var APP_JS = `<script>
|
|
|
500
534
|
// \u65E2\u5B9A 'all'\u3002sessionStorage \u306B\u4FDD\u5B58\u3057\u81EA\u52D5\u30EA\u30ED\u30FC\u30C9(meta refresh)\u3092\u8DE8\u3044\u3067\u7DAD\u6301\u3059\u308B(cccn-gran \u3068\u540C\u3058\u4ED5\u7D44\u307F)\u3002
|
|
501
535
|
var HAS_CODEX = document.querySelectorAll('[data-src]').length > 0;
|
|
502
536
|
var SRC = ssGet('cccn-src'); if(['all','claude','codex'].indexOf(SRC) < 0) SRC = 'all';
|
|
537
|
+
// \u30C1\u30E3\u30FC\u30C8\u306E\u7E26\u8EF8\u30E1\u30C8\u30EA\u30AF\u30B9(\u91D1\u984D / \u30C8\u30FC\u30AF\u30F3)\u3002\u4ED6\u306E\u8868\u793A(KPI\u30FB\u5185\u8A33\u30FB\u5C65\u6B74)\u306F\u5E38\u306B\u91D1\u984D\u304C\u4E3B\u5F79\u306E\u307E\u307E\u3002
|
|
538
|
+
var MET = ssGet('cccn-metric'); if(['usd','tok'].indexOf(MET) < 0) MET = 'usd';
|
|
539
|
+
function setMet(m){ MET = m; ssSet('cccn-metric', m); }
|
|
503
540
|
// \u8FF0\u8A9E: claude \u2192 sc \u306A\u3057 / codex \u2192 sc==='codex' / all \u2192 \u5168\u4EF6\u3002Codex \u7121\u3057(\u30C1\u30C3\u30D7\u7121\u3057)\u306A\u3089\u5E38\u306B\u5168\u4EF6\u3002
|
|
504
541
|
function activeTurns(){
|
|
505
542
|
if(!HAS_CODEX || SRC === 'all') return turns;
|
|
@@ -536,10 +573,13 @@ var APP_JS = `<script>
|
|
|
536
573
|
var k = bucketKey(tn.t, gran);
|
|
537
574
|
if(k === null) continue;
|
|
538
575
|
var b = map[k];
|
|
539
|
-
if(!b){ b = map[k] = { key:k, total:0, turns:0, bs:{} }; keys.push(k); }
|
|
576
|
+
if(!b){ b = map[k] = { key:k, total:0, turns:0, bs:{}, tin:0, tout:0, tcache:0, tokTotal:0 }; keys.push(k); }
|
|
540
577
|
b.turns++;
|
|
541
578
|
var bs = tn.bs || {};
|
|
542
579
|
for(var s in bs){ if(bs.hasOwnProperty(s)){ b.bs[s] = (b.bs[s]||0) + bs[s]; b.total += bs[s]; } }
|
|
580
|
+
var tk = tn.tk || [0,0,0];
|
|
581
|
+
b.tin += tk[0]; b.tout += tk[1]; b.tcache += tk[2];
|
|
582
|
+
b.tokTotal += tk[0] + tk[1];
|
|
543
583
|
}
|
|
544
584
|
keys.sort();
|
|
545
585
|
return keys.map(function(k){ return map[k]; });
|
|
@@ -608,8 +648,9 @@ var APP_JS = `<script>
|
|
|
608
648
|
var plotW = band * n;
|
|
609
649
|
var W = ml + plotW + mr;
|
|
610
650
|
|
|
651
|
+
var tokMode = MET === 'tok';
|
|
611
652
|
var maxTotal = 0;
|
|
612
|
-
buckets.forEach(function(b){
|
|
653
|
+
buckets.forEach(function(b){ var v = tokMode ? b.tokTotal : b.total; if(v > maxTotal) maxTotal = v; });
|
|
613
654
|
var niceMax = niceCeil(maxTotal);
|
|
614
655
|
var yscale = plotH / niceMax;
|
|
615
656
|
// \u9078\u629E\u4E2D\u30D0\u30B1\u30C3\u30C8\u304C\u73FE\u5728\u306E\u7C92\u5EA6\u306B\u5B58\u5728\u3059\u308B\u3068\u304D\u3060\u3051\u4ED6\u3092\u6DE1\u8272\u5316\u3059\u308B(\u30C7\u30FC\u30BF\u7121\u3057\u306E\u65E5\u3092\u9078\u3076\u3068
|
|
@@ -618,7 +659,7 @@ var APP_JS = `<script>
|
|
|
618
659
|
for(var sp=0; sp<buckets.length; sp++){ if(buckets[sp].key === SEL){ selPresent = true; break; } }
|
|
619
660
|
|
|
620
661
|
var svg = svgEl('svg', { 'class':'chart', viewBox:'0 0 ' + W + ' ' + H, role:'img',
|
|
621
|
-
'aria-label':'\u30B3\u30B9\u30C8\u7A4D\u307F\u4E0A\u3052\u68D2\u30B0\u30E9\u30D5', preserveAspectRatio:'xMidYMid meet' });
|
|
662
|
+
'aria-label':(tokMode ? '\u30C8\u30FC\u30AF\u30F3\u7A4D\u307F\u4E0A\u3052\u68D2\u30B0\u30E9\u30D5' : '\u30B3\u30B9\u30C8\u7A4D\u307F\u4E0A\u3052\u68D2\u30B0\u30E9\u30D5'), preserveAspectRatio:'xMidYMid meet' });
|
|
622
663
|
svg.setAttribute('width', String(W));
|
|
623
664
|
svg.setAttribute('height', String(H));
|
|
624
665
|
|
|
@@ -628,7 +669,7 @@ var APP_JS = `<script>
|
|
|
628
669
|
var yy = f2(baseY - val * yscale);
|
|
629
670
|
svg.appendChild(svgEl('line', { 'class':'grid-line', x1:ml, y1:yy, x2:W-mr, y2:yy }));
|
|
630
671
|
var lbl = svgEl('text', { 'class':'tick-label', x:ml-8, y:yy+4, 'text-anchor':'end' });
|
|
631
|
-
lbl.textContent = formatUSD(val);
|
|
672
|
+
lbl.textContent = tokMode ? formatTok(val) : formatUSD(val);
|
|
632
673
|
svg.appendChild(lbl);
|
|
633
674
|
}
|
|
634
675
|
|
|
@@ -641,9 +682,16 @@ var APP_JS = `<script>
|
|
|
641
682
|
var x = cx - barW/2;
|
|
642
683
|
var dim = (SEL !== null && selPresent && b.key !== SEL);
|
|
643
684
|
var cumV = 0;
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
685
|
+
var segList;
|
|
686
|
+
if(tokMode){
|
|
687
|
+
segList = [ ['tcache', b.tcache], ['tin', b.tin - b.tcache], ['tout', b.tout] ];
|
|
688
|
+
} else {
|
|
689
|
+
segList = [];
|
|
690
|
+
for(var j0=0;j0<slotOrder.length;j0++){ segList.push(['s'+slotOrder[j0], b.bs[slotOrder[j0]] || 0]); }
|
|
691
|
+
}
|
|
692
|
+
for(var j=0;j<segList.length;j++){
|
|
693
|
+
var segCls = segList[j][0];
|
|
694
|
+
var v = segList[j][1];
|
|
647
695
|
if(v <= 0) continue;
|
|
648
696
|
var vTop = cumV + v;
|
|
649
697
|
var yTop = baseY - vTop * yscale;
|
|
@@ -652,10 +700,11 @@ var APP_JS = `<script>
|
|
|
652
700
|
cumV = vTop;
|
|
653
701
|
var h = yBot - yTop;
|
|
654
702
|
if(h <= 0.4) continue;
|
|
655
|
-
var rect = svgEl('rect', { 'class':'seg
|
|
703
|
+
var rect = svgEl('rect', { 'class':'seg '+segCls+(dim?' dim':''), x:f2(x), y:f2(yTop), width:f2(barW), height:f2(h) });
|
|
656
704
|
svg.appendChild(rect);
|
|
657
705
|
}
|
|
658
|
-
|
|
706
|
+
// \u6700\u7D42\u30E9\u30D9\u30EB\u306F\u5E38\u306B\u51FA\u3059\u3002\u9593\u5F15\u304D\u30E9\u30D9\u30EB\u306F\u6700\u7D42\u30E9\u30D9\u30EB\u3068\u96A3\u63A5\u3057\u3066\u91CD\u306A\u3089\u306A\u3044\u4F4D\u7F6E\u3060\u3051\u306B\u51FA\u3059\u3002
|
|
707
|
+
if(i === n-1 || (i % xStep === 0 && (n-1) - i >= xStep)){
|
|
659
708
|
var xl = svgEl('text', { 'class':'tick-label', x:f2(cx), y:baseY+16, 'text-anchor':'middle' });
|
|
660
709
|
xl.textContent = bucketLabel(b.key, GRAN);
|
|
661
710
|
svg.appendChild(xl);
|
|
@@ -692,6 +741,15 @@ var APP_JS = `<script>
|
|
|
692
741
|
lastRenderedGran = GRAN;
|
|
693
742
|
}
|
|
694
743
|
|
|
744
|
+
function tipRow(keyCls, nameText, valText){
|
|
745
|
+
var row = document.createElement('div'); row.className = 'tip-row';
|
|
746
|
+
var key = document.createElement('span'); key.className = 'tip-key ' + keyCls;
|
|
747
|
+
var name = document.createElement('span'); name.className = 'tip-name'; name.textContent = nameText;
|
|
748
|
+
var val = document.createElement('span'); val.className = 'tip-val'; val.textContent = valText;
|
|
749
|
+
row.appendChild(key); row.appendChild(name); row.appendChild(val);
|
|
750
|
+
return row;
|
|
751
|
+
}
|
|
752
|
+
|
|
695
753
|
// hover\u5185\u8A33\u306F\u3001\u9078\u629E\u4E2D\u306E\u65E5/\u9031/\u6708\u306B\u304A\u3051\u308B\u91D1\u984D\u306E\u5927\u304D\u3044\u9806\u306B\u8AAD\u3080\u3002\u7A4D\u307F\u4E0A\u3052\u9806\u30FB\u8272\u306F
|
|
696
754
|
// slotOrder\u306E\u307E\u307E\u56FA\u5B9A\u3057\u3001\u540C\u984D\u3082slotOrder\u3067\u6C7A\u5B9A\u7684\u306B\u4E26\u3079\u308B\u3002
|
|
697
755
|
function tooltipSlotOrder(bucket){
|
|
@@ -708,19 +766,24 @@ var APP_JS = `<script>
|
|
|
708
766
|
if(!tip) return;
|
|
709
767
|
clearNode(tip);
|
|
710
768
|
var h = document.createElement('div'); h.className = 'tip-title';
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
var
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
769
|
+
if(MET === 'tok'){
|
|
770
|
+
h.textContent = periodText(bucket.key, GRAN) + ' \u5408\u8A08 ' + formatTok(bucket.tokTotal) + ' tokens \xB7 ' + bucket.turns + ' \u30BF\u30FC\u30F3';
|
|
771
|
+
tip.appendChild(h);
|
|
772
|
+
var segs = [ ['ktout', '\u51FA\u529B', bucket.tout], ['ktin', '\u5165\u529B(\u30AD\u30E3\u30C3\u30B7\u30E5\u4EE5\u5916)', bucket.tin - bucket.tcache], ['ktcache', '\u30AD\u30E3\u30C3\u30B7\u30E5(read+write)', bucket.tcache] ];
|
|
773
|
+
for(var j2=0;j2<segs.length;j2++){
|
|
774
|
+
if(segs[j2][2] <= 0) continue;
|
|
775
|
+
tip.appendChild(tipRow(segs[j2][0], segs[j2][1], formatTok(segs[j2][2])));
|
|
776
|
+
}
|
|
777
|
+
} else {
|
|
778
|
+
h.textContent = periodText(bucket.key, GRAN) + ' \u5408\u8A08 ' + formatUSD(bucket.total) + ' \xB7 ' + bucket.turns + ' \u30BF\u30FC\u30F3';
|
|
779
|
+
tip.appendChild(h);
|
|
780
|
+
var tipOrder = tooltipSlotOrder(bucket);
|
|
781
|
+
for(var j=0;j<tipOrder.length;j++){
|
|
782
|
+
var slot = tipOrder[j];
|
|
783
|
+
var v = bucket.bs[slot] || 0;
|
|
784
|
+
if(v <= 0) continue;
|
|
785
|
+
tip.appendChild(tipRow('k'+slot, slotName[slot] || slot, formatUSD(v)));
|
|
786
|
+
}
|
|
724
787
|
}
|
|
725
788
|
tip.hidden = false;
|
|
726
789
|
positionTip(evt);
|
|
@@ -740,23 +803,29 @@ var APP_JS = `<script>
|
|
|
740
803
|
function renderByModel(sub){
|
|
741
804
|
if(!modelEl) return;
|
|
742
805
|
clearNode(modelEl);
|
|
743
|
-
var usd = {}, jpy = {}, tcount = {}, total = 0;
|
|
806
|
+
var usd = {}, jpy = {}, tcount = {}, ttok = {}, total = 0;
|
|
744
807
|
sub.forEach(function(tn){
|
|
745
808
|
var bs = tn.bs || {}, fx = tn.fx || 0;
|
|
746
|
-
|
|
809
|
+
var tk = tn.tk || [0,0,0];
|
|
810
|
+
// \u5358\u4FA1\u4E0D\u660E\u30E2\u30C7\u30EB\u30FB\u6599\u91D10\u306Echild\u306F bs \u306E\u5024\u304C 0 \u306E\u307E\u307E\u767B\u5834\u3059\u308B\u3002\u91D1\u984D 0 \u3067\u3082\u53C2\u52A0\u3068\u3057\u3066\u96C6\u8A08\u3057\u3001
|
|
811
|
+
// \u30C8\u30FC\u30AF\u30F3\u3060\u3051\u306E\u5229\u7528\u304C\u30E2\u30C7\u30EB\u5225\u8868\u304B\u3089\u6D88\u3048\u306A\u3044\u3088\u3046\u306B\u3059\u308B(\u8868\u793A\u6761\u4EF6\u5074\u3067 usd \u3082 tok \u3082 0 \u306E\u884C\u3092\u843D\u3068\u3059)\u3002
|
|
812
|
+
for(var s in bs){ if(bs.hasOwnProperty(s)){
|
|
747
813
|
usd[s] = (usd[s]||0) + bs[s]; jpy[s] = (jpy[s]||0) + bs[s]*fx; total += bs[s];
|
|
748
814
|
tcount[s] = (tcount[s]||0) + 1;
|
|
815
|
+
// \u30BF\u30FC\u30F3\u5217\u3068\u540C\u3058\u53C2\u52A0\u30AB\u30A6\u30F3\u30C8\u65B9\u5F0F: \u305D\u306E\u30E2\u30C7\u30EB\u304C\u767B\u5834\u3057\u305F\u30BF\u30FC\u30F3\u306E\u5168\u91CF\u3092\u5404\u30E2\u30C7\u30EB\u3078\u8A08\u4E0A(\u91CD\u8907\u3042\u308A)\u3002
|
|
816
|
+
// \u30EC\u30B3\u30FC\u30C9\u306B\u30E2\u30C7\u30EB\u5225\u30C8\u30FC\u30AF\u30F3\u306F\u7121\u3044\u305F\u3081\u3001\u30BF\u30FC\u30F3\u5185\u306E\u30E2\u30C7\u30EB\u9593\u5206\u5272\u306F\u3057\u306A\u3044\u3002
|
|
817
|
+
ttok[s] = (ttok[s]||0) + tk[0] + tk[1];
|
|
749
818
|
} }
|
|
750
819
|
});
|
|
751
820
|
var table = document.createElement('table'); table.className = 'data-table';
|
|
752
821
|
var thead = document.createElement('thead');
|
|
753
|
-
thead.innerHTML = '<tr><th>\u30E2\u30C7\u30EB / Model</th><th class="c-num">\u30BF\u30FC\u30F3</th><th class="c-num">$</th><th class="c-num">\xA5</th><th class="c-num">\u69CB\u6210\u6BD4</th></tr>';
|
|
822
|
+
thead.innerHTML = '<tr><th>\u30E2\u30C7\u30EB / Model</th><th class="c-num">\u30BF\u30FC\u30F3</th><th class="c-num">$</th><th class="c-num">\xA5</th><th class="c-num">tokens</th><th class="c-num">\u69CB\u6210\u6BD4</th></tr>';
|
|
754
823
|
table.appendChild(thead);
|
|
755
824
|
var tbody = document.createElement('tbody');
|
|
756
825
|
var any = false;
|
|
757
826
|
for(var j=0;j<slotOrder.length;j++){
|
|
758
827
|
var slot = slotOrder[j];
|
|
759
|
-
if(!(usd[slot] > 0)) continue;
|
|
828
|
+
if(!(usd[slot] > 0 || (ttok[slot]||0) > 0)) continue;
|
|
760
829
|
any = true;
|
|
761
830
|
var share = total > 0 ? (usd[slot]/total*100) : 0;
|
|
762
831
|
var tr = document.createElement('tr');
|
|
@@ -766,8 +835,9 @@ var APP_JS = `<script>
|
|
|
766
835
|
var c2 = document.createElement('td'); c2.className = 'c-num'; c2.textContent = String(tcount[slot]||0);
|
|
767
836
|
var c3 = document.createElement('td'); c3.className = 'c-num'; c3.textContent = formatUSD(usd[slot]);
|
|
768
837
|
var c4 = document.createElement('td'); c4.className = 'c-num'; c4.textContent = formatJPY(jpy[slot]);
|
|
838
|
+
var c4t = document.createElement('td'); c4t.className = 'c-num'; c4t.textContent = formatTok(ttok[slot]||0);
|
|
769
839
|
var c5 = document.createElement('td'); c5.className = 'c-num'; c5.textContent = share.toFixed(1) + '%';
|
|
770
|
-
tr.appendChild(c1); tr.appendChild(c2); tr.appendChild(c3); tr.appendChild(c4); tr.appendChild(c5);
|
|
840
|
+
tr.appendChild(c1); tr.appendChild(c2); tr.appendChild(c3); tr.appendChild(c4); tr.appendChild(c4t); tr.appendChild(c5);
|
|
771
841
|
tbody.appendChild(tr);
|
|
772
842
|
}
|
|
773
843
|
table.appendChild(tbody);
|
|
@@ -785,15 +855,16 @@ var APP_JS = `<script>
|
|
|
785
855
|
var bs = tn.bs || {}, fx = tn.fx || 0, total = 0;
|
|
786
856
|
for(var s in bs){ if(bs.hasOwnProperty(s)) total += bs[s]; }
|
|
787
857
|
var name = tn.p || '(unknown)';
|
|
788
|
-
var
|
|
789
|
-
a
|
|
858
|
+
var tk = tn.tk || [0,0,0];
|
|
859
|
+
var a = agg[name] || (agg[name] = { usd:0, jpy:0, turns:0, tok:0 });
|
|
860
|
+
a.usd += total; a.jpy += total*fx; a.turns++; a.tok += tk[0] + tk[1];
|
|
790
861
|
});
|
|
791
|
-
var rows = Object.keys(agg).map(function(name){ var a = agg[name]; return { name:name, usd:a.usd, jpy:a.jpy, turns:a.turns }; });
|
|
862
|
+
var rows = Object.keys(agg).map(function(name){ var a = agg[name]; return { name:name, usd:a.usd, jpy:a.jpy, turns:a.turns, tok:a.tok }; });
|
|
792
863
|
rows.sort(function(a,b){ return b.usd - a.usd || a.name.localeCompare(b.name); });
|
|
793
864
|
if(rows.length === 0){ var p = document.createElement('p'); p.className='empty-hint'; p.textContent='\u3053\u306E\u671F\u9593\u306E\u30C7\u30FC\u30BF\u306F\u3042\u308A\u307E\u305B\u3093'; projEl.appendChild(p); return; }
|
|
794
865
|
var table = document.createElement('table'); table.className = 'data-table';
|
|
795
866
|
var thead = document.createElement('thead');
|
|
796
|
-
thead.innerHTML = '<tr><th>\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8 / Project</th><th class="c-num">\u30BF\u30FC\u30F3</th><th class="c-num">$</th><th class="c-num">\xA5</th></tr>';
|
|
867
|
+
thead.innerHTML = '<tr><th>\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8 / Project</th><th class="c-num">\u30BF\u30FC\u30F3</th><th class="c-num">$</th><th class="c-num">\xA5</th><th class="c-num">tokens</th></tr>';
|
|
797
868
|
table.appendChild(thead);
|
|
798
869
|
var tbody = document.createElement('tbody');
|
|
799
870
|
rows.forEach(function(r){
|
|
@@ -802,7 +873,8 @@ var APP_JS = `<script>
|
|
|
802
873
|
var c2 = document.createElement('td'); c2.className='c-num'; c2.textContent = String(r.turns);
|
|
803
874
|
var c3 = document.createElement('td'); c3.className='c-num'; c3.textContent = formatUSD(r.usd);
|
|
804
875
|
var c4 = document.createElement('td'); c4.className='c-num'; c4.textContent = formatJPY(r.jpy);
|
|
805
|
-
|
|
876
|
+
var c5 = document.createElement('td'); c5.className='c-num'; c5.textContent = formatTok(r.tok);
|
|
877
|
+
tr.appendChild(c1); tr.appendChild(c2); tr.appendChild(c3); tr.appendChild(c4); tr.appendChild(c5);
|
|
806
878
|
tbody.appendChild(tr);
|
|
807
879
|
});
|
|
808
880
|
table.appendChild(tbody);
|
|
@@ -888,14 +960,21 @@ var APP_JS = `<script>
|
|
|
888
960
|
var kpiCards = document.querySelectorAll('.kpi .stat');
|
|
889
961
|
var heroValueEl = document.querySelector('.hero .hero-value');
|
|
890
962
|
var heroMetaEls = document.querySelectorAll('.hero .hero-meta');
|
|
891
|
-
var
|
|
963
|
+
var heroTokEl = document.querySelector('.hero .hero-tok');
|
|
964
|
+
var heroSaEl = document.querySelector('.hero .hero-sa'); // SA \u884C(SA \u3042\u308A\u306E\u3068\u304D\u3060\u3051\u30B5\u30FC\u30D0\u304C\u63CF\u753B)
|
|
892
965
|
var heroSaPrefix = heroSaEl ? ((heroSaEl.textContent || '').split('$')[0]) : '';
|
|
966
|
+
function tokLine(tot){
|
|
967
|
+
var pct = tot.ti > 0 ? Math.round(tot.tc / tot.ti * 100) : 0;
|
|
968
|
+
return 'in ' + formatTok(tot.ti) + '(cache ' + pct + '%)/ out ' + formatTok(tot.to) + ' tokens';
|
|
969
|
+
}
|
|
893
970
|
function setKpiCard(card, tot){
|
|
894
971
|
if(!card) return;
|
|
895
972
|
var v = card.querySelector('.stat-value');
|
|
896
973
|
var m = card.querySelector('.stat-meta');
|
|
974
|
+
var tk = card.querySelector('.stat-tok');
|
|
897
975
|
if(v) v.textContent = formatUSD(tot.usd);
|
|
898
976
|
if(m) m.textContent = formatJPY(tot.jpy) + ' \xB7 ' + tot.turns + ' \u30BF\u30FC\u30F3';
|
|
977
|
+
if(tk) tk.textContent = 'in ' + formatTok(tot.ti) + ' / out ' + formatTok(tot.to);
|
|
899
978
|
}
|
|
900
979
|
function renderKpis(){
|
|
901
980
|
if(!HAS_CODEX) return;
|
|
@@ -903,25 +982,29 @@ var APP_JS = `<script>
|
|
|
903
982
|
var now = new Date();
|
|
904
983
|
var y = now.getFullYear(), mo = now.getMonth(), d = now.getDate();
|
|
905
984
|
var weekCutoff = Date.now() - 7*86400000;
|
|
906
|
-
|
|
985
|
+
function zero(){ return {usd:0,jpy:0,turns:0,ti:0,to:0,tc:0}; }
|
|
986
|
+
var today = zero(), week = zero(), month = zero(), all = zero();
|
|
907
987
|
var saUsd = 0, saJpy = 0;
|
|
988
|
+
function acc(t, u, j, tk){ t.usd+=u; t.jpy+=j; t.turns++; t.ti+=tk[0]; t.to+=tk[1]; t.tc+=tk[2]; }
|
|
908
989
|
for(var i=0;i<src.length;i++){
|
|
909
990
|
var tn = src[i], bs = tn.bs || {}, fx = tn.fx || 0, u = 0;
|
|
910
991
|
for(var s in bs){ if(bs.hasOwnProperty(s)) u += bs[s]; }
|
|
911
992
|
var j = u * fx;
|
|
993
|
+
var tk = tn.tk || [0,0,0];
|
|
912
994
|
if(tn.sa){ var sau = u - (tn.um || 0); saUsd += sau; saJpy += sau * fx; } // SA \u5206 = \u7DCF\u984D \u2212 \u30E1\u30A4\u30F3
|
|
913
|
-
all
|
|
995
|
+
acc(all, u, j, tk);
|
|
914
996
|
var dt = new Date(tn.t);
|
|
915
997
|
if(isNaN(dt.getTime())) continue;
|
|
916
|
-
if(dt.getFullYear()===y && dt.getMonth()===mo && dt.getDate()===d){ today
|
|
917
|
-
if(tn.t >= weekCutoff){ week
|
|
918
|
-
if(dt.getFullYear()===y && dt.getMonth()===mo){ month
|
|
998
|
+
if(dt.getFullYear()===y && dt.getMonth()===mo && dt.getDate()===d){ acc(today, u, j, tk); }
|
|
999
|
+
if(tn.t >= weekCutoff){ acc(week, u, j, tk); }
|
|
1000
|
+
if(dt.getFullYear()===y && dt.getMonth()===mo){ acc(month, u, j, tk); }
|
|
919
1001
|
}
|
|
920
1002
|
if(kpiCards.length >= 4){
|
|
921
1003
|
setKpiCard(kpiCards[0], today); setKpiCard(kpiCards[1], week); setKpiCard(kpiCards[2], month); setKpiCard(kpiCards[3], all);
|
|
922
1004
|
}
|
|
923
1005
|
if(heroValueEl) heroValueEl.textContent = formatUSD(all.usd);
|
|
924
1006
|
if(heroMetaEls.length > 0) heroMetaEls[0].textContent = formatJPY(all.jpy) + ' \xB7 ' + all.turns + ' \u30BF\u30FC\u30F3';
|
|
1007
|
+
if(heroTokEl) heroTokEl.textContent = tokLine(all);
|
|
925
1008
|
if(heroSaEl){
|
|
926
1009
|
heroSaEl.hidden = !(saUsd > 0);
|
|
927
1010
|
if(saUsd > 0) heroSaEl.textContent = heroSaPrefix + formatUSD(saUsd) + '(' + formatJPY(saJpy) + ')';
|
|
@@ -974,12 +1057,12 @@ var APP_JS = `<script>
|
|
|
974
1057
|
dtd.appendChild(meta);
|
|
975
1058
|
if(t.sa){
|
|
976
1059
|
var saLine = document.createElement('div'); saLine.className = 'detail-meta';
|
|
977
|
-
saLine.textContent = '\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8: ' + (t.sa.usd||'') + '(' + (t.sa.jpy||'') + ')\xB7 ' + (t.sa.models||'') + ' \xB7 API\u30B3\u30FC\u30EB ' + (t.sa.apiCalls||0);
|
|
1060
|
+
saLine.textContent = '\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8: ' + (t.sa.usd||'') + '(' + (t.sa.jpy||'') + ')\xB7 ' + (t.sa.models||'') + ' \xB7 API\u30B3\u30FC\u30EB ' + (t.sa.apiCalls||0) + (t.sa.tok ? ' \xB7 ' + t.sa.tok : '');
|
|
978
1061
|
dtd.appendChild(saLine);
|
|
979
1062
|
}
|
|
980
1063
|
if(t.ca){
|
|
981
1064
|
var caLine = document.createElement('div'); caLine.className = 'detail-meta';
|
|
982
|
-
caLine.textContent = 'Codex\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8: \u5229\u7528\u3042\u308A\
|
|
1065
|
+
caLine.textContent = 'Codex\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8: \u5229\u7528\u3042\u308A(\u6599\u91D1\u306F\u3053\u306E\u30BF\u30FC\u30F3\u306B\u542B\u3081\u306A\u3044)\xB7 \u958B\u59CB ' +
|
|
983
1066
|
(t.ca.started||0) + ' \xB7 \u7D42\u4E86 ' + (t.ca.stopped||0) + ' \xB7 \u7A2E\u5225 ' + ((t.ca.agentTypes||[]).join(', ')||'unknown');
|
|
984
1067
|
dtd.appendChild(caLine);
|
|
985
1068
|
}
|
|
@@ -1029,6 +1112,15 @@ var APP_JS = `<script>
|
|
|
1029
1112
|
if(allBtn) allBtn.classList.toggle('active', SEL === null);
|
|
1030
1113
|
var sbtns = document.querySelectorAll('[data-src]');
|
|
1031
1114
|
for(var k=0;k<sbtns.length;k++){ sbtns[k].classList.toggle('active', sbtns[k].getAttribute('data-src') === SRC); }
|
|
1115
|
+
var mbtns = document.querySelectorAll('[data-metric]');
|
|
1116
|
+
for(var mi=0;mi<mbtns.length;mi++){ mbtns[mi].classList.toggle('active', mbtns[mi].getAttribute('data-metric') === MET); }
|
|
1117
|
+
var tokMode = MET === 'tok';
|
|
1118
|
+
var modelLegend = document.getElementById('cccn-model-legend');
|
|
1119
|
+
var tokLegend = document.getElementById('cccn-tok-legend');
|
|
1120
|
+
if(modelLegend) modelLegend.hidden = tokMode;
|
|
1121
|
+
if(tokLegend) tokLegend.hidden = !tokMode;
|
|
1122
|
+
var chartTitle = document.getElementById('cccn-chart-title');
|
|
1123
|
+
if(chartTitle) chartTitle.textContent = tokMode ? '\u30C8\u30FC\u30AF\u30F3\u63A8\u79FB / Tokens over time' : '\u30B3\u30B9\u30C8\u63A8\u79FB / Cost over time';
|
|
1032
1124
|
}
|
|
1033
1125
|
|
|
1034
1126
|
// ---- \u5168\u4F53\u30EC\u30F3\u30C0\u30EA\u30F3\u30B0 ----
|
|
@@ -1051,6 +1143,10 @@ var APP_JS = `<script>
|
|
|
1051
1143
|
}
|
|
1052
1144
|
var allBtn = document.getElementById('cccn-all');
|
|
1053
1145
|
if(allBtn) allBtn.addEventListener('click', function(){ setSel(null); render(); });
|
|
1146
|
+
var metBtns = document.querySelectorAll('[data-metric]');
|
|
1147
|
+
for(var mbi=0;mbi<metBtns.length;mbi++){
|
|
1148
|
+
(function(btn){ btn.addEventListener('click', function(){ setMet(btn.getAttribute('data-metric')); render(); }); })(metBtns[mbi]);
|
|
1149
|
+
}
|
|
1054
1150
|
var srcBtns = document.querySelectorAll('[data-src]');
|
|
1055
1151
|
for(var sbi=0;sbi<srcBtns.length;sbi++){
|
|
1056
1152
|
(function(btn){ btn.addEventListener('click', function(){ setSrc(btn.getAttribute('data-src')); render(); }); })(srcBtns[sbi]);
|
|
@@ -1074,16 +1170,18 @@ var APP_JS = `<script>
|
|
|
1074
1170
|
})();
|
|
1075
1171
|
</script>`;
|
|
1076
1172
|
function statCard(label, sub, totals) {
|
|
1077
|
-
return `<div class="stat"><div class="stat-label">${esc(label)}<span class="stat-sub">${esc(sub)}</span></div><div class="stat-value">${esc(formatUSD(totals.usd))}</div><div class="stat-meta">${esc(formatJPY(totals.jpy))} \xB7 ${totals.turns} \u30BF\u30FC\u30F3</div></div>`;
|
|
1173
|
+
return `<div class="stat"><div class="stat-label">${esc(label)}<span class="stat-sub">${esc(sub)}</span></div><div class="stat-value">${esc(formatUSD(totals.usd))}</div><div class="stat-meta">${esc(formatJPY(totals.jpy))} \xB7 ${totals.turns} \u30BF\u30FC\u30F3</div><div class="stat-meta stat-tok">in ${esc(formatTokens(totals.tin))} / out ${esc(formatTokens(totals.tout))}</div></div>`;
|
|
1078
1174
|
}
|
|
1079
1175
|
function computeSurfaceBreakdown(turns) {
|
|
1080
1176
|
const map = /* @__PURE__ */ new Map();
|
|
1081
1177
|
for (const rec of turns) {
|
|
1082
1178
|
const surface = effectiveSurface(rec);
|
|
1083
|
-
const agg = map.get(surface) ?? { surface, turns: 0, usd: 0, jpy: 0 };
|
|
1179
|
+
const agg = map.get(surface) ?? { surface, turns: 0, usd: 0, jpy: 0, tokens: 0 };
|
|
1180
|
+
const tk = turnTokenTotals(rec);
|
|
1084
1181
|
agg.turns += 1;
|
|
1085
1182
|
agg.usd += turnTotalUSD(rec);
|
|
1086
1183
|
agg.jpy += turnTotalJPY(rec);
|
|
1184
|
+
agg.tokens += tk.tin + tk.tout;
|
|
1087
1185
|
map.set(surface, agg);
|
|
1088
1186
|
}
|
|
1089
1187
|
return [...map.values()].sort((a, b) => b.usd - a.usd);
|
|
@@ -1093,9 +1191,9 @@ function surfaceSection(turns) {
|
|
|
1093
1191
|
if (rows.length === 0) return "";
|
|
1094
1192
|
if (rows.length === 1 && rows[0].surface === "cli") return "";
|
|
1095
1193
|
const trs = rows.map(
|
|
1096
|
-
(r) => `<tr><td>${esc(surfaceLabel(r.surface))}</td><td class="c-num">${r.turns}</td><td class="c-num">${esc(formatUSD(r.usd))}</td><td class="c-num">${esc(formatJPY(r.jpy))}</td></tr>`
|
|
1194
|
+
(r) => `<tr><td>${esc(surfaceLabel(r.surface))}</td><td class="c-num">${r.turns}</td><td class="c-num">${esc(formatUSD(r.usd))}</td><td class="c-num">${esc(formatJPY(r.jpy))}</td><td class="c-num">${esc(formatTokens(r.tokens))}</td></tr>`
|
|
1097
1195
|
).join("");
|
|
1098
|
-
return `<section class="card"><h2>\u30B5\u30FC\u30D5\u30A7\u30B9\u5225\u5185\u8A33 / By surface</h2><p class="note">CLI \u4EE5\u5916(\u30C7\u30B9\u30AF\u30C8\u30C3\u30D7\u30A2\u30D7\u30EA\u7B49)\u304B\u3089\u306E\u5229\u7528\u5206\u306E\u5185\u8A33(\u57CB\u3081\u8FBC\u307F\u5BFE\u8C61\u671F\u9593\u30FBSA \u8FBC\u307F\u7DCF\u984D)\u3002</p><div class="table-wrap"><table class="turns"><thead><tr><th>\u30B5\u30FC\u30D5\u30A7\u30B9</th><th class="c-num">\u30BF\u30FC\u30F3</th><th class="c-num">$</th><th class="c-num">\xA5</th></tr></thead><tbody>${trs}</tbody></table></div></section>`;
|
|
1196
|
+
return `<section class="card"><h2>\u30B5\u30FC\u30D5\u30A7\u30B9\u5225\u5185\u8A33 / By surface</h2><p class="note">CLI \u4EE5\u5916(\u30C7\u30B9\u30AF\u30C8\u30C3\u30D7\u30A2\u30D7\u30EA\u7B49)\u304B\u3089\u306E\u5229\u7528\u5206\u306E\u5185\u8A33(\u57CB\u3081\u8FBC\u307F\u5BFE\u8C61\u671F\u9593\u30FBSA \u8FBC\u307F\u7DCF\u984D\u30FB\u7DCF\u30C8\u30FC\u30AF\u30F3)\u3002\u30E2\u30C7\u30EB\u4E0D\u660E\u3067\u91D1\u984D $0 \u306E\u5229\u7528\u5206\u3082 tokens \u5217\u3067\u898F\u6A21\u304C\u5206\u304B\u308A\u307E\u3059\u3002</p><div class="table-wrap"><table class="turns"><thead><tr><th>\u30B5\u30FC\u30D5\u30A7\u30B9</th><th class="c-num">\u30BF\u30FC\u30F3</th><th class="c-num">$</th><th class="c-num">\xA5</th><th class="c-num">tokens</th></tr></thead><tbody>${trs}</tbody></table></div></section>`;
|
|
1099
1197
|
}
|
|
1100
1198
|
function renderLegend(slots) {
|
|
1101
1199
|
if (slots.length < 2) return "";
|
|
@@ -1180,11 +1278,11 @@ function renderDashboard(turns, opts, fullHistory) {
|
|
|
1180
1278
|
const empty = `<div class="empty">` + (outsideEmbeddedPeriod ? `<h2>\u5BFE\u8C61\u671F\u9593\u306B\u5C65\u6B74\u304C\u3042\u308A\u307E\u305B\u3093</h2><p>\u5C65\u6B74\u306F\u3042\u308A\u307E\u3059\u304C\u3001\u76F4\u8FD1 ${opts.days} \u65E5\u9593\u306B\u306F\u8A18\u9332\u304C\u3042\u308A\u307E\u305B\u3093\u3002</p><p class="empty-hint">No history in the embedded period.</p>` : `<h2>\u307E\u3060\u5C65\u6B74\u304C\u3042\u308A\u307E\u305B\u3093</h2><p>Claude Code \u3067\u30D7\u30ED\u30F3\u30D7\u30C8\u3092\u5B9F\u884C\u3059\u308B\u3068\u3001\u3053\u3053\u306B\u30B3\u30B9\u30C8\u5C65\u6B74\u304C\u8868\u793A\u3055\u308C\u307E\u3059\u3002</p><p class="empty-hint">No history yet \u2014 run a prompt in Claude Code and it will appear here.</p>`) + `</div>`;
|
|
1181
1279
|
return head + header2 + budgetSection + empty + foot;
|
|
1182
1280
|
}
|
|
1183
|
-
const header = `<div class="head"><div><h1>ccc-notifier \u30C0\u30C3\u30B7\u30E5\u30DC\u30FC\u30C9</h1>` + variantNav + `<div class="sub">${esc(period)}<span class="muted"> \xB7 ${esc(rangeText)}</span></div><div class="sub muted">\u751F\u6210 ${esc(generatedAt)} / generated</div></div><div class="hero"><div class="hero-label">${esc(totalLabel)} / ${esc(totalLabelEn)}</div><div class="hero-value">${esc(formatUSD(kpi.all.usd))}</div><div class="hero-meta">${esc(formatJPY(kpi.all.jpy))} \xB7 ${kpi.all.turns} \u30BF\u30FC\u30F3</div>` + (anySub ? `<div class="hero-meta">\u3046\u3061\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8 ${esc(formatUSD(subUsd))}(${esc(formatJPY(subJpy))})</div>` : "") + `</div></div>`;
|
|
1281
|
+
const header = `<div class="head"><div><h1>ccc-notifier \u30C0\u30C3\u30B7\u30E5\u30DC\u30FC\u30C9</h1>` + variantNav + `<div class="sub">${esc(period)}<span class="muted"> \xB7 ${esc(rangeText)}</span></div><div class="sub muted">\u751F\u6210 ${esc(generatedAt)} / generated</div></div><div class="hero"><div class="hero-label">${esc(totalLabel)} / ${esc(totalLabelEn)}</div><div class="hero-value">${esc(formatUSD(kpi.all.usd))}</div><div class="hero-meta">${esc(formatJPY(kpi.all.jpy))} \xB7 ${kpi.all.turns} \u30BF\u30FC\u30F3</div><div class="hero-meta hero-tok">in ${esc(formatTokens(kpi.all.tin))}(cache ${kpi.all.tin > 0 ? Math.round(kpi.all.tcache / kpi.all.tin * 100) : 0}%)/ out ${esc(formatTokens(kpi.all.tout))} tokens</div>` + (anySub ? `<div class="hero-meta hero-sa">\u3046\u3061\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8 ${esc(formatUSD(subUsd))}(${esc(formatJPY(subJpy))})</div>` : "") + `</div></div>`;
|
|
1184
1282
|
const kpiSection = `<div class="kpi">` + statCard("\u4ECA\u65E5", "Today", kpi.today) + statCard("\u4ECA\u9031", "\u76F4\u8FD17\u65E5", kpi.week) + statCard("\u4ECA\u6708", "\u66A6\u6708", kpi.month) + statCard(totalLabel, totalSub, kpi.all) + `</div>`;
|
|
1185
1283
|
const srcToggle = anyCodex ? `<div class="seg-toggle" id="cccn-src-toggle"><button type="button" data-src="all">\u5168\u4F53</button><button type="button" data-src="claude">Claude</button><button type="button" data-src="codex">Codex</button></div>` : "";
|
|
1186
|
-
const chartSection = `<section class="card"><h2>\u30B3\u30B9\u30C8\u63A8\u79FB / Cost over time</h2><p class="note">\u7C92\u5EA6\u3092 \u65E5 / \u9031 / \u6708 \u3067\u5207\u308A\u66FF\u3048\u3089\u308C\u307E\u3059(\u6A2A\u30B9\u30AF\u30ED\u30FC\u30EB\u3067\u904E\u53BB\u307E\u3067)\u3002\u68D2\u3092\u30AF\u30EA\u30C3\u30AF\u3059\u308B\u3068\u305D\u306E\u671F\u9593\u304C\u9078\u629E\u3055\u308C\u3001\u4E0B\u306E\u30E2\u30C7\u30EB\u5225\u30FB\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8\u5225\u30FB\u5C65\u6B74\u304C\u9023\u52D5\u3057\u307E\u3059\u3002\u300C${esc(totalLabel)}\u300D\u3067${esc(totalSub)}\u306B\u623B\u308A\u307E\u3059\u3002\u30E2\u30C7\u30EB\u5225\u306B\u8272\u5206\u3051\u3002</p><div class="toolbar-row"><div class="seg-toggle"><button type="button" data-gran="day">\u65E5</button><button type="button" data-gran="week">\u9031</button><button type="button" data-gran="month">\u6708</button></div><button type="button" id="cccn-all" class="btn">${esc(totalLabel)}</button>` + srcToggle + `<span id="cccn-sel-label" class="sel-label"></span></div>` + renderLegend(map.slots) +
|
|
1187
|
-
const breakdownSection = `<div class="grid2"><section class="card"><h2>\u30E2\u30C7\u30EB\u5225\u5185\u8A33 / By model</h2><p class="note">\u9078\u629E\u4E2D\u306E\u671F\u9593(\u65E2\u5B9A\u306F${esc(totalLabel)})\u306E\u30B3\u30B9\u30C8\u964D\u9806\u3002\u8907\u6570\u30E2\u30C7\u30EB\u306E\u30BF\u30FC\u30F3\u306F\u5404\u30E2\u30C7\u30EB\
|
|
1284
|
+
const chartSection = `<section class="card"><h2 id="cccn-chart-title">\u30B3\u30B9\u30C8\u63A8\u79FB / Cost over time</h2><p class="note">\u7C92\u5EA6\u3092 \u65E5 / \u9031 / \u6708 \u3067\u5207\u308A\u66FF\u3048\u3089\u308C\u307E\u3059(\u6A2A\u30B9\u30AF\u30ED\u30FC\u30EB\u3067\u904E\u53BB\u307E\u3067)\u3002\u68D2\u3092\u30AF\u30EA\u30C3\u30AF\u3059\u308B\u3068\u305D\u306E\u671F\u9593\u304C\u9078\u629E\u3055\u308C\u3001\u4E0B\u306E\u30E2\u30C7\u30EB\u5225\u30FB\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8\u5225\u30FB\u5C65\u6B74\u304C\u9023\u52D5\u3057\u307E\u3059\u3002\u300C${esc(totalLabel)}\u300D\u3067${esc(totalSub)}\u306B\u623B\u308A\u307E\u3059\u3002\u7E26\u8EF8\u306F\u91D1\u984D\u3068\u30C8\u30FC\u30AF\u30F3\u3092\u5207\u308A\u66FF\u3048\u3089\u308C\u307E\u3059(\u91D1\u984D\u8EF8\u306F\u30E2\u30C7\u30EB\u5225\u306B\u8272\u5206\u3051\u3001\u30C8\u30FC\u30AF\u30F3\u8EF8\u306F\u30AD\u30E3\u30C3\u30B7\u30E5/\u5165\u529B/\u51FA\u529B\u306E3\u533A\u5206)\u3002</p><div class="toolbar-row"><div class="seg-toggle"><button type="button" data-gran="day">\u65E5</button><button type="button" data-gran="week">\u9031</button><button type="button" data-gran="month">\u6708</button></div><div class="seg-toggle" id="cccn-metric-toggle"><button type="button" data-metric="usd">\u91D1\u984D</button><button type="button" data-metric="tok">\u30C8\u30FC\u30AF\u30F3</button></div><button type="button" id="cccn-all" class="btn">${esc(totalLabel)}</button>` + srcToggle + `<span id="cccn-sel-label" class="sel-label"></span></div><div id="cccn-model-legend">` + renderLegend(map.slots) + `</div><div class="legend" id="cccn-tok-legend" hidden><span class="legend-item"><span class="swatch ktcache"></span>\u30AD\u30E3\u30C3\u30B7\u30E5(read+write)</span><span class="legend-item"><span class="swatch ktin"></span>\u5165\u529B(\u30AD\u30E3\u30C3\u30B7\u30E5\u4EE5\u5916)</span><span class="legend-item"><span class="swatch ktout"></span>\u51FA\u529B</span></div><div class="chart-scroll"><div id="cccn-chart"></div></div></section>`;
|
|
1285
|
+
const breakdownSection = `<div class="grid2"><section class="card"><h2>\u30E2\u30C7\u30EB\u5225\u5185\u8A33 / By model</h2><p class="note">\u9078\u629E\u4E2D\u306E\u671F\u9593(\u65E2\u5B9A\u306F${esc(totalLabel)})\u306E\u30B3\u30B9\u30C8\u964D\u9806\u3002\u8907\u6570\u30E2\u30C7\u30EB\u306E\u30BF\u30FC\u30F3\u306F\u3001\u30BF\u30FC\u30F3\u6570\u30FBtokens \u5217\u3068\u3082\u5404\u30E2\u30C7\u30EB\u306B\u5168\u91CF\u8A08\u4E0A(\u91CD\u8907\u3042\u308A\u3002\u30EC\u30B3\u30FC\u30C9\u306B\u30E2\u30C7\u30EB\u5225\u30C8\u30FC\u30AF\u30F3\u304C\u7121\u3044\u305F\u3081\u30BF\u30FC\u30F3\u5185\u3067\u306F\u5206\u5272\u3057\u306A\u3044)\u3002</p><div class="table-wrap" id="cccn-bymodel"></div></section><section class="card"><h2>\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8\u5225 / By project</h2><p class="note">\u9078\u629E\u4E2D\u306E\u671F\u9593\u306E\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8(\u30C7\u30A3\u30EC\u30AF\u30C8\u30EA basename)\u5358\u4F4D\u30FB\u30B3\u30B9\u30C8\u964D\u9806\u3002</p><div class="table-wrap" id="cccn-byproject"></div></section></div>`;
|
|
1188
1286
|
const capNote = "\u4EF6\u6570\u304C\u591A\u3044\u5834\u5408\u306F\u65B0\u3057\u3044\u9806\u306B\u5148\u982D200\u4EF6\u306E\u307F\u63CF\u753B\u3057\u307E\u3059(\u691C\u7D22\u3084\u3001\u4E0A\u306E\u30B0\u30E9\u30D5\u3067\u671F\u9593\u3092\u9078\u3076\u3068\u7D5E\u308A\u8FBC\u3081\u307E\u3059)\u3002";
|
|
1189
1287
|
const truncNote = anyTruncated ? `<p class="note">\u9078\u629E\u4E2D\u306E\u671F\u9593\u306E\u30BF\u30FC\u30F3\u3092\u65B0\u3057\u3044\u9806\u306B\u8868\u793A\u3057\u307E\u3059\u3002${capNote}\u30D7\u30ED\u30F3\u30D7\u30C8\u306F1\u4EF6\u3042\u305F\u308A\u6700\u5927 ${PROMPT_MAX.toLocaleString("en-US")} \u5B57\u307E\u3067(\u8D85\u904E\u5206\u306F\u300C${esc(PROMPT_TRUNC_MARK)}\u300D)\u3002\u884C\u30AF\u30EA\u30C3\u30AF\u3067\u5168\u6587\u5C55\u958B\u3002</p>` : `<p class="note">\u9078\u629E\u4E2D\u306E\u671F\u9593\u306E\u30BF\u30FC\u30F3\u3092\u65B0\u3057\u3044\u9806\u306B\u8868\u793A\u3057\u307E\u3059\u3002${capNote}\u884C\u30AF\u30EA\u30C3\u30AF\u3067\u30D7\u30ED\u30F3\u30D7\u30C8\u5168\u6587\u3092\u5C55\u958B\u3057\u307E\u3059\u3002</p>`;
|
|
1190
1288
|
const historySection = `<section class="card"><h2>\u30BF\u30FC\u30F3\u5C65\u6B74 / History</h2>` + truncNote + `<div class="toolbar"><input id="turn-search" class="search" type="search" placeholder="\u30D7\u30ED\u30F3\u30D7\u30C8\u30FB\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8\u30FB\u30E2\u30C7\u30EB\u3067\u691C\u7D22 / search\u2026" autocomplete="off"><span class="count"><span id="turn-count">0</span></span></div><div class="table-wrap"><table class="turns"><thead><tr><th>\u6642\u523B</th><th>\u30D7\u30ED\u30B8\u30A7\u30AF\u30C8</th><th>\u30E2\u30C7\u30EB</th><th class="c-num">in</th><th class="c-num">out</th><th class="c-num">$</th><th class="c-num">\xA5</th><th>\u30D7\u30ED\u30F3\u30D7\u30C8</th></tr></thead><tbody id="turn-body"></tbody></table></div></section>`;
|
|
@@ -356,7 +356,8 @@ function readSessionMetaSeed(buffer) {
|
|
|
356
356
|
sessionId: strOrNull(payload.id) ?? strOrNull(payload.session_id),
|
|
357
357
|
cwd: strOrNull(payload.cwd),
|
|
358
358
|
originator: strOrNull(payload.originator),
|
|
359
|
-
isSubagentRollout: isRecord(source) && Object.hasOwn(source, "subagent")
|
|
359
|
+
isSubagentRollout: isRecord(source) && Object.hasOwn(source, "subagent"),
|
|
360
|
+
isForkedRollout: strOrNull(payload.forked_from_id) !== null
|
|
360
361
|
};
|
|
361
362
|
}
|
|
362
363
|
function newSegmentBuf() {
|
|
@@ -395,6 +396,7 @@ async function scanWindow(rolloutPath, cursor, opts = {}) {
|
|
|
395
396
|
let sessionMetaCwd = null;
|
|
396
397
|
let sessionMetaSid = null;
|
|
397
398
|
let isSubagentRollout = false;
|
|
399
|
+
let isForkedRollout = false;
|
|
398
400
|
let originator = cursor?.codexOriginator ?? null;
|
|
399
401
|
if (startOffset > 0) {
|
|
400
402
|
const seed = readSessionMetaSeed(buffer);
|
|
@@ -403,6 +405,7 @@ async function scanWindow(rolloutPath, cursor, opts = {}) {
|
|
|
403
405
|
sessionMetaCwd = seed.cwd;
|
|
404
406
|
if (seed.originator !== null) originator = seed.originator;
|
|
405
407
|
isSubagentRollout = seed.isSubagentRollout;
|
|
408
|
+
isForkedRollout = seed.isForkedRollout;
|
|
406
409
|
}
|
|
407
410
|
}
|
|
408
411
|
let firstTs = null;
|
|
@@ -454,6 +457,7 @@ async function scanWindow(rolloutPath, cursor, opts = {}) {
|
|
|
454
457
|
if (c !== null) sessionMetaCwd = c;
|
|
455
458
|
const source = payload.source;
|
|
456
459
|
if (isRecord(source) && Object.hasOwn(source, "subagent")) isSubagentRollout = true;
|
|
460
|
+
if (strOrNull(payload.forked_from_id) !== null) isForkedRollout = true;
|
|
457
461
|
const orig = strOrNull(payload.originator);
|
|
458
462
|
if (orig !== null) originator = orig;
|
|
459
463
|
return;
|
|
@@ -532,6 +536,7 @@ async function scanWindow(rolloutPath, cursor, opts = {}) {
|
|
|
532
536
|
sessionId: rolloutId(),
|
|
533
537
|
eventKeys: windowEventKeys,
|
|
534
538
|
isSubagentRollout,
|
|
539
|
+
isForkedRollout,
|
|
535
540
|
originator,
|
|
536
541
|
firstTs,
|
|
537
542
|
lastTs,
|
|
@@ -569,6 +574,7 @@ async function aggregateCodexTurn(rolloutPath, cursor, opts = {}) {
|
|
|
569
574
|
newCursor: windowCursor(scan),
|
|
570
575
|
originator: scan.originator,
|
|
571
576
|
isSubagentRollout: scan.isSubagentRollout,
|
|
577
|
+
isForkedRollout: scan.isForkedRollout,
|
|
572
578
|
codexEventKeys: scan.eventKeys
|
|
573
579
|
};
|
|
574
580
|
}
|
|
@@ -640,6 +646,7 @@ function draftsFromScan(scan) {
|
|
|
640
646
|
const lastIndex = picked.length - 1;
|
|
641
647
|
return picked.map((s, i) => ({
|
|
642
648
|
isSubagentRollout: scan.isSubagentRollout,
|
|
649
|
+
isForkedRollout: scan.isForkedRollout,
|
|
643
650
|
agg: {
|
|
644
651
|
sessionId: scan.sessionId,
|
|
645
652
|
// session_meta はファイル先頭にしか無いので全ドラフト共通
|
|
@@ -652,6 +659,7 @@ function draftsFromScan(scan) {
|
|
|
652
659
|
originator: scan.originator,
|
|
653
660
|
// session_meta はファイル先頭にしか無いので全ドラフト共通
|
|
654
661
|
isSubagentRollout: scan.isSubagentRollout,
|
|
662
|
+
isForkedRollout: scan.isForkedRollout,
|
|
655
663
|
codexEventKeys: s.eventKeys,
|
|
656
664
|
firstTs: s.firstTs,
|
|
657
665
|
lastTs: s.endTs,
|
|
@@ -15,7 +15,8 @@ function formatJPY(n) {
|
|
|
15
15
|
function formatTokens(n) {
|
|
16
16
|
if (n < 1e3) return `${n}`;
|
|
17
17
|
if (n < 1e6) return `${(n / 1e3).toFixed(1)}k`;
|
|
18
|
-
return `${(n / 1e6).toFixed(1)}M`;
|
|
18
|
+
if (n < 1e9) return `${(n / 1e6).toFixed(1)}M`;
|
|
19
|
+
return `${(n / 1e9).toFixed(1)}B`;
|
|
19
20
|
}
|
|
20
21
|
function groupThousands(n) {
|
|
21
22
|
const sign = n < 0 ? "-" : "";
|
|
@@ -84,7 +85,9 @@ function formatIngestSummary(input, cfg) {
|
|
|
84
85
|
const label = cfg.costLabel === "api_equivalent" ? "API\u63DB\u7B97 " : "";
|
|
85
86
|
const title = `\u{1F4B0} ${label}${formatUSD(input.totalUSD)}(${formatJPY(input.totalJPY)})| hook\u975E\u4F9D\u5B58\u306E\u53D6\u308A\u8FBC\u307F ${input.recordCount}\u4EF6`;
|
|
86
87
|
const bySurfaceLine = Object.entries(input.bySurface).sort((a, b) => b[1].usd - a[1].usd).map(([surface, v]) => `${surface}: ${v.turns}\u4EF6 ${formatUSD(v.usd)}`).join(" / ");
|
|
87
|
-
const
|
|
88
|
+
const cachePct = input.totalTokens > 0 ? Math.round(input.cacheTokens / input.totalTokens * 100) : 0;
|
|
89
|
+
const tokensPart = input.totalTokens > 0 ? ` \xB7 \u8A08 ${formatTokens(input.totalTokens)} tokens(cache ${cachePct}%)` : "";
|
|
90
|
+
const body = `${bySurfaceLine}${tokensPart}
|
|
88
91
|
hook \u975E\u4F9D\u5B58\u306E\u5897\u5206\u53D6\u308A\u8FBC\u307F(scan)\u306B\u3088\u308B\u65B0\u898F\u5206\u3067\u3059`;
|
|
89
92
|
return { title, body };
|
|
90
93
|
}
|
|
@@ -12,7 +12,7 @@ import {
|
|
|
12
12
|
setCountedCalls,
|
|
13
13
|
splitIntoCodexTurnDrafts,
|
|
14
14
|
surfaceForClaudePath
|
|
15
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-GAOGTALW.js";
|
|
16
16
|
import {
|
|
17
17
|
codexHome,
|
|
18
18
|
computeCost,
|
|
@@ -20,7 +20,7 @@ import {
|
|
|
20
20
|
} from "./chunk-Q45AAPJY.js";
|
|
21
21
|
import {
|
|
22
22
|
writeDashboardHtml
|
|
23
|
-
} from "./chunk-
|
|
23
|
+
} from "./chunk-6GWPAYJQ.js";
|
|
24
24
|
import {
|
|
25
25
|
invalidateCanonicalDashboards,
|
|
26
26
|
makeFullDashboardState,
|
|
@@ -33,7 +33,7 @@ import {
|
|
|
33
33
|
formatJPY,
|
|
34
34
|
formatUSD,
|
|
35
35
|
modelDisplayName
|
|
36
|
-
} from "./chunk-
|
|
36
|
+
} from "./chunk-OHTPBABH.js";
|
|
37
37
|
import {
|
|
38
38
|
appendTurn,
|
|
39
39
|
loadCursor,
|
|
@@ -590,6 +590,41 @@ function codexDraftToRecord(draft, ts, table, fx) {
|
|
|
590
590
|
setCountedCalls(rec, draft.agg.codexEventKeys ?? []);
|
|
591
591
|
return rec;
|
|
592
592
|
}
|
|
593
|
+
function codexChildDraftToRecord(draft, ts, table, fx, ingest) {
|
|
594
|
+
const main = draft.agg.main;
|
|
595
|
+
const breakdown = computeCost(main, {}, table);
|
|
596
|
+
const rec = {
|
|
597
|
+
schemaVersion: 1,
|
|
598
|
+
ts,
|
|
599
|
+
sessionId: draft.agg.sessionId,
|
|
600
|
+
project: draft.agg.cwd ?? "",
|
|
601
|
+
gitBranch: null,
|
|
602
|
+
models: collectModels(main, {}),
|
|
603
|
+
tokens: emptyBuckets2(),
|
|
604
|
+
sidechainTokens: null,
|
|
605
|
+
apiCalls: 0,
|
|
606
|
+
costUSD: 0,
|
|
607
|
+
costByModel: {},
|
|
608
|
+
costJPY: 0,
|
|
609
|
+
fxRate: fx.rate,
|
|
610
|
+
fxSource: fx.source,
|
|
611
|
+
prompt: "",
|
|
612
|
+
ingest,
|
|
613
|
+
source: "codex",
|
|
614
|
+
surface: normalizeCodexOriginator(draft.agg.originator),
|
|
615
|
+
subagents: {
|
|
616
|
+
costUSD: breakdown.usd,
|
|
617
|
+
costByModel: { ...breakdown.byModel },
|
|
618
|
+
tokens: sumBuckets(main),
|
|
619
|
+
apiCalls: draft.agg.apiCalls,
|
|
620
|
+
agentFiles: 1
|
|
621
|
+
}
|
|
622
|
+
};
|
|
623
|
+
if (typeof draft.agg.originator === "string") rec.originator = draft.agg.originator;
|
|
624
|
+
if (breakdown.unknownModels.length > 0) rec.unknownModels = breakdown.unknownModels;
|
|
625
|
+
setCountedCalls(rec, draft.agg.codexEventKeys ?? []);
|
|
626
|
+
return rec;
|
|
627
|
+
}
|
|
593
628
|
async function processCodexRolloutLocked(rolloutPath, table, fx, daysCutoff, dryRun, summary, opts = {}) {
|
|
594
629
|
if (opts.strictRead) {
|
|
595
630
|
const file = await fsp.open(rolloutPath, "r");
|
|
@@ -598,21 +633,27 @@ async function processCodexRolloutLocked(rolloutPath, table, fx, daysCutoff, dry
|
|
|
598
633
|
const cursor = opts.ignoreCursors ? null : sanitizeCursor(loadCursor(rolloutPath));
|
|
599
634
|
const drafts = await splitIntoCodexTurnDrafts(rolloutPath, cursor);
|
|
600
635
|
if (drafts === null || drafts.length === 0) return;
|
|
601
|
-
|
|
636
|
+
const isChild = drafts[0].isSubagentRollout;
|
|
637
|
+
const isForkedChild = isChild && drafts[0].isForkedRollout;
|
|
602
638
|
const records = [];
|
|
603
|
-
|
|
604
|
-
const
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
639
|
+
if (!isForkedChild) {
|
|
640
|
+
for (const draft of drafts) {
|
|
641
|
+
const ts = draft.endTs ?? (/* @__PURE__ */ new Date()).toISOString();
|
|
642
|
+
if (daysCutoff !== null) {
|
|
643
|
+
const tsMs = Date.parse(ts);
|
|
644
|
+
if (!Number.isFinite(tsMs) || tsMs < daysCutoff) continue;
|
|
645
|
+
}
|
|
646
|
+
records.push(
|
|
647
|
+
isChild ? codexChildDraftToRecord(draft, ts, table, fx, "sweep") : codexDraftToRecord(draft, ts, table, fx)
|
|
648
|
+
);
|
|
608
649
|
}
|
|
609
|
-
records.push(codexDraftToRecord(draft, ts, table, fx));
|
|
610
650
|
}
|
|
611
651
|
for (const rec of records) {
|
|
612
652
|
summary.newRecords += 1;
|
|
613
653
|
summary.totalUSD += rec.costUSD;
|
|
614
654
|
summary.codexRecords += 1;
|
|
615
655
|
summary.codexUSD += rec.costUSD;
|
|
656
|
+
summary.subagentsUSD += rec.subagents?.costUSD ?? 0;
|
|
616
657
|
if (rec.costByModel) {
|
|
617
658
|
for (const [m, c] of Object.entries(rec.costByModel)) {
|
|
618
659
|
summary.byModel[m] = (summary.byModel[m] ?? 0) + c;
|
|
@@ -953,5 +994,6 @@ export {
|
|
|
953
994
|
collectSubagentUsage,
|
|
954
995
|
splitIntoTurnDrafts,
|
|
955
996
|
attachSubagentGroups,
|
|
997
|
+
codexChildDraftToRecord,
|
|
956
998
|
runSweep
|
|
957
999
|
};
|
|
@@ -2,13 +2,14 @@
|
|
|
2
2
|
import {
|
|
3
3
|
notifyOS,
|
|
4
4
|
notifySlack
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-2XOKH54N.js";
|
|
6
6
|
import {
|
|
7
7
|
attachSubagentGroups,
|
|
8
|
+
codexChildDraftToRecord,
|
|
8
9
|
collectSubagentUsage,
|
|
9
10
|
normalizeCodexOriginator,
|
|
10
11
|
splitIntoTurnDrafts
|
|
11
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-SKX5EMST.js";
|
|
12
13
|
import {
|
|
13
14
|
anyOf,
|
|
14
15
|
callFingerprints,
|
|
@@ -20,7 +21,7 @@ import {
|
|
|
20
21
|
scanCodexTurns,
|
|
21
22
|
setCountedCalls,
|
|
22
23
|
surfaceForClaudePath
|
|
23
|
-
} from "./chunk-
|
|
24
|
+
} from "./chunk-GAOGTALW.js";
|
|
24
25
|
import {
|
|
25
26
|
codexHome,
|
|
26
27
|
computeCost,
|
|
@@ -31,7 +32,7 @@ import {
|
|
|
31
32
|
} from "./chunk-PXMXEFM7.js";
|
|
32
33
|
import {
|
|
33
34
|
formatIngestSummary
|
|
34
|
-
} from "./chunk-
|
|
35
|
+
} from "./chunk-OHTPBABH.js";
|
|
35
36
|
import {
|
|
36
37
|
appendTurn,
|
|
37
38
|
floorKey,
|
|
@@ -240,17 +241,33 @@ function emptyResult(dryRun, fx, lockAcquired) {
|
|
|
240
241
|
failures: 0,
|
|
241
242
|
totalUSD: 0,
|
|
242
243
|
totalJPY: 0,
|
|
244
|
+
totalTokens: 0,
|
|
245
|
+
cacheTokens: 0,
|
|
243
246
|
fxRate: fx.rate,
|
|
244
247
|
fxSource: fx.source,
|
|
245
248
|
bySurface: {}
|
|
246
249
|
};
|
|
247
250
|
}
|
|
251
|
+
function recordTokenTotals(rec) {
|
|
252
|
+
let total = 0;
|
|
253
|
+
let cache = 0;
|
|
254
|
+
for (const b of [rec.tokens, rec.sidechainTokens, rec.subagents?.tokens]) {
|
|
255
|
+
if (!b) continue;
|
|
256
|
+
const cached = b.cacheRead + b.cacheWrite5m + b.cacheWrite1h;
|
|
257
|
+
total += b.input + b.output + cached;
|
|
258
|
+
cache += cached;
|
|
259
|
+
}
|
|
260
|
+
return { total, cache };
|
|
261
|
+
}
|
|
248
262
|
function addRecord(result, rec) {
|
|
249
263
|
const usd = rec.costUSD + (rec.subagents?.costUSD ?? 0);
|
|
250
264
|
const jpy = rec.costJPY + (rec.subagents?.costUSD ?? 0) * rec.fxRate;
|
|
265
|
+
const tokens = recordTokenTotals(rec);
|
|
251
266
|
result.records.push(rec);
|
|
252
267
|
result.totalUSD += usd;
|
|
253
268
|
result.totalJPY += jpy;
|
|
269
|
+
result.totalTokens += tokens.total;
|
|
270
|
+
result.cacheTokens += tokens.cache;
|
|
254
271
|
const surface = rec.surface ?? "cli";
|
|
255
272
|
const cur = result.bySurface[surface] ?? { turns: 0, usd: 0 };
|
|
256
273
|
cur.turns += 1;
|
|
@@ -365,17 +382,18 @@ async function processFiles(claudeFiles, codexFiles, claudeRoots, table, fx, dry
|
|
|
365
382
|
return;
|
|
366
383
|
}
|
|
367
384
|
const windowCursor = scan.newCursor;
|
|
368
|
-
if (drafts[0].isSubagentRollout) {
|
|
385
|
+
if (drafts[0].isSubagentRollout && drafts[0].isForkedRollout) {
|
|
369
386
|
commit(filePath, [], windowCursor);
|
|
370
387
|
return;
|
|
371
388
|
}
|
|
389
|
+
const build = drafts[0].isSubagentRollout ? (draft) => codexChildDraftToRecord(draft, draft.endTs ?? (/* @__PURE__ */ new Date()).toISOString(), table, fx, "scan") : (draft) => buildCodexRecord(draft.agg, table, fx);
|
|
372
390
|
if (cursor !== null) {
|
|
373
|
-
commit(filePath, drafts.map(
|
|
391
|
+
commit(filePath, drafts.map(build), windowCursor);
|
|
374
392
|
return;
|
|
375
393
|
}
|
|
376
394
|
const floor = recordedFloor("codex", drafts[0].agg.sessionId);
|
|
377
395
|
const target = floor === null ? drafts : (await scanCodexTurns(filePath, await codexResumePointAtTs(filePath, floor), scanOpts))?.drafts ?? [];
|
|
378
|
-
commit(filePath, target.map(
|
|
396
|
+
commit(filePath, target.map(build), windowCursor);
|
|
379
397
|
};
|
|
380
398
|
const runOver = async (files, context, handle, signature = fileMtimeMs) => {
|
|
381
399
|
for (const filePath of files) {
|
|
@@ -423,7 +441,14 @@ async function notifyIngestSummary(result, cfg) {
|
|
|
423
441
|
if (v) bySurface[surface] = v;
|
|
424
442
|
}
|
|
425
443
|
const summary = formatIngestSummary(
|
|
426
|
-
{
|
|
444
|
+
{
|
|
445
|
+
recordCount: result.records.length,
|
|
446
|
+
totalUSD: result.totalUSD,
|
|
447
|
+
totalJPY: result.totalJPY,
|
|
448
|
+
totalTokens: result.totalTokens,
|
|
449
|
+
cacheTokens: result.cacheTokens,
|
|
450
|
+
bySurface
|
|
451
|
+
},
|
|
427
452
|
cfg
|
|
428
453
|
);
|
|
429
454
|
const record = {
|
package/dist/cli.js
CHANGED
|
@@ -7,12 +7,12 @@ import {
|
|
|
7
7
|
CODEX_HOOK_TIMEOUT_SECONDS,
|
|
8
8
|
matchesMarker,
|
|
9
9
|
parseConfiguredOwnedCodexHookCommand
|
|
10
|
-
} from "./chunk-
|
|
10
|
+
} from "./chunk-XT3KWNWI.js";
|
|
11
11
|
import {
|
|
12
12
|
notifyOS,
|
|
13
13
|
notifySlack,
|
|
14
14
|
selectNotifyBackend
|
|
15
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-2XOKH54N.js";
|
|
16
16
|
import {
|
|
17
17
|
aggregateNewTurn,
|
|
18
18
|
claudeTranscriptRoots,
|
|
@@ -21,7 +21,7 @@ import {
|
|
|
21
21
|
listCodexRollouts,
|
|
22
22
|
rootForClaudePath,
|
|
23
23
|
splitIntoCodexTurnDrafts
|
|
24
|
-
} from "./chunk-
|
|
24
|
+
} from "./chunk-GAOGTALW.js";
|
|
25
25
|
import {
|
|
26
26
|
codexHome,
|
|
27
27
|
computeCost,
|
|
@@ -39,7 +39,7 @@ import {
|
|
|
39
39
|
formatJPY,
|
|
40
40
|
formatTokens,
|
|
41
41
|
formatUSD
|
|
42
|
-
} from "./chunk-
|
|
42
|
+
} from "./chunk-OHTPBABH.js";
|
|
43
43
|
import {
|
|
44
44
|
cursorPaths,
|
|
45
45
|
hasUnresolvedPendingMarker,
|
|
@@ -1044,7 +1044,7 @@ function printTable(result, days) {
|
|
|
1044
1044
|
if (result.total.codexSubagentActivity) {
|
|
1045
1045
|
const activity = result.total.codexSubagentActivity;
|
|
1046
1046
|
console.log(
|
|
1047
|
-
`(Codex\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8\u5229\u7528\u3042\u308A\
|
|
1047
|
+
`(Codex\u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8\u5229\u7528\u3042\u308A(\u6599\u91D1\u306F\u89AA\u30BF\u30FC\u30F3\u306B\u542B\u3081\u306A\u3044): ${activity.turns}\u30BF\u30FC\u30F3 / \u958B\u59CB${activity.started}\u30FB\u7D42\u4E86${activity.stopped})`
|
|
1048
1048
|
);
|
|
1049
1049
|
}
|
|
1050
1050
|
console.log("");
|
|
@@ -1157,7 +1157,7 @@ function isCodexPassiveEvent(value) {
|
|
|
1157
1157
|
async function runCodexPassiveHook(event, text) {
|
|
1158
1158
|
try {
|
|
1159
1159
|
if (event === "Stop") {
|
|
1160
|
-
const trackMod = await import("./track-
|
|
1160
|
+
const trackMod = await import("./track-GTQOULBP.js");
|
|
1161
1161
|
await trackMod.runTrack(text, { codex: true });
|
|
1162
1162
|
} else if (event === "UserPromptSubmit") {
|
|
1163
1163
|
const activity = await import("./subagent-store-USG3WJEB.js");
|
|
@@ -1242,18 +1242,18 @@ async function main(argv) {
|
|
|
1242
1242
|
const text = await readStdin();
|
|
1243
1243
|
const codex = rest.includes("--codex");
|
|
1244
1244
|
try {
|
|
1245
|
-
const trackMod = await import("./track-
|
|
1245
|
+
const trackMod = await import("./track-GTQOULBP.js");
|
|
1246
1246
|
await trackMod.runTrack(text, { codex });
|
|
1247
1247
|
} catch {
|
|
1248
1248
|
}
|
|
1249
1249
|
return 0;
|
|
1250
1250
|
}
|
|
1251
1251
|
case "init": {
|
|
1252
|
-
const { runInit } = await import("./setup-
|
|
1252
|
+
const { runInit } = await import("./setup-H52OFFBQ.js");
|
|
1253
1253
|
return await runInit(rest);
|
|
1254
1254
|
}
|
|
1255
1255
|
case "uninstall": {
|
|
1256
|
-
const { runUninstall } = await import("./setup-
|
|
1256
|
+
const { runUninstall } = await import("./setup-H52OFFBQ.js");
|
|
1257
1257
|
return await runUninstall(rest);
|
|
1258
1258
|
}
|
|
1259
1259
|
case "doctor":
|
|
@@ -1261,19 +1261,19 @@ async function main(argv) {
|
|
|
1261
1261
|
case "report":
|
|
1262
1262
|
return await runReport(rest);
|
|
1263
1263
|
case "dashboard": {
|
|
1264
|
-
const { runDashboard } = await import("./dashboard-
|
|
1264
|
+
const { runDashboard } = await import("./dashboard-GR3OMZW5.js");
|
|
1265
1265
|
return await runDashboard(rest);
|
|
1266
1266
|
}
|
|
1267
1267
|
case "sweep": {
|
|
1268
|
-
const { runSweep } = await import("./sweep-
|
|
1268
|
+
const { runSweep } = await import("./sweep-2GHO4U5C.js");
|
|
1269
1269
|
return await runSweep(rest);
|
|
1270
1270
|
}
|
|
1271
1271
|
case "scan": {
|
|
1272
|
-
const { runScan } = await import("./scan-
|
|
1272
|
+
const { runScan } = await import("./scan-YIU6CG3E.js");
|
|
1273
1273
|
return await runScan(rest);
|
|
1274
1274
|
}
|
|
1275
1275
|
case "reset-cursors": {
|
|
1276
|
-
const { runResetCursors } = await import("./reset-cursors-
|
|
1276
|
+
const { runResetCursors } = await import("./reset-cursors-UVQXFN5Y.js");
|
|
1277
1277
|
return await runResetCursors(rest);
|
|
1278
1278
|
}
|
|
1279
1279
|
case "history": {
|
|
@@ -1281,7 +1281,7 @@ async function main(argv) {
|
|
|
1281
1281
|
return await runHistory(rest);
|
|
1282
1282
|
}
|
|
1283
1283
|
case "budget": {
|
|
1284
|
-
const { runBudget } = await import("./budget-
|
|
1284
|
+
const { runBudget } = await import("./budget-KLRUKU6V.js");
|
|
1285
1285
|
return runBudget(rest);
|
|
1286
1286
|
}
|
|
1287
1287
|
case "mute": {
|
|
@@ -3,12 +3,12 @@ import {
|
|
|
3
3
|
browserOpenPlan,
|
|
4
4
|
runDashboard,
|
|
5
5
|
writeDashboardHtml
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-6GWPAYJQ.js";
|
|
7
7
|
import "./chunk-3M5UQK76.js";
|
|
8
8
|
import "./chunk-PXMXEFM7.js";
|
|
9
9
|
import "./chunk-6IVSZ3S4.js";
|
|
10
10
|
import "./chunk-DGXUSPS4.js";
|
|
11
|
-
import "./chunk-
|
|
11
|
+
import "./chunk-OHTPBABH.js";
|
|
12
12
|
import "./chunk-WONMZ466.js";
|
|
13
13
|
export {
|
|
14
14
|
browserOpenPlan,
|
|
@@ -34,6 +34,9 @@ async function runResetCursors(argv) {
|
|
|
34
34
|
console.log("\u53D6\u308A\u8FBC\u307F\u4F4D\u7F6E(cursors.json)\u3068\u4FDD\u7559\u30DE\u30FC\u30AB\u30FC\u3092\u7834\u68C4\u3057\u307E\u3057\u305F\u3002");
|
|
35
35
|
console.log("\u5C65\u6B74(history.jsonl)\u30FB\u8A2D\u5B9A\u30FB\u901A\u77E5\u5148\u306F\u305D\u306E\u307E\u307E\u3067\u3059\u3002\u4E8C\u91CD\u8A08\u4E0A\u306F\u5C65\u6B74\u5074\u306E\u6307\u7D0B\u3067\u9632\u304E\u307E\u3059\u3002");
|
|
36
36
|
console.log("\u6B21\u56DE\u306E\u53D6\u308A\u8FBC\u307F\u306F\u5168 transcript / rollout \u3092\u8AAD\u307F\u76F4\u3059\u305F\u3081\u3001\u4E00\u5EA6\u3060\u3051\u6642\u9593\u304C\u304B\u304B\u308A\u307E\u3059\u3002");
|
|
37
|
+
console.log(
|
|
38
|
+
"\u6CE8\u610F: \u904E\u53BB\u306B\u672A\u8A08\u4E0A\u3060\u3063\u305F\u5206(\u4F8B: \u65E7\u30D0\u30FC\u30B8\u30E7\u30F3\u3067\u8A08\u4E0A\u3057\u3066\u3044\u306A\u304B\u3063\u305F Codex \u30B5\u30D6\u30A8\u30FC\u30B8\u30A7\u30F3\u30C8\u5206)\u3082\u65B0\u898F\u306B\u53D6\u308A\u8FBC\u307E\u308C\u308B\u305F\u3081\u3001\u5C65\u6B74\u7DCF\u984D\u30FB\u6708\u4E88\u7B97\u306E\u6D88\u5316\u304C\u5897\u3048\u308B\u3053\u3068\u304C\u3042\u308A\u307E\u3059\u3002"
|
|
39
|
+
);
|
|
37
40
|
return 0;
|
|
38
41
|
}
|
|
39
42
|
export {
|
|
@@ -2,20 +2,21 @@
|
|
|
2
2
|
import {
|
|
3
3
|
notifyIngestSummary,
|
|
4
4
|
runIngest
|
|
5
|
-
} from "./chunk-
|
|
6
|
-
import "./chunk-
|
|
7
|
-
import "./chunk-
|
|
8
|
-
import "./chunk-
|
|
5
|
+
} from "./chunk-XXXGWLTS.js";
|
|
6
|
+
import "./chunk-2XOKH54N.js";
|
|
7
|
+
import "./chunk-SKX5EMST.js";
|
|
8
|
+
import "./chunk-GAOGTALW.js";
|
|
9
9
|
import "./chunk-Q45AAPJY.js";
|
|
10
|
-
import "./chunk-
|
|
10
|
+
import "./chunk-6GWPAYJQ.js";
|
|
11
11
|
import "./chunk-3M5UQK76.js";
|
|
12
12
|
import "./chunk-PXMXEFM7.js";
|
|
13
13
|
import "./chunk-6IVSZ3S4.js";
|
|
14
14
|
import "./chunk-DGXUSPS4.js";
|
|
15
15
|
import {
|
|
16
16
|
formatJPY,
|
|
17
|
+
formatTokens,
|
|
17
18
|
formatUSD
|
|
18
|
-
} from "./chunk-
|
|
19
|
+
} from "./chunk-OHTPBABH.js";
|
|
19
20
|
import {
|
|
20
21
|
readConfig
|
|
21
22
|
} from "./chunk-WONMZ466.js";
|
|
@@ -58,6 +59,8 @@ async function runScan(argv) {
|
|
|
58
59
|
failures: result.failures,
|
|
59
60
|
totalUSD: result.totalUSD,
|
|
60
61
|
totalJPY: result.totalJPY,
|
|
62
|
+
totalTokens: result.totalTokens,
|
|
63
|
+
cacheTokens: result.cacheTokens,
|
|
61
64
|
bySurface: result.bySurface
|
|
62
65
|
},
|
|
63
66
|
null,
|
|
@@ -73,7 +76,11 @@ async function runScan(argv) {
|
|
|
73
76
|
if (result.records.length === 0) {
|
|
74
77
|
console.log("\u65B0\u898F\u53D6\u308A\u8FBC\u307F\u306F\u3042\u308A\u307E\u305B\u3093\u3067\u3057\u305F");
|
|
75
78
|
} else {
|
|
76
|
-
|
|
79
|
+
const cachePct = result.totalTokens > 0 ? Math.round(result.cacheTokens / result.totalTokens * 100) : 0;
|
|
80
|
+
const tokensPart = result.totalTokens > 0 ? `\u3001\u8A08 ${formatTokens(result.totalTokens)} tokens(cache ${cachePct}%)` : "";
|
|
81
|
+
console.log(
|
|
82
|
+
`\u53D6\u308A\u8FBC\u307F: ${result.records.length} \u30BF\u30FC\u30F3\u3001\u5408\u8A08 ${formatUSD(result.totalUSD)}(${formatJPY(result.totalJPY)})${tokensPart}`
|
|
83
|
+
);
|
|
77
84
|
const bySurface = Object.entries(result.bySurface).sort((a, b) => (b[1]?.usd ?? 0) - (a[1]?.usd ?? 0));
|
|
78
85
|
for (const [surface, v] of bySurface) {
|
|
79
86
|
if (!v) continue;
|
|
@@ -4,11 +4,11 @@ import {
|
|
|
4
4
|
matchesMarker,
|
|
5
5
|
runInit,
|
|
6
6
|
runUninstall
|
|
7
|
-
} from "./chunk-
|
|
8
|
-
import "./chunk-
|
|
7
|
+
} from "./chunk-XT3KWNWI.js";
|
|
8
|
+
import "./chunk-2XOKH54N.js";
|
|
9
9
|
import "./chunk-Q45AAPJY.js";
|
|
10
10
|
import "./chunk-DGXUSPS4.js";
|
|
11
|
-
import "./chunk-
|
|
11
|
+
import "./chunk-OHTPBABH.js";
|
|
12
12
|
import "./chunk-WONMZ466.js";
|
|
13
13
|
export {
|
|
14
14
|
maskWebhookUrl,
|
|
@@ -1,20 +1,22 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
attachSubagentGroups,
|
|
4
|
+
codexChildDraftToRecord,
|
|
4
5
|
runSweep,
|
|
5
6
|
splitIntoTurnDrafts
|
|
6
|
-
} from "./chunk-
|
|
7
|
-
import "./chunk-
|
|
7
|
+
} from "./chunk-SKX5EMST.js";
|
|
8
|
+
import "./chunk-GAOGTALW.js";
|
|
8
9
|
import "./chunk-Q45AAPJY.js";
|
|
9
|
-
import "./chunk-
|
|
10
|
+
import "./chunk-6GWPAYJQ.js";
|
|
10
11
|
import "./chunk-3M5UQK76.js";
|
|
11
12
|
import "./chunk-PXMXEFM7.js";
|
|
12
13
|
import "./chunk-6IVSZ3S4.js";
|
|
13
14
|
import "./chunk-DGXUSPS4.js";
|
|
14
|
-
import "./chunk-
|
|
15
|
+
import "./chunk-OHTPBABH.js";
|
|
15
16
|
import "./chunk-WONMZ466.js";
|
|
16
17
|
export {
|
|
17
18
|
attachSubagentGroups,
|
|
19
|
+
codexChildDraftToRecord,
|
|
18
20
|
runSweep,
|
|
19
21
|
splitIntoTurnDrafts
|
|
20
22
|
};
|
|
@@ -2,15 +2,15 @@
|
|
|
2
2
|
import {
|
|
3
3
|
notifyIngestSummary,
|
|
4
4
|
runIngest
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-XXXGWLTS.js";
|
|
6
6
|
import {
|
|
7
7
|
notifyOS,
|
|
8
8
|
notifySlack
|
|
9
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-2XOKH54N.js";
|
|
10
10
|
import {
|
|
11
11
|
collectSubagentUsage,
|
|
12
12
|
normalizeCodexOriginator
|
|
13
|
-
} from "./chunk-
|
|
13
|
+
} from "./chunk-SKX5EMST.js";
|
|
14
14
|
import {
|
|
15
15
|
aggregateCodexTurn,
|
|
16
16
|
aggregateNewTurn,
|
|
@@ -22,14 +22,14 @@ import {
|
|
|
22
22
|
getUsdJpy,
|
|
23
23
|
messageKeyFilterOf,
|
|
24
24
|
setCountedCalls
|
|
25
|
-
} from "./chunk-
|
|
25
|
+
} from "./chunk-GAOGTALW.js";
|
|
26
26
|
import {
|
|
27
27
|
computeCost,
|
|
28
28
|
loadPriceTable
|
|
29
29
|
} from "./chunk-Q45AAPJY.js";
|
|
30
30
|
import {
|
|
31
31
|
writeDashboardHtml
|
|
32
|
-
} from "./chunk-
|
|
32
|
+
} from "./chunk-6GWPAYJQ.js";
|
|
33
33
|
import {
|
|
34
34
|
isFullDashboardDue,
|
|
35
35
|
makeFullDashboardState,
|
|
@@ -40,7 +40,7 @@ import {
|
|
|
40
40
|
} from "./chunk-PXMXEFM7.js";
|
|
41
41
|
import "./chunk-6IVSZ3S4.js";
|
|
42
42
|
import "./chunk-DGXUSPS4.js";
|
|
43
|
-
import "./chunk-
|
|
43
|
+
import "./chunk-OHTPBABH.js";
|
|
44
44
|
import {
|
|
45
45
|
appendTurn,
|
|
46
46
|
clearPendingAppend,
|
package/package.json
CHANGED