// ============================================================================ // 工单系统 Schema // Module: platform_tickets // Version: v1.3 // ============================================================================ /// 工单 model Ticket { id String @id @default(uuid()) @db.Uuid ticketNo String @unique @db.VarChar(30) @map("ticket_no") // 基本信息 title String @db.VarChar(200) description String @db.Text // 分类与优先级 categoryId String @db.Uuid @map("category_id") category TicketCategory @relation(fields: [categoryId], references: [id]) priority TicketPriority @default(MEDIUM) tags String[] @default([]) // 状态 status TicketStatus @default(OPEN) // 人员 creatorId String @db.Uuid @map("creator_id") assigneeId String? @db.Uuid @map("assignee_id") assigneeGroupId String? @db.Uuid @map("assignee_group_id") assigneeGroup AssignmentGroup? @relation(fields: [assigneeGroupId], references: [id]) watcherIds String[] @default([]) @db.Uuid @map("watcher_ids") // 时间 createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") firstResponseAt DateTime? @map("first_response_at") resolvedAt DateTime? @map("resolved_at") closedAt DateTime? @map("closed_at") dueAt DateTime? @map("due_at") // SLA slaId String? @db.Uuid @map("sla_id") sla TicketSLA? @relation(fields: [slaId], references: [id]) slaBreached Boolean @default(false) @map("sla_breached") slaPausedAt DateTime? @map("sla_paused_at") slaPausedDuration Int @default(0) @map("sla_paused_duration") // 秒 // 满意度 satisfactionRating Int? @map("satisfaction_rating") // 1-5 satisfactionComment String? @db.Text @map("satisfaction_comment") satisfactionRatedAt DateTime? @map("satisfaction_rated_at") // 来源 source TicketSource @default(WEB) externalId String? @db.VarChar(100) @map("external_id") channelMetadata Json? @map("channel_metadata") // 解决方案 resolution String? @db.Text rootCause String? @db.Text @map("root_cause") // 关联 relatedTicketIds String[] @default([]) @db.Uuid @map("related_ticket_ids") parentTicketId String? @db.Uuid @map("parent_ticket_id") parentTicket Ticket? @relation("TicketHierarchy", fields: [parentTicketId], references: [id]) childTickets Ticket[] @relation("TicketHierarchy") // 审批关联 approvalInstanceId String? @db.Uuid @map("approval_instance_id") // 多区域/多租户 region String @default("CN") @db.VarChar(10) tenantId String? @db.Uuid @map("tenant_id") language String? @db.VarChar(10) // 合规标记 complianceFlag Boolean @default(false) @map("compliance_flag") // 软删除 deletedAt DateTime? @map("deleted_at") // 关联 comments TicketComment[] activities TicketActivity[] attachments TicketAttachment[] @@index([ticketNo]) @@index([status]) @@index([categoryId]) @@index([creatorId]) @@index([assigneeId]) @@index([assigneeGroupId]) @@index([createdAt]) @@index([region]) @@index([tenantId]) @@index([tenantId, region]) @@map("tickets") @@schema("platform_tickets") } /// 工单分类 model TicketCategory { id String @id @default(uuid()) @db.Uuid name String @db.VarChar(100) code String @unique @db.VarChar(50) description String? @db.Text icon String? @db.VarChar(50) // 层级 parentId String? @db.Uuid @map("parent_id") parent TicketCategory? @relation("CategoryHierarchy", fields: [parentId], references: [id]) children TicketCategory[] @relation("CategoryHierarchy") // 配置 defaultPriority TicketPriority @default(MEDIUM) @map("default_priority") defaultAssigneeGroupId String? @db.Uuid @map("default_assignee_group_id") defaultAssigneeGroup AssignmentGroup? @relation(fields: [defaultAssigneeGroupId], references: [id]) slaId String? @db.Uuid @map("sla_id") sla TicketSLA? @relation(fields: [slaId], references: [id]) formTemplateId String? @db.Uuid @map("form_template_id") // 可见性 allowedDepartmentIds String[] @default([]) @db.Uuid @map("allowed_department_ids") allowedRoleIds String[] @default([]) @db.Uuid @map("allowed_role_ids") // 状态 isActive Boolean @default(true) @map("is_active") sortOrder Int @default(0) @map("sort_order") // 审计 createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // 关联 tickets Ticket[] @@index([code]) @@index([parentId]) @@index([isActive]) @@map("ticket_categories") @@schema("platform_tickets") } /// 工单评论 model TicketComment { id String @id @default(uuid()) @db.Uuid ticketId String @db.Uuid @map("ticket_id") ticket Ticket @relation(fields: [ticketId], references: [id]) // 内容 content String @db.Text // 类型 type CommentType @default(COMMENT) isInternal Boolean @default(false) @map("is_internal") visibilityScope VisibilityScope @default(ALL) @map("visibility_scope") // 作者 authorId String @db.Uuid @map("author_id") // @提醒 mentionedUserIds String[] @default([]) @db.Uuid @map("mentioned_user_ids") // 审计 createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") deletedAt DateTime? @map("deleted_at") // 关联 attachments TicketAttachment[] @@index([ticketId]) @@index([authorId]) @@map("ticket_comments") @@schema("platform_tickets") } /// 工单附件 model TicketAttachment { id String @id @default(uuid()) @db.Uuid ticketId String @db.Uuid @map("ticket_id") ticket Ticket @relation(fields: [ticketId], references: [id]) commentId String? @db.Uuid @map("comment_id") comment TicketComment? @relation(fields: [commentId], references: [id]) // 文件信息 fileName String @db.VarChar(255) @map("file_name") fileUrl String @db.VarChar(500) @map("file_url") fileSize Int @map("file_size") mimeType String @db.VarChar(100) @map("mime_type") // 上传者 uploadedBy String @db.Uuid @map("uploaded_by") // 审计 createdAt DateTime @default(now()) @map("created_at") @@index([ticketId]) @@index([commentId]) @@map("ticket_attachments") @@schema("platform_tickets") } /// 工单活动日志 model TicketActivity { id String @id @default(uuid()) @db.Uuid ticketId String @db.Uuid @map("ticket_id") ticket Ticket @relation(fields: [ticketId], references: [id]) // 活动类型 type ActivityType // 活动内容 content Json // 操作者(null 表示系统自动操作) operatorId String? @db.Uuid @map("operator_id") // 审计 createdAt DateTime @default(now()) @map("created_at") @@index([ticketId]) @@index([createdAt]) @@map("ticket_activities") @@schema("platform_tickets") } /// SLA 配置 model TicketSLA { id String @id @default(uuid()) @db.Uuid name String @db.VarChar(100) description String? @db.Text // 响应时间(分钟) firstResponseTime Json @map("first_response_time") // { low, medium, high, urgent } // 解决时间(分钟) resolutionTime Json @map("resolution_time") // { low, medium, high, urgent } // 工作时间配置 businessHours Json @map("business_hours") // { start, end, timezone, weekdays } excludeHolidays Boolean @default(true) @map("exclude_holidays") holidayCalendarId String? @db.Uuid @map("holiday_calendar_id") // 升级策略 escalationRules Json? @map("escalation_rules") // 状态 isActive Boolean @default(true) @map("is_active") isDefault Boolean @default(false) @map("is_default") // 审计 createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // 关联 categories TicketCategory[] tickets Ticket[] @@map("ticket_slas") @@schema("platform_tickets") } /// 处理组 model AssignmentGroup { id String @id @default(uuid()) @db.Uuid name String @db.VarChar(100) code String @unique @db.VarChar(50) description String? @db.Text // 成员 memberIds String[] @db.Uuid @map("member_ids") managerId String? @db.Uuid @map("manager_id") // 技能 skills String[] @default([]) // 分配策略 assignmentStrategy AssignmentStrategy @default(ROUND_ROBIN) @map("assignment_strategy") // 状态 isActive Boolean @default(true) @map("is_active") // 审计 createdAt DateTime @default(now()) @map("created_at") updatedAt DateTime @updatedAt @map("updated_at") // 关联 categories TicketCategory[] tickets Ticket[] @@index([code]) @@map("assignment_groups") @@schema("platform_tickets") } // ============================================================================ // 枚举定义 // ============================================================================ enum TicketStatus { OPEN ASSIGNED IN_PROGRESS PENDING RESOLVED CLOSED CANCELLED @@schema("platform_tickets") } enum TicketPriority { LOW MEDIUM HIGH URGENT @@schema("platform_tickets") } enum TicketSource { WEB MOBILE EMAIL API CHAT PHONE WALK_IN @@schema("platform_tickets") } enum CommentType { COMMENT STATUS_CHANGE ASSIGNMENT SYSTEM AI_CONTEXT @@schema("platform_tickets") } enum VisibilityScope { ALL AGENT_ONLY GROUP_ONLY INTERNAL @@schema("platform_tickets") } enum ActivityType { CREATED STATUS_CHANGED ASSIGNED REASSIGNED PRIORITY_CHANGED COMMENTED ATTACHMENT_ADDED SLA_BREACHED ESCALATED RESOLVED CLOSED REOPENED @@schema("platform_tickets") } enum AssignmentStrategy { ROUND_ROBIN LOAD_BALANCE MANUAL SKILL_BASED @@schema("platform_tickets") }