ccusage 12.3.2 → 13.0.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/LICENSE +2 -0
- package/README.md +11 -2
- package/dist/calculate-cost.d.ts +2 -2
- package/dist/calculate-cost.js +2 -1
- package/dist/{data-loader-i0_91kbD.js → data-loader-B8gFJPfi.js} +46 -50
- package/dist/{data-loader-CBwn9vk0.d.ts → data-loader-BrxITdVN.d.ts} +42 -42
- package/dist/data-loader.d.ts +2 -2
- package/dist/data-loader.js +4 -3
- package/dist/{debug-DUZvOm08.js → debug-CL2Shx1n.js} +6 -11
- package/dist/debug.js +5 -4
- package/dist/index.js +16 -31
- package/dist/{logger-BfzGx5lS.js → logger-B4PJ298G.js} +2 -2
- package/dist/logger.js +1 -1
- package/dist/{mcp-Bx-_DNLG.js → mcp-Bw62xMEM.js} +4 -3
- package/dist/mcp.d.ts +2 -2
- package/dist/mcp.js +5 -4
- package/dist/{pricing-fetcher-BkOpRIdx.d.ts → pricing-fetcher-A6FC8DhM.d.ts} +1 -0
- package/dist/pricing-fetcher-Cx71zrV9.js +365 -0
- package/dist/pricing-fetcher.d.ts +1 -1
- package/dist/pricing-fetcher.js +3 -2
- package/dist/{pricing-fetcher-mFPZYGXl.js → types.internal-CX7kpidj.js} +19 -312
- package/package.json +1 -1
- /package/dist/{calculate-cost-D3IraeGW.js → calculate-cost-CoS7we68.js} +0 -0
- /package/dist/{prompt-E8j7mEMw.js → prompt-j5YimnLx.js} +0 -0
package/LICENSE
CHANGED
|
@@ -2,6 +2,8 @@ MIT License
|
|
|
2
2
|
|
|
3
3
|
Copyright (c) 2025 ryoppippi
|
|
4
4
|
|
|
5
|
+
Logo and brand assets created by nyatinte are also licensed under MIT License.
|
|
6
|
+
|
|
5
7
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
8
|
of this software and associated documentation files (the "Software"), to deal
|
|
7
9
|
in the Software without restriction, including without limitation the rights
|
package/README.md
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
# ccusage
|
|
2
2
|
|
|
3
|
-
>
|
|
3
|
+
<div align="center">
|
|
4
|
+
<img src="docs/logo.png" alt="ccusage logo" width="256" height="256">
|
|
5
|
+
</div>
|
|
4
6
|
|
|
5
7
|
[](https://npmjs.com/package/ccusage)
|
|
6
8
|
[](https://tanstack.com/stats/npm?packageGroups=%5B%7B%22packages%22:%5B%7B%22name%22:%22ccusage%22%7D%5D%7D%5D&range=30-days&transform=none&binType=daily&showDataMode=all&height=400)
|
|
@@ -12,6 +14,8 @@
|
|
|
12
14
|
<img src="https://github.com/ryoppippi/ccusage/blob/main/docs/screenshot.png?raw=true">
|
|
13
15
|
</div>
|
|
14
16
|
|
|
17
|
+
> **ccusage(claude-code-usage)**
|
|
18
|
+
|
|
15
19
|
A CLI tool for analyzing Claude Code usage from local JSONL files.
|
|
16
20
|
|
|
17
21
|
Inspired by [this article](https://note.com/milliondev/n/n1d018da2d769) about tracking Claude Code usage costs.
|
|
@@ -19,7 +23,7 @@ Inspired by [this article](https://note.com/milliondev/n/n1d018da2d769) about tr
|
|
|
19
23
|
## What is `ccusage` (by NotebookLM)
|
|
20
24
|
|
|
21
25
|
<details>
|
|
22
|
-
<summary>
|
|
26
|
+
<summary>Podcast</summary>
|
|
23
27
|
|
|
24
28
|
# English
|
|
25
29
|
|
|
@@ -477,6 +481,10 @@ With `--breakdown` flag:
|
|
|
477
481
|
|
|
478
482
|
MIT
|
|
479
483
|
|
|
484
|
+
This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
|
|
485
|
+
|
|
486
|
+
The logo and brand assets are also licensed under the MIT License. Created by [@nyatinte](https://github.com/nyatinte).
|
|
487
|
+
|
|
480
488
|
## Author
|
|
481
489
|
|
|
482
490
|
[@ryoppippi](https://github.com/ryoppippi)
|
|
@@ -492,6 +500,7 @@ While the original approach uses DuckDB for analysis, this tool provides a more
|
|
|
492
500
|
some projects use `ccusage` internally and provide additional features:
|
|
493
501
|
|
|
494
502
|
- [claude-usage-tracker-for-mac](https://github.com/penicillin0/claude-usage-tracker-for-mac) – macOS menu bar app to visualize Claude Code usage costs by [@penicillin0](https://github.com/penicillin0).
|
|
503
|
+
- [ccusage Raycast Extension](https://www.raycast.com/nyatinte/ccusage) – Raycast extension to view Claude Code usage reports in Raycast by [@nyatinte](https://github.com/nyatinte).
|
|
495
504
|
|
|
496
505
|
## Acknowledgments
|
|
497
506
|
|
package/dist/calculate-cost.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import "./pricing-fetcher-
|
|
2
|
-
import { DailyUsage, MonthlyUsage, SessionUsage } from "./data-loader-
|
|
1
|
+
import "./pricing-fetcher-A6FC8DhM.js";
|
|
2
|
+
import { DailyUsage, MonthlyUsage, SessionUsage } from "./data-loader-BrxITdVN.js";
|
|
3
3
|
|
|
4
4
|
//#region src/calculate-cost.d.ts
|
|
5
5
|
/**
|
package/dist/calculate-cost.js
CHANGED
|
@@ -1,2 +1,3 @@
|
|
|
1
|
-
import
|
|
1
|
+
import "./types.internal-CX7kpidj.js";
|
|
2
|
+
import { calculateTotals, createTotalsObject, getTotalTokens } from "./calculate-cost-CoS7we68.js";
|
|
2
3
|
export { calculateTotals, createTotalsObject, getTotalTokens };
|
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
1
|
+
import { CLAUDE_PROJECTS_DIR_NAME, DEFAULT_CLAUDE_CODE_PATH, DEFAULT_RECENT_DAYS, PricingFetcher, USAGE_DATA_GLOB_PATTERN, USER_HOME_DIR, __commonJSMin, __require, __toESM, require_usingCtx } from "./pricing-fetcher-Cx71zrV9.js";
|
|
2
|
+
import { activityDateSchema, arrayType, createDailyDate, createMonthlyDate, createProjectPath, createSessionId, dailyDateSchema, isoTimestampSchema, messageIdSchema, modelNameSchema, monthlyDateSchema, numberType, objectType, projectPathSchema, requestIdSchema, sessionIdSchema, versionSchema } from "./types.internal-CX7kpidj.js";
|
|
3
|
+
import { logger } from "./logger-B4PJ298G.js";
|
|
3
4
|
import a, { readFile } from "node:fs/promises";
|
|
4
5
|
import F, { homedir } from "node:os";
|
|
5
6
|
import path, { posix } from "node:path";
|
|
@@ -244,6 +245,9 @@ function groupBy(arr, getKeyFromItem) {
|
|
|
244
245
|
}
|
|
245
246
|
return result;
|
|
246
247
|
}
|
|
248
|
+
function uniq(arr) {
|
|
249
|
+
return Array.from(new Set(arr));
|
|
250
|
+
}
|
|
247
251
|
var castComparer = function(comparer) {
|
|
248
252
|
return function(a$1, b$1, order) {
|
|
249
253
|
return comparer(a$1, b$1, order) * order;
|
|
@@ -3056,10 +3060,6 @@ async function glob(patternsOrOptions, options) {
|
|
|
3056
3060
|
*/
|
|
3057
3061
|
const DEFAULT_SESSION_DURATION_HOURS = 5;
|
|
3058
3062
|
/**
|
|
3059
|
-
* Default number of recent days to include when filtering blocks
|
|
3060
|
-
*/
|
|
3061
|
-
const DEFAULT_RECENT_DAYS = 3;
|
|
3062
|
-
/**
|
|
3063
3063
|
* Identifies and creates session blocks from usage entries
|
|
3064
3064
|
* Groups entries into time-based blocks (typically 5-hour periods) with gap detection
|
|
3065
3065
|
* @param entries - Array of usage entries to process
|
|
@@ -3123,14 +3123,14 @@ function createBlock(startTime, entries, now, sessionDurationMs) {
|
|
|
3123
3123
|
cacheReadInputTokens: 0
|
|
3124
3124
|
};
|
|
3125
3125
|
let costUSD = 0;
|
|
3126
|
-
const
|
|
3126
|
+
const models = [];
|
|
3127
3127
|
for (const entry of entries) {
|
|
3128
3128
|
tokenCounts.inputTokens += entry.usage.inputTokens;
|
|
3129
3129
|
tokenCounts.outputTokens += entry.usage.outputTokens;
|
|
3130
3130
|
tokenCounts.cacheCreationInputTokens += entry.usage.cacheCreationInputTokens;
|
|
3131
3131
|
tokenCounts.cacheReadInputTokens += entry.usage.cacheReadInputTokens;
|
|
3132
3132
|
costUSD += entry.costUSD ?? 0;
|
|
3133
|
-
|
|
3133
|
+
models.push(entry.model);
|
|
3134
3134
|
}
|
|
3135
3135
|
return {
|
|
3136
3136
|
id: startTime.toISOString(),
|
|
@@ -3141,7 +3141,7 @@ function createBlock(startTime, entries, now, sessionDurationMs) {
|
|
|
3141
3141
|
entries,
|
|
3142
3142
|
tokenCounts,
|
|
3143
3143
|
costUSD,
|
|
3144
|
-
models:
|
|
3144
|
+
models: uniq(models)
|
|
3145
3145
|
};
|
|
3146
3146
|
}
|
|
3147
3147
|
/**
|
|
@@ -3233,22 +3233,18 @@ function filterRecentBlocks(blocks, days = DEFAULT_RECENT_DAYS) {
|
|
|
3233
3233
|
}
|
|
3234
3234
|
var import_usingCtx = __toESM(require_usingCtx(), 1);
|
|
3235
3235
|
/**
|
|
3236
|
-
* Default Claude data directory path (~/.claude)
|
|
3237
|
-
*/
|
|
3238
|
-
const DEFAULT_CLAUDE_CODE_PATH = path.join(homedir(), ".claude");
|
|
3239
|
-
/**
|
|
3240
3236
|
* Default path for Claude data directory
|
|
3241
3237
|
* Uses environment variable CLAUDE_CONFIG_DIR if set, otherwise defaults to ~/.claude
|
|
3242
3238
|
*/
|
|
3243
3239
|
function getDefaultClaudePath() {
|
|
3244
3240
|
const envClaudeCodePath = (process$1.env.CLAUDE_CONFIG_DIR ?? "").trim();
|
|
3245
|
-
if (envClaudeCodePath === "") return DEFAULT_CLAUDE_CODE_PATH;
|
|
3241
|
+
if (envClaudeCodePath === "") return path.join(USER_HOME_DIR, DEFAULT_CLAUDE_CODE_PATH);
|
|
3246
3242
|
if (!isDirectorySync(envClaudeCodePath)) throw new Error(`CLAUDE_CONFIG_DIR path is not a valid directory: ${envClaudeCodePath}.
|
|
3247
|
-
Please set CLAUDE_CONFIG_DIR to a valid directory path, or ensure ${DEFAULT_CLAUDE_CODE_PATH} exists.
|
|
3243
|
+
Please set CLAUDE_CONFIG_DIR to a valid directory path, or ensure ${path.join(USER_HOME_DIR, DEFAULT_CLAUDE_CODE_PATH)} exists.
|
|
3248
3244
|
`.trim());
|
|
3249
|
-
const claudeCodeProjectsPath = path.join(envClaudeCodePath,
|
|
3245
|
+
const claudeCodeProjectsPath = path.join(envClaudeCodePath, CLAUDE_PROJECTS_DIR_NAME);
|
|
3250
3246
|
if (!isDirectorySync(claudeCodeProjectsPath)) throw new Error(`Claude data directory does not exist: ${claudeCodeProjectsPath}.
|
|
3251
|
-
Please set CLAUDE_CONFIG_DIR to a valid path, or ensure ${DEFAULT_CLAUDE_CODE_PATH} exists.
|
|
3247
|
+
Please set CLAUDE_CONFIG_DIR to a valid path, or ensure ${path.join(USER_HOME_DIR, DEFAULT_CLAUDE_CODE_PATH)} exists.
|
|
3252
3248
|
`.trim());
|
|
3253
3249
|
return envClaudeCodePath;
|
|
3254
3250
|
}
|
|
@@ -3256,8 +3252,8 @@ Please set CLAUDE_CONFIG_DIR to a valid path, or ensure ${DEFAULT_CLAUDE_CODE_PA
|
|
|
3256
3252
|
* Zod schema for validating Claude usage data from JSONL files
|
|
3257
3253
|
*/
|
|
3258
3254
|
const usageDataSchema = objectType({
|
|
3259
|
-
timestamp:
|
|
3260
|
-
version:
|
|
3255
|
+
timestamp: isoTimestampSchema,
|
|
3256
|
+
version: versionSchema.optional(),
|
|
3261
3257
|
message: objectType({
|
|
3262
3258
|
usage: objectType({
|
|
3263
3259
|
input_tokens: numberType(),
|
|
@@ -3265,17 +3261,17 @@ const usageDataSchema = objectType({
|
|
|
3265
3261
|
cache_creation_input_tokens: numberType().optional(),
|
|
3266
3262
|
cache_read_input_tokens: numberType().optional()
|
|
3267
3263
|
}),
|
|
3268
|
-
model:
|
|
3269
|
-
id:
|
|
3264
|
+
model: modelNameSchema.optional(),
|
|
3265
|
+
id: messageIdSchema.optional()
|
|
3270
3266
|
}),
|
|
3271
3267
|
costUSD: numberType().optional(),
|
|
3272
|
-
requestId:
|
|
3268
|
+
requestId: requestIdSchema.optional()
|
|
3273
3269
|
});
|
|
3274
3270
|
/**
|
|
3275
3271
|
* Zod schema for model-specific usage breakdown data
|
|
3276
3272
|
*/
|
|
3277
3273
|
const modelBreakdownSchema = objectType({
|
|
3278
|
-
modelName:
|
|
3274
|
+
modelName: modelNameSchema,
|
|
3279
3275
|
inputTokens: numberType(),
|
|
3280
3276
|
outputTokens: numberType(),
|
|
3281
3277
|
cacheCreationTokens: numberType(),
|
|
@@ -3286,42 +3282,42 @@ const modelBreakdownSchema = objectType({
|
|
|
3286
3282
|
* Zod schema for daily usage aggregation data
|
|
3287
3283
|
*/
|
|
3288
3284
|
const dailyUsageSchema = objectType({
|
|
3289
|
-
date:
|
|
3285
|
+
date: dailyDateSchema,
|
|
3290
3286
|
inputTokens: numberType(),
|
|
3291
3287
|
outputTokens: numberType(),
|
|
3292
3288
|
cacheCreationTokens: numberType(),
|
|
3293
3289
|
cacheReadTokens: numberType(),
|
|
3294
3290
|
totalCost: numberType(),
|
|
3295
|
-
modelsUsed: arrayType(
|
|
3291
|
+
modelsUsed: arrayType(modelNameSchema),
|
|
3296
3292
|
modelBreakdowns: arrayType(modelBreakdownSchema)
|
|
3297
3293
|
});
|
|
3298
3294
|
/**
|
|
3299
3295
|
* Zod schema for session-based usage aggregation data
|
|
3300
3296
|
*/
|
|
3301
3297
|
const sessionUsageSchema = objectType({
|
|
3302
|
-
sessionId:
|
|
3303
|
-
projectPath:
|
|
3298
|
+
sessionId: sessionIdSchema,
|
|
3299
|
+
projectPath: projectPathSchema,
|
|
3304
3300
|
inputTokens: numberType(),
|
|
3305
3301
|
outputTokens: numberType(),
|
|
3306
3302
|
cacheCreationTokens: numberType(),
|
|
3307
3303
|
cacheReadTokens: numberType(),
|
|
3308
3304
|
totalCost: numberType(),
|
|
3309
|
-
lastActivity:
|
|
3310
|
-
versions: arrayType(
|
|
3311
|
-
modelsUsed: arrayType(
|
|
3305
|
+
lastActivity: activityDateSchema,
|
|
3306
|
+
versions: arrayType(versionSchema),
|
|
3307
|
+
modelsUsed: arrayType(modelNameSchema),
|
|
3312
3308
|
modelBreakdowns: arrayType(modelBreakdownSchema)
|
|
3313
3309
|
});
|
|
3314
3310
|
/**
|
|
3315
3311
|
* Zod schema for monthly usage aggregation data
|
|
3316
3312
|
*/
|
|
3317
3313
|
const monthlyUsageSchema = objectType({
|
|
3318
|
-
month:
|
|
3314
|
+
month: monthlyDateSchema,
|
|
3319
3315
|
inputTokens: numberType(),
|
|
3320
3316
|
outputTokens: numberType(),
|
|
3321
3317
|
cacheCreationTokens: numberType(),
|
|
3322
3318
|
cacheReadTokens: numberType(),
|
|
3323
3319
|
totalCost: numberType(),
|
|
3324
|
-
modelsUsed: arrayType(
|
|
3320
|
+
modelsUsed: arrayType(modelNameSchema),
|
|
3325
3321
|
modelBreakdowns: arrayType(modelBreakdownSchema)
|
|
3326
3322
|
});
|
|
3327
3323
|
/**
|
|
@@ -3439,7 +3435,7 @@ function markAsProcessed(uniqueHash, processedHashes) {
|
|
|
3439
3435
|
* Extracts unique models from entries, excluding synthetic model
|
|
3440
3436
|
*/
|
|
3441
3437
|
function extractUniqueModels(entries, getModel) {
|
|
3442
|
-
return
|
|
3438
|
+
return uniq(entries.map(getModel).filter((m$1) => m$1 != null && m$1 !== "<synthetic>"));
|
|
3443
3439
|
}
|
|
3444
3440
|
/**
|
|
3445
3441
|
* Formats a date string to YYYY-MM-DD format
|
|
@@ -3564,8 +3560,8 @@ async function loadDailyUsageData(options) {
|
|
|
3564
3560
|
try {
|
|
3565
3561
|
var _usingCtx = (0, import_usingCtx.default)();
|
|
3566
3562
|
const claudePath = options?.claudePath ?? getDefaultClaudePath();
|
|
3567
|
-
const claudeDir = path.join(claudePath,
|
|
3568
|
-
const files = await glob([
|
|
3563
|
+
const claudeDir = path.join(claudePath, CLAUDE_PROJECTS_DIR_NAME);
|
|
3564
|
+
const files = await glob([USAGE_DATA_GLOB_PATTERN], {
|
|
3569
3565
|
cwd: claudeDir,
|
|
3570
3566
|
absolute: true
|
|
3571
3567
|
});
|
|
@@ -3604,7 +3600,7 @@ async function loadDailyUsageData(options) {
|
|
|
3604
3600
|
const totals = calculateTotals(entries, (entry) => entry.data.message.usage, (entry) => entry.cost);
|
|
3605
3601
|
const modelsUsed = extractUniqueModels(entries, (e) => e.model);
|
|
3606
3602
|
return {
|
|
3607
|
-
date,
|
|
3603
|
+
date: createDailyDate(date),
|
|
3608
3604
|
...totals,
|
|
3609
3605
|
modelsUsed,
|
|
3610
3606
|
modelBreakdowns
|
|
@@ -3628,8 +3624,8 @@ async function loadSessionData(options) {
|
|
|
3628
3624
|
try {
|
|
3629
3625
|
var _usingCtx3 = (0, import_usingCtx.default)();
|
|
3630
3626
|
const claudePath = options?.claudePath ?? getDefaultClaudePath();
|
|
3631
|
-
const claudeDir = path.join(claudePath,
|
|
3632
|
-
const files = await glob([
|
|
3627
|
+
const claudeDir = path.join(claudePath, CLAUDE_PROJECTS_DIR_NAME);
|
|
3628
|
+
const files = await glob([USAGE_DATA_GLOB_PATTERN], {
|
|
3633
3629
|
cwd: claudeDir,
|
|
3634
3630
|
absolute: true
|
|
3635
3631
|
});
|
|
@@ -3672,18 +3668,18 @@ async function loadSessionData(options) {
|
|
|
3672
3668
|
const results = Object.entries(groupedBySessions).map(([_, entries]) => {
|
|
3673
3669
|
if (entries == null) return void 0;
|
|
3674
3670
|
const latestEntry = entries.reduce((latest, current) => current.timestamp > latest.timestamp ? current : latest);
|
|
3675
|
-
const
|
|
3676
|
-
for (const entry of entries) if (entry.data.version != null)
|
|
3671
|
+
const versions = [];
|
|
3672
|
+
for (const entry of entries) if (entry.data.version != null) versions.push(entry.data.version);
|
|
3677
3673
|
const modelAggregates = aggregateByModel(entries, (entry) => entry.model, (entry) => entry.data.message.usage, (entry) => entry.cost);
|
|
3678
3674
|
const modelBreakdowns = createModelBreakdowns(modelAggregates);
|
|
3679
3675
|
const totals = calculateTotals(entries, (entry) => entry.data.message.usage, (entry) => entry.cost);
|
|
3680
3676
|
const modelsUsed = extractUniqueModels(entries, (e) => e.model);
|
|
3681
3677
|
return {
|
|
3682
|
-
sessionId: latestEntry.sessionId,
|
|
3683
|
-
projectPath: latestEntry.projectPath,
|
|
3678
|
+
sessionId: createSessionId(latestEntry.sessionId),
|
|
3679
|
+
projectPath: createProjectPath(latestEntry.projectPath),
|
|
3684
3680
|
...totals,
|
|
3685
3681
|
lastActivity: formatDate(latestEntry.timestamp),
|
|
3686
|
-
versions:
|
|
3682
|
+
versions: uniq(versions).sort(),
|
|
3687
3683
|
modelsUsed,
|
|
3688
3684
|
modelBreakdowns
|
|
3689
3685
|
};
|
|
@@ -3711,8 +3707,8 @@ async function loadMonthlyUsageData(options) {
|
|
|
3711
3707
|
const allBreakdowns = dailyEntries.flatMap((daily) => daily.modelBreakdowns);
|
|
3712
3708
|
const modelAggregates = aggregateModelBreakdowns(allBreakdowns);
|
|
3713
3709
|
const modelBreakdowns = createModelBreakdowns(modelAggregates);
|
|
3714
|
-
const
|
|
3715
|
-
for (const data of dailyEntries) for (const model of data.modelsUsed) if (model !== "<synthetic>")
|
|
3710
|
+
const models = [];
|
|
3711
|
+
for (const data of dailyEntries) for (const model of data.modelsUsed) if (model !== "<synthetic>") models.push(model);
|
|
3716
3712
|
let totalInputTokens = 0;
|
|
3717
3713
|
let totalOutputTokens = 0;
|
|
3718
3714
|
let totalCacheCreationTokens = 0;
|
|
@@ -3726,13 +3722,13 @@ async function loadMonthlyUsageData(options) {
|
|
|
3726
3722
|
totalCost += daily.totalCost;
|
|
3727
3723
|
}
|
|
3728
3724
|
const monthlyUsage = {
|
|
3729
|
-
month,
|
|
3725
|
+
month: createMonthlyDate(month),
|
|
3730
3726
|
inputTokens: totalInputTokens,
|
|
3731
3727
|
outputTokens: totalOutputTokens,
|
|
3732
3728
|
cacheCreationTokens: totalCacheCreationTokens,
|
|
3733
3729
|
cacheReadTokens: totalCacheReadTokens,
|
|
3734
3730
|
totalCost,
|
|
3735
|
-
modelsUsed:
|
|
3731
|
+
modelsUsed: uniq(models),
|
|
3736
3732
|
modelBreakdowns
|
|
3737
3733
|
};
|
|
3738
3734
|
monthlyArray.push(monthlyUsage);
|
|
@@ -3749,8 +3745,8 @@ async function loadSessionBlockData(options) {
|
|
|
3749
3745
|
try {
|
|
3750
3746
|
var _usingCtx4 = (0, import_usingCtx.default)();
|
|
3751
3747
|
const claudePath = options?.claudePath ?? getDefaultClaudePath();
|
|
3752
|
-
const claudeDir = path.join(claudePath,
|
|
3753
|
-
const files = await glob([
|
|
3748
|
+
const claudeDir = path.join(claudePath, CLAUDE_PROJECTS_DIR_NAME);
|
|
3749
|
+
const files = await glob([USAGE_DATA_GLOB_PATTERN], {
|
|
3754
3750
|
cwd: claudeDir,
|
|
3755
3751
|
absolute: true
|
|
3756
3752
|
});
|
|
@@ -3802,4 +3798,4 @@ async function loadSessionBlockData(options) {
|
|
|
3802
3798
|
_usingCtx4.d();
|
|
3803
3799
|
}
|
|
3804
3800
|
}
|
|
3805
|
-
export { DEFAULT_SESSION_DURATION_HOURS, calculateBurnRate, calculateCostForEntry, createUniqueHash, dailyUsageSchema, filterRecentBlocks, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, glob, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, projectBlockUsage, sessionUsageSchema, sortFilesByTimestamp, usageDataSchema };
|
|
3801
|
+
export { DEFAULT_SESSION_DURATION_HOURS, calculateBurnRate, calculateCostForEntry, createUniqueHash, dailyUsageSchema, filterRecentBlocks, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, glob, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, projectBlockUsage, sessionUsageSchema, sortFilesByTimestamp, uniq, usageDataSchema };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { CostMode, PricingFetcher, SortOrder } from "./pricing-fetcher-
|
|
1
|
+
import { CostMode, PricingFetcher, SortOrder } from "./pricing-fetcher-A6FC8DhM.js";
|
|
2
2
|
import { z } from "zod";
|
|
3
3
|
|
|
4
4
|
//#region src/session-blocks.internal.d.ts
|
|
@@ -56,8 +56,8 @@ declare function getDefaultClaudePath(): string;
|
|
|
56
56
|
* Zod schema for validating Claude usage data from JSONL files
|
|
57
57
|
*/
|
|
58
58
|
declare const usageDataSchema: z.ZodObject<{
|
|
59
|
-
timestamp: z.ZodString
|
|
60
|
-
version: z.ZodOptional<z.ZodString
|
|
59
|
+
timestamp: z.ZodBranded<z.ZodString, "ISOTimestamp">;
|
|
60
|
+
version: z.ZodOptional<z.ZodBranded<z.ZodString, "Version">>;
|
|
61
61
|
message: z.ZodObject<{
|
|
62
62
|
usage: z.ZodObject<{
|
|
63
63
|
input_tokens: z.ZodNumber;
|
|
@@ -75,8 +75,8 @@ declare const usageDataSchema: z.ZodObject<{
|
|
|
75
75
|
cache_creation_input_tokens?: number | undefined;
|
|
76
76
|
cache_read_input_tokens?: number | undefined;
|
|
77
77
|
}>;
|
|
78
|
-
model: z.ZodOptional<z.ZodString
|
|
79
|
-
id: z.ZodOptional<z.ZodString
|
|
78
|
+
model: z.ZodOptional<z.ZodBranded<z.ZodString, "ModelName">>;
|
|
79
|
+
id: z.ZodOptional<z.ZodBranded<z.ZodString, "MessageId">>;
|
|
80
80
|
}, "strip", z.ZodTypeAny, {
|
|
81
81
|
usage: {
|
|
82
82
|
input_tokens: number;
|
|
@@ -84,8 +84,8 @@ declare const usageDataSchema: z.ZodObject<{
|
|
|
84
84
|
cache_creation_input_tokens?: number | undefined;
|
|
85
85
|
cache_read_input_tokens?: number | undefined;
|
|
86
86
|
};
|
|
87
|
-
model?: string | undefined;
|
|
88
|
-
id?: string | undefined;
|
|
87
|
+
model?: string & z.BRAND<"ModelName"> | undefined;
|
|
88
|
+
id?: string & z.BRAND<"MessageId"> | undefined;
|
|
89
89
|
}, {
|
|
90
90
|
usage: {
|
|
91
91
|
input_tokens: number;
|
|
@@ -97,10 +97,10 @@ declare const usageDataSchema: z.ZodObject<{
|
|
|
97
97
|
id?: string | undefined;
|
|
98
98
|
}>;
|
|
99
99
|
costUSD: z.ZodOptional<z.ZodNumber>;
|
|
100
|
-
requestId: z.ZodOptional<z.ZodString
|
|
100
|
+
requestId: z.ZodOptional<z.ZodBranded<z.ZodString, "RequestId">>;
|
|
101
101
|
}, "strip", z.ZodTypeAny, {
|
|
102
|
-
timestamp: string
|
|
103
|
-
version?: string | undefined;
|
|
102
|
+
timestamp: string & z.BRAND<"ISOTimestamp">;
|
|
103
|
+
version?: string & z.BRAND<"Version"> | undefined;
|
|
104
104
|
message: {
|
|
105
105
|
usage: {
|
|
106
106
|
input_tokens: number;
|
|
@@ -108,11 +108,11 @@ declare const usageDataSchema: z.ZodObject<{
|
|
|
108
108
|
cache_creation_input_tokens?: number | undefined;
|
|
109
109
|
cache_read_input_tokens?: number | undefined;
|
|
110
110
|
};
|
|
111
|
-
model?: string | undefined;
|
|
112
|
-
id?: string | undefined;
|
|
111
|
+
model?: string & z.BRAND<"ModelName"> | undefined;
|
|
112
|
+
id?: string & z.BRAND<"MessageId"> | undefined;
|
|
113
113
|
};
|
|
114
114
|
costUSD?: number | undefined;
|
|
115
|
-
requestId?: string | undefined;
|
|
115
|
+
requestId?: string & z.BRAND<"RequestId"> | undefined;
|
|
116
116
|
}, {
|
|
117
117
|
timestamp: string;
|
|
118
118
|
version?: string | undefined;
|
|
@@ -137,14 +137,14 @@ type UsageData = z.infer<typeof usageDataSchema>;
|
|
|
137
137
|
* Zod schema for model-specific usage breakdown data
|
|
138
138
|
*/
|
|
139
139
|
declare const modelBreakdownSchema: z.ZodObject<{
|
|
140
|
-
modelName: z.ZodString
|
|
140
|
+
modelName: z.ZodBranded<z.ZodString, "ModelName">;
|
|
141
141
|
inputTokens: z.ZodNumber;
|
|
142
142
|
outputTokens: z.ZodNumber;
|
|
143
143
|
cacheCreationTokens: z.ZodNumber;
|
|
144
144
|
cacheReadTokens: z.ZodNumber;
|
|
145
145
|
cost: z.ZodNumber;
|
|
146
146
|
}, "strip", z.ZodTypeAny, {
|
|
147
|
-
modelName: string
|
|
147
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
148
148
|
inputTokens: number;
|
|
149
149
|
outputTokens: number;
|
|
150
150
|
cacheCreationTokens: number;
|
|
@@ -166,22 +166,22 @@ type ModelBreakdown = z.infer<typeof modelBreakdownSchema>;
|
|
|
166
166
|
* Zod schema for daily usage aggregation data
|
|
167
167
|
*/
|
|
168
168
|
declare const dailyUsageSchema: z.ZodObject<{
|
|
169
|
-
date: z.ZodString
|
|
169
|
+
date: z.ZodBranded<z.ZodString, "DailyDate">;
|
|
170
170
|
inputTokens: z.ZodNumber;
|
|
171
171
|
outputTokens: z.ZodNumber;
|
|
172
172
|
cacheCreationTokens: z.ZodNumber;
|
|
173
173
|
cacheReadTokens: z.ZodNumber;
|
|
174
174
|
totalCost: z.ZodNumber;
|
|
175
|
-
modelsUsed: z.ZodArray<z.ZodString, "many">;
|
|
175
|
+
modelsUsed: z.ZodArray<z.ZodBranded<z.ZodString, "ModelName">, "many">;
|
|
176
176
|
modelBreakdowns: z.ZodArray<z.ZodObject<{
|
|
177
|
-
modelName: z.ZodString
|
|
177
|
+
modelName: z.ZodBranded<z.ZodString, "ModelName">;
|
|
178
178
|
inputTokens: z.ZodNumber;
|
|
179
179
|
outputTokens: z.ZodNumber;
|
|
180
180
|
cacheCreationTokens: z.ZodNumber;
|
|
181
181
|
cacheReadTokens: z.ZodNumber;
|
|
182
182
|
cost: z.ZodNumber;
|
|
183
183
|
}, "strip", z.ZodTypeAny, {
|
|
184
|
-
modelName: string
|
|
184
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
185
185
|
inputTokens: number;
|
|
186
186
|
outputTokens: number;
|
|
187
187
|
cacheCreationTokens: number;
|
|
@@ -196,15 +196,15 @@ declare const dailyUsageSchema: z.ZodObject<{
|
|
|
196
196
|
cost: number;
|
|
197
197
|
}>, "many">;
|
|
198
198
|
}, "strip", z.ZodTypeAny, {
|
|
199
|
-
date: string
|
|
199
|
+
date: string & z.BRAND<"DailyDate">;
|
|
200
200
|
inputTokens: number;
|
|
201
201
|
outputTokens: number;
|
|
202
202
|
cacheCreationTokens: number;
|
|
203
203
|
cacheReadTokens: number;
|
|
204
204
|
totalCost: number;
|
|
205
|
-
modelsUsed: string[];
|
|
205
|
+
modelsUsed: (string & z.BRAND<"ModelName">)[];
|
|
206
206
|
modelBreakdowns: {
|
|
207
|
-
modelName: string
|
|
207
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
208
208
|
inputTokens: number;
|
|
209
209
|
outputTokens: number;
|
|
210
210
|
cacheCreationTokens: number;
|
|
@@ -236,25 +236,25 @@ type DailyUsage = z.infer<typeof dailyUsageSchema>;
|
|
|
236
236
|
* Zod schema for session-based usage aggregation data
|
|
237
237
|
*/
|
|
238
238
|
declare const sessionUsageSchema: z.ZodObject<{
|
|
239
|
-
sessionId: z.ZodString
|
|
240
|
-
projectPath: z.ZodString
|
|
239
|
+
sessionId: z.ZodBranded<z.ZodString, "SessionId">;
|
|
240
|
+
projectPath: z.ZodBranded<z.ZodString, "ProjectPath">;
|
|
241
241
|
inputTokens: z.ZodNumber;
|
|
242
242
|
outputTokens: z.ZodNumber;
|
|
243
243
|
cacheCreationTokens: z.ZodNumber;
|
|
244
244
|
cacheReadTokens: z.ZodNumber;
|
|
245
245
|
totalCost: z.ZodNumber;
|
|
246
|
-
lastActivity: z.ZodString
|
|
247
|
-
versions: z.ZodArray<z.ZodString, "many">;
|
|
248
|
-
modelsUsed: z.ZodArray<z.ZodString, "many">;
|
|
246
|
+
lastActivity: z.ZodBranded<z.ZodString, "ActivityDate">;
|
|
247
|
+
versions: z.ZodArray<z.ZodBranded<z.ZodString, "Version">, "many">;
|
|
248
|
+
modelsUsed: z.ZodArray<z.ZodBranded<z.ZodString, "ModelName">, "many">;
|
|
249
249
|
modelBreakdowns: z.ZodArray<z.ZodObject<{
|
|
250
|
-
modelName: z.ZodString
|
|
250
|
+
modelName: z.ZodBranded<z.ZodString, "ModelName">;
|
|
251
251
|
inputTokens: z.ZodNumber;
|
|
252
252
|
outputTokens: z.ZodNumber;
|
|
253
253
|
cacheCreationTokens: z.ZodNumber;
|
|
254
254
|
cacheReadTokens: z.ZodNumber;
|
|
255
255
|
cost: z.ZodNumber;
|
|
256
256
|
}, "strip", z.ZodTypeAny, {
|
|
257
|
-
modelName: string
|
|
257
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
258
258
|
inputTokens: number;
|
|
259
259
|
outputTokens: number;
|
|
260
260
|
cacheCreationTokens: number;
|
|
@@ -269,18 +269,18 @@ declare const sessionUsageSchema: z.ZodObject<{
|
|
|
269
269
|
cost: number;
|
|
270
270
|
}>, "many">;
|
|
271
271
|
}, "strip", z.ZodTypeAny, {
|
|
272
|
-
sessionId: string
|
|
273
|
-
projectPath: string
|
|
272
|
+
sessionId: string & z.BRAND<"SessionId">;
|
|
273
|
+
projectPath: string & z.BRAND<"ProjectPath">;
|
|
274
274
|
inputTokens: number;
|
|
275
275
|
outputTokens: number;
|
|
276
276
|
cacheCreationTokens: number;
|
|
277
277
|
cacheReadTokens: number;
|
|
278
278
|
totalCost: number;
|
|
279
|
-
lastActivity: string
|
|
280
|
-
versions: string[];
|
|
281
|
-
modelsUsed: string[];
|
|
279
|
+
lastActivity: string & z.BRAND<"ActivityDate">;
|
|
280
|
+
versions: (string & z.BRAND<"Version">)[];
|
|
281
|
+
modelsUsed: (string & z.BRAND<"ModelName">)[];
|
|
282
282
|
modelBreakdowns: {
|
|
283
|
-
modelName: string
|
|
283
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
284
284
|
inputTokens: number;
|
|
285
285
|
outputTokens: number;
|
|
286
286
|
cacheCreationTokens: number;
|
|
@@ -315,22 +315,22 @@ type SessionUsage = z.infer<typeof sessionUsageSchema>;
|
|
|
315
315
|
* Zod schema for monthly usage aggregation data
|
|
316
316
|
*/
|
|
317
317
|
declare const monthlyUsageSchema: z.ZodObject<{
|
|
318
|
-
month: z.ZodString
|
|
318
|
+
month: z.ZodBranded<z.ZodString, "MonthlyDate">;
|
|
319
319
|
inputTokens: z.ZodNumber;
|
|
320
320
|
outputTokens: z.ZodNumber;
|
|
321
321
|
cacheCreationTokens: z.ZodNumber;
|
|
322
322
|
cacheReadTokens: z.ZodNumber;
|
|
323
323
|
totalCost: z.ZodNumber;
|
|
324
|
-
modelsUsed: z.ZodArray<z.ZodString, "many">;
|
|
324
|
+
modelsUsed: z.ZodArray<z.ZodBranded<z.ZodString, "ModelName">, "many">;
|
|
325
325
|
modelBreakdowns: z.ZodArray<z.ZodObject<{
|
|
326
|
-
modelName: z.ZodString
|
|
326
|
+
modelName: z.ZodBranded<z.ZodString, "ModelName">;
|
|
327
327
|
inputTokens: z.ZodNumber;
|
|
328
328
|
outputTokens: z.ZodNumber;
|
|
329
329
|
cacheCreationTokens: z.ZodNumber;
|
|
330
330
|
cacheReadTokens: z.ZodNumber;
|
|
331
331
|
cost: z.ZodNumber;
|
|
332
332
|
}, "strip", z.ZodTypeAny, {
|
|
333
|
-
modelName: string
|
|
333
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
334
334
|
inputTokens: number;
|
|
335
335
|
outputTokens: number;
|
|
336
336
|
cacheCreationTokens: number;
|
|
@@ -345,15 +345,15 @@ declare const monthlyUsageSchema: z.ZodObject<{
|
|
|
345
345
|
cost: number;
|
|
346
346
|
}>, "many">;
|
|
347
347
|
}, "strip", z.ZodTypeAny, {
|
|
348
|
-
month: string
|
|
348
|
+
month: string & z.BRAND<"MonthlyDate">;
|
|
349
349
|
inputTokens: number;
|
|
350
350
|
outputTokens: number;
|
|
351
351
|
cacheCreationTokens: number;
|
|
352
352
|
cacheReadTokens: number;
|
|
353
353
|
totalCost: number;
|
|
354
|
-
modelsUsed: string[];
|
|
354
|
+
modelsUsed: (string & z.BRAND<"ModelName">)[];
|
|
355
355
|
modelBreakdowns: {
|
|
356
|
-
modelName: string
|
|
356
|
+
modelName: string & z.BRAND<"ModelName">;
|
|
357
357
|
inputTokens: number;
|
|
358
358
|
outputTokens: number;
|
|
359
359
|
cacheCreationTokens: number;
|
package/dist/data-loader.d.ts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import "./pricing-fetcher-
|
|
2
|
-
import { DailyUsage, DateFilter, LoadOptions, ModelBreakdown, MonthlyUsage, SessionUsage, UsageData, calculateCostForEntry, createUniqueHash, dailyUsageSchema, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, usageDataSchema } from "./data-loader-
|
|
1
|
+
import "./pricing-fetcher-A6FC8DhM.js";
|
|
2
|
+
import { DailyUsage, DateFilter, LoadOptions, ModelBreakdown, MonthlyUsage, SessionUsage, UsageData, calculateCostForEntry, createUniqueHash, dailyUsageSchema, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, usageDataSchema } from "./data-loader-BrxITdVN.js";
|
|
3
3
|
export { DailyUsage, DateFilter, LoadOptions, ModelBreakdown, MonthlyUsage, SessionUsage, UsageData, calculateCostForEntry, createUniqueHash, dailyUsageSchema, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, usageDataSchema };
|
package/dist/data-loader.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import "./pricing-fetcher-
|
|
2
|
-
import
|
|
3
|
-
import "./
|
|
1
|
+
import "./pricing-fetcher-Cx71zrV9.js";
|
|
2
|
+
import "./types.internal-CX7kpidj.js";
|
|
3
|
+
import { calculateCostForEntry, createUniqueHash, dailyUsageSchema, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, usageDataSchema } from "./data-loader-B8gFJPfi.js";
|
|
4
|
+
import "./logger-B4PJ298G.js";
|
|
4
5
|
export { calculateCostForEntry, createUniqueHash, dailyUsageSchema, formatDate, formatDateCompact, getDefaultClaudePath, getEarliestTimestamp, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, usageDataSchema };
|
|
@@ -1,15 +1,10 @@
|
|
|
1
|
-
import { PricingFetcher, __toESM, require_usingCtx } from "./pricing-fetcher-
|
|
2
|
-
import { glob, usageDataSchema } from "./data-loader-
|
|
3
|
-
import { logger } from "./logger-
|
|
1
|
+
import { CLAUDE_PROJECTS_DIR_NAME, DEBUG_MATCH_THRESHOLD_PERCENT, DEFAULT_CLAUDE_CODE_PATH, PricingFetcher, USAGE_DATA_GLOB_PATTERN, USER_HOME_DIR, __toESM, require_usingCtx } from "./pricing-fetcher-Cx71zrV9.js";
|
|
2
|
+
import { glob, usageDataSchema } from "./data-loader-B8gFJPfi.js";
|
|
3
|
+
import { logger } from "./logger-B4PJ298G.js";
|
|
4
4
|
import { readFile } from "node:fs/promises";
|
|
5
|
-
import { homedir } from "node:os";
|
|
6
5
|
import path from "node:path";
|
|
7
6
|
var import_usingCtx = __toESM(require_usingCtx(), 1);
|
|
8
7
|
/**
|
|
9
|
-
* Threshold percentage for considering costs as matching (0.1% tolerance)
|
|
10
|
-
*/
|
|
11
|
-
const MATCH_THRESHOLD_PERCENT = .1;
|
|
12
|
-
/**
|
|
13
8
|
* Analyzes usage data to detect pricing mismatches between stored and calculated costs
|
|
14
9
|
* Compares pre-calculated costUSD values with costs calculated from token usage
|
|
15
10
|
* @param claudePath - Optional path to Claude data directory
|
|
@@ -18,8 +13,8 @@ const MATCH_THRESHOLD_PERCENT = .1;
|
|
|
18
13
|
async function detectMismatches(claudePath) {
|
|
19
14
|
try {
|
|
20
15
|
var _usingCtx = (0, import_usingCtx.default)();
|
|
21
|
-
const claudeDir = claudePath ?? path.join(
|
|
22
|
-
const files = await glob([
|
|
16
|
+
const claudeDir = claudePath ?? path.join(USER_HOME_DIR, DEFAULT_CLAUDE_CODE_PATH, CLAUDE_PROJECTS_DIR_NAME);
|
|
17
|
+
const files = await glob([USAGE_DATA_GLOB_PATTERN], {
|
|
23
18
|
cwd: claudeDir,
|
|
24
19
|
absolute: true
|
|
25
20
|
});
|
|
@@ -63,7 +58,7 @@ async function detectMismatches(claudePath) {
|
|
|
63
58
|
avgPercentDiff: 0
|
|
64
59
|
};
|
|
65
60
|
versionStat.total++;
|
|
66
|
-
if (percentDiff <
|
|
61
|
+
if (percentDiff < DEBUG_MATCH_THRESHOLD_PERCENT) versionStat.matches++;
|
|
67
62
|
else versionStat.mismatches++;
|
|
68
63
|
versionStat.avgPercentDiff = (versionStat.avgPercentDiff * (versionStat.total - 1) + percentDiff) / versionStat.total;
|
|
69
64
|
stats.versionStats.set(data.version, versionStat);
|
package/dist/debug.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import "./pricing-fetcher-
|
|
2
|
-
import "./
|
|
3
|
-
import "./
|
|
4
|
-
import
|
|
1
|
+
import "./pricing-fetcher-Cx71zrV9.js";
|
|
2
|
+
import "./types.internal-CX7kpidj.js";
|
|
3
|
+
import "./data-loader-B8gFJPfi.js";
|
|
4
|
+
import "./logger-B4PJ298G.js";
|
|
5
|
+
import { detectMismatches, printMismatchReport } from "./debug-CL2Shx1n.js";
|
|
5
6
|
export { detectMismatches, printMismatchReport };
|