i have an issue with CloudKit in my App. The Data loads perfectly when the view is loaded initially. But when I "Pull to Refresh" I get a "fatal error: Index out of range". Strange thing is that there is no difference in Code (at least for me). When I pull to refresh, it does not even run "perform" ("B" does not get printed). Debugger does not show any error.
Do you have a clue?
Thanks in advance!
Nico
viewDidLoad:
loadCloudData()
handlePullToRefresh:
func handlePullToRefresh() {
loadCloudData()
}
loadCloudData:
func loadCloudData() {
DispatchQueue.main.async {
self.showMessage(titleText: NSLocalizedString("Loading ...", comment: "SwiftMessage Loading Title"), text: NSLocalizedString("Loading PixelCodes from Cloud", comment: "SwiftMessage Loading Title"), backgroundColor: UIColor.tileYellow(), textColor: UIColor.darkGray, image: #imageLiteral(resourceName: "cloud"))
}
dataCloud = [CKRecord]()
let query = CKQuery(recordType: PixelCodeType.recordType, predicate: NSPredicate(format: "TRUEPREDICATE", argumentArray: nil))
query.sortDescriptors = [NSSortDescriptor(key: "title", ascending: true)]
print("A")
databasePublic.perform(query, inZoneWith: nil) { (results:[CKRecord]?, error:Error?) in
print("B")
if error != nil {
print("PixelCode from Cloud not Loaded!\n\(error!.localizedDescription)")
self.couldLoadCloadData = false
DispatchQueue.main.async {
SwiftMessages.hideAll()
if self.refreshControl != nil {
if self.refreshControl!.isRefreshing {
self.refreshControl!.endRefreshing()
}
}
//"Cloud" active
self.segmentedControl.setEnabled(true, forSegmentAt: 1)
}
self.handleError(title: NSLocalizedString("Error!", comment: "SwiftMessage error title"), text: error!.localizedDescription, errorTitle: "Cloud Loading Error:loadCloudData()", error: error)
} else {
if let data = results {
print("pixelCodes updated")
self.dataCloud = data
if results!.isEmpty {
self.couldLoadCloadData = true
self.isCloudDataLoaded = false
} else {
self.couldLoadCloadData = true
self.isCloudDataLoaded = true
}
self.uploadTimes()
DispatchQueue.main.async {
if self.refreshControl != nil {
if self.refreshControl!.isRefreshing {
self.refreshControl!.endRefreshing()
}
}
SwiftMessages.hideAll()
//"Cloud" active
self.segmentedControl.setEnabled(true, forSegmentAt: 1)
self.tableView.reloadData()
}
}
}
}
}
The first thing that your loadCloudData
function does is set the dataCloud
array to an empty array, but you don't call reloadData
on the tableview so the number of items in the array and the number of items that the tableview thinks is in the array is different.
You should either call reloadData
after you clear the array or not clear the array.