缓存机制(Preview Cache)
总体说明
为避免重复转换、降低磁盘与 CPU 消耗、提升预览响应速度,预览产品在整体架构中引入了基于 Redis 的统一缓存机制。
缓存贯穿 预览请求 → 转换 → 轮询 → 再次访问 的完整生命周期,是系统性能与稳定性的关键组成部分。
当前版本采用 RedisTemplate 手动控制缓存读写 的方式,实现了对缓存结构、TTL 和清理时机的精细化管理。
一、缓存配置概览(application.yml)
1. Redis 连接与连接池配置(底层缓存载体)
yaml
spring:
data:
redis:
host: localhost
port: 6379
password:
database: 0
timeout: 200ms
lettuce:
pool:
max-active: 16
max-idle: 8
min-idle: 2
max-wait: 200ms设计要点:
- 单次操作超时 200ms
避免 Redis 异常导致请求线程被长时间阻塞。 - 连接池限额控制
在高并发轮询、批量缓存查询场景下,保证吞吐能力和稳定性。 - 统一 RedisTemplate
所有缓存读写通过统一模板完成,便于控制序列化和行为一致性。
2. 预览模块缓存配置(fileview.preview.cache)
yaml
fileview:
preview:
cache:
enabled: true
default-ttl-hours: 24
max-cache-size: 1000
conversion:
success-ttl: 86400 # 转换成功缓存(秒)
failed-ttl: 60 # 转换失败缓存(秒)
direct-preview-ttl: 86400 # 直接预览缓存(秒)当前真正生效的配置项:
conversion.success-ttlconversion.failed-ttldirect-preview-ttl
其余字段说明:
enabled:设计为缓存总开关,当前版本尚未绑定逻辑default-ttl-hours:设计为统一默认 TTL,当前版本未使用max-cache-size:设计为缓存容量控制参数,当前版本依赖 Redis 自身内存策略
从产品角度看,这些字段属于前瞻性配置项,为后续版本扩展预留。
二、缓存 Key 设计规范
1. 统一 Key 命名策略
缓存 Key 由统一的 Key 管理器 生成,避免各模块自行拼接导致混乱。
典型规则包括:
转换结果缓存:
convert:{fileId}:{targetFormat}convert:{fileId}:{targetFormat}:result
直接预览缓存:
preview:direct:{fileId}
其他业务缓存:
- 下载任务状态
- EPUB 解压目录
- 密码解锁状态
- ETag / 临时标记等
2. 设计价值
- Key 语义清晰,便于排查问题
- 支持按
fileId批量清理 - 避免不同功能之间发生 Key 冲突
三、缓存数据模型与状态表达
1. 核心缓存对象:PreviewCacheInfo
缓存中保存的是完整的预览状态快照,而不是简单的 URL 字符串。
核心信息包括:
- 文件元信息:
- 文件名、路径、格式、大小
- 预览结果:
previewUrl- 预览格式、预览文件大小
- 状态信息:
SUCCESS / FAILED / IN_PROGRESS / PASSWORD_REQUIRED等DIRECT / CONVERT模式
- 安全信息:
- 是否加密
- 错误码 / 错误原因
- 多页预览信息:
- 是否多页
- 总页数
- 每页 URL 列表
- 生命周期:
cachedAtexpiresAt
2. 设计价值
- 缓存即“最终态描述”,前端无需再进行复杂推断
- 适配直接预览、转换预览、多页预览等多种模式
- 为长轮询、重复访问提供统一数据来源
四、TTL 策略与缓存写入规则
1. 转换成功缓存
- TTL:
conversion.success-ttl(默认 24 小时) - 行为:
- 写入完整预览信息
- 支持单页与多页文件
- 多页场景下,第一页 URL 作为默认预览入口
产品意义:
成功结果可被长时间复用,大幅降低重复转换成本。
2. 转换失败缓存
- TTL:
conversion.failed-ttl(默认 60 秒) - 行为:
- 仅短暂记录失败状态与错误原因
- 到期后自动清理,允许重新尝试
产品意义:
避免“失败状态永久缓存”,提高系统自恢复能力。
3. 直接预览缓存(不经过转换)
- TTL:
direct-preview-ttl(默认 24 小时)
适用场景:
- 图片
- 可直接预览的非加密文件
产品意义:
对“无需转换”的文件提供与转换文件一致的缓存体验。
五、缓存清理与重算机制
系统支持多种主动清理策略:
1. 按文件清理
- 清除指定
fileId的所有缓存 - 适用于文件更新、权限变更等场景
2. 错误状态清理
- 当密码错误、密码过期、状态异常时
- 强制清理缓存并重新处理
3. 直接预览清理
- 用于密码校验失败、文件被撤回等场景
设计原则:
缓存是“加速器”,不是“状态锁死器”。
一旦安全条件或业务条件变化,允许重新计算,避免被缓存状态“锁死”。
六、缓存读取在预览流程中的位置
1. 预览请求的实际流程
- 请求进入预览接口
- 优先查询 Redis 缓存:
- 直接预览缓存
- 转换结果缓存
- 缓存命中:
- 直接返回结果
- 不再触发下载 / 转换 / MQ
- 缓存未命中或被清理:
- 进入完整预览流程(下载 / 转换 / 长轮询)
2. 设计价值
- 缓存命中路径完全短路后续逻辑
- 大幅减少磁盘 IO、CPU 转换、MQ 消息数量
- 是系统高性能运行的核心保障
七、小结
- 预览产品采用 Redis 作为统一缓存中心,覆盖预览全流程
- 缓存设计围绕 状态完整性、TTL 可控性、可清理性
- 成功结果长缓存、失败结果短缓存,兼顾性能与纠错能力
- 缓存命中可直接短路下载与转换流程
当前版本中,真正生效的缓存配置为:
conversion.success-ttlconversion.failed-ttldirect-preview-ttl