Swift:无法预加载 Coredata
Swift: cannot preload Coredata
当我在 "Target - Build Phases - Copy Bundle Resources" 下包含带有 Objective-C 的 SQLite 文件时,该文件将被完全复制到目标,即设备或模拟器。在目标上,我得到了整个文件:表格和内容(Records/rows)。
用 Swift 做同样的事情,表将被复制,但它们是空的:没有 records/rows。 :-(
我可以做些额外的事情吗?有没有"trick"?
我如何使用 Swift 预加载带有基本记录的核心数据???
我正在使用 Xcode v6.1.1,与 Beta 6.2 相同。
我认为这可能与文件在 iOS 上的布局方式有关。具体来说:
- 当您复制源文件时(通过 Xcode 或在安装时),它会被放入应用程序 bundle/container 目录(只读)
- 标准 CoreData 初始化代码在 Documents 目录中查找数据存储。
- 找不到您的源数据(因为它在错误的位置),CoreData 创建了一个新的空存储。
要解决此问题,您需要将应用程序目录中的应用程序目录复制到文档目录中(如果它尚不存在)。
这个 link 给出了解释和示例代码来做到这一点。但在 Objective-C 中它看起来像:
NSString *storePath = [[self applicationDocumentsDirectory]
stringByAppendingPathComponent: @"MyDB.sqlite"];
NSURL *storeUrl = [NSURL fileURLWithPath:storePath];
// Copy the default db if it doesn't already exist
NSFileManager *fileManager = [NSFileManager defaultManager];
if (![fileManager fileExistsAtPath:storePath]) {
NSString *defaultStorePath = [[NSBundle mainBundle]
pathForResource:@"MyDB" ofType:@"sqlite"];
if (defaultStorePath) {
[fileManager copyItemAtPath:defaultStorePath
toPath:storePath error:NULL];
}
}
这是我的解决方案(针对 sqlite 文件)。我不知道为什么"extravagant"在Swift。也许有更简单的方法?
很多THX pbasdf!!!
重要:在 *.sqlite 文件下,您必须将 *.sqlite-shm 和 *.sqlite-wal 添加到您的项目中
此文件将自动添加到 "Target - Build Phases - Copy Bundle Resources"
这是基于 "AppDelegate.swift"…
的标准模板
lazy var persistentStoreCoordinator: NSPersistentStoreCoordinator? = {
// The persistent store coordinator for the application. This implementation creates and return a coordinator, having added the store for the application to it. This property is optional since there are legitimate error conditions that could cause the creation of the store to fail.
// Create the coordinator and store
var coordinator: NSPersistentStoreCoordinator? = NSPersistentStoreCoordinator(managedObjectModel: self.managedObjectModel)
let dataName = „MyData.sqlite" // must be replaced by the name of your file!
let modelName = „MyData“ // must be replaced by the name of your model!
let url = self.applicationDocumentsDirectory.URLByAppendingPathComponent(dataName)
let fileManager = NSFileManager.defaultManager()
let bundle = NSBundle.mainBundle()
let fromURL = bundle.URLForResource(modelName, withExtension: "sqlite")
// check sqlite-file: must it be installed?
if !fileManager.fileExistsAtPath(url.path!) {
self.copySqlliteFiles(modelName, databaseName: dataName)
}
var error: NSError? = nil
var failureReason = "There was an error creating or loading the application's saved data."
if coordinator!.addPersistentStoreWithType(NSSQLiteStoreType, configuration: nil, URL: url, options: nil, error: &error) == nil {
...}
return coordinator
}()
// MARK: - copy sqllite-files (c) by Ray Wenderlich & Team in „“Core Data by Tutorials“
// check sqlite-files: they must be installed...
func copySqlliteFiles(modelName: String, databaseName: String)
{
let bundle = NSBundle.mainBundle()
let baseDatabaseURL = bundle.URLForResource(modelName, withExtension: "sqlite")
let documentsURL = self.applicationDocumentsDirectory
let storeURL = documentsURL.URLByAppendingPathComponent(databaseName)
NSFileManager.defaultManager().copyItemAtURL(baseDatabaseURL!, toURL: storeURL,error: nil)
let baseSHMURL = bundle.URLForResource(modelName,withExtension: "sqlite-shm")
let shmURL = self.applicationDocumentsDirectory.URLByAppendingPathComponent(databaseName + "-shm")
NSFileManager.defaultManager().copyItemAtURL(baseSHMURL!, toURL: shmURL, error: nil)
let walURL = self.applicationDocumentsDirectory.URLByAppendingPathComponent(databaseName + "-wal")
let baseWALURL = bundle.URLForResource(modelName, withExtension: "sqlite-wal")
NSFileManager.defaultManager().copyItemAtURL(baseWALURL!, toURL: walURL, error: nil)
}
我有一个与此相关的问题。我开始研究一些使用这一行的教程:
documentsURL.URLByAppendingPathComponent("StoreName")
在某些时候这停止了工作。数据不再写入商店。为了解数据未被写入的原因,我尝试打开 sqlite 文件,但无法在我的 mac 上找到正在使用的 URL。应用程序文件夹在那里,但没有 sqlite 文件。我回顾了旧的核心数据项目,发现它们使用了 .sqlite 扩展名。所以我将行修改为:
documentsURL.URLByAppendingPathComponent("StoreName.sqlite")
这似乎行得通,所以试一试。
当我在 "Target - Build Phases - Copy Bundle Resources" 下包含带有 Objective-C 的 SQLite 文件时,该文件将被完全复制到目标,即设备或模拟器。在目标上,我得到了整个文件:表格和内容(Records/rows)。
用 Swift 做同样的事情,表将被复制,但它们是空的:没有 records/rows。 :-(
我可以做些额外的事情吗?有没有"trick"?
我如何使用 Swift 预加载带有基本记录的核心数据???
我正在使用 Xcode v6.1.1,与 Beta 6.2 相同。
我认为这可能与文件在 iOS 上的布局方式有关。具体来说:
- 当您复制源文件时(通过 Xcode 或在安装时),它会被放入应用程序 bundle/container 目录(只读)
- 标准 CoreData 初始化代码在 Documents 目录中查找数据存储。
- 找不到您的源数据(因为它在错误的位置),CoreData 创建了一个新的空存储。
要解决此问题,您需要将应用程序目录中的应用程序目录复制到文档目录中(如果它尚不存在)。
这个 link 给出了解释和示例代码来做到这一点。但在 Objective-C 中它看起来像:
NSString *storePath = [[self applicationDocumentsDirectory]
stringByAppendingPathComponent: @"MyDB.sqlite"];
NSURL *storeUrl = [NSURL fileURLWithPath:storePath];
// Copy the default db if it doesn't already exist
NSFileManager *fileManager = [NSFileManager defaultManager];
if (![fileManager fileExistsAtPath:storePath]) {
NSString *defaultStorePath = [[NSBundle mainBundle]
pathForResource:@"MyDB" ofType:@"sqlite"];
if (defaultStorePath) {
[fileManager copyItemAtPath:defaultStorePath
toPath:storePath error:NULL];
}
}
这是我的解决方案(针对 sqlite 文件)。我不知道为什么"extravagant"在Swift。也许有更简单的方法? 很多THX pbasdf!!!
重要:在 *.sqlite 文件下,您必须将 *.sqlite-shm 和 *.sqlite-wal 添加到您的项目中 此文件将自动添加到 "Target - Build Phases - Copy Bundle Resources"
这是基于 "AppDelegate.swift"…
的标准模板lazy var persistentStoreCoordinator: NSPersistentStoreCoordinator? = {
// The persistent store coordinator for the application. This implementation creates and return a coordinator, having added the store for the application to it. This property is optional since there are legitimate error conditions that could cause the creation of the store to fail.
// Create the coordinator and store
var coordinator: NSPersistentStoreCoordinator? = NSPersistentStoreCoordinator(managedObjectModel: self.managedObjectModel)
let dataName = „MyData.sqlite" // must be replaced by the name of your file!
let modelName = „MyData“ // must be replaced by the name of your model!
let url = self.applicationDocumentsDirectory.URLByAppendingPathComponent(dataName)
let fileManager = NSFileManager.defaultManager()
let bundle = NSBundle.mainBundle()
let fromURL = bundle.URLForResource(modelName, withExtension: "sqlite")
// check sqlite-file: must it be installed?
if !fileManager.fileExistsAtPath(url.path!) {
self.copySqlliteFiles(modelName, databaseName: dataName)
}
var error: NSError? = nil
var failureReason = "There was an error creating or loading the application's saved data."
if coordinator!.addPersistentStoreWithType(NSSQLiteStoreType, configuration: nil, URL: url, options: nil, error: &error) == nil {
...}
return coordinator
}()
// MARK: - copy sqllite-files (c) by Ray Wenderlich & Team in „“Core Data by Tutorials“
// check sqlite-files: they must be installed...
func copySqlliteFiles(modelName: String, databaseName: String)
{
let bundle = NSBundle.mainBundle()
let baseDatabaseURL = bundle.URLForResource(modelName, withExtension: "sqlite")
let documentsURL = self.applicationDocumentsDirectory
let storeURL = documentsURL.URLByAppendingPathComponent(databaseName)
NSFileManager.defaultManager().copyItemAtURL(baseDatabaseURL!, toURL: storeURL,error: nil)
let baseSHMURL = bundle.URLForResource(modelName,withExtension: "sqlite-shm")
let shmURL = self.applicationDocumentsDirectory.URLByAppendingPathComponent(databaseName + "-shm")
NSFileManager.defaultManager().copyItemAtURL(baseSHMURL!, toURL: shmURL, error: nil)
let walURL = self.applicationDocumentsDirectory.URLByAppendingPathComponent(databaseName + "-wal")
let baseWALURL = bundle.URLForResource(modelName, withExtension: "sqlite-wal")
NSFileManager.defaultManager().copyItemAtURL(baseWALURL!, toURL: walURL, error: nil)
}
我有一个与此相关的问题。我开始研究一些使用这一行的教程:
documentsURL.URLByAppendingPathComponent("StoreName")
在某些时候这停止了工作。数据不再写入商店。为了解数据未被写入的原因,我尝试打开 sqlite 文件,但无法在我的 mac 上找到正在使用的 URL。应用程序文件夹在那里,但没有 sqlite 文件。我回顾了旧的核心数据项目,发现它们使用了 .sqlite 扩展名。所以我将行修改为:
documentsURL.URLByAppendingPathComponent("StoreName.sqlite")
这似乎行得通,所以试一试。