feat: add domain model types for session metrics and statistics

Define the core data structures that flow through the entire pipeline:

- model/session.go: SessionStats (per-session aggregates including
  token counts across 5 categories — input, output, cache_write_5m,
  cache_write_1h, cache_read), APICall (deduplicated by message.id,
  keyed to the final billed usage), and ModelUsage (per-model
  breakdown within a session). Tracks subagent relationships via
  IsSubagent/ParentSession fields.

- model/metrics.go: Higher-order aggregate types — SummaryStats
  (top-level totals with per-active-day rates for cost, tokens,
  sessions, and minutes), DailyStats/HourlyStats/WeeklyStats
  (time-bucketed views), ModelStats (cross-session model comparison
  with share percentages), ProjectStats (per-project ranking), and
  PeriodComparison (current vs previous period for delta display).

- model/budget.go: BudgetStats with plan ceiling, custom budget,
  burn rate, and projected monthly spend for the budget tab.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
teernisse
2026-02-19 13:00:45 -05:00
parent 340f688a1f
commit cfbbb9d6db
3 changed files with 161 additions and 0 deletions

12
internal/model/budget.go Normal file
View File

@@ -0,0 +1,12 @@
package model
// BudgetStats holds budget tracking and forecast data.
type BudgetStats struct {
PlanCeiling float64
CustomBudget *float64
CurrentSpend float64
DailyBurnRate float64
ProjectedMonthly float64
DaysRemaining int
BudgetUsedPercent float64
}

94
internal/model/metrics.go Normal file
View File

@@ -0,0 +1,94 @@
package model
import "time"
// SummaryStats holds the top-level aggregate across all sessions.
type SummaryStats struct {
TotalSessions int
TotalPrompts int
TotalAPICalls int
TotalDurationSecs int64
ActiveDays int
InputTokens int64
OutputTokens int64
CacheCreation5mTokens int64
CacheCreation1hTokens int64
CacheReadTokens int64
TotalBilledTokens int64
EstimatedCost float64
ActualCost *float64
CacheSavings float64
CacheHitRate float64
CostPerDay float64
TokensPerDay int64
SessionsPerDay float64
PromptsPerDay float64
MinutesPerDay float64
}
// DailyStats holds metrics for a single calendar day.
type DailyStats struct {
Date time.Time
Sessions int
Prompts int
APICalls int
DurationSecs int64
InputTokens int64
OutputTokens int64
CacheCreation5m int64
CacheCreation1h int64
CacheReadTokens int64
EstimatedCost float64
ActualCost *float64
}
// ModelStats holds aggregated metrics for a single model.
type ModelStats struct {
Model string
APICalls int
InputTokens int64
OutputTokens int64
CacheCreation5m int64
CacheCreation1h int64
CacheReadTokens int64
EstimatedCost float64
SharePercent float64
TrendDirection int // -1, 0, +1 vs previous period
}
// ProjectStats holds aggregated metrics for a single project.
type ProjectStats struct {
Project string
Sessions int
Prompts int
TotalTokens int64
EstimatedCost float64
TrendDirection int
}
// HourlyStats holds prompt/session counts for one hour of the day.
type HourlyStats struct {
Hour int
Prompts int
Sessions int
Tokens int64
}
// WeeklyStats holds metrics for one calendar week.
type WeeklyStats struct {
WeekStart time.Time
Sessions int
Prompts int
TotalTokens int64
DurationSecs int64
EstimatedCost float64
}
// PeriodComparison holds current and previous period data for delta computation.
type PeriodComparison struct {
Current SummaryStats
Previous SummaryStats
}

55
internal/model/session.go Normal file
View File

@@ -0,0 +1,55 @@
package model
import "time"
// APICall represents one deduplicated API request (final state of a message.id).
type APICall struct {
MessageID string
Model string
Timestamp time.Time
InputTokens int64
OutputTokens int64
CacheCreation5mTokens int64
CacheCreation1hTokens int64
CacheReadTokens int64
ServiceTier string
EstimatedCost float64
}
// ModelUsage tracks per-model token usage within a session.
type ModelUsage struct {
APICalls int
InputTokens int64
OutputTokens int64
CacheCreation5mTokens int64
CacheCreation1hTokens int64
CacheReadTokens int64
EstimatedCost float64
}
// SessionStats holds aggregated metrics for a single session file.
type SessionStats struct {
SessionID string
Project string
ProjectPath string
FilePath string
IsSubagent bool
ParentSession string
StartTime time.Time
EndTime time.Time
DurationSecs int64
UserMessages int
APICalls int
InputTokens int64
OutputTokens int64
CacheCreation5mTokens int64
CacheCreation1hTokens int64
CacheReadTokens int64
Models map[string]*ModelUsage
EstimatedCost float64
CacheHitRate float64
}