Overview
The logger module provides configured logger instances using consola for consistent logging throughout the application. It includes package name tagging and log level control.
Exports
logger
Application logger instance with package name tag.
export const logger : ConsolaInstance
The logger provides methods for different log levels:
Warning messages (level 1)
General log messages (level 2)
Informational messages (level 3)
Basic Usage
With Structured Data
Error Handling
import { logger } from 'ccusage/logger' ;
logger . info ( 'Loading usage data...' );
logger . debug ( 'Processing file:' , filePath );
logger . warn ( 'Missing cost data, using fallback' );
logger . error ( 'Failed to load file:' , error );
log
Direct console.log function for cases where logger formatting is not desired.
export const log : typeof console . log
Use log when you need plain output without logger formatting, such as for JSON output or raw data display.
import { log } from 'ccusage/logger' ;
import { loadDailyUsageData } from 'ccusage/data-loader' ;
const data = await loadDailyUsageData ();
// Output raw JSON without logger formatting
log ( JSON . stringify ( data , null , 2 ));
Log Levels
Control logging verbosity with the LOG_LEVEL environment variable:
Level Value Methods Shown Silent 0 None Warn 1 warn, error, fatalLog 2 log + aboveInfo 3 info + above (default)Debug 4 debug + aboveTrace 5 trace + all
Environment Variable
Programmatic Control
# Silent mode (no logs)
LOG_LEVEL = 0 ccusage daily
# Warnings only
LOG_LEVEL = 1 ccusage daily
# Debug mode
LOG_LEVEL = 4 ccusage daily
# Trace mode (maximum verbosity)
LOG_LEVEL = 5 ccusage daily
Usage Patterns
Development vs Production
import { logger } from 'ccusage/logger' ;
// Verbose logging for development
logger . debug ( 'Starting data load...' );
logger . debug ( 'Found files:' , files . length );
logger . debug ( 'Processing file:' , file );
logger . info ( 'Data loaded successfully' );
Progress Tracking
File Processing
Data Aggregation
import { logger } from 'ccusage/logger' ;
const files = await globUsageFiles ( claudePaths );
logger . info ( `Processing ${ files . length } files...` );
for ( let i = 0 ; i < files . length ; i ++ ) {
logger . debug ( `Processing file ${ i + 1 } / ${ files . length } :` , files [ i ]. file );
await processFile ( files [ i ]);
}
logger . info ( 'All files processed successfully' );
Error Context
Detailed Error Info
Graceful Degradation
import { logger } from 'ccusage/logger' ;
try {
const data = await loadSessionUsageById ( sessionId );
if ( ! data ) {
logger . warn ( 'Session not found:' , sessionId );
return null ;
}
return data ;
} catch ( error ) {
logger . error ( 'Failed to load session:' , {
sessionId ,
error: error instanceof Error ? error . message : String ( error )
});
throw error ;
}
Integration Examples
CLI Commands
import { logger , log } from 'ccusage/logger' ;
import { loadDailyUsageData } from 'ccusage/data-loader' ;
export async function dailyCommand ( options : Options ) {
logger . info ( 'Loading daily usage data...' );
const data = await loadDailyUsageData ({
since: options . since ,
until: options . until ,
mode: options . mode
});
logger . debug ( `Loaded ${ data . length } days` );
if ( options . json ) {
// Use log for raw JSON output
log ( JSON . stringify ( data , null , 2 ));
} else {
// Use logger for formatted output
logger . info ( 'Daily Usage Report' );
// ... render table ...
}
}
Library Usage
import { logger } from 'ccusage/logger' ;
import { loadDailyUsageData } from 'ccusage/data-loader' ;
import { calculateTotals } from 'ccusage/calculate-cost' ;
export async function analyzeUsage ( projectName : string ) {
logger . info ( 'Starting usage analysis for:' , projectName );
const data = await loadDailyUsageData ({
project: projectName ,
groupByProject: true
});
if ( data . length === 0 ) {
logger . warn ( 'No usage data found for project:' , projectName );
return null ;
}
logger . debug ( 'Data loaded:' , {
days: data . length ,
firstDate: data [ 0 ]?. date ,
lastDate: data [ data . length - 1 ]?. date
});
const totals = calculateTotals ( data );
logger . info ( 'Analysis complete:' , {
project: projectName ,
totalCost: totals . totalCost ,
avgCostPerDay: totals . totalCost / data . length
});
return { data , totals };
}
Best Practices
Never use console.log directly in ccusage code. Always use logger for formatted output or log for raw output.
When to Use Each Level
trace : Very detailed debugging, variable values
debug : Detailed flow information, file processing
info : General progress updates, completion messages
log : Standard output, user-facing messages
warn : Non-critical issues, fallback behaviors
error : Errors that prevent operation
Logger vs Log
Use logger : For application messages, progress updates, errors
Use log : For JSON output, tables, raw data that shouldn’t be formatted
Good: Using logger for messages
Good: Using log for raw output
Bad: Using console.log
import { logger } from 'ccusage/logger' ;
logger . info ( 'Processing complete' );
logger . debug ( 'Found' , items . length , 'items' );
logger . warn ( 'Missing optional field:' , field );