Add dashboard token usage history (#240)
This commit is contained in:
committed by
GitHub
Unverified
parent
0bc4b7cbc2
commit
62108bdc23
69
electron/utils/token-usage.ts
Normal file
69
electron/utils/token-usage.ts
Normal file
@@ -0,0 +1,69 @@
|
||||
import { readdir, readFile, stat } from 'fs/promises';
|
||||
import { join } from 'path';
|
||||
import { getOpenClawConfigDir } from './paths';
|
||||
import { logger } from './logger';
|
||||
import { parseUsageEntriesFromJsonl, type TokenUsageHistoryEntry } from './token-usage-core';
|
||||
|
||||
export { parseUsageEntriesFromJsonl, type TokenUsageHistoryEntry } from './token-usage-core';
|
||||
|
||||
async function listRecentSessionFiles(): Promise<Array<{ filePath: string; sessionId: string; agentId: string; mtimeMs: number }>> {
|
||||
const openclawDir = getOpenClawConfigDir();
|
||||
const agentsDir = join(openclawDir, 'agents');
|
||||
|
||||
try {
|
||||
const agentEntries = await readdir(agentsDir);
|
||||
const files: Array<{ filePath: string; sessionId: string; agentId: string; mtimeMs: number }> = [];
|
||||
|
||||
for (const agentId of agentEntries) {
|
||||
const sessionsDir = join(agentsDir, agentId, 'sessions');
|
||||
try {
|
||||
const sessionEntries = await readdir(sessionsDir);
|
||||
|
||||
for (const fileName of sessionEntries) {
|
||||
if (!fileName.endsWith('.jsonl') || fileName.includes('.deleted.')) continue;
|
||||
const filePath = join(sessionsDir, fileName);
|
||||
try {
|
||||
const fileStat = await stat(filePath);
|
||||
files.push({
|
||||
filePath,
|
||||
sessionId: fileName.replace(/\.jsonl$/, ''),
|
||||
agentId,
|
||||
mtimeMs: fileStat.mtimeMs,
|
||||
});
|
||||
} catch {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
} catch {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
files.sort((a, b) => b.mtimeMs - a.mtimeMs);
|
||||
return files;
|
||||
} catch {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
export async function getRecentTokenUsageHistory(limit = 20): Promise<TokenUsageHistoryEntry[]> {
|
||||
const files = await listRecentSessionFiles();
|
||||
const results: TokenUsageHistoryEntry[] = [];
|
||||
|
||||
for (const file of files) {
|
||||
if (results.length >= limit) break;
|
||||
try {
|
||||
const content = await readFile(file.filePath, 'utf8');
|
||||
const entries = parseUsageEntriesFromJsonl(content, {
|
||||
sessionId: file.sessionId,
|
||||
agentId: file.agentId,
|
||||
}, limit - results.length);
|
||||
results.push(...entries);
|
||||
} catch (error) {
|
||||
logger.debug(`Failed to read token usage transcript ${file.filePath}:`, error);
|
||||
}
|
||||
}
|
||||
|
||||
results.sort((a, b) => Date.parse(b.timestamp) - Date.parse(a.timestamp));
|
||||
return results.slice(0, limit);
|
||||
}
|
||||
Reference in New Issue
Block a user