From 9989006f3dbdeb367f51722ae94073a302443e2f Mon Sep 17 00:00:00 2001 From: lion <120344285@qq.com> Date: Thu, 16 Jul 2026 17:40:43 +0800 Subject: [PATCH] =?UTF-8?q?=E5=91=A8=E6=8A=A5=E5=B0=8F=E7=A8=8B=E5=BA=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/api/admin/assets.ts | 1 + src/api/admin/teachers.ts | 19 +++ src/components/PaperLinkTeachersDialog.vue | 1 + src/views/assets/universities/index.vue | 10 +- .../components/TeacherDetailDialog.vue | 35 +++++ src/views/teachers/index.vue | 132 +++++++++++++++--- 6 files changed, 178 insertions(+), 20 deletions(-) diff --git a/src/api/admin/assets.ts b/src/api/admin/assets.ts index cf1484e..981c32b 100644 --- a/src/api/admin/assets.ts +++ b/src/api/admin/assets.ts @@ -11,6 +11,7 @@ export interface UniversityRow { longitude?: number | null address?: string | null remark?: string | null + sort_order?: number } export interface PaperListRow { diff --git a/src/api/admin/teachers.ts b/src/api/admin/teachers.ts index 9fb88ca..96632f0 100644 --- a/src/api/admin/teachers.ts +++ b/src/api/admin/teachers.ts @@ -43,6 +43,9 @@ export interface TeacherRow { phone?: string | null email?: string | null remark?: string | null + library_status?: 'pending' | 'active' | 'rejected' + library_status_label?: string | null + approved_at?: string | null } export interface TeacherStats { @@ -50,6 +53,7 @@ export interface TeacherStats { month_followed: number overdue: number partners: number + library_pending?: number } export interface FollowRecordRow { @@ -127,6 +131,21 @@ export async function batchUpdateTeacherStar(payload: { return data.data } +export async function approveTeacher(id: number) { + const { data } = await http.post>(`/admin/v1/teachers/${id}/approve`) + return data.data +} + +export async function rejectTeacher(id: number) { + const { data } = await http.post>(`/admin/v1/teachers/${id}/reject`) + return data.data +} + +export async function batchApproveTeachers(ids: number[]) { + const { data } = await http.post>('/admin/v1/teachers/batch-approve', { ids }) + return data.data +} + export async function fetchTeacherFollowRecords(teacherId: number) { const { data } = await http.get>( `/admin/v1/teachers/${teacherId}/follow-records`, diff --git a/src/components/PaperLinkTeachersDialog.vue b/src/components/PaperLinkTeachersDialog.vue index de8e8bc..5455021 100644 --- a/src/components/PaperLinkTeachersDialog.vue +++ b/src/components/PaperLinkTeachersDialog.vue @@ -55,6 +55,7 @@ async function loadTeachers(page = teacherPage.value) { page, page_size: teacherMeta.value.per_page, keyword: teacherKeyword.value.trim() || undefined, + library_status: 'linkable', }) teacherItems.value = res.items teacherMeta.value = res.meta diff --git a/src/views/assets/universities/index.vue b/src/views/assets/universities/index.vue index 4116242..deea129 100644 --- a/src/views/assets/universities/index.vue +++ b/src/views/assets/universities/index.vue @@ -32,6 +32,7 @@ const form = ref({ latitude: '', city: '', province: '', + sort_order: 0, }) const regionOptions = [ @@ -71,7 +72,7 @@ function searchUniversities() { function openCreate() { editing.value = null - form.value = { name: '', longitude: '', latitude: '', city: '', province: '' } + form.value = { name: '', longitude: '', latitude: '', city: '', province: '', sort_order: 0 } dialog.value = true } @@ -83,6 +84,7 @@ function openEdit(row: UniversityRow) { latitude: row.latitude != null ? String(row.latitude) : '', city: row.city || '', province: row.province || '', + sort_order: row.sort_order ?? 0, } dialog.value = true } @@ -130,6 +132,7 @@ async function save() { latitude: Number(form.value.latitude), city: form.value.city || null, province: form.value.province || null, + sort_order: Number(form.value.sort_order) || 0, } if (editing.value) { await updateUniversity(editing.value.id, payload) @@ -177,6 +180,7 @@ usePageLoad(load) + @@ -239,6 +243,10 @@ usePageLoad(load) + + +

数值越小越靠前,雷达地图与列表均按此排序

+
@@ -1094,6 +1180,14 @@ usePageLoad(async () => { .talent-stat-value.is-success { color: var(--el-color-success); } +.talent-stat-value.is-warning { + color: #d97706; +} + +.library-tabs { + margin-bottom: 16px; +} + .filter-source { width: 132px; }