<template>
  <div class="page-content">
    <div class="mb-5">
      <h2 class="text-xl font-semibold">审计与用量</h2>
      <p class="text-g-500 mt-1 text-sm">查询模型调用结果、延迟、Token 明细与按日聚合</p>
    </div>

    <ElTabs v-model="tab">
      <ElTabPane label="调用审计" name="audit">
        <div class="mb-4 flex flex-wrap items-center gap-3">
          <ElDatePicker v-model="auditRange" type="datetimerange" range-separator="至" start-placeholder="开始时间" end-placeholder="结束时间" />
          <ElInput v-model="auditFilter.provider" clearable placeholder="Provider" class="!w-40" />
          <ElInput v-model="auditFilter.model" clearable placeholder="模型" class="!w-48" />
          <ElSelect v-model="auditFilter.status" clearable placeholder="状态" class="!w-32"><ElOption label="成功 200" :value="200" /><ElOption label="限流 429" :value="429" /><ElOption label="上游 502" :value="502" /><ElOption label="不可用 503" :value="503" /></ElSelect>
          <ElButton type="primary" @click="loadAudit(true)">查询</ElButton>
        </div>
        <ElTable v-loading="auditLoading" :data="auditEvents" row-key="id">
          <ElTableColumn label="时间" min-width="180"><template #default="{ row }">{{ formatTime(row.recorded_at) }}</template></ElTableColumn>
          <ElTableColumn prop="request_id" label="Request ID" min-width="220" />
          <ElTableColumn label="API Key" min-width="150"><template #default="{ row }">{{ row.api_key_name || row.api_key_id || 'bootstrap' }}</template></ElTableColumn>
          <ElTableColumn prop="provider_code" label="Provider" min-width="120" />
          <ElTableColumn prop="model" label="模型" min-width="170" />
          <ElTableColumn label="状态" width="90"><template #default="{ row }"><ElTag :type="row.status_code && row.status_code < 400 ? 'success' : 'danger'">{{ row.status_code }}</ElTag></template></ElTableColumn>
          <ElTableColumn label="Token" min-width="140"><template #default="{ row }">{{ tokenTotal(row).toLocaleString() }} <span class="text-g-500 text-xs">({{ row.prompt_tokens || 0 }}+{{ row.completion_tokens || 0 }})</span></template></ElTableColumn>
          <ElTableColumn label="成本" width="120"><template #default="{ row }">{{ costText(row.cost_microunits) }}</template></ElTableColumn>
          <ElTableColumn label="延迟" width="110"><template #default="{ row }">{{ row.latency_ms == null ? '—' : `${row.latency_ms} ms` }}</template></ElTableColumn>
        </ElTable>
        <div class="mt-4 flex justify-center"><ElButton v-if="nextBefore" :loading="auditLoading" @click="loadMore">加载更多</ElButton></div>
      </ElTabPane>

      <ElTabPane label="按日用量" name="usage">
        <div class="mb-4 flex flex-wrap items-center gap-3">
          <ElDatePicker v-model="usageRange" type="daterange" range-separator="至" start-placeholder="开始日期" end-placeholder="结束日期" />
          <ElInput v-model="usageFilter.provider" clearable placeholder="Provider" class="!w-40" />
          <ElInput v-model="usageFilter.model" clearable placeholder="模型" class="!w-48" />
          <ElButton type="primary" @click="loadUsage">查询</ElButton>
        </div>
        <div class="mb-4 grid grid-cols-1 gap-4 md:grid-cols-4">
          <ElCard shadow="never"><div class="text-g-500 text-sm">请求数</div><div class="mt-2 text-2xl font-semibold">{{ usageTotals.requests.toLocaleString() }}</div></ElCard>
          <ElCard shadow="never"><div class="text-g-500 text-sm">失败请求</div><div class="mt-2 text-2xl font-semibold">{{ usageTotals.failed.toLocaleString() }}</div></ElCard>
          <ElCard shadow="never"><div class="text-g-500 text-sm">Token</div><div class="mt-2 text-2xl font-semibold">{{ usageTotals.tokens.toLocaleString() }}</div></ElCard>
          <ElCard shadow="never"><div class="text-g-500 text-sm">估算成本</div><div class="mt-2 text-2xl font-semibold">{{ costText(usageTotals.cost) }}</div></ElCard>
        </div>
        <ElTable v-loading="usageLoading" :data="dailyUsage" :row-key="usageRowKey">
          <ElTableColumn label="日期" width="120"><template #default="{ row }">{{ row.date.slice(0, 10) }}</template></ElTableColumn>
          <ElTableColumn prop="api_key_name" label="API Key" min-width="150" />
          <ElTableColumn prop="provider_code" label="Provider" min-width="120" />
          <ElTableColumn prop="model" label="模型" min-width="170" />
          <ElTableColumn prop="requests" label="请求" width="100" />
          <ElTableColumn prop="failed_requests" label="失败" width="100" />
          <ElTableColumn label="输入 Token" min-width="130"><template #default="{ row }">{{ row.prompt_tokens.toLocaleString() }}</template></ElTableColumn>
          <ElTableColumn label="输出 Token" min-width="130"><template #default="{ row }">{{ row.completion_tokens.toLocaleString() }}</template></ElTableColumn>
          <ElTableColumn label="成本" min-width="120"><template #default="{ row }">{{ costText(row.cost_microunits) }}</template></ElTableColumn>
        </ElTable>
      </ElTabPane>
    </ElTabs>
  </div>
