# 用户偏好设置 **本文引用的文件** - [preferences.service.ts](file://server/src/modules/preferences/preferences.service.ts) - [preferences.controller.ts](file://server/src/modules/preferences/preferences.controller.ts) - [schema.prisma](file://server/prisma/schema.prisma) - [index.vue](file://my-uniapp-vue3/src/pages/settings/index.vue) - [app.ts](file://server/src/app.ts) - [storage.ts](file://my-uniapp-vue3/src/utils/storage.ts) ## 目录 1. [简介](#简介) 2. [项目结构](#项目结构) 3. [核心组件](#核心组件) 4. [架构总览](#架构总览) 5. [详细组件分析](#详细组件分析) 6. [依赖关系分析](#依赖关系分析) 7. [性能考虑](#性能考虑) 8. [故障排除指南](#故障排除指南) 9. [结论](#结论) ## 简介 本文件面向AI有声书生成平台的用户偏好设置模型,围绕UserPreference模型的配置项进行深入解析,包括播放速度、音质、主题、默认音色ID、默认音量、自动播放下一首、仅WiFi下载等个性化设置字段。文档详细说明每个配置项的作用机制、取值范围与业务逻辑,并解释网络相关设置对用户体验的影响。同时提供偏好设置的CRUD操作示例,涵盖用户首次登录时的默认配置初始化、偏好修改更新、设置同步等实现方法。 ## 项目结构 用户偏好设置涉及前后端协作: - 前端(UniApp/Vue3)负责界面展示与交互,调用后端接口并本地持久化。 - 后端(Koa/Prisma)提供REST接口,访问MySQL数据库中的UserPreference表。 - 路由注册将“/api/user/preferences”挂载至偏好设置控制器。 ```mermaid graph TB subgraph "前端UniApp/Vue3" FE_Settings["设置页面
index.vue"] FE_Store["本地存储
storage.ts"] end subgraph "后端Koa" BE_Router["路由注册
app.ts"] BE_Controller["控制器
preferences.controller.ts"] BE_Service["服务层
preferences.service.ts"] end subgraph "数据库Prisma/MySQL" DB_Model["UserPreference 模型
schema.prisma"] end FE_Settings --> |HTTP 请求| BE_Router BE_Router --> BE_Controller BE_Controller --> BE_Service BE_Service --> DB_Model FE_Settings --> |本地缓存| FE_Store ``` 图表来源 - [app.ts:106](file://server/src/app.ts#L106) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) - [storage.ts:1-63](file://my-uniapp-vue3/src/utils/storage.ts#L1-L63) 章节来源 - [app.ts:106](file://server/src/app.ts#L106) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) - [storage.ts:1-63](file://my-uniapp-vue3/src/utils/storage.ts#L1-L63) ## 核心组件 - UserPreference 数据模型:定义用户偏好的字段、默认值与约束。 - 偏好设置控制器:提供获取与更新用户偏好的接口。 - 偏好设置服务层:封装数据库访问逻辑,包含upsert语义的默认初始化与条件更新。 - 前端设置页面:提供UI交互、本地缓存与后端同步。 章节来源 - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-73](file://server/src/modules/preferences/preferences.service.ts#L8-L73) - [index.vue:190-208](file://my-uniapp-vue3/src/pages/settings/index.vue#L190-L208) ## 架构总览 用户偏好设置采用“前端界面 + 后端接口 + 数据库模型”的分层设计。前端通过HTTP请求与后端交互,后端通过Prisma ORM访问MySQL;同时前端本地存储用于提升初次加载体验与离线可用性。 ```mermaid sequenceDiagram participant U as "用户" participant FE as "前端设置页面
index.vue" participant API as "后端接口
preferences.controller.ts" participant SVC as "服务层
preferences.service.ts" participant DB as "数据库
UserPreference" U->>FE : 打开设置页面 FE->>FE : 读取本地缓存
uni.getStorageSync('userPreferences') FE->>API : GET /api/user/preferences API->>SVC : getPreferences(userId) SVC->>DB : upsert 默认值 DB-->>SVC : 返回偏好记录 SVC-->>API : 返回偏好数据 API-->>FE : 响应数据 FE->>FE : 合并本地与远端偏好 FE->>FE : 保存到本地缓存 U->>FE : 修改偏好如默认音量 FE->>API : PUT /api/user/preferences API->>SVC : updatePreferences(userId, data) SVC->>DB : upsert 条件更新 DB-->>SVC : 返回更新后的记录 SVC-->>API : 返回更新结果 API-->>FE : 响应更新结果 FE->>FE : 同步本地缓存 ``` 图表来源 - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-73](file://server/src/modules/preferences/preferences.service.ts#L8-L73) - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) ## 详细组件分析 ### UserPreference 数据模型与字段说明 UserPreference模型定义了用户偏好的字段、默认值与约束,确保每个用户拥有独立且完整的偏好记录。 ```mermaid erDiagram USER ||--o| USER_PREFERENCE : "拥有" USER_PREFERENCE { int id PK int userId UK float playSpeed string quality string theme string defaultVoiceId int defaultVolume boolean autoPlayNext boolean wifiOnlyDownload datetime createdAt datetime updatedAt } ``` 图表来源 - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [schema.prisma:34](file://server/prisma/schema.prisma#L34) 字段作用与默认值 - playSpeed:播放速度,默认1.0(1倍速),用于控制TTS播放速率。 - quality:音质模式,默认"standard"(标准),影响音频生成质量与体积。 - theme:主题,默认"light"(浅色),影响界面外观。 - defaultVoiceId:默认音色ID,默认"cherry",用于生成音频时的默认音色。 - defaultVolume:默认音量,默认50,范围通常为0-100。 - autoPlayNext:自动播放下一首,默认true,提升连续收听体验。 - wifiOnlyDownload:仅WiFi下载,默认false,节省流量并避免产生额外费用。 章节来源 - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [preferences.service.ts:17-23](file://server/src/modules/preferences/preferences.service.ts#L17-L23) - [index.vue:200-208](file://my-uniapp-vue3/src/pages/settings/index.vue#L200-L208) ### 偏好设置控制器与路由 - GET /api/user/preferences:获取当前用户的偏好设置。 - PUT /api/user/preferences:更新部分或全部偏好设置。 - 控制器在开发环境使用测试用户ID,生产环境从上下文提取真实用户ID。 章节来源 - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [app.ts:106](file://server/src/app.ts#L106) ### 偏好设置服务层(CRUD与默认初始化) - getPreferences(userId):使用upsert语义,若不存在则按默认值创建,存在则返回现有记录。 - updatePreferences(userId, data):若已有记录则更新,否则按传入数据(缺失字段使用默认值)创建。 ```mermaid flowchart TD Start(["进入 getPreferences"]) --> Upsert["upsert 用户偏好
不存在则使用默认值创建"] Upsert --> ReturnPref["返回偏好记录"] ReturnPref --> End(["结束"]) UpdateStart(["进入 updatePreferences"]) --> FindExisting["查询是否存在记录"] FindExisting --> Exists{"存在?"} Exists --> |是| Update["更新记录"] Exists --> |否| Create["按传入数据创建
缺失字段使用默认值"] Update --> UpdateEnd(["返回更新结果"]) Create --> UpdateEnd ``` 图表来源 - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [preferences.service.ts:33-73](file://server/src/modules/preferences/preferences.service.ts#L33-L73) 章节来源 - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [preferences.service.ts:33-73](file://server/src/modules/preferences/preferences.service.ts#L33-L73) ### 前端设置页面与本地缓存 - 初始化:优先从本地缓存加载,再从后端拉取最新偏好,最后合并并写回本地缓存。 - 交互:支持修改默认音色、默认音量、自动播放下一首、仅WiFi下载等。 - 同步:每次修改后调用PUT接口更新后端,并同步本地缓存。 ```mermaid sequenceDiagram participant Page as "设置页面
index.vue" participant Local as "本地缓存
uni.getStorageSync" participant API as "后端接口
preferences.controller.ts" Page->>Local : 读取本地偏好 Page->>API : GET /api/user/preferences API-->>Page : 返回偏好数据 Page->>Page : 合并本地与远端偏好 Page->>Local : 写入合并后的偏好 Page->>API : PUT /api/user/preferences修改后 API-->>Page : 返回更新结果 Page->>Local : 同步本地缓存 ``` 图表来源 - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) 章节来源 - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) - [storage.ts:1-63](file://my-uniapp-vue3/src/utils/storage.ts#L1-L63) ### 网络相关设置:仅WiFi下载(wifiOnlyDownload) - 作用:当开启后,应用在非WiFi环境下阻止自动下载音频,避免产生移动流量费用。 - 业务逻辑:前端在触发下载前检查该开关,后端不直接参与此判断,但可通过接口返回当前偏好供前端决策。 - 用户体验:减少意外流量消耗,提升用户对网络使用的可控性。 章节来源 - [index.vue:266-270](file://my-uniapp-vue3/src/pages/settings/index.vue#L266-L270) - [schema.prisma:87-88](file://server/prisma/schema.prisma#L87-L88) ### 音色与音量设置 - defaultVoiceId:默认音色ID,前端提供音色选择器,后端存储对应字符串标识。 - defaultVolume:默认音量,前端滑条范围0-100,后端存储整数值。 - 业务逻辑:生成音频时优先使用用户偏好中的音色与音量,允许用户随时调整。 章节来源 - [index.vue:175-187](file://my-uniapp-vue3/src/pages/settings/index.vue#L175-L187) - [index.vue:254-258](file://my-uniapp-vue3/src/pages/settings/index.vue#L254-L258) - [schema.prisma:85-86](file://server/prisma/schema.prisma#L85-L86) - [schema.prisma:86-87](file://server/prisma/schema.prisma#L86-L87) ### 主题设置(theme) - 支持"light"(浅色)、"dark"(深色)、"auto"(跟随系统)三种模式。 - 前端本地存储主题键值,应用主题变更;与UserPreference中的theme字段配合使用。 章节来源 - [index.vue:167-172](file://my-uniapp-vue3/src/pages/settings/index.vue#L167-L172) - [schema.prisma:84-85](file://server/prisma/schema.prisma#L84-L85) ### 自动播放下一首(autoPlayNext) - 当开启时,播放完当前音频后自动播放下一首,提升连续收听体验。 - 与播放器逻辑配合,后端仅存储该偏好值。 章节来源 - [index.vue:260-264](file://my-uniapp-vue3/src/pages/settings/index.vue#L260-L264) - [schema.prisma:87-88](file://server/prisma/schema.prisma#L87-L88) ## 依赖关系分析 - 控制器依赖服务层,服务层依赖Prisma客户端访问数据库。 - 前端设置页面依赖HTTP请求工具与本地存储工具。 - 路由在应用启动时注册,将"/api/user/preferences"映射到控制器。 ```mermaid graph LR FE_Index["设置页面
index.vue"] --> FE_Request["HTTP 请求工具"] FE_Index --> FE_Store["本地存储
storage.ts"] FE_Request --> BE_Controller["控制器
preferences.controller.ts"] BE_Controller --> BE_Service["服务层
preferences.service.ts"] BE_Service --> DB["UserPreference 模型
schema.prisma"] APP["应用入口
app.ts"] --> BE_Controller ``` 图表来源 - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) - [storage.ts:1-63](file://my-uniapp-vue3/src/utils/storage.ts#L1-L63) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [app.ts:106](file://server/src/app.ts#L106) 章节来源 - [app.ts:106](file://server/src/app.ts#L106) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [schema.prisma:79-92](file://server/prisma/schema.prisma#L79-L92) - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) - [storage.ts:1-63](file://my-uniapp-vue3/src/utils/storage.ts#L1-L63) ## 性能考虑 - 本地缓存优先策略:首次渲染直接使用本地缓存,减少等待时间,随后异步拉取后端数据进行合并。 - upsert语义:避免重复创建,降低数据库写入压力,提高初始化效率。 - 滑条与开关交互:前端即时反馈,减少不必要的网络请求,仅在必要时调用PUT接口。 ## 故障排除指南 - 无法获取或保存偏好 - 检查后端路由是否正确注册至"/api/user/preferences"。 - 确认用户上下文是否正确传递(开发环境使用测试用户ID)。 - 查看数据库连接与Prisma迁移状态。 - 本地缓存不同步 - 确认前端在成功响应后执行了本地缓存写入。 - 检查跨端存储差异(H5与小程序)。 - 默认值异常 - 检查服务层upsert默认值逻辑与数据库模型默认值是否一致。 章节来源 - [app.ts:106](file://server/src/app.ts#L106) - [preferences.controller.ts:12-47](file://server/src/modules/preferences/preferences.controller.ts#L12-L47) - [preferences.service.ts:8-28](file://server/src/modules/preferences/preferences.service.ts#L8-L28) - [index.vue:272-309](file://my-uniapp-vue3/src/pages/settings/index.vue#L272-L309) ## 结论 UserPreference模型为AI有声书平台提供了完善的个性化能力,覆盖播放、外观、下载与存储等多个维度。通过前后端协同与本地缓存策略,既保证了用户体验的流畅性,又确保了数据的一致性与可靠性。后续可在保持现有默认值与upsert语义的基础上,进一步扩展更多偏好项并完善边界校验与错误处理。