Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 28 additions & 0 deletions src/app/components/event-tab/event-tab.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -229,6 +229,16 @@
</td>
</tr>
}
@if (selectedEvent()?.cacheCreationTokenCount) {
<tr>
<td>cacheCreationTokenCount</td>
<td>
<span class="value-cell numeric-cell">
<span [matTooltip]="(selectedEvent()!.cacheCreationTokenCount | number) || ''">{{ selectedEvent()!.cacheCreationTokenCount | number }}</span>
</span>
</td>
</tr>
}
</table>
} @else {
<table app-info-table title="Usage Summary for Event">
Expand All @@ -245,10 +255,28 @@
<td>Total Prompt Tokens</td>
<td class="numeric-cell">{{ sessionUsageMetadata()['Prompt Tokens'] | number }}</td>
</tr>
@if (sessionUsageMetadata()['Cached Content Tokens'] > 0) {
<tr>
<td>Total Cached Content Tokens</td>
<td class="numeric-cell">{{ sessionUsageMetadata()['Cached Content Tokens'] | number }}</td>
</tr>
}
@if (sessionUsageMetadata()['Cache Creation Tokens'] > 0) {
<tr>
<td>Total Cache Creation Tokens</td>
<td class="numeric-cell">{{ sessionUsageMetadata()['Cache Creation Tokens'] | number }}</td>
</tr>
}
<tr>
<td>Total Candidates Tokens</td>
<td class="numeric-cell">{{ sessionUsageMetadata()['Candidates Tokens'] | number }}</td>
</tr>
@if (sessionUsageMetadata()['Thoughts Tokens'] > 0) {
<tr>
<td>Total Thoughts Tokens</td>
<td class="numeric-cell">{{ sessionUsageMetadata()['Thoughts Tokens'] | number }}</td>
</tr>
}
<tr>
<td>Total Tokens</td>
<td class="numeric-cell">{{ sessionUsageMetadata()['Total Tokens'] | number }}</td>
Expand Down
16 changes: 16 additions & 0 deletions src/app/components/event-tab/event-tab.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -190,24 +190,40 @@ export class EventTabComponent {
const allEvents = Array.from(this.eventDataMap().values());
let totalPromptTokens = 0;
let totalCandidatesTokens = 0;
let totalCachedContentTokens = 0;
let totalThoughtsTokens = 0;
let totalCacheCreationTokens = 0;
let totalTokens = 0;

allEvents.forEach(ev => {
const metadata = ev.usageMetadata;
if (metadata) {
const prompt = metadata.promptTokenCount ?? metadata.promptTokens ?? 0;
const candidates = metadata.candidatesTokenCount ?? metadata.candidatesTokens ?? 0;
const cachedContent = metadata.cachedContentTokenCount ?? metadata.cachedContentTokens ?? 0;
const thoughts = metadata.thoughtsTokenCount ?? metadata.thoughtsTokens ?? 0;
const total = metadata.totalTokenCount ?? metadata.totalTokens ?? 0;

totalPromptTokens += Number(prompt);
totalCandidatesTokens += Number(candidates);
totalCachedContentTokens += Number(cachedContent);
totalThoughtsTokens += Number(thoughts);
totalTokens += Number(total);
}
// Cache-write (creation) tokens live on the event itself, not in
// usageMetadata: google.genai's usage type forbids extra fields, so ADK
// surfaces them on the serializable event (alongside cacheMetadata)
// instead. Read/reasoning above are genuine usageMetadata fields.
const cacheCreation = ev.cacheCreationTokenCount ?? ev.cacheCreationTokens ?? 0;
totalCacheCreationTokens += Number(cacheCreation);
});

return {
'Prompt Tokens': totalPromptTokens,
'Candidates Tokens': totalCandidatesTokens,
'Cached Content Tokens': totalCachedContentTokens,
'Cache Creation Tokens': totalCacheCreationTokens,
'Thoughts Tokens': totalThoughtsTokens,
'Total Tokens': totalTokens
};
});
Expand Down
4 changes: 4 additions & 0 deletions src/app/core/models/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,10 @@ export declare interface Event extends LlmResponse {
inputTranscription?: { text: string; };
outputTranscription?: { text: string; };
usageMetadata?: any;
// Prompt-cache write (creation) tokens. Serialized on the event itself
// rather than inside usageMetadata because google.genai's usage type
// forbids extra fields.
cacheCreationTokenCount?: number;
interrupted?: boolean;
turnComplete?: boolean;
systemInstructionChanged?: boolean;
Expand Down