Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
39 changes: 39 additions & 0 deletions internal/viewer/server_extra_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,45 @@ func TestRenderTemplate_SessionPage(t *testing.T) {
}
}

func TestRenderTemplate_SecondarySectionsCollapsedByDefault(t *testing.T) {
rr := httptest.NewRecorder()
vs := &ViewSession{
Summary: SessionSummary{
SessionID: "abc",
CWD: "/test",
FilesReviewed: []string{"main.go"},
},
TokenUsage: TokenUsageSummary{
FileTokenBreakdown: []FileTokenUsage{{FilePath: "main.go"}},
},
Files: []*FileGroup{{FilePath: "main.go", Tasks: map[TaskType][]*TaskCard{}}},
Comments: []*ReviewComment{{
FilePath: "main.go",
Content: "Keep this visible",
}},
}

renderTemplate(rr, "session.html", sessionPageData{
EncodedRepo: "repo",
RepoName: "MyRepo",
Session: vs,
})

body := rr.Body.String()
if count := strings.Count(body, `<details class="file-accordion section-accordion">`); count != 2 {
t.Fatalf("collapsed secondary section count = %d, want 2", count)
}
if strings.Contains(body, `<details class="file-accordion section-accordion" open>`) {
t.Fatal("secondary sections should be collapsed by default")
}
if !strings.Contains(body, `<details class="token-breakdown">`) || strings.Contains(body, `<details class="token-breakdown" open>`) {
t.Fatal("file token breakdown should be rendered and collapsed by default")
}
if !strings.Contains(body, `<details class="comment-file-group" open>`) {
t.Fatal("review comment groups should remain expanded")
}
}

