Files
steipete--codexbar/Tests/CodexBarTests/ClaudeWebUsageExtraWindowTests.swift
2026-07-13 12:22:33 +08:00

84 lines
3.6 KiB
Swift

import Foundation
import Testing
@testable import CodexBarCore
struct ClaudeWebUsageExtraWindowTests {
@Test
func `parses claude web API sonnet usage response`() throws {
let json = """
{
"five_hour": { "utilization": 9, "resets_at": "2025-12-23T16:00:00.000Z" },
"seven_day_sonnet": { "utilization": 6, "resets_at": "2025-12-30T23:00:00.000Z" }
}
"""
let data = Data(json.utf8)
let parsed = try ClaudeWebAPIFetcher._parseUsageResponseForTesting(data)
#expect(parsed.opusPercentUsed == 6)
}
@Test
func `ignores merged claude web API omelette usage window`() throws {
let json = """
{
"five_hour": { "utilization": 9, "resets_at": "2025-12-23T16:00:00.000Z" },
"seven_day_omelette": { "utilization": 26, "resets_at": "2025-12-30T23:00:00.000Z" },
"seven_day_cowork": { "utilization": 11, "resets_at": "2025-12-31T23:00:00.000Z" }
}
"""
let data = Data(json.utf8)
let parsed = try ClaudeWebAPIFetcher._parseUsageResponseForTesting(data)
#expect(parsed.extraRateWindows.count == 1)
#expect(parsed.extraRateWindows.contains { $0.id == "claude-design" } == false)
#expect(parsed.extraRateWindows.first(where: { $0.id == "claude-routines" })?.window.usedPercent == 11)
}
@Test
func `parses claude web API cowork null as zero routines window`() throws {
let json = """
{
"five_hour": { "utilization": 9, "resets_at": "2025-12-23T16:00:00.000Z" },
"seven_day_omelette": { "utilization": 26, "resets_at": "2025-12-30T23:00:00.000Z" },
"seven_day_cowork": null
}
"""
let data = Data(json.utf8)
let parsed = try ClaudeWebAPIFetcher._parseUsageResponseForTesting(data)
#expect(parsed.extraRateWindows.first(where: { $0.id == "claude-routines" })?.window.usedPercent == 0)
#expect(parsed.extraRateWindows.contains { $0.id == "claude-design" } == false)
}
@Test
func `surfaces Fable scoped weekly limit from claude web API limits array`() throws {
// Real shape observed 2026-07-03 from claude.ai/api/organizations/{org}/usage during
// Anthropic's Fable 5 promotional access window (up to 50% of the weekly limit).
let json = """
{
"five_hour": { "utilization": 16, "resets_at": "2026-07-03T00:30:00.440902+00:00" },
"seven_day": { "utilization": 10, "resets_at": "2026-07-08T09:00:00.440924+00:00" },
"limits": [
{
"kind": "session", "group": "session", "percent": 16,
"resets_at": "2026-07-03T00:30:00.440902+00:00", "scope": null, "is_active": true
},
{
"kind": "weekly_all", "group": "weekly", "percent": 10,
"resets_at": "2026-07-08T09:00:00.440924+00:00", "scope": null, "is_active": false
},
{
"kind": "weekly_scoped", "group": "weekly", "percent": 5,
"resets_at": "2026-07-08T09:00:00.441154+00:00",
"scope": { "model": { "id": null, "display_name": "Fable" }, "surface": null },
"is_active": false
}
]
}
"""
let data = Data(json.utf8)
let parsed = try ClaudeWebAPIFetcher._parseUsageResponseForTesting(data)
let fable = parsed.extraRateWindows.first(where: { $0.id == "claude-weekly-scoped-fable" })
#expect(fable?.title == "Fable only")
#expect(fable?.window.usedPercent == 5)
#expect(fable?.window.resetsAt != nil)
}
}