// This is your Prisma schema file,
// learn more about it in the docs: https://pris.ly/d/prisma-schema

generator client {
  provider = "prisma-client-js"
}

datasource db {
  provider = "mysql"
  url      = env("DATABASE_URL")
}

/// 租户表
model Tenant {
  id          Int      @id @default(autoincrement())
  name        String /// 租户名称
  code        String   @unique /// 租户编码（唯一，用于访问链接）
  domain      String?  @unique /// 租户域名（可选，用于子域名访问）
  description String? /// 租户描述
  isSuper     Int      @default(0) @map("is_super") /// 是否为超级租户：0-否，1-是
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID（超级租户的用户ID）
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  users                       User[]
  roles                       Role[]
  menus                       TenantMenu[]
  permissions                 Permission[]
  dicts                       Dict[]
  configs                     Config[]
  school                      School? /// 学校信息（一对一）
  grades                      Grade[] /// 年级
  departments                 Department[] /// 部门
  classes                     Class[] /// 班级
  teachers                    Teacher[] /// 教师
  students                    Student[] /// 学生
  contestTeams                ContestTeam[] /// 赛事团队
  contestTeamMembers          ContestTeamMember[] /// 团队成员
  contestRegistrations        ContestRegistration[] /// 赛事报名
  contestRegistrationTeachers ContestRegistrationTeacher[] /// 报名指导老师关联
  contestWorks                ContestWork[] /// 参赛作品
  contestWorkAttachments      ContestWorkAttachment[] /// 作品附件
  contestWorkScores           ContestWorkScore[] /// 作品评分
  contestReviewRules          ContestReviewRule[] /// 评审规则
  // 作业管理关联
  homeworks                   Homework[] /// 作业
  homeworkSubmissions         HomeworkSubmission[] /// 作业提交记录
  homeworkReviewRules         HomeworkReviewRule[] /// 作业评审规则
  homeworkScores              HomeworkScore[] /// 作业评分
  // AI 3D 生成关联
  ai3dTasks                   AI3DTask[] /// AI 3D 生成任务
  creatorUser                 User?                        @relation("TenantCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser                User?                        @relation("TenantModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@map("tenants")
}

/// 用户表
model User {
  id           Int      @id @default(autoincrement())
  tenantId     Int      @map("tenant_id") /// 租户ID
  username     String /// 用户名（在租户内唯一）
  password     String /// 密码（加密存储）
  nickname     String /// 昵称
  email        String? /// 邮箱（在租户内唯一，可选）
  phone        String? /// 联系方式/手机号
  gender       String? /// 性别：male-男，female-女
  avatar       String? /// 头像URL
  organization String? /// 所属单位（用于评委等独立用户）
  status       String   @default("enabled") /// 账号状态：enabled-启用，disabled-停用
  validState   Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator      Int?     @map("creator") /// 创建人ID
  modifier     Int?     @map("modifier") /// 修改人ID
  createTime   DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime   DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant                              Tenant                       @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  roles                               UserRole[]
  logs                                Log[]
  createdBy                           User?                        @relation("UserCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifiedBy                          User?                        @relation("UserModifier", fields: [modifier], references: [id], onDelete: SetNull)
  createdUsers                        User[]                       @relation("UserCreator")
  modifiedUsers                       User[]                       @relation("UserModifier")
  createdRoles                        Role[]                       @relation("RoleCreator")
  modifiedRoles                       Role[]                       @relation("RoleModifier")
  createdPermissions                  Permission[]                 @relation("PermissionCreator")
  modifiedPermissions                 Permission[]                 @relation("PermissionModifier")
  createdMenus                        Menu[]                       @relation("MenuCreator")
  modifiedMenus                       Menu[]                       @relation("MenuModifier")
  createdDicts                        Dict[]                       @relation("DictCreator")
  modifiedDicts                       Dict[]                       @relation("DictModifier")
  createdDictItems                    DictItem[]                   @relation("DictItemCreator")
  modifiedDictItems                   DictItem[]                   @relation("DictItemModifier")
  createdConfigs                      Config[]                     @relation("ConfigCreator")
  modifiedConfigs                     Config[]                     @relation("ConfigModifier")
  createdTenants                      Tenant[]                     @relation("TenantCreator")
  modifiedTenants                     Tenant[]                     @relation("TenantModifier")
  teacher                             Teacher? /// 教师信息（一对一）
  student                             Student? /// 学生信息（一对一）
  createdSchools                      School[]                     @relation("SchoolCreator")
  modifiedSchools                     School[]                     @relation("SchoolModifier")
  createdGrades                       Grade[]                      @relation("GradeCreator")
  modifiedGrades                      Grade[]                      @relation("GradeModifier")
  createdDepartments                  Department[]                 @relation("DepartmentCreator")
  modifiedDepartments                 Department[]                 @relation("DepartmentModifier")
  createdClasses                      Class[]                      @relation("ClassCreator")
  modifiedClasses                     Class[]                      @relation("ClassModifier")
  createdTeachers                     Teacher[]                    @relation("TeacherCreator")
  modifiedTeachers                    Teacher[]                    @relation("TeacherModifier")
  createdStudents                     Student[]                    @relation("StudentCreator")
  modifiedStudents                    Student[]                    @relation("StudentModifier")
  // 赛事相关关联
  createdContests                     Contest[]                    @relation("ContestCreator")
  modifiedContests                    Contest[]                    @relation("ContestModifier")
  createdContestAttachments           ContestAttachment[]          @relation("ContestAttachmentCreator")
  modifiedContestAttachments          ContestAttachment[]          @relation("ContestAttachmentModifier")
  createdContestReviewRules           ContestReviewRule[]          @relation("ContestReviewRuleCreator")
  modifiedContestReviewRules          ContestReviewRule[]          @relation("ContestReviewRuleModifier")
  createdContestTeams                 ContestTeam[]                @relation("ContestTeamCreator")
  modifiedContestTeams                ContestTeam[]                @relation("ContestTeamModifier")
  ledContestTeams                     ContestTeam[]                @relation("ContestTeamLeader")
  createdContestTeamMembers           ContestTeamMember[]          @relation("ContestTeamMemberCreator")
  modifiedContestTeamMembers          ContestTeamMember[]          @relation("ContestTeamMemberModifier")
  contestTeamMembers                  ContestTeamMember[]          @relation("ContestTeamMemberUser")
  createdContestRegistrations         ContestRegistration[]        @relation("ContestRegistrationCreator")
  modifiedContestRegistrations        ContestRegistration[]        @relation("ContestRegistrationModifier")
  contestRegistrations                ContestRegistration[]        @relation("ContestRegistrationUser")
  createdContestWorks                 ContestWork[]                @relation("ContestWorkCreator")
  modifiedContestWorks                ContestWork[]                @relation("ContestWorkModifier")
  createdContestWorkAttachments       ContestWorkAttachment[]      @relation("ContestWorkAttachmentCreator")
  modifiedContestWorkAttachments      ContestWorkAttachment[]      @relation("ContestWorkAttachmentModifier")
  createdContestWorkJudgeAssignments  ContestWorkJudgeAssignment[] @relation("ContestWorkJudgeAssignmentCreator")
  modifiedContestWorkJudgeAssignments ContestWorkJudgeAssignment[] @relation("ContestWorkJudgeAssignmentModifier")
  assignedContestWorks                ContestWorkJudgeAssignment[] @relation("ContestWorkJudgeAssignmentJudge")
  createdContestWorkScores            ContestWorkScore[]           @relation("ContestWorkScoreCreator")
  modifiedContestWorkScores           ContestWorkScore[]           @relation("ContestWorkScoreModifier")
  scoredContestWorks                  ContestWorkScore[]           @relation("ContestWorkScoreJudge")
  createdContestNotices               ContestNotice[]              @relation("ContestNoticeCreator")
  modifiedContestNotices              ContestNotice[]              @relation("ContestNoticeModifier")
  contestJudges                       ContestJudge[]               @relation("ContestJudgeUser")
  createdContestJudges                ContestJudge[]               @relation("ContestJudgeCreator")
  modifiedContestJudges               ContestJudge[]               @relation("ContestJudgeModifier")
  contestRegistrationTeachers         ContestRegistrationTeacher[] @relation("ContestRegistrationTeacherUser")
  createdContestRegistrationTeachers  ContestRegistrationTeacher[] @relation("ContestRegistrationTeacherCreator")
  modifiedContestRegistrationTeachers ContestRegistrationTeacher[] @relation("ContestRegistrationTeacherModifier")
  // 作业管理关联
  createdHomeworks                    Homework[]                   @relation("HomeworkCreator")
  modifiedHomeworks                   Homework[]                   @relation("HomeworkModifier")
  homeworkSubmissions                 HomeworkSubmission[]         @relation("HomeworkSubmissionStudent")
  createdHomeworkSubmissions          HomeworkSubmission[]         @relation("HomeworkSubmissionCreator")
  modifiedHomeworkSubmissions         HomeworkSubmission[]         @relation("HomeworkSubmissionModifier")
  createdHomeworkReviewRules          HomeworkReviewRule[]         @relation("HomeworkReviewRuleCreator")
  modifiedHomeworkReviewRules         HomeworkReviewRule[]         @relation("HomeworkReviewRuleModifier")
  homeworkScoresAsReviewer            HomeworkScore[]              @relation("HomeworkScoreReviewer")
  createdHomeworkScores               HomeworkScore[]              @relation("HomeworkScoreCreator")
  modifiedHomeworkScores              HomeworkScore[]              @relation("HomeworkScoreModifier")
  // AI 3D 生成关联
  ai3dTasks                           AI3DTask[]                   @relation("AI3DTaskUser") /// 用户的 AI 3D 生成任务

  @@unique([tenantId, username])
  @@unique([tenantId, email])
  @@map("users")
}

/// 角色表
model Role {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  name        String /// 角色名称（在租户内唯一）
  code        String /// 角色编码（在租户内唯一）
  description String? /// 角色描述
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant           @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  users        UserRole[]
  permissions  RolePermission[]
  creatorUser  User?            @relation("RoleCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?            @relation("RoleModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, name])
  @@unique([tenantId, code])
  @@map("roles")
}

/// 用户角色关联表
model UserRole {
  id     Int @id @default(autoincrement())
  userId Int @map("user_id") /// 用户ID
  roleId Int @map("role_id") /// 角色ID

  user User @relation(fields: [userId], references: [id], onDelete: Cascade)
  role Role @relation(fields: [roleId], references: [id], onDelete: Cascade)

  @@unique([userId, roleId])
  @@map("user_roles")
}

/// 权限表
model Permission {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  name        String /// 权限名称
  code        String /// 权限编码（在租户内唯一）
  resource    String /// 资源名称，如 user, role, menu
  action      String /// 操作类型，如 create, read, update, delete
  description String? /// 权限描述
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant           @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  roles        RolePermission[]
  creatorUser  User?            @relation("PermissionCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?            @relation("PermissionModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, resource, action])
  @@unique([tenantId, code])
  @@map("permissions")
}

