模式版本
模式版本可标识 Realm 模式在某个时间点的状态。Realm 会跟踪每个 Realm 的模式版本,并使用该信息将每个 Realm 中的对象映射到正确的模式。
模式版本是指打开 Realm 时可以选择性地包含在 Realm 配置中的递增整数。如果客户端应用程序在打开 Realm 时未指定版本号,则该 Realm 默认采用 0 版本。
重要
单调递增版本
迁移必须将 Realm 更新到更高的模式版本。如果客户端应用程序打开的 Realm 的模式版本低于该 Realm 的当前版本,或是指定的模式版本与该 Realm 的当前版本相同但包含不同对象模式,Realm 则会引发错误。
迁移
迁移是一种将 Realm 及其包含的任何对象从一个模式版本更新到较新版本的函数。 通过迁移,您可以随时间灵活地更改对象模式,以适应新功能和重构。
提示
在开发期间绕过迁移
在开发或调试应用程序时,您可能更愿意删除而不是迁移 Realm。 使用deleteRealmIfMigrationNeeded标志在模式不匹配需要迁移时自动删除数据库。
切勿将此标记设为 true 的应用发布到生产环境。
每当您打开模式版本高于该 Realm 当前版本的现有 Realm 时,Realm 都会运行您定义的迁移函数。 该函数可以访问 Realm 的版本号,并以增量方式更新 Realm 中的对象以符合新模式。
Realm 会自动迁移某些更改(例如,新的和已删除的属性),但不会自动为新属性设置值,除非更新后的对象模式制定了默认值。您可在迁移函数中定义其他逻辑,以进一步自定义属性值。
添加属性
要将属性添加到模式,请将新属性添加到对象的类,并设置Realm 配置对象的schemaVersion 。
例子
使用模式版本1的域具有附带firstName和lastName属性的Person对象类型。 开发者决定向Person类添加一个age属性。
为了迁移 Realm 以符合更新的Person模式,开发者将 Realm 的模式版本设置为2 。
const Person = { name: 'Person', properties: { firstName: 'string', lastName: 'string', age: 'int' } }
const realm = await Realm.open({ schema: [Person], schemaVersion: 2 });
删除属性
要从模式中删除属性,请从对象的类中删除该属性,并设置Realm 配置对象的schemaVersion 。 删除属性不会影响现有对象。
例子
使用模式版本 1 的 Realm 有附带 weight 属性的 Dog 对象类型。开发者决定从模式中删除该属性。
为了迁移 Realm 以符合更新的Dog模式,开发者将 Realm 的模式版本设置为2 。
const realm = await Realm.open({ schema: [Dog], schemaVersion: 2 });
为属性重命名
要重命名对象属性,请在对象模式中更改属性名称,然后使用递增的模式版本和迁移函数打开域 ,该函数更新现有对象以使用新的属性名称。
迁移不允许您直接重命名属性。 相反,您可以使用更新的名称创建新属性,从旧属性复制值,然后删除旧属性。
例子
使用模式版本1的 Realm 具有Person对象类型。 原始模式具有firstName和lastName字段。 开发者稍后决定Person类应使用组合的fullName字段,并删除单独的firstName和lastName字段。
为了迁移 Realm 以符合更新的Person模式,开发者将 Realm 的模式版本设置为2 ,并定义一个迁移函数以根据现有的firstName和lastName属性设置fullName的值。
Realm.open({ schema: [Person], schemaVersion: 2, onMigration: (oldRealm, newRealm) => { // only apply this change if upgrading to schemaVersion 2 if (oldRealm.schemaVersion < 2) { const oldObjects = oldRealm.objects('Person'); const newObjects = newRealm.objects('Person'); // loop through all objects and set the fullName property in the new schema for (const objectIndex in oldObjects) { const oldObject = oldObjects[objectIndex]; const newObject = newObjects[objectIndex]; newObject.fullName = `${oldObject.firstName} ${oldObject.lastName}`; } } } });
修改属性类型
要修改属性的类型,请将要修改的字段的属性类型设置为新的数据类型。 然后,设置Realm 配置对象的schemaVersion和migration回调函数。
注意
同步 Realm仅支持非重大更改,以确保较旧的客户端可以与较新的客户端同步。 这意味着同步 Realm 不支持修改模式的属性类型。
例子
使用模式版本1的域具有Dog对象类型。 原始模式具有属性类型为Object ID _id 随后,开发者决定Dog类的_id字段的类型应为string ,并更新模式。
为了迁移 Realm 以符合更新的Dog模式,开发者将 Realm 的模式版本设置为2 ,并定义一个迁移函数以将Object ID类型转换为string类型。
const realm = await Realm.open({ schema: [Dog], schemaVersion: 2, onMigration: (oldRealm, newRealm) => { if(oldRealm.schemaVersion < 2){ const oldObjects = oldRealm.objects('Dog'); const newObjects = newRealm.objects('Dog'); // loop through all objects and set the _id property in the new schema for (const objectIndex in oldObjects) { const oldObject = oldObjects[objectIndex]; const newObject = newObjects[objectIndex]; newObject._id = oldObject._id.toHexString(); } } }, });