// // PersistenceController.swift // JustOneThing // // Created by Alan Francis on 07/07/2023. // import CoreData //MARK: - URL Extension // https://developer.apple.com/forums/thread/78120 // There's an issue with tvOS and the path to the local DB. // This little extension encapsulates that public extension URL { /// Returns a URL for the given app group and database pointing to the sqlite database. static func storeURL(for appGroup: String, databaseName: String) -> URL { var containerUrl:URL guard let initialContainer = FileManager.default.containerURL(forSecurityApplicationGroupIdentifier: appGroup) else { fatalError("Shared file container could not be created.") } #if os(tvOS) containerUrl = initialContainer.appendingPathComponent("Library/Caches") #else containerUrl = initialContainer #endif return containerUrl.appendingPathComponent("\(databaseName).sqlite") } } //MARK: - PeristenceController struct PersistenceController { let container: NSPersistentCloudKitContainer init(inMemory: Bool = false) { container = NSPersistentCloudKitContainer(name: "JustOneThingCloudModel") if inMemory { container.persistentStoreDescriptions.first!.url = URL(fileURLWithPath: "/dev/null") } else { let url = URL.storeURL(for: "group.com.alancfrancis.apps.JustOneThing", databaseName: "JustOneThingCloudModel") container.persistentStoreDescriptions.first!.url = url } container.loadPersistentStores(completionHandler: { (storeDescription, error) in if let error = error as NSError? { Self.processError(error:error) } }) container.viewContext.automaticallyMergesChangesFromParent = true } } //MARK: - static convenience extension PersistenceController { static let shared = PersistenceController() var viewContext:NSManagedObjectContext { get { container.viewContext } } } //MARK: - error handling extension PersistenceController { static func processError(error:NSError) { // Replace this implementation with code to handle the error appropriately. // fatalError() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development. /* Typical reasons for an error here include: * The parent directory does not exist, cannot be created, or disallows writing. * The persistent store is not accessible, due to permissions or data protection when the device is locked. * The device is out of space. * The store could not be migrated to the current model version. Check the error message to determine what the actual problem was. */ fatalError("Unresolved error \(error), \(error.userInfo)") } } extension PersistenceController { static var preview: PersistenceController = { let result = PersistenceController(inMemory: true) let viewContext = result.container.viewContext var i = 1 for _ in 0..<10 { let newItem = PersistentThing(context: viewContext) newItem.text = "action \(i)" newItem.createdAt = Date() newItem.uuid = UUID() i = i+1 } do { try viewContext.save() } catch { // Replace this implementation with code to handle the error appropriately. // fatalError() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development. let nsError = error as NSError fatalError("Unresolved error \(nsError), \(nsError.userInfo)") } return result }() }