/// 角色权限关联表
model RolePermission {
  id           Int @id @default(autoincrement())
  roleId       Int @map("role_id") /// 角色ID
  permissionId Int @map("permission_id") /// 权限ID

  role       Role       @relation(fields: [roleId], references: [id], onDelete: Cascade)
  permission Permission @relation(fields: [permissionId], references: [id], onDelete: Cascade)

  @@unique([roleId, permissionId])
  @@map("role_permissions")
}

/// 菜单表（全局菜单模板，超级租户管理）
model Menu {
  id         Int      @id @default(autoincrement())
  name       String /// 菜单名称
  path       String? /// 路由路径
  icon       String? /// 图标
  component  String? /// 组件路径
  parentId   Int?     @map("parent_id") /// 父菜单ID
  permission String? /// 权限编码（用于控制菜单显示，如：menu:read）
  sort       Int      @default(0) /// 排序
  validState Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator    Int?     @map("creator") /// 创建人ID
  modifier   Int?     @map("modifier") /// 修改人ID
  createTime DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime DateTime @updatedAt @map("modify_time") /// 修改时间

  parent       Menu?        @relation("MenuTree", fields: [parentId], references: [id])
  children     Menu[]       @relation("MenuTree")
  tenantMenus  TenantMenu[] /// 租户菜单关联
  creatorUser  User?        @relation("MenuCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?        @relation("MenuModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@map("menus")
}

/// 租户菜单关联表（租户分配的菜单）
model TenantMenu {
  id       Int @id @default(autoincrement())
  tenantId Int @map("tenant_id") /// 租户ID
  menuId   Int @map("menu_id") /// 菜单ID

  tenant Tenant @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  menu   Menu   @relation(fields: [menuId], references: [id], onDelete: Cascade)

  @@unique([tenantId, menuId])
  @@map("tenant_menus")
}

/// 数据字典表
model Dict {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  name        String /// 字典名称
  code        String /// 字典编码（在租户内唯一）
  description String? /// 字典描述
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant     @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  items        DictItem[]
  creatorUser  User?      @relation("DictCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?      @relation("DictModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, code])
  @@map("dicts")
}