</template>

<script setup lang="ts">
  import { AuditEvent, DailyUsage, fetchAuditEvents, fetchDailyUsage } from '@/api/audit'

  const tab = ref('audit')
  const now = new Date()
  const auditRange = ref<[Date, Date]>([new Date(now.getTime() - 24 * 3600_000), now])
  const usageRange = ref<[Date, Date]>([new Date(now.getFullYear(), now.getMonth(), now.getDate() - 29), now])
  const auditFilter = reactive<{ provider: string; model: string; status?: number }>({ provider: '', model: '' })
  const usageFilter = reactive({ provider: '', model: '' })
  const auditEvents = ref<AuditEvent[]>([])
  const dailyUsage = ref<DailyUsage[]>([])
  const auditLoading = ref(false)
  const usageLoading = ref(false)
  const nextBefore = ref('')
  const usageTotals = computed(() => dailyUsage.value.reduce((total, row) => ({ requests: total.requests + row.requests, failed: total.failed + row.failed_requests, tokens: total.tokens + row.prompt_tokens + row.completion_tokens, cost: total.cost + row.cost_microunits }), { requests: 0, failed: 0, tokens: 0, cost: 0 }))

  async function loadAudit(reset: boolean) {
    auditLoading.value = true
    try {
      const result = await fetchAuditEvents({ from: auditRange.value[0].toISOString(), to: auditRange.value[1].toISOString(), provider: auditFilter.provider || undefined, model: auditFilter.model || undefined, status: auditFilter.status, before: reset ? undefined : nextBefore.value || undefined, limit: 50 })
      auditEvents.value = reset ? result.items : [...auditEvents.value, ...result.items]
      nextBefore.value = result.next_before
    } finally { auditLoading.value = false }
  }
  function loadMore() { return loadAudit(false) }
  async function loadUsage() {
    usageLoading.value = true
    try { dailyUsage.value = await fetchDailyUsage({ from: localDate(usageRange.value[0]), to: localDate(usageRange.value[1]), provider: usageFilter.provider || undefined, model: usageFilter.model || undefined }) } finally { usageLoading.value = false }
  }
  function localDate(value: Date) { const year = value.getFullYear(); const month = String(value.getMonth() + 1).padStart(2, '0'); const day = String(value.getDate()).padStart(2, '0'); return `${year}-${month}-${day}` }
  function tokenTotal(row: AuditEvent) { return (row.prompt_tokens || 0) + (row.completion_tokens || 0) }
  function usageRowKey(row: DailyUsage) { return `${row.date}:${row.api_key_id}:${row.provider_code}:${row.model}` }
  function formatTime(value: string) { return new Date(value).toLocaleString() }
  function costText(value: number | null | undefined) { return value ? `USD ${(value / 1e6).toFixed(6)}` : '—' }
  onMounted(() => { loadAudit(true); loadUsage() })
</script>
