Skip to content
Merged
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
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
- Codex pace: extrapolate historically exhausted weeks for run-out forecasts and avoid contradictory reset headlines. Thanks @Yuxin-Qiao!
- Settings: switch tabs immediately before animated window resizing and reduce Providers sidebar work. Thanks @elijahfriedman!
- Windsurf: import complete Devin sessions from the current app origin before legacy browser storage. Thanks @kiranmagic7!
- Antigravity: humanize raw model identifiers while preserving server-provided quota labels. Thanks @bcharleson!
- Menu bar: show provider status markers only for the provider rendered in each icon. Thanks @Zihao-Qi!
- Codex CLI: make automatic usage reads prefer OAuth and CLI sources instead of blocking on the optional web dashboard.
- Codex web: apply `--web-timeout` to the full cookie import, account verification, retry, and dashboard fetch path.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -356,6 +356,49 @@ public struct AntigravityStatusSnapshot: Sendable {
return .other
}

static func quotaDisplayLabel(_ quota: AntigravityModelQuota) -> String {
let trimmed = quota.label.trimmingCharacters(in: .whitespacesAndNewlines)
guard trimmed.isEmpty || trimmed == quota.modelId else { return quota.label }
return Self.humanizedModelID(quota.modelId)
}

static func humanizedModelID(_ modelId: String) -> String {
let parts = modelId.split(separator: "-").map(String.init)
var words: [String] = []
var index = 0

while index < parts.count {
let part = parts[index]
if Self.isSingleDigit(part), index + 1 < parts.count, Self.isSingleDigit(parts[index + 1]) {
var versionParts = [part]
index += 1
while index < parts.count, Self.isSingleDigit(parts[index]) {
versionParts.append(parts[index])
index += 1
}
words.append(versionParts.joined(separator: "."))
continue
}

if part.allSatisfy({ $0.isNumber || $0 == "." }) {
words.append(part)
} else if Self.modelLabelAcronyms.contains(part.lowercased()) {
words.append(part.uppercased())
} else {
words.append(part.prefix(1).uppercased() + part.dropFirst())
}
index += 1
}

return words.joined(separator: " ")
}

private static let modelLabelAcronyms: Set<String> = ["ai", "api", "gpt", "oss"]

private static func isSingleDigit(_ value: String) -> Bool {
value.count == 1 && value.allSatisfy(\.isNumber)
}

private static func rateWindow(for quota: AntigravityModelQuota) -> RateWindow {
RateWindow(
usedPercent: 100 - quota.remainingPercent,
Expand Down Expand Up @@ -558,7 +601,7 @@ public struct AntigravityStatusSnapshot: Sendable {
id: m.quota.modelId == compactFallbackModelID
? Self.compactFallbackWindowID(modelID: m.quota.modelId)
: m.quota.modelId,
title: m.quota.label,
title: Self.quotaDisplayLabel(m.quota),
window: Self.rateWindow(for: m.quota),
usageKnown: m.quota.remainingFraction != nil)
}
Expand Down
25 changes: 25 additions & 0 deletions Tests/CodexBarTests/AntigravityModelLabelTests.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import Testing
@testable import CodexBarCore

struct AntigravityModelLabelTests {
@Test
func `humanizes raw model ids when label matches model id`() {
#expect(AntigravityStatusSnapshot.humanizedModelID("gemini-3-pro-preview") == "Gemini 3 Pro Preview")
#expect(AntigravityStatusSnapshot.humanizedModelID("gemini-2.5-flash") == "Gemini 2.5 Flash")
#expect(AntigravityStatusSnapshot.humanizedModelID("example-3-1-pro-low") == "Example 3.1 Pro Low")
#expect(AntigravityStatusSnapshot.humanizedModelID("gpt-api-oss") == "GPT API OSS")
#expect(AntigravityStatusSnapshot.humanizedModelID("").isEmpty)
}

@Test
func `preserves custom model labels`() {
let quota = AntigravityModelQuota(
label: "Custom enterprise label",
modelId: "gemini-3-pro-preview",
remainingFraction: 1,
resetTime: nil,
resetDescription: nil)

#expect(AntigravityStatusSnapshot.quotaDisplayLabel(quota) == "Custom enterprise label")
}
}
8 changes: 4 additions & 4 deletions Tests/CodexBarTests/AntigravityStatusProbeTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -1630,14 +1630,14 @@ extension AntigravityStatusProbeTests {
let snapshot = AntigravityStatusSnapshot(
modelQuotas: [
AntigravityModelQuota(
label: "gemini-3-pro-high",
modelId: "gemini-3-pro-high",
label: "gemini-3-pro-preview",
modelId: "gemini-3-pro-preview",
remainingFraction: 1,
resetTime: nil,
resetDescription: nil),
AntigravityModelQuota(
label: "gemini-3-1-pro-low",
modelId: "gemini-3-1-pro-low",
label: "gemini-2.5-pro",
modelId: "gemini-2.5-pro",
remainingFraction: 1,
resetTime: nil,
resetDescription: nil),
Expand Down