/// 字典项表
model DictItem {
  id         Int      @id @default(autoincrement())
  dictId     Int      @map("dict_id") /// 字典ID
  label      String /// 标签
  value      String /// 值
  sort       Int      @default(0) /// 排序
  validState Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator    Int?     @map("creator") /// 创建人ID
  modifier   Int?     @map("modifier") /// 修改人ID
  createTime DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime DateTime @updatedAt @map("modify_time") /// 修改时间

  dict         Dict  @relation(fields: [dictId], references: [id], onDelete: Cascade)
  creatorUser  User? @relation("DictItemCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User? @relation("DictItemModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@map("dict_items")
}

/// 系统配置表
model Config {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  key         String /// 配置键（在租户内唯一）
  value       String /// 配置值
  description String? /// 配置描述
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  creatorUser  User?  @relation("ConfigCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?  @relation("ConfigModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, key])
  @@map("configs")
}

/// 日志记录表
model Log {
  id         Int      @id @default(autoincrement())
  userId     Int?     @map("user_id") /// 用户ID
  action     String /// 操作类型
  content    String?  @db.Text /// 操作内容（使用 TEXT 类型支持长文本）
  ip         String? /// IP地址
  userAgent  String?  @map("user_agent") /// 用户代理
  createTime DateTime @default(now()) @map("create_time") /// 创建时间

  user User? @relation(fields: [userId], references: [id], onDelete: SetNull)

  @@map("logs")
}

/// 学校信息表（扩展租户信息）
model School {
  id          Int       @id @default(autoincrement())
  tenantId    Int       @unique @map("tenant_id") /// 租户ID（一对一）
  address     String? /// 学校地址
  phone       String? /// 联系电话
  principal   String? /// 校长姓名
  established DateTime? /// 建校时间
  description String?   @db.Text /// 学校描述
  logo        String? /// 学校Logo URL
  website     String? /// 学校网站
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime  @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  creatorUser  User?  @relation("SchoolCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?  @relation("SchoolModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@map("schools")
}

/// 年级表
model Grade {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  name        String /// 年级名称（如：一年级、二年级）
  code        String /// 年级编码（在租户内唯一，如：grade_1, grade_2）
  level       Int /// 年级级别（用于排序，如：1, 2, 3）
  description String? /// 年级描述
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant  @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  classes      Class[] /// 班级
  creatorUser  User?   @relation("GradeCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?   @relation("GradeModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, code])
  @@unique([tenantId, level])
  @@map("grades")
}

/// 部门表（支持树形结构）
model Department {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  name        String /// 部门名称
  code        String /// 部门编码（在租户内唯一）
  parentId    Int?     @map("parent_id") /// 父部门ID（支持树形结构）
  description String? /// 部门描述
  sort        Int      @default(0) /// 排序
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant       Tenant       @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  parent       Department?  @relation("DepartmentTree", fields: [parentId], references: [id])
  children     Department[] @relation("DepartmentTree")
  teachers     Teacher[] /// 教师
  creatorUser  User?        @relation("DepartmentCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?        @relation("DepartmentModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, code])
  @@map("departments")
}

/// 班级表
model Class {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  gradeId     Int      @map("grade_id") /// 年级ID
  name        String /// 班级名称（如：一年级1班、二年级2班）
  code        String /// 班级编码（在租户内唯一）
  type        Int      @default(1) @map("type") /// 班级类型：1-行政班级（教学班级），2-兴趣班
  capacity    Int? /// 班级容量（可选）
  description String? /// 班级描述
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 修改时间

  tenant                 Tenant                 @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  grade                  Grade                  @relation(fields: [gradeId], references: [id], onDelete: Cascade)
  students               Student[] /// 学生（行政班级）
  studentInterestClasses StudentInterestClass[] /// 学生兴趣班关联
  creatorUser            User?                  @relation("ClassCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser           User?                  @relation("ClassModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, code])
  @@map("classes")
}

