feat: update frontend for four-tier role system
Add Student Admin and Teacher Admin roles to constants, types, store, permissions, routes, and admin UI. Teacher Admin sees contests and problemsets in sidebar; Student Admin sees only problems. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -24,7 +24,7 @@ const isNotRegularUser = computed(
|
|||||||
>
|
>
|
||||||
{{ getUserRole(props.user.admin_type).label }}
|
{{ getUserRole(props.user.admin_type).label }}
|
||||||
</n-tag>
|
</n-tag>
|
||||||
<n-tag size="small" v-if="props.user.admin_type === USER_TYPE.ADMIN">
|
<n-tag size="small" v-if="props.user.admin_type === USER_TYPE.STUDENT_ADMIN || props.user.admin_type === USER_TYPE.TEACHER_ADMIN">
|
||||||
{{
|
{{
|
||||||
props.user.problem_permission === PROBLEM_PERMISSION.ALL
|
props.user.problem_permission === PROBLEM_PERMISSION.ALL
|
||||||
? "全部"
|
? "全部"
|
||||||
|
|||||||
@@ -38,7 +38,8 @@ const userEditing = ref<User | null>(null)
|
|||||||
|
|
||||||
const adminOptions = [
|
const adminOptions = [
|
||||||
{ label: "全部用户", value: "" },
|
{ label: "全部用户", value: "" },
|
||||||
{ label: "管理员", value: USER_TYPE.ADMIN },
|
{ label: "学生管理员", value: USER_TYPE.STUDENT_ADMIN },
|
||||||
|
{ label: "教师管理员", value: USER_TYPE.TEACHER_ADMIN },
|
||||||
{ label: "超级管理员", value: USER_TYPE.SUPER_ADMIN },
|
{ label: "超级管理员", value: USER_TYPE.SUPER_ADMIN },
|
||||||
]
|
]
|
||||||
|
|
||||||
@@ -106,7 +107,8 @@ const columns: DataTableColumn<User>[] = [
|
|||||||
|
|
||||||
const options: SelectOption[] = [
|
const options: SelectOption[] = [
|
||||||
{ label: "普通", value: USER_TYPE.REGULAR_USER },
|
{ label: "普通", value: USER_TYPE.REGULAR_USER },
|
||||||
{ label: "管理员", value: USER_TYPE.ADMIN },
|
{ label: "学生管理员", value: USER_TYPE.STUDENT_ADMIN },
|
||||||
|
{ label: "教师管理员", value: USER_TYPE.TEACHER_ADMIN },
|
||||||
{ label: "超级管理员", value: USER_TYPE.SUPER_ADMIN },
|
{ label: "超级管理员", value: USER_TYPE.SUPER_ADMIN },
|
||||||
]
|
]
|
||||||
|
|
||||||
@@ -166,7 +168,7 @@ function createNewUser() {
|
|||||||
username: "",
|
username: "",
|
||||||
real_name: "",
|
real_name: "",
|
||||||
email: "",
|
email: "",
|
||||||
admin_type: "Admin",
|
admin_type: "Student Admin",
|
||||||
problem_permission: "None",
|
problem_permission: "None",
|
||||||
create_time: new Date(),
|
create_time: new Date(),
|
||||||
last_login: new Date(),
|
last_login: new Date(),
|
||||||
@@ -312,7 +314,7 @@ watch(() => [query.page, query.limit, query.type, query.orderBy], listUsers)
|
|||||||
<n-input v-model:value="password" />
|
<n-input v-model:value="password" />
|
||||||
</n-form-item-gi>
|
</n-form-item-gi>
|
||||||
<n-form-item-gi
|
<n-form-item-gi
|
||||||
v-if="!create && userEditing.admin_type === USER_TYPE.ADMIN"
|
v-if="!create && (userEditing.admin_type === USER_TYPE.STUDENT_ADMIN || userEditing.admin_type === USER_TYPE.TEACHER_ADMIN)"
|
||||||
:span="1"
|
:span="1"
|
||||||
label="出题权限"
|
label="出题权限"
|
||||||
>
|
>
|
||||||
|
|||||||
11
src/main.ts
11
src/main.ts
@@ -40,7 +40,9 @@ router.beforeEach(async (to, from, next) => {
|
|||||||
if (
|
if (
|
||||||
to.matched.some(
|
to.matched.some(
|
||||||
(record) =>
|
(record) =>
|
||||||
record.meta.requiresSuperAdmin || record.meta.requiresProblemPermission,
|
record.meta.requiresSuperAdmin ||
|
||||||
|
record.meta.requiresTeacherAdmin ||
|
||||||
|
record.meta.requiresProblemPermission,
|
||||||
)
|
)
|
||||||
) {
|
) {
|
||||||
if (!storage.get(STORAGE_KEY.AUTHED)) {
|
if (!storage.get(STORAGE_KEY.AUTHED)) {
|
||||||
@@ -63,6 +65,13 @@ router.beforeEach(async (to, from, next) => {
|
|||||||
next("/")
|
next("/")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
} else if (
|
||||||
|
to.matched.some((record) => record.meta.requiresTeacherAdmin)
|
||||||
|
) {
|
||||||
|
if (!userStore.isTeacherOrAbove) {
|
||||||
|
next("/")
|
||||||
|
return
|
||||||
|
}
|
||||||
} else if (
|
} else if (
|
||||||
to.matched.some((record) => record.meta.requiresProblemPermission)
|
to.matched.some((record) => record.meta.requiresProblemPermission)
|
||||||
) {
|
) {
|
||||||
|
|||||||
@@ -182,48 +182,48 @@ export const admins: RouteRecordRaw = {
|
|||||||
path: "contest/list",
|
path: "contest/list",
|
||||||
name: "admin contest list",
|
name: "admin contest list",
|
||||||
component: () => import("admin/contest/list.vue"),
|
component: () => import("admin/contest/list.vue"),
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "contest/create",
|
path: "contest/create",
|
||||||
name: "admin contest create",
|
name: "admin contest create",
|
||||||
component: () => import("admin/contest/detail.vue"),
|
component: () => import("admin/contest/detail.vue"),
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "contest/edit/:contestID",
|
path: "contest/edit/:contestID",
|
||||||
name: "admin contest edit",
|
name: "admin contest edit",
|
||||||
component: () => import("admin/contest/detail.vue"),
|
component: () => import("admin/contest/detail.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "contest/:contestID/problem/list",
|
path: "contest/:contestID/problem/list",
|
||||||
name: "admin contest problem list",
|
name: "admin contest problem list",
|
||||||
component: () => import("admin/problem/list.vue"),
|
component: () => import("admin/problem/list.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "contest/:contestID/problem/create",
|
path: "contest/:contestID/problem/create",
|
||||||
name: "admin contest problem create",
|
name: "admin contest problem create",
|
||||||
component: () => import("admin/problem/detail.vue"),
|
component: () => import("admin/problem/detail.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "contest/:contestID/problem/edit/:problemID",
|
path: "contest/:contestID/problem/edit/:problemID",
|
||||||
name: "admin contest problem edit",
|
name: "admin contest problem edit",
|
||||||
component: () => import("admin/problem/detail.vue"),
|
component: () => import("admin/problem/detail.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "contest/:contestID/helper",
|
path: "contest/:contestID/helper",
|
||||||
name: "admin contest helper",
|
name: "admin contest helper",
|
||||||
component: () => import("admin/contest/helper.vue"),
|
component: () => import("admin/contest/helper.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
// 只有super_admin可以访问的路由
|
// 只有super_admin可以访问的路由
|
||||||
{
|
{
|
||||||
@@ -293,27 +293,27 @@ export const admins: RouteRecordRaw = {
|
|||||||
path: "problemset/list",
|
path: "problemset/list",
|
||||||
name: "admin problemset list",
|
name: "admin problemset list",
|
||||||
component: () => import("admin/problemset/list.vue"),
|
component: () => import("admin/problemset/list.vue"),
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "problemset/create",
|
path: "problemset/create",
|
||||||
name: "admin problemset create",
|
name: "admin problemset create",
|
||||||
component: () => import("admin/problemset/edit.vue"),
|
component: () => import("admin/problemset/edit.vue"),
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "problemset/edit/:problemSetId",
|
path: "problemset/edit/:problemSetId",
|
||||||
name: "admin problemset edit",
|
name: "admin problemset edit",
|
||||||
component: () => import("admin/problemset/edit.vue"),
|
component: () => import("admin/problemset/edit.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: "problemset/:problemSetId",
|
path: "problemset/:problemSetId",
|
||||||
name: "admin problemset detail",
|
name: "admin problemset detail",
|
||||||
component: () => import("admin/problemset/detail.vue"),
|
component: () => import("admin/problemset/detail.vue"),
|
||||||
props: true,
|
props: true,
|
||||||
meta: { requiresSuperAdmin: true },
|
meta: { requiresTeacherAdmin: true },
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -166,7 +166,7 @@ const menus = computed<MenuOption[]>(() => [
|
|||||||
label: () =>
|
label: () =>
|
||||||
h(
|
h(
|
||||||
RouterLink,
|
RouterLink,
|
||||||
{ to: userStore.isTheAdmin ? "/admin/problem/list" : "/admin" },
|
{ to: userStore.isSuperAdmin ? "/admin" : "/admin/problem/list" },
|
||||||
{ default: () => "后台" },
|
{ default: () => "后台" },
|
||||||
),
|
),
|
||||||
show: userStore.isAdminRole,
|
show: userStore.isAdminRole,
|
||||||
|
|||||||
@@ -19,8 +19,8 @@ const options = computed<MenuOption[]>(() => {
|
|||||||
},
|
},
|
||||||
]
|
]
|
||||||
|
|
||||||
// admin 可以访问的功能
|
// Student Admin: only problems
|
||||||
if (userStore.isTheAdmin) {
|
if (userStore.isStudentAdmin) {
|
||||||
baseOptions.push({
|
baseOptions.push({
|
||||||
label: () =>
|
label: () =>
|
||||||
h(RouterLink, { to: "/admin/problem/list" }, { default: () => "题目" }),
|
h(RouterLink, { to: "/admin/problem/list" }, { default: () => "题目" }),
|
||||||
@@ -28,7 +28,40 @@ const options = computed<MenuOption[]>(() => {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
// super_admin 可以访问的功能
|
// Teacher Admin: problems + contests + problemsets
|
||||||
|
if (userStore.isTeacherAdmin) {
|
||||||
|
baseOptions.push(
|
||||||
|
{
|
||||||
|
label: () =>
|
||||||
|
h(
|
||||||
|
RouterLink,
|
||||||
|
{ to: "/admin/problem/list" },
|
||||||
|
{ default: () => "题目" },
|
||||||
|
),
|
||||||
|
key: "admin problem list",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: () =>
|
||||||
|
h(
|
||||||
|
RouterLink,
|
||||||
|
{ to: "/admin/contest/list" },
|
||||||
|
{ default: () => "比赛" },
|
||||||
|
),
|
||||||
|
key: "admin contest list",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: () =>
|
||||||
|
h(
|
||||||
|
RouterLink,
|
||||||
|
{ to: "/admin/problemset/list" },
|
||||||
|
{ default: () => "题单" },
|
||||||
|
),
|
||||||
|
key: "admin problemset list",
|
||||||
|
},
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Super Admin: everything
|
||||||
if (userStore.isSuperAdmin) {
|
if (userStore.isSuperAdmin) {
|
||||||
baseOptions.push(
|
baseOptions.push(
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -13,10 +13,21 @@ export const useUserStore = defineStore("user", () => {
|
|||||||
const isAuthed = computed(() => !!user.value?.email)
|
const isAuthed = computed(() => !!user.value?.email)
|
||||||
const isAdminRole = computed(
|
const isAdminRole = computed(
|
||||||
() =>
|
() =>
|
||||||
user.value?.admin_type === USER_TYPE.ADMIN ||
|
user.value?.admin_type === USER_TYPE.STUDENT_ADMIN ||
|
||||||
|
user.value?.admin_type === USER_TYPE.TEACHER_ADMIN ||
|
||||||
|
user.value?.admin_type === USER_TYPE.SUPER_ADMIN,
|
||||||
|
)
|
||||||
|
const isStudentAdmin = computed(
|
||||||
|
() => user.value?.admin_type === USER_TYPE.STUDENT_ADMIN,
|
||||||
|
)
|
||||||
|
const isTeacherAdmin = computed(
|
||||||
|
() => user.value?.admin_type === USER_TYPE.TEACHER_ADMIN,
|
||||||
|
)
|
||||||
|
const isTeacherOrAbove = computed(
|
||||||
|
() =>
|
||||||
|
user.value?.admin_type === USER_TYPE.TEACHER_ADMIN ||
|
||||||
user.value?.admin_type === USER_TYPE.SUPER_ADMIN,
|
user.value?.admin_type === USER_TYPE.SUPER_ADMIN,
|
||||||
)
|
)
|
||||||
const isTheAdmin = computed(() => user.value?.admin_type === USER_TYPE.ADMIN)
|
|
||||||
const isSuperAdmin = computed(
|
const isSuperAdmin = computed(
|
||||||
() => user.value?.admin_type === USER_TYPE.SUPER_ADMIN,
|
() => user.value?.admin_type === USER_TYPE.SUPER_ADMIN,
|
||||||
)
|
)
|
||||||
@@ -47,7 +58,9 @@ export const useUserStore = defineStore("user", () => {
|
|||||||
isFinished,
|
isFinished,
|
||||||
user,
|
user,
|
||||||
isAdminRole,
|
isAdminRole,
|
||||||
isTheAdmin,
|
isStudentAdmin,
|
||||||
|
isTeacherAdmin,
|
||||||
|
isTeacherOrAbove,
|
||||||
isSuperAdmin,
|
isSuperAdmin,
|
||||||
hasProblemPermission,
|
hasProblemPermission,
|
||||||
isAuthed,
|
isAuthed,
|
||||||
|
|||||||
@@ -133,7 +133,8 @@ export const CONTEST_TYPE = {
|
|||||||
|
|
||||||
export const USER_TYPE = {
|
export const USER_TYPE = {
|
||||||
REGULAR_USER: "Regular User",
|
REGULAR_USER: "Regular User",
|
||||||
ADMIN: "Admin",
|
STUDENT_ADMIN: "Student Admin",
|
||||||
|
TEACHER_ADMIN: "Teacher Admin",
|
||||||
SUPER_ADMIN: "Super Admin",
|
SUPER_ADMIN: "Super Admin",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -133,15 +133,22 @@ export function debounce<T extends (...args: any[]) => any>(
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function getUserRole(role: User["admin_type"]): {
|
export function getUserRole(role: User["admin_type"]): {
|
||||||
type: "default" | "info" | "error"
|
type: "default" | "info" | "warning" | "error"
|
||||||
label: "普通" | "管理员" | "超管"
|
label: "普通" | "学生管理员" | "教师管理员" | "超管"
|
||||||
} {
|
} {
|
||||||
const roleMap = {
|
const roleMap = {
|
||||||
[USER_TYPE.REGULAR_USER]: {
|
[USER_TYPE.REGULAR_USER]: {
|
||||||
type: "default" as const,
|
type: "default" as const,
|
||||||
label: "普通" as const,
|
label: "普通" as const,
|
||||||
},
|
},
|
||||||
[USER_TYPE.ADMIN]: { type: "info" as const, label: "管理员" as const },
|
[USER_TYPE.STUDENT_ADMIN]: {
|
||||||
|
type: "info" as const,
|
||||||
|
label: "学生管理员" as const,
|
||||||
|
},
|
||||||
|
[USER_TYPE.TEACHER_ADMIN]: {
|
||||||
|
type: "warning" as const,
|
||||||
|
label: "教师管理员" as const,
|
||||||
|
},
|
||||||
[USER_TYPE.SUPER_ADMIN]: {
|
[USER_TYPE.SUPER_ADMIN]: {
|
||||||
type: "error" as const,
|
type: "error" as const,
|
||||||
label: "超管" as const,
|
label: "超管" as const,
|
||||||
|
|||||||
@@ -1,19 +1,15 @@
|
|||||||
import { useUserStore } from "shared/store/user"
|
import { useUserStore } from "shared/store/user"
|
||||||
|
|
||||||
/**
|
|
||||||
* 权限检查工具函数
|
|
||||||
*/
|
|
||||||
export function usePermissions() {
|
export function usePermissions() {
|
||||||
const userStore = useUserStore()
|
const userStore = useUserStore()
|
||||||
|
|
||||||
return {
|
return {
|
||||||
// 基本权限检查
|
|
||||||
isAuthenticated: computed(() => userStore.isAuthed),
|
isAuthenticated: computed(() => userStore.isAuthed),
|
||||||
isAdminRole: computed(() => userStore.isAdminRole),
|
isAdminRole: computed(() => userStore.isAdminRole),
|
||||||
|
isTeacherOrAbove: computed(() => userStore.isTeacherOrAbove),
|
||||||
isSuperAdmin: computed(() => userStore.isSuperAdmin),
|
isSuperAdmin: computed(() => userStore.isSuperAdmin),
|
||||||
hasProblemPermission: computed(() => userStore.hasProblemPermission),
|
hasProblemPermission: computed(() => userStore.hasProblemPermission),
|
||||||
|
|
||||||
// 功能权限检查
|
|
||||||
canManageUsers: computed(() => userStore.isSuperAdmin),
|
canManageUsers: computed(() => userStore.isSuperAdmin),
|
||||||
canManageAnnouncements: computed(() => userStore.isSuperAdmin),
|
canManageAnnouncements: computed(() => userStore.isSuperAdmin),
|
||||||
canManageComments: computed(() => userStore.isSuperAdmin),
|
canManageComments: computed(() => userStore.isSuperAdmin),
|
||||||
@@ -22,9 +18,10 @@ export function usePermissions() {
|
|||||||
canSendMessages: computed(() => userStore.isSuperAdmin),
|
canSendMessages: computed(() => userStore.isSuperAdmin),
|
||||||
|
|
||||||
canManageProblems: computed(() => userStore.hasProblemPermission),
|
canManageProblems: computed(() => userStore.hasProblemPermission),
|
||||||
canManageContests: computed(() => userStore.isSuperAdmin),
|
canManageContests: computed(() => userStore.isTeacherOrAbove),
|
||||||
|
canManageProblemsets: computed(() => userStore.isTeacherOrAbove),
|
||||||
|
canViewClassroomData: computed(() => userStore.isTeacherOrAbove),
|
||||||
|
|
||||||
// 题目权限细分检查
|
|
||||||
canManageAllProblems: computed(
|
canManageAllProblems: computed(
|
||||||
() =>
|
() =>
|
||||||
userStore.user?.problem_permission === "All" || userStore.isSuperAdmin,
|
userStore.user?.problem_permission === "All" || userStore.isSuperAdmin,
|
||||||
@@ -34,17 +31,15 @@ export function usePermissions() {
|
|||||||
userStore.user?.problem_permission === "Own" && !userStore.isSuperAdmin,
|
userStore.user?.problem_permission === "Own" && !userStore.isSuperAdmin,
|
||||||
),
|
),
|
||||||
|
|
||||||
// 获取用户权限级别描述
|
|
||||||
getUserPermissionLevel: computed(() => {
|
getUserPermissionLevel: computed(() => {
|
||||||
if (userStore.isSuperAdmin) return "超级管理员"
|
if (userStore.isSuperAdmin) return "超级管理员"
|
||||||
if (userStore.isAdminRole) return "管理员"
|
if (userStore.isTeacherAdmin) return "教师管理员"
|
||||||
|
if (userStore.isStudentAdmin) return "学生管理员"
|
||||||
return "普通用户"
|
return "普通用户"
|
||||||
}),
|
}),
|
||||||
|
|
||||||
// 获取题目权限描述
|
|
||||||
getProblemPermissionLevel: computed(() => {
|
getProblemPermissionLevel: computed(() => {
|
||||||
if (!userStore.user) return "无权限"
|
if (!userStore.user) return "无权限"
|
||||||
|
|
||||||
switch (userStore.user.problem_permission) {
|
switch (userStore.user.problem_permission) {
|
||||||
case "All":
|
case "All":
|
||||||
return "管理所有题目"
|
return "管理所有题目"
|
||||||
@@ -59,13 +54,9 @@ export function usePermissions() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 路由权限检查
|
|
||||||
*/
|
|
||||||
export function checkRoutePermission(routeName: string): boolean {
|
export function checkRoutePermission(routeName: string): boolean {
|
||||||
const userStore = useUserStore()
|
const userStore = useUserStore()
|
||||||
|
|
||||||
// 需要super admin权限的路由
|
|
||||||
const superAdminRoutes = [
|
const superAdminRoutes = [
|
||||||
"admin home",
|
"admin home",
|
||||||
"admin config",
|
"admin config",
|
||||||
@@ -79,35 +70,39 @@ export function checkRoutePermission(routeName: string): boolean {
|
|||||||
"admin tutorial list",
|
"admin tutorial list",
|
||||||
"admin tutorial create",
|
"admin tutorial create",
|
||||||
"admin tutorial edit",
|
"admin tutorial edit",
|
||||||
|
]
|
||||||
|
|
||||||
|
const teacherAdminRoutes = [
|
||||||
"admin contest list",
|
"admin contest list",
|
||||||
"admin contest create",
|
"admin contest create",
|
||||||
"admin contest edit",
|
"admin contest edit",
|
||||||
"admin contest problem list",
|
"admin contest problem list",
|
||||||
"admin contest problem create",
|
"admin contest problem create",
|
||||||
"admin contest problem edit",
|
"admin contest problem edit",
|
||||||
|
"admin contest helper",
|
||||||
|
"admin problemset list",
|
||||||
|
"admin problemset create",
|
||||||
|
"admin problemset edit",
|
||||||
|
"admin problemset detail",
|
||||||
]
|
]
|
||||||
|
|
||||||
// 需要题目权限的路由
|
|
||||||
const problemPermissionRoutes = [
|
const problemPermissionRoutes = [
|
||||||
"admin problem list",
|
"admin problem list",
|
||||||
"admin problem create",
|
"admin problem create",
|
||||||
"admin problem edit",
|
"admin problem edit",
|
||||||
]
|
]
|
||||||
|
|
||||||
// 需要基本admin权限的路由
|
|
||||||
const adminRoutes: string[] = ["admin problem list"]
|
|
||||||
|
|
||||||
if (superAdminRoutes.includes(routeName)) {
|
if (superAdminRoutes.includes(routeName)) {
|
||||||
return userStore.isSuperAdmin
|
return userStore.isSuperAdmin
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (teacherAdminRoutes.includes(routeName)) {
|
||||||
|
return userStore.isTeacherOrAbove
|
||||||
|
}
|
||||||
|
|
||||||
if (problemPermissionRoutes.includes(routeName)) {
|
if (problemPermissionRoutes.includes(routeName)) {
|
||||||
return userStore.hasProblemPermission
|
return userStore.hasProblemPermission
|
||||||
}
|
}
|
||||||
|
|
||||||
if (adminRoutes.includes(routeName)) {
|
|
||||||
return userStore.isAdminRole
|
|
||||||
}
|
|
||||||
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ export interface Profile {
|
|||||||
submission_number: number
|
submission_number: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export type UserAdminType = "Regular User" | "Admin" | "Super Admin"
|
export type UserAdminType = "Regular User" | "Student Admin" | "Teacher Admin" | "Super Admin"
|
||||||
|
|
||||||
export interface User {
|
export interface User {
|
||||||
id: number
|
id: number
|
||||||
|
|||||||
Reference in New Issue
Block a user