This commit is contained in:
hptangxi
2025-07-07 09:58:45 +08:00
parent 0f85381082
commit 639fdd413f
8 changed files with 66 additions and 43 deletions

View File

@@ -1,6 +1,5 @@
<script setup lang="ts">
import GlobalProviders from "@/components/GlobalProviders.vue";
import GlobalTaskProgressBar from "@/components/GlobalTaskProgressBar.vue";
import Layout from "@/components/Layout.vue";
import { useAuthKey } from "@/services/auth";
import { computed } from "vue";
@@ -14,9 +13,6 @@ const isLoggedIn = computed(() => !!authKey.value);
<div id="app-root">
<layout v-if="isLoggedIn" key="layout" />
<router-view v-else key="auth" />
<!-- 全局任务进度条 -->
<global-task-progress-bar />
</div>
</global-providers>
</template>

View File

@@ -26,7 +26,8 @@ export const keysApi = {
},
// 获取分组统计信息
async getGroupStats(groupId: number): Promise<GroupStats> {
async getGroupStats(): Promise<any> {
// 传参补充groupId
await new Promise(resolve => setTimeout(resolve, 200));
return {};
},
@@ -96,11 +97,15 @@ export const keysApi = {
},
// 删除密钥
deleteKeys(group_id: number, keys_text: string): Promise<void> {
return http.post("/keys/delete-multiple", {
async deleteKeys(
group_id: number,
keys_text: string
): Promise<{ deleted_count: number; ignored_count: number; total_in_group: number }> {
const res = await http.post("/keys/delete-multiple", {
group_id,
keys_text,
});
return res.data;
},
// 测试密钥
@@ -117,7 +122,7 @@ export const keysApi = {
},
// 清空所有无效密钥
clearAllInvalidKeys(group_id: number): Promise<void> {
clearAllInvalidKeys(group_id: number): Promise<{ data: { message: string } }> {
return http.post(
"/keys/clear-all-invalid",
{ group_id },

View File

@@ -121,10 +121,6 @@ function handleClose() {
border-radius="3px"
class="progress-bar"
/>
<n-text v-if="taskInfo.message" depth="3" class="progress-message">
{{ taskInfo.message }}
</n-text>
</div>
</n-card>
</template>

View File

@@ -1,4 +1,5 @@
<script setup lang="ts">
import GlobalTaskProgressBar from "@/components/GlobalTaskProgressBar.vue";
import Logout from "@/components/Logout.vue";
import NavBar from "@/components/NavBar.vue";
</script>
@@ -32,6 +33,9 @@ import NavBar from "@/components/NavBar.vue";
</div>
</n-layout-content>
</n-layout>
<!-- 全局任务进度条 -->
<global-task-progress-bar />
</template>
<style scoped>

View File

@@ -15,6 +15,7 @@ import {
NModal,
NSelect,
useMessage,
type FormRules,
} from "naive-ui";
import { reactive, ref, watch } from "vue";
@@ -67,28 +68,36 @@ const channelTypeOptions = ref<{ label: string; value: string }[]>([]);
const configOptions = ref<GroupConfigOption[]>([]);
// 表单验证规则
const rules = {
name: {
required: true,
message: "请输入分组名称",
trigger: ["blur", "input"],
},
channel_type: {
required: true,
message: "请选择渠道类型",
trigger: ["blur", "change"],
},
test_model: {
required: true,
message: "请输入测试模型",
trigger: ["blur", "input"],
},
upstreams: {
type: "array",
min: 1,
message: "至少需要一个上游地址",
trigger: ["blur", "change"],
},
const rules: FormRules = {
name: [
{
required: true,
message: "请输入分组名称",
trigger: ["blur", "input"],
},
],
channel_type: [
{
required: true,
message: "请选择渠道类型",
trigger: ["blur", "change"],
},
],
test_model: [
{
required: true,
message: "请输入测试模型",
trigger: ["blur", "input"],
},
],
upstreams: [
{
type: "array",
min: 1,
message: "至少需要一个上游地址",
trigger: ["blur", "change"],
},
],
};
// 监听弹窗显示状态
@@ -223,7 +232,7 @@ async function handleSubmit() {
// 将configItems转换为config对象
const config: Record<string, number> = {};
formData.configItems.forEach(item => {
formData.configItems.forEach((item: any) => {
if (item.key && item.key.trim()) {
config[item.key] = item.value;
}
@@ -412,8 +421,9 @@ async function handleSubmit() {
label: opt.name,
value: opt.key,
disabled:
formData.configItems.map(item => item.key)?.includes(opt.key) &&
opt.key !== configItem.key,
formData.configItems
.map((item: any) => item.key)
?.includes(opt.key) && opt.key !== configItem.key,
}))
"
placeholder="请选择配置参数"

View File

@@ -49,7 +49,7 @@ watch(
);
async function loadStats() {
if (!props.group) {
if (!props.group?.id) {
stats.value = null;
return;
}
@@ -57,7 +57,7 @@ async function loadStats() {
try {
loading.value = true;
if (props.group?.id) {
stats.value = await keysApi.getGroupStats(props.group.id);
stats.value = await keysApi.getGroupStats();
}
} finally {
loading.value = false;

View File

@@ -52,8 +52,8 @@ async function handleSubmit() {
try {
loading.value = true;
const { data } = await keysApi.deleteKeys(props.groupId, keysText.value);
const { deleted_count, ignored_count, total_in_group } = data || {};
const res = await keysApi.deleteKeys(props.groupId, keysText.value);
const { deleted_count, ignored_count, total_in_group } = res || {};
const msg = `成功删除 ${deleted_count} 个密钥,忽略 ${ignored_count} 个密钥。当前分组共有 ${total_in_group} 个密钥。`;
message.info(msg, {
closable: true,

View File

@@ -37,7 +37,7 @@ const props = defineProps<Props>();
const keys = ref<KeyRow[]>([]);
const loading = ref(false);
const searchText = ref("");
const statusFilter = ref<"all" | "valid" | "invalid">("all");
const statusFilter = ref<"all" | "active" | "inactive">("all");
const currentPage = ref(1);
const pageSize = ref(9);
const total = ref(0);
@@ -64,7 +64,7 @@ const moreOptions = [
];
// 防抖定时器
let searchTimer: number | undefined = undefined;
let searchTimer: ReturnType<typeof setTimeout> | undefined = undefined;
let testingMsg: any = null;
let restoreMsg: any = null;
let deleteMsg: any = null;
@@ -206,6 +206,9 @@ async function restoreKey(key: KeyRow) {
positiveText: "确定",
negativeText: "取消",
onPositiveClick: async () => {
if (!props.selectedGroup?.id) {
return;
}
restoreMsg = window.$message.info("正在恢复密钥...", {
duration: 0,
});
@@ -234,6 +237,9 @@ async function deleteKey(key: KeyRow) {
positiveText: "确定",
negativeText: "取消",
onPositiveClick: async () => {
if (!props.selectedGroup?.id) {
return;
}
deleteMsg = window.$message.info("正在删除密钥...", {
duration: 0,
});
@@ -313,6 +319,9 @@ async function restoreAllInvalid() {
positiveText: "确定",
negativeText: "取消",
onPositiveClick: async () => {
if (!props.selectedGroup?.id) {
return;
}
restoreMsg = window.$message.info("正在恢复密钥...", {
duration: 0,
});
@@ -361,6 +370,9 @@ async function clearAllInvalid() {
positiveText: "确定",
negativeText: "取消",
onPositiveClick: async () => {
if (!props.selectedGroup?.id) {
return;
}
deleteMsg = window.$message.info("正在清除密钥...", {
duration: 0,
});