2025-12-18 19:07:21 +08:00
|
|
|
|
openapi: "3.0.0"
|
|
|
|
|
|
info:
|
|
|
|
|
|
title: "Survey System API"
|
|
|
|
|
|
version: "1.1.0"
|
|
|
|
|
|
components:
|
|
|
|
|
|
securitySchemes:
|
|
|
|
|
|
AdminBearerAuth:
|
|
|
|
|
|
type: http
|
|
|
|
|
|
scheme: bearer
|
|
|
|
|
|
bearerFormat: JWT
|
|
|
|
|
|
schemas:
|
|
|
|
|
|
User:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["id", "name", "phone", "createdAt"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
id:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
phone:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
createdAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
AdminUserView:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["id", "name", "phone", "createdAt", "password"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
id:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
phone:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
createdAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
password:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "密码 (敏感字段;前端掩码显示)"
|
2025-12-19 16:02:38 +08:00
|
|
|
|
groupIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "所属用户组ID列表"
|
|
|
|
|
|
UserGroup:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["id", "name", "createdAt"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
id:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
isSystem:
|
|
|
|
|
|
type: boolean
|
|
|
|
|
|
createdAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
memberCount:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
description: "成员数量"
|
2025-12-18 19:07:21 +08:00
|
|
|
|
QuestionCategory:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["id", "name", "createdAt"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
id:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
createdAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
Question:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["content", "type", "answer", "score"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
content:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
type:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
enum: ["single", "multiple", "judgment", "text"]
|
|
|
|
|
|
category:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "题目类别名称,缺省为通用"
|
|
|
|
|
|
default: "通用"
|
|
|
|
|
|
options:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
answer:
|
|
|
|
|
|
oneOf:
|
|
|
|
|
|
- type: string
|
|
|
|
|
|
- type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
score:
|
|
|
|
|
|
type: number
|
|
|
|
|
|
ExamSubject:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["id", "name", "totalScore", "timeLimitMinutes", "typeRatios", "categoryRatios"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
id:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
totalScore:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
timeLimitMinutes:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
default: 60
|
|
|
|
|
|
typeRatios:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
additionalProperties: false
|
|
|
|
|
|
properties:
|
|
|
|
|
|
single:
|
|
|
|
|
|
type: number
|
|
|
|
|
|
multiple:
|
|
|
|
|
|
type: number
|
|
|
|
|
|
judgment:
|
|
|
|
|
|
type: number
|
|
|
|
|
|
text:
|
|
|
|
|
|
type: number
|
|
|
|
|
|
categoryRatios:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
additionalProperties:
|
|
|
|
|
|
type: number
|
|
|
|
|
|
ExamTask:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["id", "name", "subjectId", "startAt", "endAt"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
id:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
subjectId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
startAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
endAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
2025-12-19 16:02:38 +08:00
|
|
|
|
selectionConfig:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "JSON string storing original selection of userIds and groupIds"
|
2025-12-18 19:07:21 +08:00
|
|
|
|
Pagination:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["page", "limit", "total", "pages"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
page:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
limit:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
total:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
pages:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
paths:
|
|
|
|
|
|
/api/users:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "创建用户或登录"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["name", "phone", "password"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "用户姓名,2-20位中英文"
|
|
|
|
|
|
phone:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "手机号"
|
|
|
|
|
|
password:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "登录密码"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User created"
|
|
|
|
|
|
|
|
|
|
|
|
/api/users/{id}:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取用户信息"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User details"
|
|
|
|
|
|
|
|
|
|
|
|
/api/questions/import:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "Excel导入题目"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
multipart/form-data:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
properties:
|
|
|
|
|
|
file:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: binary
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Import result"
|
|
|
|
|
|
|
|
|
|
|
|
/api/questions:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取题目列表"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "type"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
enum: ["single", "multiple", "judgment", "text"]
|
|
|
|
|
|
- name: "category"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
- name: "page"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
- name: "limit"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "List of questions"
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "添加单题"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
$ref: "#/components/schemas/Question"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Question created"
|
|
|
|
|
|
|
|
|
|
|
|
/api/questions/{id}:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新题目"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
$ref: "#/components/schemas/Question"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Question updated"
|
|
|
|
|
|
delete:
|
|
|
|
|
|
summary: "删除题目"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Question deleted"
|
|
|
|
|
|
|
|
|
|
|
|
/api/quiz/generate:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "生成随机试卷"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["userId", "subjectId"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
userId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
subjectId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "考试科目ID"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Generated quiz"
|
|
|
|
|
|
|
|
|
|
|
|
/api/quiz/submit:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "提交答题"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["userId", "answers"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
userId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
answers:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Submission result"
|
|
|
|
|
|
|
|
|
|
|
|
/api/quiz/records/{userId}:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取用户答题记录"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "userId"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User quiz records"
|
|
|
|
|
|
|
|
|
|
|
|
/api/quiz/records/detail/{recordId}:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取答题记录详情"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "recordId"
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Record detail"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/login:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "管理员登录"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["username", "password"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
username:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
password:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Login success"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/statistics:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取统计数据"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Statistics data"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/users:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取用户列表 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "page"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: integer
|
|
|
|
|
|
- name: "limit"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: integer
|
2025-12-19 16:02:38 +08:00
|
|
|
|
- name: "keyword"
|
|
|
|
|
|
in: query
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description: "搜索关键词(姓名/手机)"
|
2025-12-18 19:07:21 +08:00
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User list"
|
2025-12-19 16:02:38 +08:00
|
|
|
|
post:
|
|
|
|
|
|
summary: "创建用户 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["name", "phone", "password"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
phone:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
password:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
groupIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User created"
|
2025-12-18 19:07:21 +08:00
|
|
|
|
delete:
|
|
|
|
|
|
summary: "删除用户 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["userId"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
userId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Deleted"
|
|
|
|
|
|
|
2025-12-19 16:02:38 +08:00
|
|
|
|
/api/admin/users/{id}:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新用户 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
phone:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
password:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
groupIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User updated"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/user-groups:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取用户组列表"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Group list"
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "创建用户组"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["name"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Group created"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/user-groups/{id}:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新用户组"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
description:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Group updated"
|
|
|
|
|
|
delete:
|
|
|
|
|
|
summary: "删除用户组"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Group deleted"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/user-groups/{id}/members:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取用户组成员"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Group members"
|
|
|
|
|
|
|
2025-12-18 19:07:21 +08:00
|
|
|
|
/api/admin/users/export:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "导出用户 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Export users"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/users/import:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "导入用户 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
multipart/form-data:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
properties:
|
|
|
|
|
|
file:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: binary
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Import users"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/users/{userId}/records:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取用户历史答题记录 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: userId
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User records"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/question-categories:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取题目类别列表 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Category list"
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "新增题目类别 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["name"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Created"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/question-categories/{id}:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新题目类别 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["name"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Updated"
|
|
|
|
|
|
delete:
|
|
|
|
|
|
summary: "删除题目类别 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Deleted"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/subjects:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取考试科目列表 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Subjects"
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "新增考试科目 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
$ref: "#/components/schemas/ExamSubject"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Created"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/subjects/{id}:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新考试科目 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
$ref: "#/components/schemas/ExamSubject"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Updated"
|
|
|
|
|
|
delete:
|
|
|
|
|
|
summary: "删除考试科目 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Deleted"
|
|
|
|
|
|
|
|
|
|
|
|
/api/subjects:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取考试科目列表 (用户)"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Subjects"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/tasks:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取考试任务列表 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Tasks"
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "新增考试任务并分派用户 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
2025-12-19 16:02:38 +08:00
|
|
|
|
description: "Create task with mixed selection of users and groups (system handles de-duplication)"
|
2025-12-18 19:07:21 +08:00
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
2025-12-19 16:02:38 +08:00
|
|
|
|
required: ["name", "subjectId", "startAt", "endAt"]
|
2025-12-18 19:07:21 +08:00
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
subjectId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
startAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
endAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
userIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
2025-12-19 16:02:38 +08:00
|
|
|
|
groupIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
2025-12-18 19:07:21 +08:00
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Created"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/tasks/{id}:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新考试任务 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
2025-12-19 16:02:38 +08:00
|
|
|
|
description: "Update task with mixed selection (system handles de-duplication)"
|
2025-12-18 19:07:21 +08:00
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
2025-12-19 16:02:38 +08:00
|
|
|
|
properties:
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
subjectId:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
startAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
endAt:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
format: date-time
|
|
|
|
|
|
userIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
groupIds:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
items:
|
|
|
|
|
|
type: string
|
2025-12-18 19:07:21 +08:00
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Updated"
|
|
|
|
|
|
delete:
|
|
|
|
|
|
summary: "删除考试任务 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Deleted"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/tasks/{id}/report:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "导出任务报表 (管理员)"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: id
|
|
|
|
|
|
in: path
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Task report"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/config:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取抽题配置"
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Quiz config"
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "更新抽题配置"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Config updated"
|
2025-12-19 16:02:38 +08:00
|
|
|
|
|
|
|
|
|
|
/api/admin/configs:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取所有系统配置"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "All configs"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/password:
|
|
|
|
|
|
put:
|
|
|
|
|
|
summary: "修改管理员密码"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["oldPassword", "newPassword"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
oldPassword:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
newPassword:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Password updated"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/export/{type}:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "通用数据导出"
|
|
|
|
|
|
description: "type: users, questions, records, answers"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "type"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
enum: ["users", "questions", "records", "answers"]
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "JSON export data"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/restore:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "数据恢复"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
required: true
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
properties:
|
|
|
|
|
|
users:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
questions:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
records:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
answers:
|
|
|
|
|
|
type: array
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Data restored"
|
|
|
|
|
|
|
|
|
|
|
|
/api/exam-tasks/user/{userId}:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取指定用户的考试任务"
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "userId"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "User tasks"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/tasks/{id}/users:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取任务分派的用户"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "id"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Task users"
|
|
|
|
|
|
|
|
|
|
|
|
/api/admin/active-tasks:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "获取当前活跃任务统计"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Active tasks stats"
|
|
|
|
|
|
|
|
|
|
|
|
/api/users/validate:
|
|
|
|
|
|
post:
|
|
|
|
|
|
summary: "验证用户信息(用于导入校验)"
|
|
|
|
|
|
requestBody:
|
|
|
|
|
|
content:
|
|
|
|
|
|
application/json:
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: object
|
|
|
|
|
|
required: ["phone"]
|
|
|
|
|
|
properties:
|
|
|
|
|
|
phone:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
name:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Validation result"
|
|
|
|
|
|
|
|
|
|
|
|
/api/users/name/{name}:
|
|
|
|
|
|
get:
|
|
|
|
|
|
summary: "根据姓名查找用户"
|
|
|
|
|
|
security:
|
|
|
|
|
|
- AdminBearerAuth: []
|
|
|
|
|
|
parameters:
|
|
|
|
|
|
- name: "name"
|
|
|
|
|
|
in: "path"
|
|
|
|
|
|
required: true
|
|
|
|
|
|
schema:
|
|
|
|
|
|
type: string
|
|
|
|
|
|
responses:
|
|
|
|
|
|
"200":
|
|
|
|
|
|
description: "Users found"
|