ccusage 15.10.0 → 16.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/README.md +1 -0
- package/config-schema.json +783 -0
- package/dist/calculate-cost.d.ts +1 -1
- package/dist/{data-loader-BJnD_oR3.d.ts → data-loader--Ga8BPdt.d.ts} +4 -0
- package/dist/{data-loader-Dhwqb-FE.js → data-loader-Bf4qMLf2.js} +3 -3
- package/dist/data-loader.d.ts +1 -1
- package/dist/data-loader.js +3 -3
- package/dist/{debug-DseOsUbb.js → debug-Oi3WqR-w.js} +3 -3
- package/dist/debug.js +4 -4
- package/dist/index.js +200 -88
- package/dist/{logger-yNFB24CE.js → logger-ClcgjXEW.js} +1 -1
- package/dist/logger.js +1 -1
- package/dist/{mcp-Cfnsg0lJ.js → mcp-DW2TXqtN.js} +10 -10
- package/dist/mcp.d.ts +2 -4
- package/dist/mcp.js +4 -4
- package/dist/{pricing-fetcher-D3tIkxxO.js → pricing-fetcher-CUQk_dDN.js} +3 -3
- package/dist/pricing-fetcher.js +2 -2
- package/package.json +2 -1
package/dist/calculate-cost.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import "./pricing-fetcher-BgDfBZ05.js";
|
|
2
|
-
import { DailyUsage, MonthlyUsage, SessionUsage, WeeklyUsage } from "./data-loader
|
|
2
|
+
import { DailyUsage, MonthlyUsage, SessionUsage, WeeklyUsage } from "./data-loader--Ga8BPdt.js";
|
|
3
3
|
|
|
4
4
|
//#region src/_token-utils.d.ts
|
|
5
5
|
|
|
@@ -7,6 +7,10 @@ import { z } from "zod";
|
|
|
7
7
|
* Days of the week for weekly aggregation
|
|
8
8
|
*/
|
|
9
9
|
declare const WEEK_DAYS: readonly ["sunday", "monday", "tuesday", "wednesday", "thursday", "friday", "saturday"];
|
|
10
|
+
/**
|
|
11
|
+
* Default configuration file name for storing usage data
|
|
12
|
+
* Used to load and save configuration settings
|
|
13
|
+
*/
|
|
10
14
|
//#endregion
|
|
11
15
|
//#region src/_session-blocks.d.ts
|
|
12
16
|
/**
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { CLAUDE_CONFIG_DIR_ENV, CLAUDE_PROJECTS_DIR_NAME, CONTEXT_LOW_THRESHOLD_ENV, CONTEXT_MEDIUM_THRESHOLD_ENV, DEFAULT_CLAUDE_CODE_PATH, DEFAULT_CLAUDE_CONFIG_PATH, DEFAULT_CONTEXT_USAGE_THRESHOLDS, DEFAULT_RECENT_DAYS, PricingFetcher, USAGE_DATA_GLOB_PATTERN, USER_HOME_DIR, __commonJSMin, __require, __toESM, isFailure, isPromise, isSuccess, require_usingCtx } from "./pricing-fetcher-
|
|
1
|
+
import { CLAUDE_CONFIG_DIR_ENV, CLAUDE_PROJECTS_DIR_NAME, CONTEXT_LOW_THRESHOLD_ENV, CONTEXT_MEDIUM_THRESHOLD_ENV, DEFAULT_CLAUDE_CODE_PATH, DEFAULT_CLAUDE_CONFIG_PATH, DEFAULT_CONTEXT_USAGE_THRESHOLDS, DEFAULT_RECENT_DAYS, PricingFetcher, USAGE_DATA_GLOB_PATTERN, USER_HOME_DIR, __commonJSMin, __require, __toESM, isFailure, isPromise, isSuccess, require_usingCtx } from "./pricing-fetcher-CUQk_dDN.js";
|
|
2
2
|
import { getTotalTokens } from "./_token-utils-WjkbrjKv.js";
|
|
3
3
|
import { activityDateSchema, arrayType, booleanType, createBucket, createDailyDate, createMonthlyDate, createProjectPath, createSessionId, createWeeklyDate, dailyDateSchema, isoTimestampSchema, messageIdSchema, modelNameSchema, monthlyDateSchema, numberType, objectType, projectPathSchema, requestIdSchema, sessionIdSchema, stringType, unionType, versionSchema, weeklyDateSchema } from "./_types-BbEk8t2a.js";
|
|
4
|
-
import { logger } from "./logger-
|
|
4
|
+
import { logger } from "./logger-ClcgjXEW.js";
|
|
5
5
|
import a, { readFile } from "node:fs/promises";
|
|
6
6
|
import path, { posix } from "node:path";
|
|
7
7
|
import process$1 from "node:process";
|
|
@@ -2761,4 +2761,4 @@ async function loadSessionBlockData(options) {
|
|
|
2761
2761
|
_usingCtx6.d();
|
|
2762
2762
|
}
|
|
2763
2763
|
}
|
|
2764
|
-
export { DEFAULT_SESSION_DURATION_HOURS, bucketUsageSchema, calculateBurnRate, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, filterRecentBlocks, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, glob, globUsageFiles, identifySessionBlocks, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, projectBlockUsage, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, uniq, unwrap, usageDataSchema, weeklyUsageSchema };
|
|
2764
|
+
export { DEFAULT_SESSION_DURATION_HOURS, bucketUsageSchema, calculateBurnRate, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, filterRecentBlocks, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, glob, globUsageFiles, identifySessionBlocks, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, projectBlockUsage, sessionUsageSchema, sortFilesByTimestamp, toArray, transcriptMessageSchema, transcriptUsageSchema, uniq, unwrap, usageDataSchema, weeklyUsageSchema };
|
package/dist/data-loader.d.ts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import "./pricing-fetcher-BgDfBZ05.js";
|
|
2
|
-
import { BucketUsage, DailyUsage, DateFilter, GlobResult, LoadOptions, ModelBreakdown, MonthlyUsage, SessionUsage, UsageData, WeeklyUsage, bucketUsageSchema, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, usageDataSchema, weeklyUsageSchema } from "./data-loader
|
|
2
|
+
import { BucketUsage, DailyUsage, DateFilter, GlobResult, LoadOptions, ModelBreakdown, MonthlyUsage, SessionUsage, UsageData, WeeklyUsage, bucketUsageSchema, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, usageDataSchema, weeklyUsageSchema } from "./data-loader--Ga8BPdt.js";
|
|
3
3
|
export { BucketUsage, DailyUsage, DateFilter, GlobResult, LoadOptions, ModelBreakdown, MonthlyUsage, SessionUsage, UsageData, WeeklyUsage, bucketUsageSchema, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, usageDataSchema, weeklyUsageSchema };
|
package/dist/data-loader.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import "./pricing-fetcher-
|
|
1
|
+
import "./pricing-fetcher-CUQk_dDN.js";
|
|
2
2
|
import "./_token-utils-WjkbrjKv.js";
|
|
3
3
|
import "./_types-BbEk8t2a.js";
|
|
4
|
-
import { bucketUsageSchema, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, usageDataSchema, weeklyUsageSchema } from "./data-loader-
|
|
5
|
-
import "./logger-
|
|
4
|
+
import { bucketUsageSchema, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, usageDataSchema, weeklyUsageSchema } from "./data-loader-Bf4qMLf2.js";
|
|
5
|
+
import "./logger-ClcgjXEW.js";
|
|
6
6
|
export { bucketUsageSchema, calculateContextTokens, calculateCostForEntry, createUniqueHash, dailyUsageSchema, extractProjectFromPath, formatDate, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, loadBucketUsageData, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, modelBreakdownSchema, monthlyUsageSchema, sessionUsageSchema, sortFilesByTimestamp, transcriptMessageSchema, transcriptUsageSchema, usageDataSchema, weeklyUsageSchema };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { CLAUDE_PROJECTS_DIR_NAME, DEBUG_MATCH_THRESHOLD_PERCENT, PricingFetcher, USAGE_DATA_GLOB_PATTERN, __toESM, isFailure, require_usingCtx, try_ } from "./pricing-fetcher-
|
|
2
|
-
import { getClaudePaths, glob, unwrap, usageDataSchema } from "./data-loader-
|
|
3
|
-
import { logger } from "./logger-
|
|
1
|
+
import { CLAUDE_PROJECTS_DIR_NAME, DEBUG_MATCH_THRESHOLD_PERCENT, PricingFetcher, USAGE_DATA_GLOB_PATTERN, __toESM, isFailure, require_usingCtx, try_ } from "./pricing-fetcher-CUQk_dDN.js";
|
|
2
|
+
import { getClaudePaths, glob, unwrap, usageDataSchema } from "./data-loader-Bf4qMLf2.js";
|
|
3
|
+
import { logger } from "./logger-ClcgjXEW.js";
|
|
4
4
|
import { readFile } from "node:fs/promises";
|
|
5
5
|
import path from "node:path";
|
|
6
6
|
var import_usingCtx = /* @__PURE__ */ __toESM(require_usingCtx(), 1);
|
package/dist/debug.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import "./pricing-fetcher-
|
|
1
|
+
import "./pricing-fetcher-CUQk_dDN.js";
|
|
2
2
|
import "./_token-utils-WjkbrjKv.js";
|
|
3
3
|
import "./_types-BbEk8t2a.js";
|
|
4
|
-
import "./data-loader-
|
|
5
|
-
import "./logger-
|
|
6
|
-
import { detectMismatches, printMismatchReport } from "./debug-
|
|
4
|
+
import "./data-loader-Bf4qMLf2.js";
|
|
5
|
+
import "./logger-ClcgjXEW.js";
|
|
6
|
+
import { detectMismatches, printMismatchReport } from "./debug-Oi3WqR-w.js";
|
|
7
7
|
export { detectMismatches, printMismatchReport };
|
package/dist/index.js
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import { BLOCKS_COMPACT_WIDTH_THRESHOLD, BLOCKS_DEFAULT_TERMINAL_WIDTH, BLOCKS_WARNING_THRESHOLD, BURN_RATE_THRESHOLDS, DEFAULT_RECENT_DAYS, DEFAULT_REFRESH_INTERVAL_SECONDS, MAX_REFRESH_INTERVAL_SECONDS, MCP_DEFAULT_PORT, MIN_REFRESH_INTERVAL_SECONDS, MIN_RENDER_INTERVAL_MS, PROJECT_ALIASES_ENV, PricingFetcher, WEEK_DAYS, __commonJSMin, __require, __toESM, inspectError, isFailure, isSuccess, map, pipe, require_usingCtx, succeed, try_ } from "./pricing-fetcher-
|
|
2
|
+
import { BLOCKS_COMPACT_WIDTH_THRESHOLD, BLOCKS_DEFAULT_TERMINAL_WIDTH, BLOCKS_WARNING_THRESHOLD, BURN_RATE_THRESHOLDS, CONFIG_FILE_NAME, DEFAULT_RECENT_DAYS, DEFAULT_REFRESH_INTERVAL_SECONDS, MAX_REFRESH_INTERVAL_SECONDS, MCP_DEFAULT_PORT, MIN_REFRESH_INTERVAL_SECONDS, MIN_RENDER_INTERVAL_MS, PROJECT_ALIASES_ENV, PricingFetcher, WEEK_DAYS, __commonJSMin, __require, __toESM, inspect, inspectError, isFailure, isSuccess, map, pipe, require_usingCtx, succeed, try_ } from "./pricing-fetcher-CUQk_dDN.js";
|
|
3
3
|
import { getTotalTokens } from "./_token-utils-WjkbrjKv.js";
|
|
4
4
|
import { CostModes, SortOrders, filterDateSchema, statuslineHookJsonSchema } from "./_types-BbEk8t2a.js";
|
|
5
5
|
import { calculateTotals, createTotalsObject } from "./calculate-cost-BDqO4yWA.js";
|
|
6
|
-
import { DEFAULT_SESSION_DURATION_HOURS, calculateBurnRate, calculateContextTokens, calculateCostForEntry, createUniqueHash, filterRecentBlocks, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, identifySessionBlocks, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, projectBlockUsage, sortFilesByTimestamp, uniq, unwrap, usageDataSchema } from "./data-loader-
|
|
7
|
-
import { description, log, logger, name, version } from "./logger-
|
|
8
|
-
import { detectMismatches, printMismatchReport } from "./debug-
|
|
9
|
-
import { createMcpHttpApp, createMcpServer, startMcpServerStdio } from "./mcp-
|
|
6
|
+
import { DEFAULT_SESSION_DURATION_HOURS, calculateBurnRate, calculateContextTokens, calculateCostForEntry, createUniqueHash, filterRecentBlocks, formatDateCompact, getClaudePaths, getContextUsageThresholds, getEarliestTimestamp, getUsageLimitResetTime, globUsageFiles, identifySessionBlocks, loadDailyUsageData, loadMonthlyUsageData, loadSessionBlockData, loadSessionData, loadSessionUsageById, loadWeeklyUsageData, projectBlockUsage, sortFilesByTimestamp, toArray, uniq, unwrap, usageDataSchema } from "./data-loader-Bf4qMLf2.js";
|
|
7
|
+
import { description, log, logger, name, version } from "./logger-ClcgjXEW.js";
|
|
8
|
+
import { detectMismatches, printMismatchReport } from "./debug-Oi3WqR-w.js";
|
|
9
|
+
import { createMcpHttpApp, createMcpServer, startMcpServerStdio } from "./mcp-DW2TXqtN.js";
|
|
10
10
|
import a, { readFile, stat } from "node:fs/promises";
|
|
11
11
|
import path, { join } from "node:path";
|
|
12
12
|
import process$1 from "node:process";
|
|
@@ -817,7 +817,94 @@ var require_picocolors = /* @__PURE__ */ __commonJSMin(((exports, module) => {
|
|
|
817
817
|
};
|
|
818
818
|
};
|
|
819
819
|
module.exports = createColors(), module.exports.createColors = createColors;
|
|
820
|
-
})), import_picocolors$8 = /* @__PURE__ */ __toESM(require_picocolors(), 1);
|
|
820
|
+
})), import_picocolors$8 = /* @__PURE__ */ __toESM(require_picocolors(), 1), import_usingCtx$3 = /* @__PURE__ */ __toESM(require_usingCtx(), 1);
|
|
821
|
+
function extractExplicitArgs(tokens) {
|
|
822
|
+
const explicit = {};
|
|
823
|
+
for (const token of tokens) if (typeof token === "object" && token !== null) {
|
|
824
|
+
const t = token;
|
|
825
|
+
if (t.kind === "option" && typeof t.name === "string") explicit[t.name] = true;
|
|
826
|
+
}
|
|
827
|
+
return explicit;
|
|
828
|
+
}
|
|
829
|
+
function getConfigSearchPaths() {
|
|
830
|
+
const claudeConfigDirs = [join(process$1.cwd(), ".ccusage"), ...toArray(getClaudePaths())];
|
|
831
|
+
return claudeConfigDirs.map((dir) => join(dir, CONFIG_FILE_NAME));
|
|
832
|
+
}
|
|
833
|
+
function validateConfigJson(data) {
|
|
834
|
+
if (typeof data !== "object" || data === null) return false;
|
|
835
|
+
const config = data;
|
|
836
|
+
return !(config.$schema != null && typeof config.$schema !== "string" || config.defaults != null && (typeof config.defaults !== "object" || config.defaults === null) || config.commands != null && (typeof config.commands !== "object" || config.commands === null));
|
|
837
|
+
}
|
|
838
|
+
function loadConfigFile(filePath, debug$4 = false) {
|
|
839
|
+
if (!existsSync(filePath)) {
|
|
840
|
+
if (debug$4) logger.info(` • Checking: ${filePath} (not found)`);
|
|
841
|
+
return void 0;
|
|
842
|
+
}
|
|
843
|
+
const parseConfigFileResult = pipe(try_({
|
|
844
|
+
try: () => {
|
|
845
|
+
const content = readFileSync(filePath, "utf-8"), data = JSON.parse(content);
|
|
846
|
+
if (!validateConfigJson(data)) throw new Error("Invalid configuration structure");
|
|
847
|
+
return data.source = filePath, data;
|
|
848
|
+
},
|
|
849
|
+
catch: (error) => error
|
|
850
|
+
})(), inspect(() => {
|
|
851
|
+
if (logger.debug(`Parsed configuration file: ${filePath}`), debug$4) logger.info(` • Checking: ${filePath} (found ✓)`);
|
|
852
|
+
}), inspectError((error) => {
|
|
853
|
+
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
854
|
+
if (logger.warn(`Error parsing configuration file at ${filePath}: ${errorMessage}`), debug$4) logger.info(` • Checking: ${filePath} (error: ${errorMessage})`);
|
|
855
|
+
}), unwrap(void 0));
|
|
856
|
+
return parseConfigFileResult;
|
|
857
|
+
}
|
|
858
|
+
function loadConfig(configPath, debug$4 = false) {
|
|
859
|
+
if (debug$4) logger.info("Debug mode enabled - showing config loading details\n");
|
|
860
|
+
if (configPath != null) {
|
|
861
|
+
if (debug$4) logger.info("Using specified config file:"), logger.info(` • Path: ${configPath}`);
|
|
862
|
+
const config = loadConfigFile(configPath, debug$4);
|
|
863
|
+
if (config == null) logger.warn(`Configuration file not found or invalid: ${configPath}`);
|
|
864
|
+
else if (debug$4) logger.info(""), logger.info(`Loaded config from: ${configPath}`), logger.info(` • Schema: ${config.$schema ?? "none"}`), logger.info(` • Has defaults: ${config.defaults != null ? "yes" : "no"}${config.defaults != null ? ` (${Object.keys(config.defaults).length} options)` : ""}`), logger.info(` • Has command configs: ${config.commands != null ? "yes" : "no"}${config.commands != null ? ` (${Object.keys(config.commands).join(", ")})` : ""}`);
|
|
865
|
+
return config;
|
|
866
|
+
}
|
|
867
|
+
if (debug$4) logger.info("Searching for config files:");
|
|
868
|
+
for (const searchPath of getConfigSearchPaths()) {
|
|
869
|
+
const config = loadConfigFile(searchPath, debug$4);
|
|
870
|
+
if (config != null) {
|
|
871
|
+
if (debug$4) logger.info(""), logger.info(`Loaded config from: ${searchPath}`), logger.info(` • Schema: ${config.$schema ?? "none"}`), logger.info(` • Has defaults: ${config.defaults != null ? "yes" : "no"}${config.defaults != null ? ` (${Object.keys(config.defaults).length} options)` : ""}`), logger.info(` • Has command configs: ${config.commands != null ? "yes" : "no"}${config.commands != null ? ` (${Object.keys(config.commands).join(", ")})` : ""}`);
|
|
872
|
+
return config;
|
|
873
|
+
}
|
|
874
|
+
}
|
|
875
|
+
if (logger.debug("No valid configuration file found"), debug$4) logger.info(""), logger.info("No valid configuration file found");
|
|
876
|
+
return void 0;
|
|
877
|
+
}
|
|
878
|
+
function mergeConfigWithArgs(ctx, config, debug$4 = false) {
|
|
879
|
+
if (config == null) {
|
|
880
|
+
if (debug$4) logger.info(""), logger.info(`No config file loaded, using CLI args only for '${ctx.name ?? "unknown"}' command`);
|
|
881
|
+
return ctx.values;
|
|
882
|
+
}
|
|
883
|
+
const merged = {}, commandName = ctx.name, sources = {};
|
|
884
|
+
if (config.defaults != null) for (const [key, value$1] of Object.entries(config.defaults)) merged[key] = value$1, sources[key] = "defaults";
|
|
885
|
+
if (commandName != null && config.commands?.[commandName] != null) for (const [key, value$1] of Object.entries(config.commands[commandName])) merged[key] = value$1, sources[key] = "command config";
|
|
886
|
+
const explicit = extractExplicitArgs(ctx.tokens);
|
|
887
|
+
for (const [key, value$1] of Object.entries(ctx.values)) if (value$1 != null && explicit[key] === true) merged[key] = value$1, sources[key] = "CLI";
|
|
888
|
+
if (logger.debug(`Merged config for ${commandName ?? "unknown"}:`, merged), debug$4) {
|
|
889
|
+
logger.info(""), logger.info(`Merging options for '${commandName ?? "unknown"}' command:`);
|
|
890
|
+
const bySource = {
|
|
891
|
+
"defaults": [],
|
|
892
|
+
"command config": [],
|
|
893
|
+
"CLI": []
|
|
894
|
+
};
|
|
895
|
+
for (const [key, source] of Object.entries(sources)) if (bySource[source] != null) bySource[source].push(`${key}=${JSON.stringify(merged[key])}`);
|
|
896
|
+
if (bySource.defaults.length > 0) logger.info(` • From defaults: ${bySource.defaults.join(", ")}`);
|
|
897
|
+
if (bySource["command config"].length > 0) logger.info(` • From command config: ${bySource["command config"].join(", ")}`);
|
|
898
|
+
if (bySource.CLI.length > 0) logger.info(` • From CLI args: ${bySource.CLI.join(", ")}`);
|
|
899
|
+
logger.info(" • Final merged options: {");
|
|
900
|
+
for (const [key, value$1] of Object.entries(merged)) {
|
|
901
|
+
const source = sources[key] ?? "unknown";
|
|
902
|
+
logger.info(` ${key}: ${JSON.stringify(value$1)} (from ${source}),`);
|
|
903
|
+
}
|
|
904
|
+
logger.info(" }");
|
|
905
|
+
}
|
|
906
|
+
return merged;
|
|
907
|
+
}
|
|
821
908
|
const getContext = (raw) => ({
|
|
822
909
|
start: process$1.hrtime.bigint(),
|
|
823
910
|
command: raw.map((part) => getCommandPart(stripVTControlCharacters(part))).join(" "),
|
|
@@ -1077,6 +1164,10 @@ const sharedArgs = {
|
|
|
1077
1164
|
short: "q",
|
|
1078
1165
|
description: "Process JSON output with jq command (requires jq binary, implies --json)"
|
|
1079
1166
|
},
|
|
1167
|
+
config: {
|
|
1168
|
+
type: "string",
|
|
1169
|
+
description: "Path to configuration file (default: auto-discovery)"
|
|
1170
|
+
},
|
|
1080
1171
|
compact: {
|
|
1081
1172
|
type: "boolean",
|
|
1082
1173
|
description: "Force compact mode for narrow displays (better for screenshots)",
|
|
@@ -3072,7 +3163,7 @@ const blocksCommand = define({
|
|
|
3072
3163
|
},
|
|
3073
3164
|
toKebab: true,
|
|
3074
3165
|
async run(ctx) {
|
|
3075
|
-
const
|
|
3166
|
+
const config = loadConfig(ctx.values.config, ctx.values.debug), mergedOptions = mergeConfigWithArgs(ctx, config, ctx.values.debug), useJson = mergedOptions.json || mergedOptions.jq != null;
|
|
3076
3167
|
if (useJson) logger.level = 0;
|
|
3077
3168
|
if (ctx.values.sessionLength <= 0) logger.error("Session length must be a positive number"), process$1.exit(1);
|
|
3078
3169
|
let blocks = await loadSessionBlockData({
|
|
@@ -3354,18 +3445,11 @@ const dailyCommand = define({
|
|
|
3354
3445
|
}
|
|
3355
3446
|
},
|
|
3356
3447
|
async run(ctx) {
|
|
3357
|
-
const
|
|
3448
|
+
const config = loadConfig(ctx.values.config, ctx.values.debug), mergedOptions = mergeConfigWithArgs(ctx, config, ctx.values.debug), useJson = Boolean(mergedOptions.json) || mergedOptions.jq != null;
|
|
3358
3449
|
if (useJson) logger.level = 0;
|
|
3359
3450
|
const dailyData = await loadDailyUsageData({
|
|
3360
|
-
|
|
3361
|
-
|
|
3362
|
-
mode: ctx.values.mode,
|
|
3363
|
-
order: ctx.values.order,
|
|
3364
|
-
offline: ctx.values.offline,
|
|
3365
|
-
groupByProject: ctx.values.instances,
|
|
3366
|
-
project: ctx.values.project,
|
|
3367
|
-
timezone: ctx.values.timezone,
|
|
3368
|
-
locale: ctx.values.locale
|
|
3451
|
+
...mergedOptions,
|
|
3452
|
+
groupByProject: mergedOptions.instances
|
|
3369
3453
|
});
|
|
3370
3454
|
if (dailyData.length === 0) {
|
|
3371
3455
|
if (useJson) log(JSON.stringify([]));
|
|
@@ -3373,12 +3457,12 @@ const dailyCommand = define({
|
|
|
3373
3457
|
process$1.exit(0);
|
|
3374
3458
|
}
|
|
3375
3459
|
const totals = calculateTotals(dailyData);
|
|
3376
|
-
if (
|
|
3460
|
+
if (mergedOptions.debug && !useJson) {
|
|
3377
3461
|
const mismatchStats = await detectMismatches(void 0);
|
|
3378
|
-
printMismatchReport(mismatchStats,
|
|
3462
|
+
printMismatchReport(mismatchStats, mergedOptions.debugSamples);
|
|
3379
3463
|
}
|
|
3380
3464
|
if (useJson) {
|
|
3381
|
-
const jsonOutput =
|
|
3465
|
+
const jsonOutput = Boolean(mergedOptions.instances) && dailyData.some((d) => d.project != null) ? {
|
|
3382
3466
|
projects: groupByProject(dailyData),
|
|
3383
3467
|
totals: createTotalsObject(totals)
|
|
3384
3468
|
} : {
|
|
@@ -3396,8 +3480,8 @@ const dailyCommand = define({
|
|
|
3396
3480
|
})),
|
|
3397
3481
|
totals: createTotalsObject(totals)
|
|
3398
3482
|
};
|
|
3399
|
-
if (
|
|
3400
|
-
const jqResult = await processWithJq(jsonOutput,
|
|
3483
|
+
if (mergedOptions.jq != null) {
|
|
3484
|
+
const jqResult = await processWithJq(jsonOutput, mergedOptions.jq);
|
|
3401
3485
|
if (isFailure(jqResult)) logger.error(jqResult.error.message), process$1.exit(1);
|
|
3402
3486
|
log(jqResult.value);
|
|
3403
3487
|
} else log(JSON.stringify(jsonOutput, null, 2));
|
|
@@ -3425,7 +3509,7 @@ const dailyCommand = define({
|
|
|
3425
3509
|
"right",
|
|
3426
3510
|
"right"
|
|
3427
3511
|
],
|
|
3428
|
-
dateFormatter: (dateStr) => formatDateCompact(dateStr,
|
|
3512
|
+
dateFormatter: (dateStr) => formatDateCompact(dateStr, mergedOptions.timezone, mergedOptions.locale ?? void 0),
|
|
3429
3513
|
compactHead: [
|
|
3430
3514
|
"Date",
|
|
3431
3515
|
"Models",
|
|
@@ -3443,7 +3527,7 @@ const dailyCommand = define({
|
|
|
3443
3527
|
compactThreshold: 100,
|
|
3444
3528
|
forceCompact: ctx.values.compact
|
|
3445
3529
|
});
|
|
3446
|
-
if (
|
|
3530
|
+
if (Boolean(mergedOptions.instances) && dailyData.some((d) => d.project != null)) {
|
|
3447
3531
|
const projectGroups = groupDataByProject(dailyData);
|
|
3448
3532
|
let isFirstProject = true;
|
|
3449
3533
|
for (const [projectName, projectData] of Object.entries(projectGroups)) {
|
|
@@ -3476,7 +3560,7 @@ const dailyCommand = define({
|
|
|
3476
3560
|
formatNumber(data.cacheReadTokens),
|
|
3477
3561
|
formatNumber(getTotalTokens(data)),
|
|
3478
3562
|
formatCurrency(data.totalCost)
|
|
3479
|
-
]),
|
|
3563
|
+
]), mergedOptions.breakdown) pushBreakdownRows(table, data.modelBreakdowns);
|
|
3480
3564
|
isFirstProject = false;
|
|
3481
3565
|
}
|
|
3482
3566
|
} else for (const data of dailyData) if (table.push([
|
|
@@ -3488,7 +3572,7 @@ const dailyCommand = define({
|
|
|
3488
3572
|
formatNumber(data.cacheReadTokens),
|
|
3489
3573
|
formatNumber(getTotalTokens(data)),
|
|
3490
3574
|
formatCurrency(data.totalCost)
|
|
3491
|
-
]),
|
|
3575
|
+
]), mergedOptions.breakdown) pushBreakdownRows(table, data.modelBreakdowns);
|
|
3492
3576
|
if (table.push([
|
|
3493
3577
|
"",
|
|
3494
3578
|
"",
|
|
@@ -3900,17 +3984,9 @@ const monthlyCommand = define({
|
|
|
3900
3984
|
description: "Show usage report grouped by month",
|
|
3901
3985
|
...sharedCommandConfig,
|
|
3902
3986
|
async run(ctx) {
|
|
3903
|
-
const
|
|
3987
|
+
const config = loadConfig(ctx.values.config, ctx.values.debug), mergedOptions = mergeConfigWithArgs(ctx, config, ctx.values.debug), useJson = Boolean(mergedOptions.json) || mergedOptions.jq != null;
|
|
3904
3988
|
if (useJson) logger.level = 0;
|
|
3905
|
-
const monthlyData = await loadMonthlyUsageData(
|
|
3906
|
-
since: ctx.values.since,
|
|
3907
|
-
until: ctx.values.until,
|
|
3908
|
-
mode: ctx.values.mode,
|
|
3909
|
-
order: ctx.values.order,
|
|
3910
|
-
offline: ctx.values.offline,
|
|
3911
|
-
timezone: ctx.values.timezone,
|
|
3912
|
-
locale: ctx.values.locale
|
|
3913
|
-
});
|
|
3989
|
+
const monthlyData = await loadMonthlyUsageData(mergedOptions);
|
|
3914
3990
|
if (monthlyData.length === 0) {
|
|
3915
3991
|
if (useJson) {
|
|
3916
3992
|
const emptyOutput = {
|
|
@@ -3929,9 +4005,9 @@ const monthlyCommand = define({
|
|
|
3929
4005
|
process$1.exit(0);
|
|
3930
4006
|
}
|
|
3931
4007
|
const totals = calculateTotals(monthlyData);
|
|
3932
|
-
if (
|
|
4008
|
+
if (mergedOptions.debug && !useJson) {
|
|
3933
4009
|
const mismatchStats = await detectMismatches(void 0);
|
|
3934
|
-
printMismatchReport(mismatchStats,
|
|
4010
|
+
printMismatchReport(mismatchStats, mergedOptions.debugSamples);
|
|
3935
4011
|
}
|
|
3936
4012
|
if (useJson) {
|
|
3937
4013
|
const jsonOutput = {
|
|
@@ -3948,8 +4024,8 @@ const monthlyCommand = define({
|
|
|
3948
4024
|
})),
|
|
3949
4025
|
totals: createTotalsObject(totals)
|
|
3950
4026
|
};
|
|
3951
|
-
if (
|
|
3952
|
-
const jqResult = await processWithJq(jsonOutput,
|
|
4027
|
+
if (mergedOptions.jq != null) {
|
|
4028
|
+
const jqResult = await processWithJq(jsonOutput, mergedOptions.jq);
|
|
3953
4029
|
if (isFailure(jqResult)) logger.error(jqResult.error.message), process$1.exit(1);
|
|
3954
4030
|
log(jqResult.value);
|
|
3955
4031
|
} else log(JSON.stringify(jsonOutput, null, 2));
|
|
@@ -3977,7 +4053,7 @@ const monthlyCommand = define({
|
|
|
3977
4053
|
"right",
|
|
3978
4054
|
"right"
|
|
3979
4055
|
],
|
|
3980
|
-
dateFormatter: (dateStr) => formatDateCompact(dateStr,
|
|
4056
|
+
dateFormatter: (dateStr) => formatDateCompact(dateStr, mergedOptions.timezone, mergedOptions.locale ?? "en-CA"),
|
|
3981
4057
|
compactHead: [
|
|
3982
4058
|
"Month",
|
|
3983
4059
|
"Models",
|
|
@@ -4004,7 +4080,7 @@ const monthlyCommand = define({
|
|
|
4004
4080
|
formatNumber(data.cacheReadTokens),
|
|
4005
4081
|
formatNumber(getTotalTokens(data)),
|
|
4006
4082
|
formatCurrency(data.totalCost)
|
|
4007
|
-
]),
|
|
4083
|
+
]), mergedOptions.breakdown) pushBreakdownRows(table, data.modelBreakdowns);
|
|
4008
4084
|
if (table.push([
|
|
4009
4085
|
"",
|
|
4010
4086
|
"",
|
|
@@ -4116,15 +4192,15 @@ const sessionCommand = define({
|
|
|
4116
4192
|
},
|
|
4117
4193
|
toKebab: true,
|
|
4118
4194
|
async run(ctx) {
|
|
4119
|
-
const
|
|
4195
|
+
const config = loadConfig(ctx.values.config, ctx.values.debug), mergedOptions = mergeConfigWithArgs(ctx, config, ctx.values.debug), useJson = mergedOptions.json || mergedOptions.jq != null;
|
|
4120
4196
|
if (useJson) logger.level = 0;
|
|
4121
|
-
if (
|
|
4122
|
-
id:
|
|
4123
|
-
mode:
|
|
4124
|
-
offline:
|
|
4125
|
-
jq:
|
|
4126
|
-
timezone:
|
|
4127
|
-
locale:
|
|
4197
|
+
if (mergedOptions.id != null) return handleSessionIdLookup({ values: {
|
|
4198
|
+
id: mergedOptions.id,
|
|
4199
|
+
mode: mergedOptions.mode,
|
|
4200
|
+
offline: mergedOptions.offline,
|
|
4201
|
+
jq: mergedOptions.jq,
|
|
4202
|
+
timezone: mergedOptions.timezone,
|
|
4203
|
+
locale: mergedOptions.locale ?? "en-CA"
|
|
4128
4204
|
} }, useJson);
|
|
4129
4205
|
const sessionData = await loadSessionData({
|
|
4130
4206
|
since: ctx.values.since,
|
|
@@ -5132,7 +5208,12 @@ function getSemaphore(sessionId) {
|
|
|
5132
5208
|
const semaphore = createLimoJson(semaphorePath);
|
|
5133
5209
|
return semaphore;
|
|
5134
5210
|
}
|
|
5135
|
-
const
|
|
5211
|
+
const visualBurnRateChoices = [
|
|
5212
|
+
"off",
|
|
5213
|
+
"emoji",
|
|
5214
|
+
"text",
|
|
5215
|
+
"emoji-text"
|
|
5216
|
+
], statuslineCommand = define({
|
|
5136
5217
|
name: "statusline",
|
|
5137
5218
|
description: "Display compact status line for Claude Code hooks with hybrid time+file caching (Beta)",
|
|
5138
5219
|
toKebab: true,
|
|
@@ -5141,6 +5222,15 @@ const statuslineCommand = define({
|
|
|
5141
5222
|
...sharedArgs.offline,
|
|
5142
5223
|
default: true
|
|
5143
5224
|
},
|
|
5225
|
+
visualBurnRate: {
|
|
5226
|
+
type: "enum",
|
|
5227
|
+
choices: visualBurnRateChoices,
|
|
5228
|
+
description: "Controls the visualization of the burn rate status",
|
|
5229
|
+
default: "off",
|
|
5230
|
+
short: "vb",
|
|
5231
|
+
negatable: false,
|
|
5232
|
+
toKebab: true
|
|
5233
|
+
},
|
|
5144
5234
|
cache: {
|
|
5145
5235
|
type: "boolean",
|
|
5146
5236
|
description: "Enable cache for status line output (default: true)",
|
|
@@ -5150,16 +5240,18 @@ const statuslineCommand = define({
|
|
|
5150
5240
|
type: "number",
|
|
5151
5241
|
description: `Refresh interval in seconds for cache expiry (default: ${DEFAULT_REFRESH_INTERVAL_SECONDS})`,
|
|
5152
5242
|
default: DEFAULT_REFRESH_INTERVAL_SECONDS
|
|
5153
|
-
}
|
|
5243
|
+
},
|
|
5244
|
+
config: sharedArgs.config,
|
|
5245
|
+
debug: sharedArgs.debug
|
|
5154
5246
|
},
|
|
5155
5247
|
async run(ctx) {
|
|
5156
5248
|
logger.level = 0;
|
|
5157
|
-
const
|
|
5249
|
+
const config = loadConfig(ctx.values.config, ctx.values.debug), mergedOptions = mergeConfigWithArgs(ctx, config, ctx.values.debug), refreshInterval = mergedOptions.refreshInterval, stdin$2 = await getStdin();
|
|
5158
5250
|
if (stdin$2.length === 0) log("❌ No input provided"), process$1.exit(1);
|
|
5159
5251
|
const hookDataJson = JSON.parse(stdin$2.trim()), hookDataParseResult = statuslineHookJsonSchema.safeParse(hookDataJson);
|
|
5160
5252
|
if (!hookDataParseResult.success) log("❌ Invalid input format:", hookDataParseResult.error.message), process$1.exit(1);
|
|
5161
5253
|
const hookData = hookDataParseResult.data, sessionId = hookData.session_id, initialSemaphoreState = pipe(succeed(getSemaphore(sessionId)), map((semaphore) => semaphore.data), unwrap(void 0)), currentMtime = await getFileModifiedTime(hookData.transcript_path);
|
|
5162
|
-
if (
|
|
5254
|
+
if (mergedOptions.cache && initialSemaphoreState != null) {
|
|
5163
5255
|
const now = Date.now(), timeElapsed = now - (initialSemaphoreState.lastUpdateTime ?? 0), isExpired = timeElapsed >= refreshInterval * 1e3, isFileModified = initialSemaphoreState.transcriptMtime !== currentMtime;
|
|
5164
5256
|
if (!isExpired && !isFileModified) {
|
|
5165
5257
|
log(initialSemaphoreState.lastOutput);
|
|
@@ -5209,7 +5301,7 @@ const statuslineCommand = define({
|
|
|
5209
5301
|
const sessionCost = await pipe(try_({
|
|
5210
5302
|
try: loadSessionUsageById(sessionId, {
|
|
5211
5303
|
mode: "auto",
|
|
5212
|
-
offline:
|
|
5304
|
+
offline: mergedOptions.offline
|
|
5213
5305
|
}),
|
|
5214
5306
|
catch: (error) => error
|
|
5215
5307
|
}), map((sessionCost$1) => sessionCost$1?.totalCost), inspectError((error) => logger.error("Failed to load session data:", error)), unwrap(void 0)), today = /* @__PURE__ */ new Date(), todayStr = today.toISOString().split("T")[0]?.replace(/-/g, "") ?? "", todayCost = await pipe(try_({
|
|
@@ -5217,7 +5309,7 @@ const statuslineCommand = define({
|
|
|
5217
5309
|
since: todayStr,
|
|
5218
5310
|
until: todayStr,
|
|
5219
5311
|
mode: "auto",
|
|
5220
|
-
offline:
|
|
5312
|
+
offline: mergedOptions.offline
|
|
5221
5313
|
}),
|
|
5222
5314
|
catch: (error) => error
|
|
5223
5315
|
}), map((dailyData) => {
|
|
@@ -5229,7 +5321,7 @@ const statuslineCommand = define({
|
|
|
5229
5321
|
}), inspectError((error) => logger.error("Failed to load daily data:", error)), unwrap(0)), { blockInfo, burnRateInfo } = await pipe(try_({
|
|
5230
5322
|
try: loadSessionBlockData({
|
|
5231
5323
|
mode: "auto",
|
|
5232
|
-
offline:
|
|
5324
|
+
offline: mergedOptions.offline
|
|
5233
5325
|
}),
|
|
5234
5326
|
catch: (error) => error
|
|
5235
5327
|
}), map((blocks) => {
|
|
@@ -5242,8 +5334,26 @@ const statuslineCommand = define({
|
|
|
5242
5334
|
});
|
|
5243
5335
|
if (activeBlock != null) {
|
|
5244
5336
|
const now = /* @__PURE__ */ new Date(), remaining = Math.round((activeBlock.endTime.getTime() - now.getTime()) / (1e3 * 60)), blockCost = activeBlock.costUSD, blockInfo$1 = `${formatCurrency(blockCost)} block (${formatRemainingTime(remaining)})`, burnRate = calculateBurnRate(activeBlock), burnRateInfo$1 = burnRate != null ? (() => {
|
|
5245
|
-
const costPerHour = burnRate.costPerHour, costPerHourStr = `${formatCurrency(costPerHour)}/hr`,
|
|
5246
|
-
|
|
5337
|
+
const renderEmojiStatus = ctx.values.visualBurnRate === "emoji" || ctx.values.visualBurnRate === "emoji-text", renderTextStatus = ctx.values.visualBurnRate === "text" || ctx.values.visualBurnRate === "emoji-text", costPerHour = burnRate.costPerHour, costPerHourStr = `${formatCurrency(costPerHour)}/hr`, burnStatus = burnRate.tokensPerMinuteForIndicator < 2e3 ? "normal" : burnRate.tokensPerMinuteForIndicator < 5e3 ? "moderate" : "high", burnStatusMappings = {
|
|
5338
|
+
normal: {
|
|
5339
|
+
emoji: "🟢",
|
|
5340
|
+
textValue: "Normal",
|
|
5341
|
+
coloredString: import_picocolors$1.default.green
|
|
5342
|
+
},
|
|
5343
|
+
moderate: {
|
|
5344
|
+
emoji: "⚠️",
|
|
5345
|
+
textValue: "Moderate",
|
|
5346
|
+
coloredString: import_picocolors$1.default.yellow
|
|
5347
|
+
},
|
|
5348
|
+
high: {
|
|
5349
|
+
emoji: "🚨",
|
|
5350
|
+
textValue: "High",
|
|
5351
|
+
coloredString: import_picocolors$1.default.red
|
|
5352
|
+
}
|
|
5353
|
+
}, { emoji, textValue, coloredString } = burnStatusMappings[burnStatus], burnRateOutputSegments = [coloredString(costPerHourStr)];
|
|
5354
|
+
if (renderEmojiStatus) burnRateOutputSegments.push(emoji);
|
|
5355
|
+
if (renderTextStatus) burnRateOutputSegments.push(coloredString(`(${textValue})`));
|
|
5356
|
+
return ` | 🔥 ${burnRateOutputSegments.join(" ")}`;
|
|
5247
5357
|
})() : "";
|
|
5248
5358
|
return {
|
|
5249
5359
|
blockInfo: blockInfo$1,
|
|
@@ -5258,7 +5368,7 @@ const statuslineCommand = define({
|
|
|
5258
5368
|
blockInfo: "No active block",
|
|
5259
5369
|
burnRateInfo: ""
|
|
5260
5370
|
})), contextInfo = await pipe(try_({
|
|
5261
|
-
try: calculateContextTokens(hookData.transcript_path, hookData.model.id,
|
|
5371
|
+
try: calculateContextTokens(hookData.transcript_path, hookData.model.id, mergedOptions.offline),
|
|
5262
5372
|
catch: (error) => error
|
|
5263
5373
|
}), inspectError((error) => logger.debug(`Failed to calculate context tokens: ${error instanceof Error ? error.message : String(error)}`)), map((ctx$1) => {
|
|
5264
5374
|
if (ctx$1 == null) return void 0;
|
|
@@ -5272,7 +5382,7 @@ const statuslineCommand = define({
|
|
|
5272
5382
|
if (isSuccess(mainProcessingResult)) try {
|
|
5273
5383
|
var _usingCtx3 = (0, import_usingCtx.default)();
|
|
5274
5384
|
const statusLine = mainProcessingResult.value;
|
|
5275
|
-
if (log(statusLine), !
|
|
5385
|
+
if (log(statusLine), !mergedOptions.cache) return;
|
|
5276
5386
|
const semaphore = _usingCtx3.u(getSemaphore(sessionId));
|
|
5277
5387
|
semaphore.data = {
|
|
5278
5388
|
date: (/* @__PURE__ */ new Date()).toISOString(),
|
|
@@ -5293,7 +5403,7 @@ const statuslineCommand = define({
|
|
|
5293
5403
|
var _usingCtx4 = (0, import_usingCtx.default)();
|
|
5294
5404
|
if (initialSemaphoreState?.lastOutput != null && initialSemaphoreState.lastOutput !== "") log(initialSemaphoreState.lastOutput);
|
|
5295
5405
|
else log("❌ Error generating status");
|
|
5296
|
-
if (logger.error("Error in statusline command:", mainProcessingResult.error), !
|
|
5406
|
+
if (logger.error("Error in statusline command:", mainProcessingResult.error), !mergedOptions.cache) return;
|
|
5297
5407
|
const semaphore = _usingCtx4.u(getSemaphore(sessionId));
|
|
5298
5408
|
if (semaphore.data != null) semaphore.data.isUpdating = false, semaphore.data.pid = void 0;
|
|
5299
5409
|
} catch (_) {
|
|
@@ -5319,18 +5429,9 @@ const weeklyCommand = define({
|
|
|
5319
5429
|
},
|
|
5320
5430
|
toKebab: true,
|
|
5321
5431
|
async run(ctx) {
|
|
5322
|
-
const
|
|
5432
|
+
const config = loadConfig(ctx.values.config, ctx.values.debug), mergedOptions = mergeConfigWithArgs(ctx, config, ctx.values.debug), useJson = Boolean(mergedOptions.json) || mergedOptions.jq != null;
|
|
5323
5433
|
if (useJson) logger.level = 0;
|
|
5324
|
-
const weeklyData = await loadWeeklyUsageData(
|
|
5325
|
-
since: ctx.values.since,
|
|
5326
|
-
until: ctx.values.until,
|
|
5327
|
-
timezone: ctx.values.timezone,
|
|
5328
|
-
mode: ctx.values.mode,
|
|
5329
|
-
order: ctx.values.order,
|
|
5330
|
-
offline: ctx.values.offline,
|
|
5331
|
-
startOfWeek: ctx.values.startOfWeek,
|
|
5332
|
-
locale: ctx.values.locale
|
|
5333
|
-
});
|
|
5434
|
+
const weeklyData = await loadWeeklyUsageData(mergedOptions);
|
|
5334
5435
|
if (weeklyData.length === 0) {
|
|
5335
5436
|
if (useJson) {
|
|
5336
5437
|
const emptyOutput = {
|
|
@@ -5349,9 +5450,9 @@ const weeklyCommand = define({
|
|
|
5349
5450
|
process$1.exit(0);
|
|
5350
5451
|
}
|
|
5351
5452
|
const totals = calculateTotals(weeklyData);
|
|
5352
|
-
if (
|
|
5453
|
+
if (mergedOptions.debug && !useJson) {
|
|
5353
5454
|
const mismatchStats = await detectMismatches(void 0);
|
|
5354
|
-
printMismatchReport(mismatchStats,
|
|
5455
|
+
printMismatchReport(mismatchStats, mergedOptions.debugSamples);
|
|
5355
5456
|
}
|
|
5356
5457
|
if (useJson) {
|
|
5357
5458
|
const jsonOutput = {
|
|
@@ -5368,8 +5469,8 @@ const weeklyCommand = define({
|
|
|
5368
5469
|
})),
|
|
5369
5470
|
totals: createTotalsObject(totals)
|
|
5370
5471
|
};
|
|
5371
|
-
if (
|
|
5372
|
-
const jqResult = await processWithJq(jsonOutput,
|
|
5472
|
+
if (mergedOptions.jq != null) {
|
|
5473
|
+
const jqResult = await processWithJq(jsonOutput, mergedOptions.jq);
|
|
5373
5474
|
if (isFailure(jqResult)) logger.error(jqResult.error.message), process$1.exit(1);
|
|
5374
5475
|
log(jqResult.value);
|
|
5375
5476
|
} else log(JSON.stringify(jsonOutput, null, 2));
|
|
@@ -5397,7 +5498,7 @@ const weeklyCommand = define({
|
|
|
5397
5498
|
"right",
|
|
5398
5499
|
"right"
|
|
5399
5500
|
],
|
|
5400
|
-
dateFormatter: (dateStr) => formatDateCompact(dateStr,
|
|
5501
|
+
dateFormatter: (dateStr) => formatDateCompact(dateStr, mergedOptions.timezone, mergedOptions.locale ?? void 0),
|
|
5401
5502
|
compactHead: [
|
|
5402
5503
|
"Week",
|
|
5403
5504
|
"Models",
|
|
@@ -5424,7 +5525,7 @@ const weeklyCommand = define({
|
|
|
5424
5525
|
formatNumber(data.cacheReadTokens),
|
|
5425
5526
|
formatNumber(getTotalTokens(data)),
|
|
5426
5527
|
formatCurrency(data.totalCost)
|
|
5427
|
-
]),
|
|
5528
|
+
]), mergedOptions.breakdown) pushBreakdownRows(table, data.modelBreakdowns);
|
|
5428
5529
|
if (table.push([
|
|
5429
5530
|
"",
|
|
5430
5531
|
"",
|
|
@@ -5446,14 +5547,25 @@ const weeklyCommand = define({
|
|
|
5446
5547
|
]), log(table.toString()), table.isCompactMode()) logger.info("\nRunning in Compact Mode"), logger.info("Expand terminal width to see cache metrics and total tokens");
|
|
5447
5548
|
}
|
|
5448
5549
|
}
|
|
5449
|
-
}),
|
|
5450
|
-
|
|
5550
|
+
}), subCommandUnion = [
|
|
5551
|
+
["daily", dailyCommand],
|
|
5552
|
+
["monthly", monthlyCommand],
|
|
5553
|
+
["weekly", weeklyCommand],
|
|
5554
|
+
["session", sessionCommand],
|
|
5555
|
+
["blocks", blocksCommand],
|
|
5556
|
+
["mcp", mcpCommand],
|
|
5557
|
+
["statusline", statuslineCommand]
|
|
5558
|
+
], subCommands = /* @__PURE__ */ new Map();
|
|
5559
|
+
for (const [name$1, command] of subCommandUnion) subCommands.set(name$1, command);
|
|
5451
5560
|
const mainCommand = dailyCommand;
|
|
5452
|
-
|
|
5453
|
-
|
|
5454
|
-
|
|
5455
|
-
|
|
5456
|
-
|
|
5457
|
-
|
|
5458
|
-
|
|
5561
|
+
async function run() {
|
|
5562
|
+
await cli(process$1.argv.slice(2), mainCommand, {
|
|
5563
|
+
name,
|
|
5564
|
+
version,
|
|
5565
|
+
description,
|
|
5566
|
+
subCommands,
|
|
5567
|
+
renderHeader: null
|
|
5568
|
+
});
|
|
5569
|
+
}
|
|
5570
|
+
await run();
|
|
5459
5571
|
export {};
|
|
@@ -761,7 +761,7 @@ function _getDefaultLogLevel() {
|
|
|
761
761
|
return g ? LogLevels.debug : R ? LogLevels.warn : LogLevels.info;
|
|
762
762
|
}
|
|
763
763
|
const consola = createConsola$1();
|
|
764
|
-
var name = "ccusage", version = "
|
|
764
|
+
var name = "ccusage", version = "16.0.0", description = "Usage analysis tool for Claude Code";
|
|
765
765
|
const logger = consola.withTag(name);
|
|
766
766
|
if (process$1.env.LOG_LEVEL != null) {
|
|
767
767
|
const level = Number.parseInt(process$1.env.LOG_LEVEL, 10);
|
package/dist/logger.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { log, logger } from "./logger-
|
|
1
|
+
import { log, logger } from "./logger-ClcgjXEW.js";
|
|
2
2
|
export { log, logger };
|