mirror of
https://github.com/fawney19/Aether.git
synced 2026-10-07 01:47:47 +08:00
fix(providers): refresh Antigravity grouped quotas
This commit is contained in:
@@ -45,11 +45,11 @@
|
||||
|
||||
<div class="py-2">
|
||||
<div
|
||||
v-if="items.length > 0"
|
||||
v-if="displayItems.length > 0"
|
||||
class="grid grid-cols-2 gap-3"
|
||||
>
|
||||
<div
|
||||
v-for="item in items"
|
||||
v-for="item in displayItems"
|
||||
:key="item.model"
|
||||
>
|
||||
<div class="flex items-center justify-between text-[10px] mb-0.5">
|
||||
@@ -238,6 +238,48 @@ function buildItemsFromQuotaSnapshot(quota: QuotaStatusSnapshot | null | undefin
|
||||
return dedupeAntigravityQuotaItemsByLabel(items)
|
||||
}
|
||||
|
||||
function buildGroupedItemsFromQuotaSnapshot(
|
||||
quota: QuotaStatusSnapshot | null | undefined,
|
||||
): QuotaItem[] {
|
||||
if (!quota) return []
|
||||
|
||||
const providerType = String(quota.provider_type || '').trim().toLowerCase()
|
||||
if (providerType && providerType !== 'antigravity') return []
|
||||
|
||||
const windows = Array.isArray(quota.windows)
|
||||
? quota.windows.filter(window => String(window?.scope || '').trim().toLowerCase() === 'quota_group')
|
||||
: []
|
||||
|
||||
return windows
|
||||
.map((window) => {
|
||||
const code = String(window.code || '').trim()
|
||||
const label = String(window.label || code).trim()
|
||||
if (!code || !label) return null
|
||||
|
||||
const usedPercent =
|
||||
typeof window.used_ratio === 'number'
|
||||
? Math.max(Math.min(window.used_ratio * 100, 100), 0)
|
||||
: typeof window.remaining_ratio === 'number'
|
||||
? Math.max(Math.min((1 - window.remaining_ratio) * 100, 100), 0)
|
||||
: null
|
||||
if (usedPercent == null) return null
|
||||
|
||||
const remainingPercent =
|
||||
typeof window.remaining_ratio === 'number'
|
||||
? Math.max(Math.min(window.remaining_ratio * 100, 100), 0)
|
||||
: Math.max(100 - usedPercent, 0)
|
||||
|
||||
return {
|
||||
model: code,
|
||||
label,
|
||||
usedPercent,
|
||||
remainingPercent,
|
||||
resetSeconds: getQuotaWindowLiveResetSeconds(quota, window),
|
||||
} satisfies QuotaItem
|
||||
})
|
||||
.filter((item): item is QuotaItem => item !== null)
|
||||
}
|
||||
|
||||
const rawItems = computed<QuotaItem[]>(() => {
|
||||
const snapshotItems = buildItemsFromQuotaSnapshot(props.quotaSnapshot)
|
||||
if (snapshotItems.length > 0) return snapshotItems
|
||||
@@ -291,6 +333,8 @@ const rawItems = computed<QuotaItem[]>(() => {
|
||||
})
|
||||
|
||||
const items = computed<QuotaItem[]>(() => summarizeAntigravityQuotaItems(rawItems.value))
|
||||
const groupedItems = computed<QuotaItem[]>(() => buildGroupedItemsFromQuotaSnapshot(props.quotaSnapshot))
|
||||
const displayItems = computed<QuotaItem[]>(() => [...groupedItems.value, ...items.value])
|
||||
|
||||
async function handleTestModel(modelName: string) {
|
||||
if (!props.providerId || testingModel.value) return
|
||||
|
||||
+32
-2
@@ -2,7 +2,7 @@ import { describe, expect, it, vi } from 'vitest'
|
||||
import { createApp, defineComponent, h } from 'vue'
|
||||
|
||||
import AntigravityQuotaDialog from '@/features/providers/components/AntigravityQuotaDialog.vue'
|
||||
import type { UpstreamMetadata } from '@/api/endpoints/types'
|
||||
import type { QuotaStatusSnapshot, UpstreamMetadata } from '@/api/endpoints/types'
|
||||
|
||||
vi.mock('@/components/ui', async () => {
|
||||
const { defineComponent, h } = await import('vue')
|
||||
@@ -77,7 +77,7 @@ vi.mock('@/utils/errorParser', () => ({
|
||||
parseApiError: (value: unknown) => String(value),
|
||||
}))
|
||||
|
||||
function mount(metadata: UpstreamMetadata) {
|
||||
function mount(metadata: UpstreamMetadata, quotaSnapshot?: QuotaStatusSnapshot) {
|
||||
const root = document.createElement('div')
|
||||
document.body.appendChild(root)
|
||||
|
||||
@@ -86,6 +86,7 @@ function mount(metadata: UpstreamMetadata) {
|
||||
return () => h(AntigravityQuotaDialog, {
|
||||
open: true,
|
||||
metadata,
|
||||
quotaSnapshot,
|
||||
keyName: 'Key-1',
|
||||
})
|
||||
},
|
||||
@@ -102,6 +103,35 @@ function mount(metadata: UpstreamMetadata) {
|
||||
}
|
||||
|
||||
describe('AntigravityQuotaDialog', () => {
|
||||
it('renders grouped five-hour and weekly quota windows', () => {
|
||||
const { root, unmount } = mount({}, {
|
||||
code: 'ok',
|
||||
provider_type: 'antigravity',
|
||||
exhausted: false,
|
||||
windows: [{
|
||||
code: 'group:0:3p-5h',
|
||||
label: 'Claude and GPT models · 5 hour',
|
||||
scope: 'quota_group',
|
||||
used_ratio: 0.75,
|
||||
remaining_ratio: 0.25,
|
||||
}, {
|
||||
code: 'group:0:3p-weekly',
|
||||
label: 'Claude and GPT models · weekly',
|
||||
scope: 'quota_group',
|
||||
used_ratio: 0.2,
|
||||
remaining_ratio: 0.8,
|
||||
}],
|
||||
})
|
||||
const text = root.textContent || ''
|
||||
|
||||
expect(text).toContain('Claude and GPT models · 5 hour')
|
||||
expect(text).toContain('25.0%')
|
||||
expect(text).toContain('Claude and GPT models · weekly')
|
||||
expect(text).toContain('80.0%')
|
||||
|
||||
unmount()
|
||||
})
|
||||
|
||||
it('hides quota buckets outside the shared pool summary families', () => {
|
||||
const rawIdentifier = 'RateLimitResetCredit_05cbb6eeeb9c81918e011d8300f9ebfb'
|
||||
const { root, unmount } = mount({
|
||||
|
||||
Reference in New Issue
Block a user