我在realm.io一个swift应用程序中使用www.example.com。这是我第一次运行迁移,因为我有一个生产中的应用程序。我改变了其中一个模型,并添加了几个额外的字段。
我遵循了文档中的示例,然后在不起作用时参考了github repo的示例,我认为它可能比文档中的示例更复杂。
下面是我的appdelegate.swift文件中的内容:
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
print ("i'm in here")
// Override point for customization after application launch.
// Inside your application(application:didFinishLaunchingWithOptions:)
window = UIWindow(frame: UIScreen.mainScreen().bounds)
window?.rootViewController = UIViewController()
window?.makeKeyAndVisible()
// copy over old data files for migration
let defaultPath = Realm.Configuration.defaultConfiguration.path!
let defaultParentPath = (defaultPath as NSString).stringByDeletingLastPathComponent
if let v0Path = bundlePath("default-v0.realm") {
do {
try NSFileManager.defaultManager().removeItemAtPath(defaultPath)
try NSFileManager.defaultManager().copyItemAtPath(v0Path, toPath: defaultPath)
} catch {}
}
let config = Realm.Configuration(
// Set the new schema version. This must be greater than the previously used
// version (if you've never set a schema version before, the version is 0).
schemaVersion: 1,
// Set the block which will be called automatically when opening a Realm with
// a schema version lower than the one set above
migrationBlock: { migration, oldSchemaVersion in
// We haven’t migrated anything yet, so oldSchemaVersion == 0
if (oldSchemaVersion < 1) {
// Nothing to do!
// Realm will automatically detect new properties and removed properties
// And will update the schema on disk automatically
}
})
// define a migration block
// you can define this inline, but we will reuse this to migrate realm files from multiple versions
// to the most current version of our data model
let migrationBlock: MigrationBlock = { migration, oldSchemaVersion in
if oldSchemaVersion < 1 {
}
print("Migration complete.")
}
Realm.Configuration.defaultConfiguration = Realm.Configuration(schemaVersion: 1, migrationBlock: migrationBlock)
// Tell Realm to use this new configuration object for the default Realm
Realm.Configuration.defaultConfiguration = config
// Now that we've told Realm how to handle the schema change, opening the file
// will automatically perform the migration
_ = try! Realm()
return true
}
print
从来不运行,我觉得很奇怪。我搞砸了什么吗?我想我一定是。
以下是文档中的说明,我不确定他们是否遗漏了一些内容:
// Inside your application(application:didFinishLaunchingWithOptions:)
let config = Realm.Configuration(
// Set the new schema version. This must be greater than the previously used
// version (if you've never set a schema version before, the version is 0).
schemaVersion: 1,
// Set the block which will be called automatically when opening a Realm with
// a schema version lower than the one set above
migrationBlock: { migration, oldSchemaVersion in
// We haven’t migrated anything yet, so oldSchemaVersion == 0
if (oldSchemaVersion < 1) {
// Nothing to do!
// Realm will automatically detect new properties and removed properties
// And will update the schema on disk automatically
}
})
// Tell Realm to use this new configuration object for the default Realm
Realm.Configuration.defaultConfiguration = config
// Now that we've told Realm how to handle the schema change, opening the file
// will automatically perform the migration
let realm = try! Realm()
你知道我哪里做错了吗
5条答案
按热度按时间j1dl9f461#
这最终成为了解决方案。我不能说是我自己想到的,因为我没有。我得到了realm的一位名叫克莱尔的出色工程师的出色帮助。
以下是需要做的事情:
这是第一个被加载的视图控制器,它立即查询领域数据库来构建数组。在Claire的建议下,领域被延迟加载(或尝试),构建数组的代码被移到viewDidLoad方法中,而之前它是在顶部调用的。
这使得领域到迁移可以提前运行。正如您可能想象的那样,我诚实地假设视图直到
AppDelegate
中加载了application
函数之后才被加载。然而,我想我错了。所以,这将解决它。如果你碰巧遇到同样的问题,给予这个。
更新日期:
下面是appDelegate函数的外观:
bq8i3lrv2#
这按预期工作,在降级时抛出异常(如果使用版本不同的分支)等。还显示了一些示例迁移。
显然,这不会像
SomeObject
等那样编译,但您可以理解:)p8ekf7hl3#
看起来你完全复制了Realm Swift 'Migration'示例中的代码,并将其原封不动地粘贴了下来。其中很多代码实际上是在每次运行示例应用时“设置”一个新的演示迁移,而实际上对于正常的Realm迁移来说并不必要。
领域迁移有两个组件:
1.提升
Configuration
对象中的模式版本号。领域文件从版本0开始,每次要执行新的迁移时,将其增加1。1.请提供一个迁移块,该块将在每次增加领域方案版本时执行多次。虽然块本身是必需的,但它的目的是让您复制/转换旧领域文件中的任何数据。如果只是添加新字段,则可以将块留空。
如果您的
UIViewController
在其实现中使用了Realm,最好将您的迁移代码放在UIWindow
代码之前,以确保在UIViewController
开始使用它之前已经发生了迁移(否则您将得到一个异常)。由于您所要做的只是向其中添加几个字段,因此下面就是您所需要的全部代码:
o2gm4chl4#
我发现这在视图控制器中工作得最好:
换句话说,将配置赋值移到块中,这样它就不会执行得太晚。
dffbzjpn5#
基于我之前的答案here
或者,如果您希望在所有操作之前运行迁移,可以覆盖
AppDelegate
的init()
,如下所示:需要记住的几点:
1.您可能需要检查,此处允许/可以执行哪些操作,例如,在初始化应用程序委派之前
1.另一种更简洁的方法是,将
AppDelegate
子类化,并添加从init调用的新委托方法,例如applicationWillInitialize
,如果需要,还可以添加applicationDidInitialize