// Kokorone 資料模型 // R-2 會將 provider 由 sqlite 切換為 postgresql,並為 MemoryRetriever 加上 pgvector 語意檢索。 generator client { provider = "prisma-client" output = "../packages/db/generated" } datasource db { provider = "sqlite" } enum CharacterSource { ORIGINAL // 原創 EXISTING_WORK // 既有作品 } enum CharacterBuildStatus { CANDIDATE // 候補 BUILT // 已建置 } enum MemorySource { INTERACTION // 互動 OFFLINE_GENERATED // 離線生成 SOURCE_EXTRACTION // 原作萃取 } // 情緒標籤類型:對應情緒子系統六種狀態(見 D 群組) enum EmotionTag { CALM // 平靜 JOY // 愉悅 SAD // 低落 ALERT // 警戒 SHY // 害羞 GRUMPY // 彆扭 } enum RelationshipStage { STRANGER // 陌生 0-19 ACQUAINTANCE // 認識 20-39 FRIEND // 朋友 40-59 CLOSE_AMBIGUOUS // 摯友-曖昧 60-79 BONDED // 羈絆 80-100 } model User { id String @id @default(cuid()) name String createdAt DateTime @default(now()) updatedAt DateTime @updatedAt relationships Relationship[] relatedMemories EpisodicMemory[] @@map("users") } model Work { id String @id @default(cuid()) title String volumeProgress String? // 卷數進度 worldview String? // 世界觀 progressAnchor String? // 作品進度錨定點(M-9/N 群組使用;描述作品實際描寫過的時期) createdAt DateTime @default(now()) updatedAt DateTime @updatedAt characters Character[] @@map("works") } model Character { id String @id @default(cuid()) workId String? work Work? @relation(fields: [workId], references: [id], onDelete: SetNull) source CharacterSource buildStatus CharacterBuildStatus @default(CANDIDATE) // 角色設定表七欄位 basicInfo String // 基本資料:名字、年齡、外型、出身 backgroundStory String // 背景故事:成長經歷、重大事件 personalityArchetype String // 性格原型:傲嬌/冷淡/天然呆/元氣/大小姐/三無 likesDislikes String // 喜好/厭惡 goalsObsessions String // 目標/執念 speechStyle String // 說話方式:口癖、語尾詞、第一/第二人稱 initialRelationValue String? // 人際初始值:對誰親近、對誰有心結 createdAt DateTime @default(now()) updatedAt DateTime @updatedAt aliases CharacterAlias[] episodicMemories EpisodicMemory[] semanticMemories SemanticMemory[] proceduralRules ProceduralRule[] emotionState EmotionState? relationships Relationship[] @@map("characters") } model CharacterAlias { id String @id @default(cuid()) characterId String character Character @relation(fields: [characterId], references: [id], onDelete: Cascade) formalName String // 正式名 nickname String? // 暱稱 calledByOthers String? // 他人稱呼(作品中其他角色如何稱呼) createdAt DateTime @default(now()) @@map("character_aliases") } model EpisodicMemory { id String @id @default(cuid()) characterId String character Character @relation(fields: [characterId], references: [id], onDelete: Cascade) content String occurredAt DateTime // 發生時間 emotionTag EmotionTag emotionIntensity Float // 情緒強度 retrievalCount Int @default(0) // 提取次數 lastRetrievedAt DateTime? source MemorySource weight Float @default(1) // 權重(供遺忘/檢索排序使用) relatedUserId String? // 這段記憶與哪位使用者相關(E-5 關係加權檢索用) relatedUser User? @relation(fields: [relatedUserId], references: [id], onDelete: SetNull) createdAt DateTime @default(now()) @@map("episodic_memories") } model SemanticMemory { id String @id @default(cuid()) characterId String character Character @relation(fields: [characterId], references: [id], onDelete: Cascade) fact String // 去情境化事實 about String // 對象(關於誰/什麼) createdAt DateTime @default(now()) @@map("semantic_memories") } model ProceduralRule { id String @id @default(cuid()) characterId String character Character @relation(fields: [characterId], references: [id], onDelete: Cascade) situation String // 情境 responsePattern String // 回應模式 weight Float @default(1) createdAt DateTime @default(now()) updatedAt DateTime @updatedAt @@map("procedural_rules") } model EmotionState { id String @id @default(cuid()) characterId String @unique character Character @relation(fields: [characterId], references: [id], onDelete: Cascade) calm Float @default(100) // 平靜 joy Float @default(0) // 愉悅 sad Float @default(0) // 低落 alert Float @default(0) // 警戒 shy Float @default(0) // 害羞 grumpy Float @default(0) // 彆扭 updatedAt DateTime @updatedAt @@map("emotion_states") } model Relationship { id String @id @default(cuid()) characterId String character Character @relation(fields: [characterId], references: [id], onDelete: Cascade) userId String user User @relation(fields: [userId], references: [id], onDelete: Cascade) intimacy Int @default(0) // 親密度 0~100 trust Int @default(0) // 信任度 0~100 firstMet DateTime? lastInteraction DateTime? interactionCount Int @default(0) stage RelationshipStage @default(STRANGER) ledgerEntries SentimentLedgerEntry[] createdAt DateTime @default(now()) updatedAt DateTime @updatedAt @@unique([characterId, userId]) @@map("relationships") } model SentimentLedgerEntry { id String @id @default(cuid()) relationshipId String relationship Relationship @relation(fields: [relationshipId], references: [id], onDelete: Cascade) date DateTime event String weight Float // 允許正負:正向事件為正值,負向事件為負值 createdAt DateTime @default(now()) @@map("sentiment_ledger_entries") }