mirror of
https://gitee.com/wanwujie/sub2api
synced 2026-04-15 04:14:46 +08:00
feat: add claude max usage simulation with group switch
This commit is contained in:
@@ -691,6 +691,58 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Claude Max Usage 模拟(仅 anthropic 平台) -->
|
||||
<div v-if="createForm.platform === 'anthropic'" class="border-t pt-4">
|
||||
<div class="mb-1.5 flex items-center gap-1">
|
||||
<label class="text-sm font-medium text-gray-700 dark:text-gray-300">
|
||||
{{ t('admin.groups.claudeMaxSimulation.title') }}
|
||||
</label>
|
||||
<div class="group relative inline-flex">
|
||||
<Icon
|
||||
name="questionCircle"
|
||||
size="sm"
|
||||
:stroke-width="2"
|
||||
class="cursor-help text-gray-400 transition-colors hover:text-primary-500 dark:text-gray-500 dark:hover:text-primary-400"
|
||||
/>
|
||||
<div class="pointer-events-none absolute bottom-full left-0 z-50 mb-2 w-80 opacity-0 transition-all duration-200 group-hover:pointer-events-auto group-hover:opacity-100">
|
||||
<div class="rounded-lg bg-gray-900 p-3 text-white shadow-lg dark:bg-gray-800">
|
||||
<p class="text-xs leading-relaxed text-gray-300">
|
||||
{{ t('admin.groups.claudeMaxSimulation.tooltip') }}
|
||||
</p>
|
||||
<div class="absolute -bottom-1.5 left-3 h-3 w-3 rotate-45 bg-gray-900 dark:bg-gray-800"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="flex items-center gap-3">
|
||||
<button
|
||||
type="button"
|
||||
@click="createForm.simulate_claude_max_enabled = !createForm.simulate_claude_max_enabled"
|
||||
:class="[
|
||||
'relative inline-flex h-6 w-11 items-center rounded-full transition-colors',
|
||||
createForm.simulate_claude_max_enabled ? 'bg-primary-500' : 'bg-gray-300 dark:bg-dark-600'
|
||||
]"
|
||||
>
|
||||
<span
|
||||
:class="[
|
||||
'inline-block h-4 w-4 transform rounded-full bg-white shadow transition-transform',
|
||||
createForm.simulate_claude_max_enabled ? 'translate-x-6' : 'translate-x-1'
|
||||
]"
|
||||
/>
|
||||
</button>
|
||||
<span class="text-sm text-gray-500 dark:text-gray-400">
|
||||
{{
|
||||
createForm.simulate_claude_max_enabled
|
||||
? t('admin.groups.claudeMaxSimulation.enabled')
|
||||
: t('admin.groups.claudeMaxSimulation.disabled')
|
||||
}}
|
||||
</span>
|
||||
</div>
|
||||
<p class="mt-2 text-xs text-gray-500 dark:text-gray-400">
|
||||
{{ t('admin.groups.claudeMaxSimulation.hint') }}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<!-- 无效请求兜底(仅 anthropic/antigravity 平台,且非订阅分组) -->
|
||||
<div
|
||||
v-if="['anthropic', 'antigravity'].includes(createForm.platform) && createForm.subscription_type !== 'subscription'"
|
||||
@@ -1371,6 +1423,58 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Claude Max Usage 模拟(仅 anthropic 平台) -->
|
||||
<div v-if="editForm.platform === 'anthropic'" class="border-t pt-4">
|
||||
<div class="mb-1.5 flex items-center gap-1">
|
||||
<label class="text-sm font-medium text-gray-700 dark:text-gray-300">
|
||||
{{ t('admin.groups.claudeMaxSimulation.title') }}
|
||||
</label>
|
||||
<div class="group relative inline-flex">
|
||||
<Icon
|
||||
name="questionCircle"
|
||||
size="sm"
|
||||
:stroke-width="2"
|
||||
class="cursor-help text-gray-400 transition-colors hover:text-primary-500 dark:text-gray-500 dark:hover:text-primary-400"
|
||||
/>
|
||||
<div class="pointer-events-none absolute bottom-full left-0 z-50 mb-2 w-80 opacity-0 transition-all duration-200 group-hover:pointer-events-auto group-hover:opacity-100">
|
||||
<div class="rounded-lg bg-gray-900 p-3 text-white shadow-lg dark:bg-gray-800">
|
||||
<p class="text-xs leading-relaxed text-gray-300">
|
||||
{{ t('admin.groups.claudeMaxSimulation.tooltip') }}
|
||||
</p>
|
||||
<div class="absolute -bottom-1.5 left-3 h-3 w-3 rotate-45 bg-gray-900 dark:bg-gray-800"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="flex items-center gap-3">
|
||||
<button
|
||||
type="button"
|
||||
@click="editForm.simulate_claude_max_enabled = !editForm.simulate_claude_max_enabled"
|
||||
:class="[
|
||||
'relative inline-flex h-6 w-11 items-center rounded-full transition-colors',
|
||||
editForm.simulate_claude_max_enabled ? 'bg-primary-500' : 'bg-gray-300 dark:bg-dark-600'
|
||||
]"
|
||||
>
|
||||
<span
|
||||
:class="[
|
||||
'inline-block h-4 w-4 transform rounded-full bg-white shadow transition-transform',
|
||||
editForm.simulate_claude_max_enabled ? 'translate-x-6' : 'translate-x-1'
|
||||
]"
|
||||
/>
|
||||
</button>
|
||||
<span class="text-sm text-gray-500 dark:text-gray-400">
|
||||
{{
|
||||
editForm.simulate_claude_max_enabled
|
||||
? t('admin.groups.claudeMaxSimulation.enabled')
|
||||
: t('admin.groups.claudeMaxSimulation.disabled')
|
||||
}}
|
||||
</span>
|
||||
</div>
|
||||
<p class="mt-2 text-xs text-gray-500 dark:text-gray-400">
|
||||
{{ t('admin.groups.claudeMaxSimulation.hint') }}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<!-- 无效请求兜底(仅 anthropic/antigravity 平台,且非订阅分组) -->
|
||||
<div
|
||||
v-if="['anthropic', 'antigravity'].includes(editForm.platform) && editForm.subscription_type !== 'subscription'"
|
||||
@@ -1883,6 +1987,8 @@ const createForm = reactive({
|
||||
sora_video_price_per_request_hd: null as number | null,
|
||||
// Claude Code 客户端限制(仅 anthropic 平台使用)
|
||||
claude_code_only: false,
|
||||
// Claude Max usage 模拟开关(仅 anthropic 平台)
|
||||
simulate_claude_max_enabled: false,
|
||||
fallback_group_id: null as number | null,
|
||||
fallback_group_id_on_invalid_request: null as number | null,
|
||||
// 模型路由开关
|
||||
@@ -2123,6 +2229,8 @@ const editForm = reactive({
|
||||
sora_video_price_per_request_hd: null as number | null,
|
||||
// Claude Code 客户端限制(仅 anthropic 平台使用)
|
||||
claude_code_only: false,
|
||||
// Claude Max usage 模拟开关(仅 anthropic 平台)
|
||||
simulate_claude_max_enabled: false,
|
||||
fallback_group_id: null as number | null,
|
||||
fallback_group_id_on_invalid_request: null as number | null,
|
||||
// 模型路由开关
|
||||
@@ -2221,6 +2329,7 @@ const closeCreateModal = () => {
|
||||
createForm.sora_video_price_per_request = null
|
||||
createForm.sora_video_price_per_request_hd = null
|
||||
createForm.claude_code_only = false
|
||||
createForm.simulate_claude_max_enabled = false
|
||||
createForm.fallback_group_id = null
|
||||
createForm.fallback_group_id_on_invalid_request = null
|
||||
createForm.supported_model_scopes = ['claude', 'gemini_text', 'gemini_image']
|
||||
@@ -2239,6 +2348,8 @@ const handleCreateGroup = async () => {
|
||||
// 构建请求数据,包含模型路由配置
|
||||
const requestData = {
|
||||
...createForm,
|
||||
simulate_claude_max_enabled:
|
||||
createForm.platform === 'anthropic' ? createForm.simulate_claude_max_enabled : false,
|
||||
model_routing: convertRoutingRulesToApiFormat(createModelRoutingRules.value)
|
||||
}
|
||||
await adminAPI.groups.create(requestData)
|
||||
@@ -2278,6 +2389,7 @@ const handleEdit = async (group: AdminGroup) => {
|
||||
editForm.sora_video_price_per_request = group.sora_video_price_per_request
|
||||
editForm.sora_video_price_per_request_hd = group.sora_video_price_per_request_hd
|
||||
editForm.claude_code_only = group.claude_code_only || false
|
||||
editForm.simulate_claude_max_enabled = group.simulate_claude_max_enabled || false
|
||||
editForm.fallback_group_id = group.fallback_group_id
|
||||
editForm.fallback_group_id_on_invalid_request = group.fallback_group_id_on_invalid_request
|
||||
editForm.model_routing_enabled = group.model_routing_enabled || false
|
||||
@@ -2297,6 +2409,7 @@ const closeEditModal = () => {
|
||||
showEditModal.value = false
|
||||
editingGroup.value = null
|
||||
editModelRoutingRules.value = []
|
||||
editForm.simulate_claude_max_enabled = false
|
||||
editForm.copy_accounts_from_group_ids = []
|
||||
}
|
||||
|
||||
@@ -2312,6 +2425,8 @@ const handleUpdateGroup = async () => {
|
||||
// 转换 fallback_group_id: null -> 0 (后端使用 0 表示清除)
|
||||
const payload = {
|
||||
...editForm,
|
||||
simulate_claude_max_enabled:
|
||||
editForm.platform === 'anthropic' ? editForm.simulate_claude_max_enabled : false,
|
||||
fallback_group_id: editForm.fallback_group_id === null ? 0 : editForm.fallback_group_id,
|
||||
fallback_group_id_on_invalid_request:
|
||||
editForm.fallback_group_id_on_invalid_request === null
|
||||
@@ -2368,6 +2483,21 @@ watch(
|
||||
if (!['anthropic', 'antigravity'].includes(newVal)) {
|
||||
createForm.fallback_group_id_on_invalid_request = null
|
||||
}
|
||||
if (newVal !== 'anthropic') {
|
||||
createForm.simulate_claude_max_enabled = false
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
watch(
|
||||
() => editForm.platform,
|
||||
(newVal) => {
|
||||
if (!['anthropic', 'antigravity'].includes(newVal)) {
|
||||
editForm.fallback_group_id_on_invalid_request = null
|
||||
}
|
||||
if (newVal !== 'anthropic') {
|
||||
editForm.simulate_claude_max_enabled = false
|
||||
}
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user