SoundShock SoundShock - 6 months ago 40
Swift Question

App crashes at reloadData() for Collectionview with a background fetch

So I am doing a background fetch, and after I want to update the UI. The background fetching itself (database) works, but when I want to update the UI, I get a crash

unexpectedly found nil while unwrapping an Optional value

According to my xCode
self.newestPublicationsCollectionView.reloadData()
is where the crash occurs in the updateCollections() function.

func updateCollections() {
// get latest data from Database
latestPublications = getNewestPublications()

self.newestPublicationsCollectionView.reloadData()

self.newestPublicationsCollectionView.layoutIfNeeded()

// fix wrong content height
self.newestPublicationsCollectionViewHeight.constant = self.newestPublicationsCollectionView.collectionViewLayout.collectionViewContentSize().height
}


Other code in the AppDelegate:

func application(application: UIApplication, performFetchWithCompletionHandler completionHandler: (UIBackgroundFetchResult) -> Void) {

let fetchViewController = PublicationOverviewController()
fetchViewController.fetch {
dispatch_async(dispatch_get_main_queue()) {
fetchViewController.updateCollections()
}
completionHandler(.NewData)
}
}


The .fetch in my PublicationOverviewController

func fetch(completion: () -> Void) {
PublicationFetcher.shared.fetchAllPublications()
completion()
}


I thought the crash was because I needed the UI on the main thread, but that didn't help. Any input would be nice.

DETAILS:

In my PublicationFetcher.shared.fetchAllPublications() I do the following:


  • get data from backend

  • dispatch_async(dispatch_get_main_queue()) { () -> Void in NSNotificationCenter.defaultCenter().postNotificationName("RELOAD_NOTIFICATION", object: nil) }



and under that Reload Notification I do a
updateCollections()

Answer

Don't initialize PublicationOverviewController() again because it will give you new instance of that view and you would not get your referenced collectionView. Also you will get all UI controls nil before viewDidLoad: get calls.

Example:

let *controller : PublicationOverviewController = PublicationOverviewController()
// controller.collectionView will be nil here because view haven't loaded yet

What you can do Post a notification in applicationDidBecomeActive: method and observe it in PublicationOverviewController then reload your collectionView in respective method.