iCloud & Data

RSS for tag

Learn how to integrate your app with iCloud and data frameworks for effective data storage

CloudKit Documentation

Post

Replies

Boosts

Views

Activity

iPadOS 18 Beta and SwiftData issues
I had a series of @Model classes with some mandatory attributes and some optional. Pre-move to 18, everything was working fine. After the migration, it reports that every single non-Optional attribute is nil upon trying to save. The error is CoreData related but not sure if its in the Core layer or Swift layer. Sample error (with app data removed) is : SwiftData.DefaultStore save failed with error: Error Domain=NSCocoaErrorDomain Code=1560 "Multiple validation errors occurred." Error Domain=NSCocoaErrorDomain Code=1570 \"%{PROPERTY}@ is a required value.\" UserInfo={NSValidationErrorObject=<NSManagedObject: 0x30388b2a0> NSLocalizedDescription=%{PROPERTY}@ is a required value., NSValidationErrorKey=systemName, NSValidationErrorValue=null}" I have modified the code to provide default values for all constructors in an attempt to see a difference, but get the same errors
0
1
73
1d
CoreData result class has 'Sendable' warnings
In an iOS viewController, I use the NSDiffableDataSource to populate a tableView from the results of a CoreData fetchController. The result class is defined by CoreData - in this case a class named CDFilterStack. In xCode 16.0 Beta with strict concurrency checking = 'Complete' the CDFilterStack class has this warning everywhere it is referenced. "Type 'CDFilterStack' does not conform to the 'Sendable' protocol; this is an error in the Swift 6 language mode." The class definition of CDFilterStack is not editable because it is generated by CoreData. I think I need to mark this class (and other similar classes) as @preconcurrency... but how & where? Here's one method sample that generates three of these warnings func initialSnapShot() -> NSDiffableDataSourceSnapshot<Int, CDFilterStack> { var snapshot = NSDiffableDataSourceSnapshot<Int, CDFilterStack>() if let sections = dataProvider.fetchedResultsController.sections { for index in 0..<sections.count { let thisSection = sections[index] guard let sectionStacks = thisSection.objects as? [CDFilterStack] else { continue} snapshot.appendSections([index]) snapshot.appendItems(sectionStacks) } // for loop that will continue on error in objects } return snapshot } Careful reading of the various migration guides hasn't produced an example of how to handle this.. (btw the migration guides are nicely done:)
1
0
82
2d
Social network app & posting content via a server
Hello, I have had an app that I created myself with Xcode for a long time and I also had it briefly for about two months as a beta in the App Store. At some point I had to take them out because I couldn't solve the problem with a server. I wanted to have a server via iCloud, Kit and Fire Base to upload and display content such as text images, videos. It should be an app that is very similar or the same as TikTok and Instagram just more data protection more 3-D visual design just a modern design and much better built than TikTok Instagram. Unfortunately, I didn't get it or almost Fire Base did it but the problem is that he always says yes this picture or this video or other error message were displayed, but among other things this error message was displayed. Hold this content can't be found in the server or something like that maybe someone here knows what she can do or knows about Fire Base maybe I did something wrong but actually I really taped everything at Fire Base and checked and switched everything on but nothing worked. I hope you can help me.
0
0
86
2d
I'm using CloudKit+CoreData to sync ... looking for faster alternative channel when multiple computers are editing at same time
I am using CloudKit+CoreData to store and sync and share my apps data. In my somewhat limited testing this is working quite well, but sync performance is unpredictable. Often it is very fast, sometimes it just stops until I put Mac app in background or restart. I guess from this thread this behavior is by design: https://developer.apple.com/forums/thread/756315 I'm accepting that! :) My plan is that I will use CloudKit+CoreData for source of truth syncing, but now I'm looking for an alternative channel that I can use to sync when multiple devices are working on this data at the same time. I think the basic design could be: When a device starts editing a CKRecord Post device IP and record ID to well known location/discovery service Watch that location to see other devices that are editing that record Make direct connection to those devices and sync through that connection (still also saving/merging with iCloud). I think I know how to solve the data merge problems that will show up in this scenario, but I don't know what technologies I should use to create the sync channel. I'm looking for ideas. I don't want to run my own server. SharePlay session seems almost perfect, but I'm not sure if it's really intended for this purpose. In particular I would want the session to start automatically (using participants from CKShare) without users having to manually join. Also I would like it to work with a single account (when I am viewing same data on my Mac and iOS device). My other thought is that I would store active users+ip's in the synced CloudKit+CoreData store and then use Network.framework to connect and sync those active users. I think this could work, but is quite low level and might be a lot of work. Are there other options that I'm missing or things I should think about? Thanks, Jesse
0
0
55
2d
SwiftData FatalError Unknown Relationship Key
Some of our users on iOS 17.5+ started to encounter crash due to: SwiftData/BackingData.swift:669: Fatal error: Unknown Relationship Key - subscription) We have tried using SwiftData on the MainActor only but an issues still effects some of our users. Our models look like these: @Model public final class ProfileModel { public static let fetchDescriptor = FetchDescriptor<ProfileModel>.self public enum Gender: Codable { case female case male case other } public enum Units: Codable { case imperial case metric } public enum Eating: Codable { case empath case enthusiast case explorer case guardian case harmonizer case pacifier case regulator case stoic case iosDefault } public enum RegistrationSource: Codable { case iOS case web } public enum NHE: Codable { case combined case emotional case mindless } public enum Goal: Codable { case beHealthier case energyIncrease case healthyHabits case looseWeight case relationshipsWithFood } public enum WeightLossFocus: Codable { case activity case healthyHabits case nutrition case other } @Attribute(.unique) public let id: String public let isPaid: Bool public let eating: Eating public let registrationSource: RegistrationSource public let nhe: NHE? public let firstName: String? public let lastName: String? public let gender: Gender? public let height: String? public let age: Int? public let weight: String? public let targetWeight: String? public let bmi: String? public let goal: Goal? public let units: Units? public let weightLossFocus: WeightLossFocus? @Relationship(deleteRule: .cascade) public var subscription: ProfileSubscriptionModel? public init( id: String, isPaid: Bool, eating: Eating, registrationSource: RegistrationSource, nhe: NHE?, firstName: String?, lastName: String?, gender: Gender?, height: String?, age: Int?, weight: String?, targetWeight: String?, bmi: String?, goal: Goal?, units: Units?, weightLossFocus: WeightLossFocus?, subscription: ProfileSubscriptionModel? ) { self.id = id self.isPaid = isPaid self.eating = eating self.registrationSource = registrationSource self.nhe = nhe self.firstName = firstName self.lastName = lastName self.gender = gender self.height = height self.age = age self.weight = weight self.targetWeight = targetWeight self.bmi = bmi self.goal = goal self.units = units self.weightLossFocus = weightLossFocus self.subscription = subscription } } @Model public final class ProfileSubscriptionModel { public static let fetchDescriptor = FetchDescriptor<ProfileSubscriptionModel>.self public let price: Double public let currency: String public let period: Int public let status: String public let expirationDate: Date public let cancelledAt: Date? public init(price: Double, currency: String, period: Int, status: String, expirationDate: Date, cancelledAt: Date?) { self.price = price self.currency = currency self.period = period self.status = status self.expirationDate = expirationDate self.cancelledAt = cancelledAt } }
0
0
90
3d
SwiftData - Context missing for optional
I have encountered an issue that when using a ModelActor to sync data in the background, the app will crash if one of the operations is to remove a PersistentModel from the context. This is running on the latest beta of Xcode 16 with visionOS 1.2 as target and in Swift 6 language mode. The code is being executed in a ModelActor. The error is first thrown by: #5 0x00000001c3223280 in PersistentModel.getValue<τ_0_0>(forKey:) () Thread 1: Fatal error: Context is missing for Optional(SwiftData.PersistentIdentifier(id: SwiftData.PersistentIdentifier.ID(url: x-coredata://97AA86BC-475D-4509-9004-D1182ABA1922/Reminder/p303), implementation: SwiftData.PersistentIdentifierImplementation)) func globalSync() async { await fetchAndSyncFolders() let result = await fetchReminders() switch result { case .success(let ekReminders): var localReminders = (try? await fetch(FetchDescriptor<Reminder>())) ?? [] // Handle local reminders with nil ekReminderID by creating new EKReminders for them for reminder in localReminders { if reminder.ekReminderID == nil { await self.createEkReminder(reminder: reminder) } } // Re-fetch local reminders to include newly created EKReminderIDs localReminders = (try? await fetch(FetchDescriptor<Reminder>())) ?? [] var localReminderDict = [String: Reminder]() for reminder in localReminders { if let ekReminderID = reminder.ekReminderID { if let existingReminder = localReminderDict[ekReminderID] { self.delete(model: existingReminder) } else { localReminderDict[ekReminderID] = reminder } } } let ekReminderDict = createReminderLookup(byID: ekReminders) await self.syncReminders(localReminders: Array(localReminderDict.values), localReminderDict: localReminderDict, ekReminderDict: ekReminderDict) // Merge duplicates await self.mergeDuplicates(localReminders: localReminders) save() case .failure(let error): print("Failed to fetch reminders: \(error.localizedDescription)") } }
0
2
95
3d
Prevent Data Retention in Core Data When View is Dismissed
Prerequisite Information I am trying to use Core Data in my SwiftUI app. I have created 3 entities, a Record, a Header and an Entry. The Record contains the Header entities. The Header contain other Header or Entry entities. The Entry has a title and a value. My List view looks like this, I fetch the records with a @FetchRequest. NavigationView { List { ForEach(records) { record in NavigationLink(destination: DetailView(headers: record.headers!.allObjects as? [Header] ?? [], isNewEntry: true)) { Text(record.id!.uuidString) } } } } In my DetailView I have a form that passes the details to other views which create a DisclosureGroup for a Header, a bold Text for a subheader, and a TextField for an Entry let headers: [Header] let isNewEntry: Bool @Environment(\.managedObjectContext) var managedObjectContext init(headers: [Header], isNewEntry: Bool = false) { self.headers = headers self.isNewEntry = isNewEntry } Form { ForEach(Array(headers.enumerated()), id: \.element) { index, header in HeaderView(header: header, isExpanded: Binding( get: { self.expandedStates[header.id!, default: false] }, set: { self.expandedStates[header.id!] = $0 } )) } } Problem When I press the record in the list, it takes me to the DetailView where I can write something in the TextField. Then if I slide back and do not press the save button and then press the same record again from the list, it retains the data I wrote in the TextField. Question How can I make it so that the data is not retained if I slide back except only when I press the save button? Please let me know if any other information is needed or if something is unclear.
0
1
91
3d
`Task` at `createSampleData` function in What's new in SwiftData session
I was looking to the example code that point from What's new in SwiftData session and noticed something that I cannot understand about Swift concurrency. from this snippet: static func createSampleData(into modelContext: ModelContext) { Task { @MainActor in let sampleDataTrips: [Trip] = Trip.previewTrips let sampleDataLA: [LivingAccommodation] = LivingAccommodation.preview let sampleDataBLT: [BucketListItem] = BucketListItem.previewBLTs let sampleData: [any PersistentModel] = sampleDataTrips + sampleDataLA + sampleDataBLT sampleData.forEach { modelContext.insert($0) } if let firstTrip = sampleDataTrips.first, let firstLivingAccommodation = sampleDataLA.first, let firstBucketListItem = sampleDataBLT.first { firstTrip.livingAccommodation = firstLivingAccommodation firstTrip.bucketList.append(firstBucketListItem) } if let lastTrip = sampleDataTrips.last, let lastBucketListItem = sampleDataBLT.last { lastTrip.bucketList.append(lastBucketListItem) } try? modelContext.save() } } From the code snippet, I cannot see any task that needs to be marked with await, and it is also marked as @MainActor. My question is: why do we need to put Task here? It seems like all the code will run on the main thread anyway. I am just afraid that I might be missing some concept of Swift concurrency or SwiftData here. Thank you
2
0
154
3d
What is the proper way to handle videos in SwiftData ?
I'm creating an application with swiftui which gets images and videos from the Photos picker then store them with swiftData for later use. I save both images and videos as data with  @Attribute(.externalStorage). But it just seems wrong to me to store the videos that way, they can be several gigabytes in size . What is the correct way to handle something like this ? Is it to store the url and then each time the user wants to see a video save a temporary video ?. If that's the case can anyone show me how this should be done? Any comments appreciated Guillermo
0
0
69
4d
NSFetchedResultsController - NSInvalidArgumentException
Good morning, I've developed an application where we download a JSON of objects and we store those information on a CoreData table. We've also created a Collection view used to show those information through a NSFetchedResultsController. Can someone helps me to understand the reason why I get this issue? Thanks indeed Fatal Exception: NSInvalidArgumentException 0 CoreFoundation 0x83f20 __exceptionPreprocess 1 libobjc.A.dylib 0x16018 objc_exception_throw 2 CoreFoundation 0x1b6250 _NSArrayRaiseInsertNilException 3 CoreFoundation 0x16f5c -[__NSCFArray objectAtIndex:] 4 CoreData 0x13af14 -[_PFMutableProxyArray subarrayWithRange:] 5 CoreData 0xc4948 -[_NSDefaultSectionInfo objects] 6 CoreData 0x9c3fc -[NSFetchedResultsController _conditionallyDispatchSnapshotToDelegate:updatesInfo:] 7 CoreData 0x6d4ec __82-[NSFetchedResultsController(PrivateMethods) _core_managedObjectContextDidChange:]_block_invoke 8 CoreData 0x270dc developerSubmittedBlockToNSManagedObjectContextPerform 9 CoreData 0x9d0ec -[NSManagedObjectContext performBlockAndWait:] 10 CoreData 0x9c6e8 -[NSFetchedResultsController _core_managedObjectContextDidChange:] 11 CoreFoundation 0x5178c __CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ 12 CoreFoundation 0x516a8 ___CFXRegistrationPost_block_invoke 13 CoreFoundation 0x515f0 _CFXRegistrationPost 14 CoreFoundation 0x4fbb8 _CFXNotificationPost 15 Foundation 0x31574 -[NSNotificationCenter postNotificationName:object:userInfo:] 16 CoreData 0x6a548 -[NSManagedObjectContext _createAndPostChangeNotification:deletions:updates:refreshes:deferrals:wasMerge:] 17 CoreData 0x69d10 -[NSManagedObjectContext _postRefreshedObjectsNotificationAndClearList] 18 CoreData 0x68a4c -[NSManagedObjectContext _processRecentChanges:] 19 CoreData 0x91494 -[NSManagedObjectContext _coreMergeChangesFromDidSaveDictionary:usingObjectIDs:withClientQueryGeneration:] 20 CoreData 0x90334 -[NSManagedObjectContext mergeChangesFromContextDidSaveNotification:] 21 CoreData 0x270dc developerSubmittedBlockToNSManagedObjectContextPerform 22 libdispatch.dylib 0x3dd4 _dispatch_client_callout 23 libdispatch.dylib 0x125a4 _dispatch_main_queue_drain 24 libdispatch.dylib 0x121b8 _dispatch_main_queue_callback_4CF 25 CoreFoundation 0x56710 __CFRUNLOOP_IS_SERVICING_THE_MAIN_DISPATCH_QUEUE__ 26 CoreFoundation 0x53914 __CFRunLoopRun 27 CoreFoundation 0x52cd8 CFRunLoopRunSpecific 28 GraphicsServices 0x11a8 GSEventRunModal 29 UIKitCore 0x40a90c -[UIApplication _run] 30 UIKitCore 0x4be9d0 UIApplicationMain 31 Rainbow 0x80c0 main + 15 (main.swift:15) 32 ??? 0x1b3419e4c (Mancante)
1
0
95
4d
Crash: NSFetchedResultsController NSInvalidArgumentException
Good morning, I've developed an application in order to show the information stored into a CoraData Table on a CollectionView through a NSFetchedResultsController. Several times I got this issue, is there anyone who can help me to understand the reason why this happens? Thanks indeed. Fatal Exception: NSInvalidArgumentException 0 CoreFoundation 0x83f20 __exceptionPreprocess 1 libobjc.A.dylib 0x16018 objc_exception_throw 2 CoreFoundation 0x1b6250 _NSArrayRaiseInsertNilException 3 CoreFoundation 0x16f5c -[__NSCFArray objectAtIndex:] 4 CoreData 0x13af14 -[_PFMutableProxyArray subarrayWithRange:] 5 CoreData 0xc4948 -[_NSDefaultSectionInfo objects] 6 CoreData 0x9c3fc -[NSFetchedResultsController _conditionallyDispatchSnapshotToDelegate:updatesInfo:] 7 CoreData 0x6d4ec __82-[NSFetchedResultsController(PrivateMethods) _core_managedObjectContextDidChange:]_block_invoke 8 CoreData 0x270dc developerSubmittedBlockToNSManagedObjectContextPerform 9 CoreData 0x9d0ec -[NSManagedObjectContext performBlockAndWait:] 10 CoreData 0x9c6e8 -[NSFetchedResultsController _core_managedObjectContextDidChange:] 11 CoreFoundation 0x5178c CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER 12 CoreFoundation 0x516a8 ___CFXRegistrationPost_block_invoke 13 CoreFoundation 0x515f0 _CFXRegistrationPost 14 CoreFoundation 0x4fbb8 _CFXNotificationPost 15 Foundation 0x31574 -[NSNotificationCenter postNotificationName:object:userInfo:] 16 CoreData 0x6a548 -[NSManagedObjectContext _createAndPostChangeNotification:deletions:updates:refreshes:deferrals:wasMerge:] 17 CoreData 0x69d10 -[NSManagedObjectContext _postRefreshedObjectsNotificationAndClearList] 18 CoreData 0x68a4c -[NSManagedObjectContext _processRecentChanges:] 19 CoreData 0x91494 -[NSManagedObjectContext _coreMergeChangesFromDidSaveDictionary:usingObjectIDs:withClientQueryGeneration:] 20 CoreData 0x90334 -[NSManagedObjectContext mergeChangesFromContextDidSaveNotification:] 21 CoreData 0x270dc developerSubmittedBlockToNSManagedObjectContextPerform 22 libdispatch.dylib 0x3dd4 _dispatch_client_callout 23 libdispatch.dylib 0x125a4 _dispatch_main_queue_drain 24 libdispatch.dylib 0x121b8 _dispatch_main_queue_callback_4CF 25 CoreFoundation 0x56710 CFRUNLOOP_IS_SERVICING_THE_MAIN_DISPATCH_QUEUE 26 CoreFoundation 0x53914 __CFRunLoopRun 27 CoreFoundation 0x52cd8 CFRunLoopRunSpecific 28 GraphicsServices 0x11a8 GSEventRunModal 29 UIKitCore 0x40a90c -[UIApplication _run] 30 UIKitCore 0x4be9d0 UIApplicationMain 31 Cloud 0x80c0 main + 15 (main.swift:15) 32 ??? 0x1b3419e4c (Mancante)
0
0
58
4d
Sqlite database locked
Hi guys, 🙏I have a problem with repeated saving to the database. If I do the first update it is OK, but after the second attempt the update fails and the console says "Failed to commit transaction: database is locked". Here is my function: func updateMapCoordinates(radius: Int32) { // Otevření databáze, pokud není otevřená guard db != nil else { print("Database connection is nil") return } var statement: OpaquePointer? = nil let updateQuery = "UPDATE \(mapTable) SET radius = ? WHERE id = 1;" // Začátek transakce if sqlite3_exec(db, "BEGIN TRANSACTION", nil, nil, nil) != SQLITE_OK { let errorMessage = String(cString: sqlite3_errmsg(db)) print("Failed to begin transaction: \(errorMessage)") return } if sqlite3_prepare_v2(db, updateQuery, -1, &statement, nil) == SQLITE_OK { sqlite3_bind_int(statement, 1, radius) print("uložím \(radius)") if sqlite3_step(statement) == SQLITE_DONE { print("Coordinates saved successfully") } else { let errorMessage = String(cString: sqlite3_errmsg(db)) print("Failed to save coordinates: \(errorMessage)") } } else { let errorMessage = String(cString: sqlite3_errmsg(db)) print("SAVE statement could not be prepared: \(errorMessage)") } // Finalizace statementu sqlite3_finalize(statement) // Ukončení transakce if sqlite3_exec(db, "COMMIT", nil, nil, nil) != SQLITE_OK { let errorMessage = String(cString: sqlite3_errmsg(db)) print("Failed to commit transaction: \(errorMessage)") sqlite3_exec(db, "ROLLBACK", nil, nil, nil) } }
0
0
61
4d
@Attribute(.unique) working as intended, kind of
I have a model that has a unique property, e.g.: @Model final class UserWord @Attribute(.unique) let word: String let partOfSpeech: PartOfSpeech let metaData: ... At the end of the init I have this: init(...) { if partOfSpeech == .verb { metaData = fetchMeta() } } This works fine when a word is newly created and saved. But let's say there's a unique conflict and a user tries to save a new entry with the same word. Apparently this init still fires and fetchMeta edits the existing entry which gives me the error: CoreData: error: Mutating a managed object 0xb890d8167c911ade <x-coredata://4C75194F-D923-477F-BB22-ACBDECCD7530/UserWord/p2> (0x600002170af0) after it has been removed from its context. I think the solution here is to do some manual checking of the modelContext before saving. Would love to hear other's thoughts.
0
0
82
4d
Library/Caches for app groups: automatically deleted when needed ?
In an app we can use FileManager.SearchPathDirectory.cachesDirectory (objc:NSCachesDirectory) to store files that could be recreated if necessary (and will be automatically deleted by iOS in cases of low disk memory). For app groups, there is a shared location that is automatically created as soon as we use containerURL(forSecurityApplicationGroupIdentifier:) (objc:containerURLForSecurityApplicationGroupIdentifier) : Library/Caches Is this cache directory (created by iOS) also gets automatically deleted by iOS in cases of low disk memory ? I also have more related questions : does this cache directory size count in the used disk space by the app displayed in the settings app ? is this cache directory (and same question for the top containerURL directory) saved in the cloud backups ? Does anyone have any information about this?
4
0
108
5d
Swift Data Array with Elements to conform protocol
Hi, I'm try to convert from CoreData to SwiftData. Problem is that I'm using inheritance in CoreData. So, I have a base class "animal" and "cat" and "bird" inherit from it. I can have a array of type "animal" which contains both cats and dogs. Now as I try to move to SwiftData I tried the following approach protocol Animal { var name: String { get set } } @Model class Cat: Animal { var name: String var legs: Int } @Model class Bird: Animal { var name: String var legs: Int var wings: Int } @Model class Enviroment { //leads to error: //Type 'any Animal' cannot conform to 'PersistentModel' var animals: [any Animal] } So how to I get around of this? I would like to store multiple types of animals (classes that conform to protocol animal) … but how can I achieve that? Thanks
0
0
73
6d
iOS 18 SwiftData ModelContext reset
Since the iOS 18 and Xcode 16, I've been getting some really strange SwiftData errors when passing @Model classes around. The error I'm seeing is the following: SwiftData/BackingData.swift:409: Fatal error: This model instance was destroyed by calling ModelContext.reset and is no longer usable. PersistentIdentifier(id: SwiftData.PersistentIdentifier.ID(url: x-coredata://34EE9059-A7B5-4484-96A0-D10786AC9FB0/TestApp/p2), implementation: SwiftData.PersistentIdentifierImplementation) The same issue also happens when I try to retrieve a model from the ModelContext using its PersistentIdentifier and try to do anything with it. I have no idea what could be causing this. I'm guessing this is just a bug in the iOS 18 Beta, since I couldn't find a single discussion about this on Google, I figured I'd mention it. if someone has a workaround or something, that would be much appreciated.
0
3
125
6d
Understanding Syncing between Core Data and CloudKit Public Database using NSPersistantCloudKitContainer
Can someone please give me an overview of how sync works between Core Data and the public CloudKit database when using the NSPersistentCloudKitContainer and please point out my misunderstandings based on what I describe below? In the following code, I'm successfully connecting to the public database in CloudKit using the NSPersistentCloudKitContainer. Below is how I have Core Data and CloudKit set up for your reference. In CloudKit I have a set of PublicIconImage that I created manually via the CloudKit Console. I intend to be able to download all images from the public database at the app launch to the local device and manage them via Core Data to minimize server requests, which works but only if the user is logged in. This is the behavior I see: When the app launches, all the CloudKit images get mirrored to Core Data and displayed on the screen but only if the user is logged in with the Apple ID, otherwise nothing gets mirrored. What I was expecting: I was under the impression that when connecting to the public database in CloudKit you didn't need to be logged in to read data. Now, if the user is logged in on the first launch, all data is successfully mirrored to Core Data, but then if the user logs off, all data previously mirrored gets removed from Core Data, and I was under the impression that since Core Data had the data already locally, it would keep the data already downloaded regardless if it can connect to CloudKit or not. What am I doing wrong? Core Data Model: Entity: PublicIconImage Attributes: id (UUID), imageName (String), image (Binary Data). CloudKit Schema in Public Database: Record: CD_PublicIconImage Fields: CD_id (String), CD_imageName (String), CD_image (Bytes). Core Data Manager class CoreDataManager: ObservableObject{ // Singleton static let instance = CoreDataManager() private let queue = DispatchQueue(label: "CoreDataManagerQueue") private var iCloudSync = true lazy var context: NSManagedObjectContext = { return container.viewContext }() lazy var container: NSPersistentContainer = { return setupContainer() }() func updateCloudKitContainer() { queue.sync { container = setupContainer() } } func setupContainer()->NSPersistentContainer{ let container = NSPersistentCloudKitContainer(name: "CoreDataContainer") guard let description = container.persistentStoreDescriptions.first else{ fatalError("###\(#function): Failed to retrieve a persistent store description.") } description.setOption(true as NSNumber, forKey: NSPersistentHistoryTrackingKey) let cloudKitContainerIdentifier = "iCloud.com.example.PublicDatabaseTest" let options = NSPersistentCloudKitContainerOptions(containerIdentifier: cloudKitContainerIdentifier) description.cloudKitContainerOptions = options description.cloudKitContainerOptions?.databaseScope = .public // Specify Public Database container.loadPersistentStores { (description, error) in if let error = error{ print("Error loading Core Data. \(error)") } } container.viewContext.automaticallyMergesChangesFromParent = true container.viewContext.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy return container } func save(){ do{ try context.save() }catch let error{ print("Error saving Core Data. \(error.localizedDescription)") } } } View Model Class class PublicIconImageViewModel: ObservableObject { let manager: CoreDataManager @Published var publicIcons: [PublicIconImage] = [] init(coreDataManager: CoreDataManager = .instance) { self.manager = coreDataManager loadPublicIcons() } func loadPublicIcons() { let request = NSFetchRequest<PublicIconImage>(entityName: "PublicIconImage") let sort = NSSortDescriptor(keyPath: \PublicIconImage.imageName, ascending: true) request.sortDescriptors = [sort] do { publicIcons = try manager.context.fetch(request) } catch let error { print("Error fetching PublicIconImages. \(error.localizedDescription)") } } } SwiftUI View struct ContentView: View { @EnvironmentObject private var publicIconViewModel: PublicIconImageViewModel var body: some View { VStack { List { ForEach(publicIconViewModel.publicIcons) { icon in HStack{ Text(icon.imageName ?? "unknown name") Spacer() if let iconImageData = icon.image, let uiImage = UIImage(data: iconImageData) { Image(uiImage: uiImage) .resizable() .aspectRatio(contentMode: .fit) .frame(width: 35, height: 35) } } } } .onAppear { // give some time to get the images downlaoded DispatchQueue.main.asyncAfter(deadline: .now() + 5){ publicIconViewModel.loadPublicIcons() } } } .padding() } }
0
0
85
1w
Deleting CloudKit data
I have been testing an app which uses cloudKit with SWIFTDATA and after testing for several months my 200GB iCloud store is showing 168GB for iCloud Drive. Now my iCloud drive is only 22.6GB so the rest of the 168GB must be data from my app. Also, I have function in my app to delete all iCloud Data which I thought that should clean up iCloud storage but it does not. I tried resetting the Develop Environment but no change to iCloud data. Also I have several other containers in iCloud created while getting iCloud working which I would like to delete but I understand you can’t. https://forums.developer.apple.com/forums/thread/45251?answerId=788694022#788694022 Bottom line cloudkit console has been pretty much useless for me and I need a way to manage (delete containers and data). Am I missing something?
1
0
86
1w
SwiftData migration error
CrashLog Distributor ID: com.apple.AppStore Hardware Model: iPhone15,3 Process: DeadLineTodo [5556] Path: /private/var/containers/Bundle/Application/348CC8D5-05FD-41DF-93A3-C15562EF4AA8/DeadLineTodo.app/DeadLineTodo Identifier: andy.DeadLineTodo Version: 2.4.0 (3) AppStoreTools: 15F31e AppVariant: 1:iPhone15,3:17 Code Type: ARM-64 (Native) Role: Foreground Parent Process: launchd [1] Coalition: andy.DeadLineTodo [2089] Date/Time: 2024-06-08 19:13:53.6259 +0800 Launch Time: 2024-06-08 19:13:53.2839 +0800 OS Version: iPhone OS 17.5.1 (21F90) Release Type: User Baseband Version: 2.60.02 Report Version: 104 Exception Type: EXC_BREAKPOINT (SIGTRAP) Exception Codes: 0x0000000000000001, 0x0000000195a2d8c0 Termination Reason: SIGNAL 5 Trace/BPT trap: 5 Terminating Process: exc handler [5556] Triggered by Thread: 0 Thread 0 name: Thread 0 Crashed: 0 libswiftCore.dylib 0x0000000195a2d8c0 _assertionFailure(_:_:file:line:flags:) + 264 (AssertCommon.swift:144) 1 DeadLineTodo 0x0000000100dde700 DeadLineTodoApp.init() + 1140 (DeadLineTodoApp.swift:46) 2 DeadLineTodo 0x0000000100ddef30 protocol witness for App.init() in conformance DeadLineTodoApp + 28 (<compiler-generated>:0) 3 SwiftUI 0x000000019b2c84c0 static App.main() + 116 (App.swift:114) 4 DeadLineTodo 0x0000000100ddeec4 static DeadLineTodoApp.$main() + 40 (<compiler-generated>:0) 5 DeadLineTodo 0x0000000100ddef5c main + 12 (DeadLineTodoApp.swift:32) 6 dyld 0x00000001ba7d1e4c start + 2240 (dyldMain.cpp:1298) Thread 1: 0 libsystem_pthread.dylib 0x00000001f3fa40c4 start_wqthread + 0 (:-1) Thread 2: 0 libsystem_pthread.dylib 0x00000001f3fa40c4 start_wqthread + 0 (:-1) Thread 0 crashed with ARM Thread State (64-bit): x0: 0x8000000100f01ad0 x1: 0x0000000000000000 x2: 0x0000000000000000 x3: 0x00000003019e9bc0 x4: 0x0000000000000000 x5: 0x000000016f16f3e0 x6: 0x000000000000002e x7: 0x0000000000000000 x8: 0x0000000000000100 x9: 0x00000000000000ff x10: 0x0000000000001b80 x11: 0x00000000f3444870 x12: 0x00000000000007fb x13: 0x00000000000007fd x14: 0x00000000f364506f x15: 0x000000000000006f x16: 0x00000000f3444870 x17: 0x0000000000045000 x18: 0x0000000000000000 x19: 0x0000000100f01dba x20: 0x8000000100f01ad0 x21: 0x0000000000000000 x22: 0x000000000000000b x23: 0x0000000000000022 x24: 0x000000000000002e x25: 0x0000000100f01ac0 x26: 0xd000000000000025 x27: 0x0000000000000000 x28: 0x0000000000000000 fp: 0x000000016f16f5c0 lr: 0x0000000195a2d8c0 sp: 0x000000016f16f4f0 pc: 0x0000000195a2d8c0 cpsr: 0x60001000 esr: 0xf2000001 (Breakpoint) brk 1 Binary Images: 0x100c90000 - 0x100f0ffff DeadLineTodo arm64 <c16650393d4537299a08b798b8227d31> /private/var/containers/Bundle/Application/348CC8D5-05FD-41DF-93A3-C15562EF4AA8/DeadLineTodo.app/DeadLineTodo 0x101214000 - 0x10121ffff libobjc-trampolines.dylib arm64e <2e2c05f8377a30899ad91926d284dd03> /private/preboot/Cryptexes/OS/usr/lib/libobjc-trampolines.dylib 0x1959f4000 - 0x195f43fff libswiftCore.dylib arm64e <d9ad5cc1ca2c3f0a8091652b0df56d14> /usr/lib/swift/libswiftCore.dylib 0x19af1c000 - 0x19ccbafff SwiftUI arm64e <c1325fda9da239d2ab83a338b4d8a884> /System/Library/Frameworks/SwiftUI.framework/SwiftUI 0x1ba795000 - 0x1ba821ef7 dyld arm64e <71846eacee653697bf7d790b6a07dcdb> /usr/lib/dyld 0x1f3fa3000 - 0x1f3fafff3 libsystem_pthread.dylib arm64e <1196b6c3333d3450818ff3663484b8eb> /usr/lib/system/libsystem_pthread.dylib EOF DeadLineTodoApp.swift import SwiftUI import SwiftData typealias TodoData = TodoDataSchemaV8.TodoData typealias UserSetting = TodoDataSchemaV8.UserSetting enum TodoDataMigrationPlan: SchemaMigrationPlan { static var schemas: [VersionedSchema.Type] { [TodoDataSchemaV1.self, TodoDataSchemaV2.self, TodoDataSchemaV3.self, TodoDataSchemaV4.self, TodoDataSchemaV5.self, TodoDataSchemaV6.self, TodoDataSchemaV7.self, TodoDataSchemaV8.self] } static var stages: [MigrationStage]{ [migrationV1toV2, migrationV2toV3, migrationV3toV4, migrationV4toV5, migrationV5toV6, migrationV6toV7, migrationV7toV8] } static let migrationV1toV2 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV1.self, toVersion: TodoDataSchemaV2.self) static let migrationV2toV3 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV2.self, toVersion: TodoDataSchemaV3.self) static let migrationV3toV4 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV3.self, toVersion: TodoDataSchemaV4.self) static let migrationV4toV5 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV4.self, toVersion: TodoDataSchemaV5.self) static let migrationV5toV6 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV5.self, toVersion: TodoDataSchemaV6.self) static let migrationV6toV7 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV6.self, toVersion: TodoDataSchemaV7.self) static let migrationV7toV8 = MigrationStage.lightweight(fromVersion: TodoDataSchemaV7.self, toVersion: TodoDataSchemaV8.self) } @main struct DeadLineTodoApp: App { let container: ModelContainer @StateObject var store = StoreKitManager() @State var updated: Bool = false init() { do { container = try ModelContainer( for: TodoData.self, UserSetting.self, migrationPlan: TodoDataMigrationPlan.self) } catch { print("初始化模型容器时发生错误:\(error)") fatalError("Failed to initialize model container.") } } var body: some Scene { WindowGroup { ContentView(updated: $updated) .environmentObject(store) } .modelContainer(container) } }
0
0
103
1w