/// 教师表
model Teacher {
  id           Int       @id @default(autoincrement())
  userId       Int       @unique @map("user_id") /// 用户ID（一对一）
  tenantId     Int       @map("tenant_id") /// 租户ID
  departmentId Int       @map("department_id") /// 部门ID
  employeeNo   String?   @map("employee_no") /// 工号（在租户内唯一）
  phone        String? /// 联系电话
  idCard       String?   @map("id_card") /// 身份证号
  gender       Int? /// 性别：1-男，2-女
  birthDate    DateTime? @map("birth_date") /// 出生日期
  hireDate     DateTime? @map("hire_date") /// 入职日期
  subject      String? /// 任教科目（可选，如：语文、数学）
  title        String? /// 职称（可选，如：高级教师、一级教师）
  description  String?   @db.Text /// 教师描述
  validState   Int       @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator      Int? /// 创建人ID
  modifier     Int? /// 修改人ID
  createTime   DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime   DateTime  @updatedAt @map("modify_time") /// 修改时间

  user         User       @relation(fields: [userId], references: [id], onDelete: Cascade)
  tenant       Tenant     @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  department   Department @relation(fields: [departmentId], references: [id], onDelete: Restrict)
  creatorUser  User?      @relation("TeacherCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?      @relation("TeacherModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, employeeNo])
  @@map("teachers")
}

/// 学生表
model Student {
  id             Int       @id @default(autoincrement())
  userId         Int       @unique @map("user_id") /// 用户ID（一对一）
  tenantId       Int       @map("tenant_id") /// 租户ID
  classId        Int       @map("class_id") /// 行政班级ID
  studentNo      String?   @map("student_no") /// 学号（在租户内唯一）
  phone          String? /// 联系电话
  idCard         String?   @map("id_card") /// 身份证号
  gender         Int? /// 性别：1-男，2-女
  birthDate      DateTime? @map("birth_date") /// 出生日期
  enrollmentDate DateTime? @map("enrollment_date") /// 入学日期
  parentName     String?   @map("parent_name") /// 家长姓名
  parentPhone    String?   @map("parent_phone") /// 家长电话
  address        String? /// 家庭地址
  description    String?   @db.Text /// 学生描述
  validState     Int       @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效
  creator        Int? /// 创建人ID
  modifier       Int? /// 修改人ID
  createTime     DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime     DateTime  @updatedAt @map("modify_time") /// 修改时间

  user            User                   @relation(fields: [userId], references: [id], onDelete: Cascade)
  tenant          Tenant                 @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  class           Class                  @relation(fields: [classId], references: [id], onDelete: Restrict)
  interestClasses StudentInterestClass[] /// 兴趣班关联
  creatorUser     User?                  @relation("StudentCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser    User?                  @relation("StudentModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, studentNo])
  @@map("students")
}

/// 学生兴趣班关联表（多对多）
model StudentInterestClass {
  id        Int @id @default(autoincrement())
  studentId Int @map("student_id") /// 学生ID
  classId   Int @map("class_id") /// 兴趣班ID

  student Student @relation(fields: [studentId], references: [id], onDelete: Cascade)
  class   Class   @relation(fields: [classId], references: [id], onDelete: Cascade)

  @@unique([studentId, classId])
  @@map("student_interest_classes")
}

// ============================================
// 赛事管理模块
// ============================================

