您在 sidetablename 表上遇到主键约束冲突。
因此,我相信您的问题在于您如何创建和复制种子数据库。
不幸的是,您没有提供该信息。因此,我只是猜测你是如何做到的。
我假设您使用 Mac 应用程序创建了数据库,或者在 iOS 模拟器中创建了数据库。然后,您将 sqlite 文件从创建它的位置复制到捆绑资源中。
由于自 iOS/OSX 7/10.9 以来 WAL 一直是默认模式,因此我假设您在 WAL 模式下创建了种子数据库。这意味着您可能错过了 -wal 和 -shm 文件。如果您指定任何数据属性应使用外部存储,那么您也会错过该数据。
创建要复制的种子数据库时,还需要复制 -shm/wal 文件,或者需要以回滚日志模式创建数据库,这将在文件中包含所有添加的数据。
您可以通过在添加持久性存储时设置以下选项来实现这一点(如果您已经使用选项,只需将此选项与其他选项合并即可)。
NSDictionary *options = @{NSSQLitePragmasOption:@{@"journal_mode":@"DELETE"}};
if (![persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType
configuration:nil
URL:storeURL
options:options
error:&error]) {
// Handle error
}
这是在创建要复制到捆绑包的数据库时添加持久性存储的方式。它将确保所有内容都在实际的数据库文件中。
现在,运行代码创建种子文件后,您应该转到该目录并查看是否还有其他文件。最好的方法是在终端中。转到该目录并执行“ls -lat”,这将列出按时间排序的所有文件。
Caveat:SQLite 和 Core Data 都可以创建与 sqlite 文件一起使用的额外文件,具体取决于两个实体的配置。因此,一般来说,您应该将每个核心数据持久存储视为一个文件包。换句话说,您应该仅为核心数据存储创建一个单独的目录。这样,当 SQLite 或 core data 决定创建额外文件时,所有内容都被限制在一个目录中。
当您将文件复制到创建种子数据库的捆绑资源中时,您需要确保复制所有内容。
同样,部署时您应该将捆绑包中的所有内容复制到设备。
但是,您应该考虑使用这些方法,而不是使用文件系统NSPersistentStoreCoordinator
...
/* Used for save as - performance may vary depending on the type of old and
new store; the old store is usually removed from the coordinator by the
migration operation, and therefore is no longer a useful reference after
invoking this method
*/
- (NSPersistentStore *)migratePersistentStore:(NSPersistentStore *)store
toURL:(NSURL *)URL
options:(nullable NSDictionary *)options
withType:(NSString *)storeType
error:(NSError **)error;
/* copy or overwrite the target persistent store in accordance with the store
class's requirements. It is important to pass similar options as
addPersistentStoreWithType: ... SQLite stores will honor file locks, journal
files, journaling modes, and other intricacies. Other stores will default
to using NSFileManager.
*/
- (BOOL)replacePersistentStoreAtURL:(NSURL *)destinationURL
destinationOptions:(nullable NSDictionary *)destinationOptions
withPersistentStoreFromURL:(NSURL *)sourceURL
sourceOptions:(nullable NSDictionary *)sourceOptions
storeType:(NSString *)storeType
error:(NSError**)error NS_AVAILABLE(10_11, 9_0);
因此,我相信,如果您正确创建数据库,然后将其完全正确地复制到资源包和应用程序中,那么您的问题就会消失。