您知道有什么方法可以删除存储在Core Data中的所有条目吗?我的schema应该保持不变;我只想把它重置为空白。
Edit
我希望以编程方式做到这一点,这样用户就可以基本上按下重置按钮。
您知道有什么方法可以删除存储在Core Data中的所有条目吗?我的schema应该保持不变;我只想把它重置为空白。
Edit
我希望以编程方式做到这一点,这样用户就可以基本上按下重置按钮。
当前回答
下面这个版本可以删除每个表中的每条记录。
斯威夫特4
static func resetDatabase() {
do {
try dataStore.persistentStoreCoordinator.managedObjectModel.entities.forEach { (entity) in
if let name = entity.name {
let fetch = NSFetchRequest<NSFetchRequestResult>(entityName: name)
let request = NSBatchDeleteRequest(fetchRequest: fetch)
try mainContext.execute(request)
}
}
try mainContext.save()
} catch {
print("error resenting the database: \(error.localizedDescription)")
}
}
其他回答
iOS 10和Swift 3
假设您的实体名称是“Photo”,并且您创建了一个CoreDataStack类…
func clearData() {
do {
let context = CoreDataStack.sharedInstance.persistentContainer.viewContext
let fetchRequest = NSFetchRequest<NSFetchRequestResult>(entityName: "Photo")
do {
let objects = try context.fetch(fetchRequest) as? [NSManagedObject]
_ = objects.map{$0.map{context.delete($0)}}
CoreDataStack.sharedInstance.saveContext()
} catch let error {
print("ERROR DELETING : \(error)")
}
}
}
这里有一个很好的教程,教你如何使用CoreData以及如何使用这个方法。 https://medium.com/compileswift/parsing-json-response-and-save-it-in-coredata-step-by-step-fb58fc6ce16f#.1tu6kt8qb
Swift 5.1解决方案
public static func reset() {
let coordinator = _persistentContainer.persistentStoreCoordinator
for store in coordinator.persistentStores where store.url != nil {
try? coordinator.remove(store)
try? FileManager.default.removeItem(atPath: store.url!.path)
}
}
您仍然可以使用NSFileManager:removeItemAtPath::方法以编程方式删除该文件。
NSPersistentStore *store = ...;
NSError *error;
NSURL *storeURL = store.URL;
NSPersistentStoreCoordinator *storeCoordinator = ...;
[storeCoordinator removePersistentStore:store error:&error];
[[NSFileManager defaultManager] removeItemAtPath:storeURL.path error:&error];
然后,只需将持久存储添加回去,以确保正确地重新创建它。
遍历每个实体的编程方式既慢又容易出错。这样做的用途是如果您想删除一些实体而不是其他实体。然而,您仍然需要确保您保留了引用完整性,否则您将无法持久您的更改。
仅仅删除存储并重新创建它既快速又安全,当然可以在运行时以编程方式完成。
iOS5+更新
随着iOS 5和OS X 10.7引入外部二进制存储(allowsExternalBinaryDataStorage或Store in external Record File),简单地删除由storeurl指向的文件是不够的。你会留下外部记录文件。由于这些外部记录文件的命名方案不是公开的,所以我还没有一个通用的解决方案。- 12年5月8日23:00
似乎有两种方法:
假设您的核心数据堆栈有一个典型的单例。
import CoreData
public let core = Core.shared
public final class Core {
static let shared = Core()
var container: NSPersistentContainer!
private init() {
container = NSPersistentContainer(name: "stuff")
//deleteSql()
container.loadPersistentStores { storeDescription, error in
if let error = error { print("Error loading... \(error)") }
}
//deleteAll()
}
func saveContext() { // typical save helper
if container.viewContext.hasChanges {
do { try container.viewContext.save()
} catch { print("Error saving... \(error)") }
}
}
然后……
func deleteSql() {
let url = FileManager.default.urls(
for: .applicationSupportDirectory,
in: .userDomainMask)[0].appendingPathComponent( "stuff.sqlite" )
guard FileManager.default.fileExists(atPath: url.path) else {
print("nothing to delete!")
return
}
do {
try container.persistentStoreCoordinator.destroyPersistentStore(
at: url, ofType: "sqlite", options: nil)
print("totally scorched the sql file. you DO now have to LOAD again")
}
catch {
print("there was no sql file there!")
}
}
func deleteAll() { // courtesy @Politta
for e in container.persistentStoreCoordinator.managedObjectModel.entities {
let r = NSBatchDeleteRequest(
fetchRequest: NSFetchRequest(entityName: e.name ?? ""))
let _ = try? container.viewContext.execute(r)
}
saveContext()
print("conventionally deleted everything from within core data. carry on")
}
}
.
1. 焦化SQL文件
感谢优秀的@J。能源部的答案。您完全销毁了sql文件。
你必须这样做
在加载核心数据之前,即在创建容器之后,但是 在真正载入商店之前。)
(注意示例代码“//deleteSql()”就在初始化之前。)
2. 逐个删除核心数据中的所有内容
感谢精彩的@Politta回答。一旦core data启动并运行,就可以随时执行此操作。
(注意示例代码“//deleteAll()”是在初始化之后。)
方法一在开发过程中可能更有用。方法二在生产中可能更有用(在相对不常见的情况下,由于某种原因需要擦除所有内容)。
这里我的swift3版本删除所有记录。'Users'是实体名称
@IBAction func btnDelAll_touchupinside(_ sender: Any) {
let appDelegate = UIApplication.shared.delegate as! AppDelegate
let managedObjectContext = appDelegate.persistentContainer.viewContext
let fetchReq = NSFetchRequest<NSFetchRequestResult>(entityName: "Users")
let req = NSBatchDeleteRequest(fetchRequest: fetchReq)
do {
try managedObjectContext.execute(req)
} catch {
// Error Handling
}
}