/// 赛事表
model Contest {
  id                Int       @id @default(autoincrement())
  contestName       String    @map("contest_name") /// 赛事名称
  contestType       String    @map("contest_type") /// 赛事类型：individual/team
  contestState      String    @default("unpublished") @map("contest_state") /// 赛事状态：unpublished/published
  status            String    @default("ongoing") /// 赛事进度状态：ongoing/finished
  startTime         DateTime  @map("start_time") /// 赛事开始时间
  endTime           DateTime  @map("end_time") /// 赛事结束时间
  address           String? /// 线下地址
  content           String?   @db.Text /// 赛事详情
  contestTenants    Json?     @map("contest_tenants") /// 授权租户ID数组
  coverUrl          String?   @map("cover_url") /// 封面url
  posterUrl         String?   @map("poster_url") /// 海报url
  contactName       String?   @map("contact_name") /// 联系人
  contactPhone      String?   @map("contact_phone") /// 联系电话
  contactQrcode     String?   @map("contact_qrcode") /// 联系人二维码
  organizers        Json? /// 主办单位数组
  coOrganizers      Json?     @map("co_organizers") /// 协办单位数组
  sponsors          Json? /// 赞助单位数组
  // 报名配置
  registerStartTime DateTime  @map("register_start_time") /// 报名开始时间
  registerEndTime   DateTime  @map("register_end_time") /// 报名结束时间
  registerState     String?   @map("register_state") /// 报名任务状态：started/closed
  requireAudit      Boolean   @default(true) @map("require_audit") /// 报名是否需要审核
  allowedGrades     Json?     @map("allowed_grades") /// 允许报名的年级ID数组
  allowedClasses    Json?     @map("allowed_classes") /// 允许报名的班级ID数组
  teamMinMembers    Int?      @map("team_min_members") /// 团队最少成员数
  teamMaxMembers    Int?      @map("team_max_members") /// 团队最多成员数
  // 作品配置
  submitRule        String    @default("once") @map("submit_rule") /// 提交规则：once/resubmit
  submitStartTime   DateTime  @map("submit_start_time") /// 作品提交开始时间
  submitEndTime     DateTime  @map("submit_end_time") /// 作品提交结束时间
  workType          String?   @map("work_type") /// 作品类型（如：image/video/document/code）
  workRequirement   String?   @map("work_requirement") @db.Text /// 作品要求说明
  // 评审配置
  reviewRuleId      Int?      @map("review_rule_id") /// 评审规则id
  reviewStartTime   DateTime  @map("review_start_time") /// 评审开始时间
  reviewEndTime     DateTime  @map("review_end_time") /// 评审结束时间
  // 赛果配置
  resultState       String    @default("unpublished") @map("result_state") /// 赛果状态：unpublished/published
  resultPublishTime DateTime? @map("result_publish_time") /// 结果发布时间
  creator           Int? /// 创建人ID
  modifier          Int? /// 修改人ID
  createTime        DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime        DateTime  @updatedAt @map("modify_time") /// 更新时间
  validState        Int       @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  attachments     ContestAttachment[] /// 赛事附件
  reviewRule      ContestReviewRule?           @relation("ContestReviewRuleContest", fields: [reviewRuleId], references: [id], onDelete: SetNull)
  teams           ContestTeam[] /// 赛事团队
  registrations   ContestRegistration[] /// 报名记录
  works           ContestWork[] /// 参赛作品
  judges          ContestJudge[] /// 比赛评委
  workAssignments ContestWorkJudgeAssignment[] @relation("ContestWorkJudgeAssignmentContest") /// 作品分配
  workScores      ContestWorkScore[]           @relation("ContestWorkScoreContest") /// 作品评分
  notices         ContestNotice[] /// 赛事公告
  creatorUser     User?                        @relation("ContestCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser    User?                        @relation("ContestModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([contestName])
  @@index([contestState])
  @@index([startTime, endTime])
  @@index([reviewRuleId])
  @@map("t_contest")
}

/// 赛事附件表
model ContestAttachment {
  id         Int      @id @default(autoincrement())
  contestId  Int      @map("contest_id") /// 赛事id
  fileName   String   @map("file_name") /// 文件名
  fileUrl    String   @map("file_url") /// 文件路径
  format     String? /// 文件类型（png,mp4）
  fileType   String?  @map("file_type") /// 素材类型（image,video）
  size       String   @default("0") /// 文件大小
  creator    Int? /// 创建人ID
  modifier   Int? /// 修改人ID
  createTime DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime DateTime @updatedAt @map("modify_time") /// 更新时间
  validState Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  contest      Contest @relation(fields: [contestId], references: [id], onDelete: Cascade)
  creatorUser  User?   @relation("ContestAttachmentCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?   @relation("ContestAttachmentModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([contestId])
  @@map("t_contest_attachment")
}

/// 评审规则表（独立存在，可被多个赛事使用）
model ContestReviewRule {
  id              Int      @id @default(autoincrement())
  tenantId        Int      @map("tenant_id") /// 租户ID
  ruleName        String   @map("rule_name") /// 规则名称
  ruleDescription String?  @map("rule_description") @db.Text /// 规则说明
  judgeCount      Int?     @map("judge_count") /// 评委数量
  dimensions      Json /// 评分维度配置JSON
  calculationRule String   @default("average") @map("calculation_rule") /// 计算规则：average/remove_max_min/remove_min
  creator         Int? /// 创建人ID
  modifier        Int? /// 修改人ID
  createTime      DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime      DateTime @updatedAt @map("modify_time") /// 更新时间
  validState      Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant    @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  contests     Contest[] @relation("ContestReviewRuleContest") /// 使用此规则的赛事列表
  creatorUser  User?     @relation("ContestReviewRuleCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?     @relation("ContestReviewRuleModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([tenantId])
  @@map("t_contest_review_rule")
}

/// 赛事团队表
model ContestTeam {
  id           Int      @id @default(autoincrement())
  tenantId     Int      @map("tenant_id") /// 团队所属租户ID
  contestId    Int      @map("contest_id") /// 赛事id
  teamName     String   @map("team_name") /// 团队名称（租户内唯一）
  leaderUserId Int      @map("leader_user_id") /// 团队负责人用户id
  maxMembers   Int?     @map("max_members") /// 团队最大成员数
  creator      Int? /// 创建人ID
  modifier     Int? /// 修改人ID
  createTime   DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime   DateTime @updatedAt @map("modify_time") /// 更新时间
  validState   Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant        Tenant                @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  contest       Contest               @relation(fields: [contestId], references: [id], onDelete: Cascade)
  leader        User                  @relation("ContestTeamLeader", fields: [leaderUserId], references: [id], onDelete: Restrict)
  members       ContestTeamMember[] /// 团队成员
  registrations ContestRegistration[] /// 报名记录
  creatorUser   User?                 @relation("ContestTeamCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser  User?                 @relation("ContestTeamModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, contestId, teamName])
  @@index([contestId])
  @@index([leaderUserId])
  @@map("t_contest_team")
}

/// 团队成员表
model ContestTeamMember {
  id         Int      @id @default(autoincrement())
  tenantId   Int      @map("tenant_id") /// 成员所属租户ID
  teamId     Int      @map("team_id") /// 团队id
  userId     Int      @map("user_id") /// 成员用户id
  role       String   @default("member") /// 成员角色：member/leader/mentor
  creator    Int? /// 创建人ID
  modifier   Int? /// 修改人ID
  createTime DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime DateTime @updatedAt @map("modify_time") /// 更新时间

  tenant       Tenant      @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  team         ContestTeam @relation(fields: [teamId], references: [id], onDelete: Cascade)
  user         User        @relation("ContestTeamMemberUser", fields: [userId], references: [id], onDelete: Cascade)
  creatorUser  User?       @relation("ContestTeamMemberCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?       @relation("ContestTeamMemberModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, teamId, userId])
  @@index([teamId])
  @@index([userId])
  @@map("t_contest_team_member")
}

/// 赛事报名表
model ContestRegistration {
  id                Int       @id @default(autoincrement())
  contestId         Int       @map("contest_id") /// 赛事id
  tenantId          Int       @map("tenant_id") /// 所属租户ID
  registrationType  String?   @map("registration_type") /// 报名类型：individual/team
  teamId            Int?      @map("team_id") /// 团队id
  teamName          String?   @map("team_name") /// 团队名称快照（团队赛）
  userId            Int       @map("user_id") /// 账号id
  accountNo         String    @map("account_no") /// 报名账号（记录报名快照）
  accountName       String    @map("account_name") /// 报名账号名称（记录报名快照）
  role              String? /// 报名角色快照：leader/member/mentor
  registrationState String    @default("pending") @map("registration_state") /// 报名状态：pending/passed/rejected/withdrawn
  registrant        Int? /// 实际报名人用户ID
  registrationTime  DateTime  @map("registration_time") /// 报名时间
  reason            String?   @db.VarChar(1023) /// 审核理由
  operator          Int? /// 审核人用户ID
  operationDate     DateTime? @map("operation_date") /// 审核时间
  creator           Int? /// 创建人ID
  modifier          Int? /// 修改人ID
  createTime        DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime        DateTime  @updatedAt @map("modify_time") /// 更新时间

  contest      Contest       @relation(fields: [contestId], references: [id], onDelete: Cascade)
  tenant       Tenant        @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  team         ContestTeam?  @relation(fields: [teamId], references: [id], onDelete: SetNull)
  user         User          @relation("ContestRegistrationUser", fields: [userId], references: [id], onDelete: Restrict)
  works        ContestWork[] /// 参赛作品
  creatorUser  User?         @relation("ContestRegistrationCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?         @relation("ContestRegistrationModifier", fields: [modifier], references: [id], onDelete: SetNull)

  teachers ContestRegistrationTeacher[] /// 指导老师关联

  @@index([contestId, tenantId])
  @@index([userId, contestId])
  @@index([teamId])
  @@index([registrationState])
  @@map("t_contest_registration")
}

/// 报名指导老师关联表
model ContestRegistrationTeacher {
  id             Int      @id @default(autoincrement())
  registrationId Int      @map("registration_id") /// 报名记录ID
  tenantId       Int      @map("tenant_id") /// 租户ID
  userId         Int      @map("user_id") /// 指导老师用户ID
  isDefault      Boolean  @default(false) @map("is_default") /// 是否为默认指导老师（报名时自动添加的，不能移除）
  creator        Int? /// 创建人ID
  modifier       Int? /// 修改人ID
  createTime     DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime     DateTime @updatedAt @map("modify_time") /// 更新时间

  registration ContestRegistration @relation(fields: [registrationId], references: [id], onDelete: Cascade)
  tenant       Tenant              @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  user         User                @relation("ContestRegistrationTeacherUser", fields: [userId], references: [id], onDelete: Cascade)
  creatorUser  User?               @relation("ContestRegistrationTeacherCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?               @relation("ContestRegistrationTeacherModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([tenantId, registrationId, userId])
  @@index([registrationId])
  @@index([userId])
  @@map("t_contest_registration_teacher")
}

/// 参赛作品表
model ContestWork {
  id                 Int      @id @default(autoincrement())
  tenantId           Int      @map("tenant_id") /// 作品所属租户ID
  contestId          Int      @map("contest_id") /// 赛事id
  registrationId     Int      @map("registration_id") /// 报名记录id
  workNo             String?  @unique @map("work_no") /// 作品编号（展示用唯一编号）
  title              String /// 作品标题
  description        String?  @db.Text /// 作品说明
  files              Json? /// 作品文件列表（简易场景）
  version            Int      @default(1) /// 作品版本号（递增）
  isLatest           Boolean  @default(true) @map("is_latest") /// 是否最新版本
  status             String   @default("submitted") /// 作品状态：submitted/locked/reviewing/rejected/accepted
  submitTime         DateTime @default(now()) @map("submit_time") /// 提交时间
  submitterUserId    Int?     @map("submitter_user_id") /// 提交人用户id
  submitterAccountNo String?  @map("submitter_account_no") /// 提交人账号
  submitSource       String   @default("teacher") @map("submit_source") /// 提交来源：teacher/student/team_leader
  previewUrl         String?  @map("preview_url") @db.Text /// 作品预览URL（兼容单预览图）
  previewUrls        Json?    @map("preview_urls") /// 作品预览图URL列表（多模型场景）
  aiModelMeta        Json?    @map("ai_model_meta") /// AI建模元数据
  // 赛果相关字段
  finalScore         Decimal? @map("final_score") @db.Decimal(10, 2) /// 最终得分（根据规则计算）
  rank               Int? /// 排名
  awardLevel         String?  @map("award_level") /// 奖项等级：first/second/third/excellent/none
  awardName          String?  @map("award_name") /// 奖项名称（如：一等奖、金奖）
  certificateUrl     String?  @map("certificate_url") /// 证书URL
  creator            Int? /// 创建人ID
  modifier           Int? /// 修改人ID
  createTime         DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime         DateTime @updatedAt @map("modify_time") /// 更新时间
  validState         Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant                       @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  contest      Contest                      @relation(fields: [contestId], references: [id], onDelete: Cascade)
  registration ContestRegistration          @relation(fields: [registrationId], references: [id], onDelete: Restrict)
  attachments  ContestWorkAttachment[] /// 作品附件
  assignments  ContestWorkJudgeAssignment[] /// 作品分配
  scores       ContestWorkScore[] /// 作品评分
  creatorUser  User?                        @relation("ContestWorkCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?                        @relation("ContestWorkModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([tenantId, contestId, isLatest])
  @@index([registrationId])
  @@index([tenantId, contestId, submitTime, status])
  @@index([contestId, status])
  @@map("t_contest_work")
}

/// 作品附件文件表
model ContestWorkAttachment {
  id         Int      @id @default(autoincrement())
  tenantId   Int      @map("tenant_id") /// 所属租户ID
  contestId  Int      @map("contest_id") /// 赛事id
  workId     Int      @map("work_id") /// 作品id
  fileName   String   @map("file_name") /// 文件名
  fileUrl    String   @map("file_url") /// 文件路径
  format     String? /// 文件类型（png,mp4）
  fileType   String?  @map("file_type") /// 素材类型（image,video）
  size       String   @default("0") /// 文件大小
  creator    Int? /// 创建人ID
  modifier   Int? /// 修改人ID
  createTime DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime DateTime @updatedAt @map("modify_time") /// 更新时间

  work         ContestWork @relation(fields: [workId], references: [id], onDelete: Cascade)
  tenant       Tenant      @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  creatorUser  User?       @relation("ContestWorkAttachmentCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?       @relation("ContestWorkAttachmentModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([tenantId, contestId, workId])
  @@map("t_contest_work_attachment")
}

/// 比赛评委关联表（比赛与评委的多对多关系）
model ContestJudge {
  id          Int      @id @default(autoincrement())
  contestId   Int      @map("contest_id") /// 比赛id
  judgeId     Int      @map("judge_id") /// 评委用户id
  specialty   String? /// 评审专业领域（可选）
  weight      Decimal? @db.Decimal(3, 2) /// 评审权重（可选，用于加权平均计算）
  description String?  @db.Text /// 评委在该比赛中的说明
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 更新时间
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  contest      Contest @relation(fields: [contestId], references: [id], onDelete: Cascade)
  judge        User    @relation("ContestJudgeUser", fields: [judgeId], references: [id], onDelete: Cascade)
  creatorUser  User?   @relation("ContestJudgeCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?   @relation("ContestJudgeModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([contestId, judgeId])
  @@index([contestId])
  @@index([judgeId])
  @@map("t_contest_judge")
}

/// 作品分配表（评委分配作品）
model ContestWorkJudgeAssignment {
  id             Int      @id @default(autoincrement())
  contestId      Int      @map("contest_id") /// 赛事id
  workId         Int      @map("work_id") /// 作品id
  judgeId        Int      @map("judge_id") /// 评委用户id
  assignmentTime DateTime @default(now()) @map("assignment_time") /// 分配时间
  status         String   @default("assigned") /// 分配状态：assigned/reviewing/completed
  creator        Int? /// 创建人ID
  modifier       Int? /// 修改人ID
  createTime     DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime     DateTime @updatedAt @map("modify_time") /// 更新时间

  contest      Contest            @relation("ContestWorkJudgeAssignmentContest", fields: [contestId], references: [id], onDelete: Cascade)
  work         ContestWork        @relation(fields: [workId], references: [id], onDelete: Cascade)
  judge        User               @relation("ContestWorkJudgeAssignmentJudge", fields: [judgeId], references: [id], onDelete: Restrict)
  scores       ContestWorkScore[] /// 评分记录
  creatorUser  User?              @relation("ContestWorkJudgeAssignmentCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?              @relation("ContestWorkJudgeAssignmentModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([workId, judgeId])
  @@index([contestId, judgeId])
  @@index([workId])
  @@index([status])
  @@map("t_contest_work_judge_assignment")
}

/// 作品评分表
model ContestWorkScore {
  id              Int      @id @default(autoincrement())
  tenantId        Int      @map("tenant_id") /// 所属租户ID
  contestId       Int      @map("contest_id") /// 赛事id
  workId          Int      @map("work_id") /// 作品id
  assignmentId    Int      @map("assignment_id") /// 分配记录id
  judgeId         Int      @map("judge_id") /// 评委用户id
  judgeName       String   @map("judge_name") /// 评委姓名
  dimensionScores Json     @map("dimension_scores") /// 各维度评分JSON
  totalScore      Decimal  @map("total_score") @db.Decimal(10, 2) /// 总分
  comments        String?  @db.Text /// 评语
  scoreTime       DateTime @map("score_time") /// 评分时间
  creator         Int? /// 创建人ID
  modifier        Int? /// 修改人ID
  createTime      DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime      DateTime @updatedAt @map("modify_time") /// 更新时间
  validState      Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant                     @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  contest      Contest                    @relation("ContestWorkScoreContest", fields: [contestId], references: [id], onDelete: Cascade)
  work         ContestWork                @relation(fields: [workId], references: [id], onDelete: Cascade)
  assignment   ContestWorkJudgeAssignment @relation(fields: [assignmentId], references: [id], onDelete: Restrict)
  judge        User                       @relation("ContestWorkScoreJudge", fields: [judgeId], references: [id], onDelete: Restrict)
  creatorUser  User?                      @relation("ContestWorkScoreCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?                      @relation("ContestWorkScoreModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([contestId, workId, judgeId])
  @@index([workId])
  @@index([assignmentId])
  @@map("t_contest_work_score")
}

/// 赛事公告表
model ContestNotice {
  id          Int       @id @default(autoincrement())
  contestId   Int       @map("contest_id") /// 赛事id
  title       String /// 公告标题
  content     String    @db.Text /// 公告内容
  noticeType  String    @default("manual") @map("notice_type") /// 公告类型：system/manual/urgent
  priority    Int       @default(0) /// 优先级（数字越大优先级越高）
  publishTime DateTime? @map("publish_time") /// 发布时间
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime  @updatedAt @map("modify_time") /// 更新时间
  validState  Int       @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  contest      Contest @relation(fields: [contestId], references: [id], onDelete: Cascade)
  creatorUser  User?   @relation("ContestNoticeCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?   @relation("ContestNoticeModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([contestId])
  @@index([publishTime])
  @@index([noticeType])
  @@map("t_contest_notice")
}

// ============================================
// 作业管理模块
// ============================================

/// 作业表
model Homework {
  id              Int       @id @default(autoincrement())
  tenantId        Int       @map("tenant_id") /// 租户ID
  name            String /// 作业名称
  content         String?   @db.Text /// 作业内容（富文本）
  status          String    @default("unpublished") /// 作业状态：unpublished/published
  publishTime     DateTime? @map("publish_time") /// 发布时间
  submitStartTime DateTime  @map("submit_start_time") /// 提交开始时间
  submitEndTime   DateTime  @map("submit_end_time") /// 提交结束时间
  attachments     Json? /// 附件列表 [{fileName, fileUrl, size}]
  publishScope    Json?     @map("publish_scope") /// 公开范围（班级ID数组）
  reviewRuleId    Int?      @map("review_rule_id") /// 评审规则ID
  creator         Int? /// 创建人ID
  modifier        Int? /// 修改人ID
  createTime      DateTime  @default(now()) @map("create_time") /// 创建时间
  modifyTime      DateTime  @updatedAt @map("modify_time") /// 更新时间
  validState      Int       @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant               @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  reviewRule   HomeworkReviewRule?  @relation(fields: [reviewRuleId], references: [id], onDelete: SetNull)
  submissions  HomeworkSubmission[] /// 作业提交记录
  creatorUser  User?                @relation("HomeworkCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?                @relation("HomeworkModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([tenantId, status])
  @@index([tenantId, submitStartTime, submitEndTime])
  @@map("t_homework")
}

/// 作业提交表
model HomeworkSubmission {
  id              Int      @id @default(autoincrement())
  tenantId        Int      @map("tenant_id") /// 租户ID
  homeworkId      Int      @map("homework_id") /// 作业ID
  studentId       Int      @map("student_id") /// 学生用户ID
  workNo          String?  @map("work_no") /// 作品编号
  workName        String   @map("work_name") /// 作品名称
  workDescription String?  @map("work_description") @db.Text /// 作品介绍
  files           Json? /// 作品文件列表
  attachments     Json? /// 附件列表
  submitTime      DateTime @default(now()) @map("submit_time") /// 提交时间
  status          String   @default("pending") /// 状态：pending/reviewed/rejected
  totalScore      Decimal? @map("total_score") @db.Decimal(10, 2) /// 总分
  creator         Int? /// 创建人ID
  modifier        Int? /// 修改人ID
  createTime      DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime      DateTime @updatedAt @map("modify_time") /// 更新时间
  validState      Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant          @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  homework     Homework        @relation(fields: [homeworkId], references: [id], onDelete: Cascade)
  student      User            @relation("HomeworkSubmissionStudent", fields: [studentId], references: [id], onDelete: Cascade)
  scores       HomeworkScore[] /// 评分记录
  creatorUser  User?           @relation("HomeworkSubmissionCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?           @relation("HomeworkSubmissionModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([homeworkId, studentId])
  @@index([tenantId, homeworkId])
  @@index([studentId])
  @@index([status])
  @@map("t_homework_submission")
}

/// 作业评审规则表
model HomeworkReviewRule {
  id          Int      @id @default(autoincrement())
  tenantId    Int      @map("tenant_id") /// 租户ID
  name        String /// 规则名称
  description String?  @db.Text /// 规则描述
  criteria    Json /// 评分标准 [{name, maxScore, description}]
  creator     Int? /// 创建人ID
  modifier    Int? /// 修改人ID
  createTime  DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime  DateTime @updatedAt @map("modify_time") /// 更新时间
  validState  Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant     @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  homeworks    Homework[] /// 关联的作业
  creatorUser  User?      @relation("HomeworkReviewRuleCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?      @relation("HomeworkReviewRuleModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@index([tenantId])
  @@map("t_homework_review_rule")
}

/// 作业评分表
model HomeworkScore {
  id              Int      @id @default(autoincrement())
  tenantId        Int      @map("tenant_id") /// 租户ID
  submissionId    Int      @map("submission_id") /// 提交记录ID
  reviewerId      Int      @map("reviewer_id") /// 评审人ID
  dimensionScores Json     @map("dimension_scores") /// 各维度评分
  totalScore      Decimal  @map("total_score") @db.Decimal(10, 2) /// 总分
  comments        String?  @db.Text /// 评语
  scoreTime       DateTime @default(now()) @map("score_time") /// 评分时间
  creator         Int? /// 创建人ID
  modifier        Int? /// 修改人ID
  createTime      DateTime @default(now()) @map("create_time") /// 创建时间
  modifyTime      DateTime @updatedAt @map("modify_time") /// 更新时间
  validState      Int      @default(1) @map("valid_state") /// 有效状态：1-有效，2-失效

  tenant       Tenant             @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  submission   HomeworkSubmission @relation(fields: [submissionId], references: [id], onDelete: Cascade)
  reviewer     User               @relation("HomeworkScoreReviewer", fields: [reviewerId], references: [id], onDelete: Restrict)
  creatorUser  User?              @relation("HomeworkScoreCreator", fields: [creator], references: [id], onDelete: SetNull)
  modifierUser User?              @relation("HomeworkScoreModifier", fields: [modifier], references: [id], onDelete: SetNull)

  @@unique([submissionId, reviewerId])
  @@index([tenantId, submissionId])
  @@index([reviewerId])
  @@map("t_homework_score")
}

// ============================================
// AI 3D 模型生成模块
// ============================================

/// AI 3D 生成任务表
model AI3DTask {
  id             Int       @id @default(autoincrement())
  tenantId       Int       @map("tenant_id") /// 租户ID
  userId         Int       @map("user_id") /// 用户ID（任务归属用户）
  inputType      String    @map("input_type") /// 输入类型：text | image
  inputContent   String    @map("input_content") @db.Text /// 输入内容：文字描述或图片URL
  generateType   String    @default("Normal") @map("generate_type") /// 生成类型：Normal(带纹理) | Geometry(白模) | LowPoly(低多边形) | Sketch(草图)
  status         String    @default("pending") /// 任务状态：pending | processing | completed | failed | timeout
  resultUrl      String?   @map("result_url") @db.Text /// 生成的3D模型URL（单个结果，兼容旧数据）
  previewUrl     String?   @map("preview_url") @db.Text /// 预览图URL（单个结果，兼容旧数据）
  resultUrls     Json?     @map("result_urls") /// 生成的3D模型URL数组（多个结果，文生3D生成4个）
  previewUrls    Json?     @map("preview_urls") /// 预览图URL数组（多个结果）
  errorMessage   String?   @map("error_message") @db.Text /// 失败时的错误信息
  externalTaskId String?   @map("external_task_id") /// 外部AI服务的任务ID
  retryCount     Int       @default(0) @map("retry_count") /// 已重试次数
  createTime     DateTime  @default(now()) @map("create_time") /// 创建时间
  completeTime   DateTime? @map("complete_time") /// 完成时间

  tenant Tenant @relation(fields: [tenantId], references: [id], onDelete: Cascade)
  user   User   @relation("AI3DTaskUser", fields: [userId], references: [id], onDelete: Cascade)

  @@index([userId])
  @@index([tenantId])
  @@index([status])
  @@index([createTime])
  @@map("t_ai_3d_task")
}