func TestRenderTemplate_ExecutionError(t *testing.T) {
rr := httptest.NewRecorder()
// Pass wrong data type to trigger template execution error
Expand Down
32 changes: 32 additions & 0 deletions internal/viewer/static/style.css
Original file line number Diff line number Diff line change
Expand Up @@ -420,6 +420,26 @@ h3 {
}
.token-table tbody tr:hover { background: var(--accent-soft); }

.token-breakdown-toggle {
display: flex;
align-items: center;
gap: 0.5rem;
color: var(--text-secondary);
cursor: pointer;
font-size: 0.82rem;
font-weight: 600;
list-style: none;
padding: 0.25rem 0 0.75rem;
}
.token-breakdown-toggle::-webkit-details-marker { display: none; }
.token-breakdown-toggle::marker { content: none; }
.token-breakdown-toggle .file-count-badge { margin-left: auto; }
.token-breakdown[open] > .token-breakdown-toggle .chevron-sm { transform: rotate(45deg); }
Comment thread
Linxiushen marked this conversation as resolved.
.token-breakdown-body {
overflow-x: auto;
padding-top: 0.25rem;
}

/* ── File List ── */
.file-list {
list-style: none;
Expand Down Expand Up @@ -548,6 +568,18 @@ h3 {
padding: 1rem 1.25rem 1.25rem;
}

.section-accordion {
margin-top: 1.25rem;
}
.section-title {
flex: 1;
font-weight: 600;
}
.section-accordion .file-list,
.section-accordion .conversations {
margin: 0;
}

/* Task Group */
.task-group { margin-bottom: 1.25rem; }
.task-group:last-child { margin-bottom: 0; }
Expand Down
71 changes: 48 additions & 23 deletions internal/viewer/templates/session.html
Original file line number Diff line number Diff line change
Expand Up @@ -80,20 +80,29 @@ <h3>Token Usage</h3>
{{end}}
</div>
{{with .Session.TokenUsage.FileTokenBreakdown}}
<table class="token-table">
<thead><tr><th>File</th><th>Prompt</th><th>Completion</th>{{if or $.Session.TokenUsage.TotalCacheReadTokens $.Session.TokenUsage.TotalCacheWriteTokens}}<th>Cache Read</th><th>Cache Write</th>{{end}}<th>Total</th></tr></thead>
<tbody>
{{range .}}
<tr>
<td title="{{.FilePath}}">{{.FilePath | truncate 60}}</td>
<td title="{{.PromptTokens}}">{{formatNumber .PromptTokens}}</td>
<td title="{{.CompletionTokens}}">{{formatNumber .CompletionTokens}}</td>
{{if or $.Session.TokenUsage.TotalCacheReadTokens $.Session.TokenUsage.TotalCacheWriteTokens}}<td title="{{.CacheReadTokens}}">{{formatNumber .CacheReadTokens}}</td><td title="{{.CacheWriteTokens}}">{{formatNumber .CacheWriteTokens}}</td>{{end}}
<td title="{{add .PromptTokens .CompletionTokens}}"><strong>{{formatNumber (add .PromptTokens .CompletionTokens)}}</strong></td>
</tr>
{{end}}
</tbody>
</table>
<details class="token-breakdown">
<summary class="token-breakdown-toggle">
<span class="chevron-sm"></span>
Comment thread
Linxiushen marked this conversation as resolved.
<span>File breakdown</span>
<span class="file-count-badge">{{len .}} files</span>
</summary>
<div class="token-breakdown-body">
<table class="token-table">
<thead><tr><th>File</th><th>Prompt</th><th>Completion</th>{{if or $.Session.TokenUsage.TotalCacheReadTokens $.Session.TokenUsage.TotalCacheWriteTokens}}<th>Cache Read</th><th>Cache Write</th>{{end}}<th>Total</th></tr></thead>
<tbody>
{{range .}}
<tr>
<td title="{{.FilePath}}">{{.FilePath | truncate 60}}</td>
<td title="{{.PromptTokens}}">{{formatNumber .PromptTokens}}</td>
<td title="{{.CompletionTokens}}">{{formatNumber .CompletionTokens}}</td>
{{if or $.Session.TokenUsage.TotalCacheReadTokens $.Session.TokenUsage.TotalCacheWriteTokens}}<td title="{{.CacheReadTokens}}">{{formatNumber .CacheReadTokens}}</td><td title="{{.CacheWriteTokens}}">{{formatNumber .CacheWriteTokens}}</td>{{end}}
<td title="{{add .PromptTokens .CompletionTokens}}"><strong>{{formatNumber (add .PromptTokens .CompletionTokens)}}</strong></td>
</tr>
{{end}}
</tbody>
</table>
</div>
</details>
{{end}}
</div>

Expand Down Expand Up @@ -151,16 +160,30 @@ <h3>Review Comments ({{len .Session.Comments}} findings)</h3>
{{end}}

{{if .Session.Summary.FilesReviewed}}
<h3>Files Reviewed</h3>
<ul class="file-list">
{{range .Session.Summary.FilesReviewed}}
<li>{{.}}</li>
{{end}}
</ul>
<details class="file-accordion section-accordion">
<summary class="file-accordion-header">
<span class="chevron"></span>
<span class="section-title">Files Reviewed</span>
<span class="file-count-badge">{{len .Session.Summary.FilesReviewed}} files</span>
</summary>
<div class="file-accordion-body">
<ul class="file-list">
{{range .Session.Summary.FilesReviewed}}
<li>{{.}}</li>
{{end}}
</ul>
</div>
</details>
{{end}}

<h3>Conversations ({{len .Session.Files}} files)</h3>
<div class="conversations">
<details class="file-accordion section-accordion">
<summary class="file-accordion-header">
<span class="chevron"></span>
<span class="section-title">Conversations</span>
<span class="file-count-badge">{{len .Session.Files}} files</span>
</summary>
Comment thread
Linxiushen marked this conversation as resolved.
<div class="file-accordion-body">
<div class="conversations">
Comment thread
Linxiushen marked this conversation as resolved.
Comment thread
Linxiushen marked this conversation as resolved.
Comment thread
Linxiushen marked this conversation as resolved.
{{range .Session.Files}}
<details class="file-accordion">
<summary class="file-accordion-header">
Expand Down Expand Up @@ -229,7 +252,9 @@ <h4 class="task-type-label">
</div>
</details>
{{end}}
</div>
</div>
</div>
</details>

<script src="/static/session.js"></script>
</main>
Expand Down
Loading