IndexedDB版本升级必须通过递增版本号触发onupgradeneeded事件,在其中显式重建对象存储和索引;结构变更与数据迁移须解耦,旧数据需在普通事务中分批转换,且跨版本升级需用oldVersion < 判断确保兼容。

IndexedDB 的数据库版本升级通过 onupgradeneeded 事件实现,这是唯一能安全创建、删除或修改对象存储(object store)和索引的地方。版本升级不是自动的“迁移脚本”,而是由开发者在该事件中显式控制结构变更逻辑,关键在于:版本号递增 + 事件内按需重建结构 + 兼容旧数据。
版本号是升级触发器,必须严格递增
IndexedDB 不比较结构差异,只看打开时传入的 version 是否大于当前数据库版本。如果新版本更高,就会触发 onupgradeneeded;相等或更低则不会触发,也不会报错。
- 首次打开用
indexedDB.open("mydb", 1)→ 创建 v1 数据库 - 后续想加字段,必须调用
indexedDB.open("mydb", 2)→ 触发 v1→v2 升级 - 跳过中间版本(如从 v1 直接到 v3)也可以,但
onupgradeneeded中需覆盖所有中间变更逻辑
onupgradeneeded 中只能操作 event.target.result(IDBDatabase)
该事件的 event.target.result 是即将升级完成的数据库实例,此时可安全调用 createObjectStore、deleteObjectStore、transaction.objectStore() 等方法。注意:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
-
不能读写已有数据:v1 的数据还不可见,事务尚未提交,无法用
get或put操作旧记录(除非你手动开启只读事务并访问旧 store —— 但不推荐) -
新建 store 会清空同名旧 store:调用
createObjectStore("users")时若已存在同名 store,会抛出"InvalidStateError";必须先deleteObjectStore("users")再重建 -
索引需在 store 创建后立即添加:在
createObjectStore返回的IDBObjectStore上调用createIndex,否则后续无法补建(v2 升级时删了再建,索引也得重来)
处理数据迁移:升级后手动遍历+转换
结构变更(如新增字段、拆分字段、改主键)后,旧数据不会自动适配。你需要在 onupgradeneeded 处理完结构后,**另起一个普通事务**(非 upgrade 事务)去读取、转换、写回数据。
立即学习“Java免费学习笔记(深入)”;
- 例如:v1 中
{name: "Alice"},v2 要求{fullName: "Alice", firstName: "Alice", lastName: ""} - v2 升级时先删旧 store、建新 store 和索引
- 然后用
db.transaction("users", "readwrite")打开新 store,用openCursor()遍历旧格式数据,构造新对象并put进新 store - 注意游标遍历时避免阻塞 UI,可分批处理(如每次 100 条 +
setTimeout或requestIdleCallback)
降级不被支持,需业务层兜底
IndexedDB 不允许将数据库版本往回调(如从 v3 打开 v2)。如果用户安装了旧版应用,应主动检测并提示更新,或在初始化时判断当前版本是否低于期望值,走兼容路径(比如只读旧字段、忽略新字段)。
- 打开时检查
event.oldVersion和event.newVersion,可据此做分支逻辑 - 对跨多版本升级(如 v1→v4),可在
onupgradeneeded中用switch(event.oldVersion)分段处理,避免重复执行已生效的变更 - 上线前务必在真实环境测试升级路径,尤其关注大数据库的迁移耗时与内存占用

















