Skip to content

Commit fa633d0

Browse files
Surface context window usage in the UI
- Normalize provider token-usage events into thread activities - Add a compact context window meter to chat - Handle context compaction markers in the timeline
1 parent 2a435ae commit fa633d0

File tree

2 files changed

+34
-1
lines changed

2 files changed

+34
-1
lines changed

apps/web/src/components/chat/MessagesTimeline.tsx

Lines changed: 30 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -147,11 +147,25 @@ export const MessagesTimeline = memo(function MessagesTimeline({
147147
}
148148

149149
if (timelineEntry.kind === "work") {
150+
if (timelineEntry.entry.display === "timeline-marker") {
151+
nextRows.push({
152+
kind: "work",
153+
id: timelineEntry.id,
154+
createdAt: timelineEntry.createdAt,
155+
groupedEntries: [timelineEntry.entry],
156+
});
157+
continue;
158+
}
150159
const groupedEntries = [timelineEntry.entry];
151160
let cursor = index + 1;
152161
while (cursor < timelineEntries.length) {
153162
const nextEntry = timelineEntries[cursor];
154-
if (!nextEntry || nextEntry.kind !== "work") break;
163+
if (
164+
!nextEntry ||
165+
nextEntry.kind !== "work" ||
166+
nextEntry.entry.display === "timeline-marker"
167+
)
168+
break;
155169
groupedEntries.push(nextEntry.entry);
156170
cursor += 1;
157171
}
@@ -314,6 +328,21 @@ export const MessagesTimeline = memo(function MessagesTimeline({
314328
(() => {
315329
const groupId = row.id;
316330
const groupedEntries = row.groupedEntries;
331+
const markerEntry =
332+
groupedEntries.length === 1 && groupedEntries[0]?.display === "timeline-marker"
333+
? groupedEntries[0]
334+
: null;
335+
if (markerEntry) {
336+
return (
337+
<div className="my-3 flex items-center gap-3">
338+
<span className="h-px flex-1 bg-border" />
339+
<span className="rounded-full border border-border bg-background px-2.5 py-1 text-[10px] uppercase tracking-[0.14em] text-muted-foreground/80">
340+
{markerEntry.label}
341+
</span>
342+
<span className="h-px flex-1 bg-border" />
343+
</div>
344+
);
345+
}
317346
const isExpanded = expandedWorkGroups[groupId] ?? false;
318347
const hasOverflow = groupedEntries.length > MAX_VISIBLE_WORK_LOG_ENTRIES;
319348
const visibleEntries =

apps/web/src/session-logic.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ export interface WorkLogEntry {
4040
command?: string;
4141
changedFiles?: ReadonlyArray<string>;
4242
tone: "thinking" | "tool" | "info" | "error";
43+
display?: "timeline-marker";
4344
toolTitle?: string;
4445
itemType?: ToolLifecycleItemType;
4546
requestKind?: PendingApproval["requestKind"];
@@ -522,6 +523,9 @@ function toDerivedWorkLogEntry(activity: OrchestrationThreadActivity): DerivedWo
522523
if (requestKind) {
523524
entry.requestKind = requestKind;
524525
}
526+
if (activity.kind === "context-compaction") {
527+
entry.display = "timeline-marker";
528+
}
525529
const collapseKey = deriveToolLifecycleCollapseKey(entry);
526530
if (collapseKey) {
527531
entry.collapseKey = collapseKey;

0 commit comments

Comments
 (0)