Initial commit: 网络验证平台

This commit is contained in:
Admin
2026-04-27 17:22:56 +08:00
commit afe67d704e
780 changed files with 88960 additions and 0 deletions
+138
View File
@@ -0,0 +1,138 @@
<script setup lang="ts">
import { Icon } from '@iconify/vue'
import { onMounted, ref } from 'vue'
import api from '@/services/api'
interface Card {
id: number
code: string
app_name: string
card_type_name: string
status: string
created_at: string
used_at: string | null
}
const loading = ref(true)
const cards = ref<Card[]>([])
onMounted(async () => {
try {
const data = await api.get<Card[]>('/agent/cards')
cards.value = data || []
}
catch (error) {
console.error('获取卡密列表失败:', error)
}
finally {
loading.value = false
}
})
function formatDate(dateStr: string) {
if (!dateStr)
return '-'
return new Date(dateStr).toLocaleDateString('zh-CN')
}
function getStatusBadge(status: string) {
const map: Record<string, { label: string, class: string }> = {
unused: { label: '未使用', class: 'bg-green-500/10 text-green-500' },
used: { label: '已使用', class: 'bg-blue-500/10 text-blue-500' },
expired: { label: '已过期', class: 'bg-red-500/10 text-red-500' },
disabled: { label: '已禁用', class: 'bg-gray-500/10 text-gray-500' },
}
return map[status] || { label: status, class: '' }
}
</script>
<template>
<div class="space-y-6">
<div class="flex items-center justify-between">
<div>
<h1 class="text-2xl font-bold">
卡密管理
</h1>
<p class="text-muted-foreground">
管理您生成的卡密
</p>
</div>
<UiButton as-child>
<router-link to="/agent/cards/create">
<Icon icon="lucide:plus" class="mr-2 h-4 w-4" />
生成卡密
</router-link>
</UiButton>
</div>
<UiCard>
<UiCardContent class="p-0">
<div v-if="loading" class="flex items-center justify-center py-12">
<Icon icon="lucide:loader-2" class="size-8 animate-spin text-muted-foreground" />
</div>
<div v-else-if="cards.length === 0" class="text-center py-12 text-muted-foreground">
<Icon icon="lucide:key" class="size-16 mx-auto mb-4 opacity-30" />
<p>暂无卡密记录</p>
<UiButton class="mt-4" as-child>
<router-link to="/agent/cards/create">
生成卡密
</router-link>
</UiButton>
</div>
<div v-else class="overflow-x-auto">
<table class="w-full">
<thead class="bg-muted/50">
<tr>
<th class="px-4 py-3 text-left text-sm font-medium">
卡密
</th>
<th class="px-4 py-3 text-left text-sm font-medium">
应用
</th>
<th class="px-4 py-3 text-left text-sm font-medium">
卡类
</th>
<th class="px-4 py-3 text-left text-sm font-medium">
状态
</th>
<th class="px-4 py-3 text-left text-sm font-medium">
创建时间
</th>
<th class="px-4 py-3 text-left text-sm font-medium">
使用时间
</th>
</tr>
</thead>
<tbody class="divide-y">
<tr v-for="card in cards" :key="card.id" class="hover:bg-muted/30">
<td class="px-4 py-3 font-mono text-sm">
{{ card.code }}
</td>
<td class="px-4 py-3 text-sm">
{{ card.app_name }}
</td>
<td class="px-4 py-3 text-sm">
{{ card.card_type_name }}
</td>
<td class="px-4 py-3">
<UiBadge :class="getStatusBadge(card.status).class" variant="outline">
{{ getStatusBadge(card.status).label }}
</UiBadge>
</td>
<td class="px-4 py-3 text-sm text-muted-foreground">
{{ formatDate(card.created_at) }}
</td>
<td class="px-4 py-3 text-sm text-muted-foreground">
{{ formatDate(card.used_at) }}
</td>
</tr>
</tbody>
</table>
</div>
</UiCardContent>
</UiCard>
</div>
</template>