Firebase完成下载后如何直接执行代码?

我有代码需要在Firebase完成下载我的任务下载之后立即执行。 问题是此代码始终在下载完成之前运行。

if currentVersionNumber  Void in if (error != nil) { // Uh-oh, an error occurred! print("Feed: error occured") print(error) } else { // Data for "images/island.jpg" is returned cards.imageName = data! print("Feed: downloaded \(cards.name)") } } // add to updated list of cards updateCards.append(cards); } }) } else { print("Feed: cards are up to date. \(currentVersionNumber)") } }) 

此代码从Firebase数据库下载我想要的项目,但在完成之前将运行任何代码。 如何制作它以便我可以选择在下载完成后立即执行代码块?

这些网络请求运行异步,因此在网络请求完成后,它们之后的任何代码都将继续运行。

你应该在内部闭包中移动updateCards.append(cards),这样在第二个闭包完成之前不会调用它,如果你有其他代码需要在完成后运行,你可以将它移到这个函数内部或使用带有完成处理程序的闭包来确保在运行依赖于响应的更多代码之前完成所有网络请求。

 getCardData { [weak self] in // do whatever you need to do after completion } func getCardData(_ completion: () -> ()) { print("Feed: button donwloading cards") //self.databaseButton.setTitle("Downloading New Cards...", for: .normal) ref.observe(.value, with: { snapshot in print("Feed: Checking for new cards from firebase") for item in snapshot.children { // Download in memory with a maximum allowed size of 1MB (1 * 1024 * 1024 bytes) cardRef.data(withMaxSize: 1 * 1024 * 1024) { (data, error) -> Void in if (error != nil) { // Uh-oh, an error occurred! print("Feed: error occured") print(error) completion() // this is where you would normally throw an error or have a closure that accepts an optional error you would pass in to know it failed } else { // Data for "images/island.jpg" is returned cards.imageName = data! print("Feed: downloaded \(cards.name)") updateCards.append(cards); completion()// now you know all network requests are complete } } } }) } 

发生这种情况是因为Firebase的所有更新都发生在后台线程中,而您的代码在主线程上执行。 要处理此问题,请在一个函数内部调用firebase方法,该函数具有一个在您的firebase下载完成后立即调用的闭包。

例如:

viewDidLoad

 override func viewDidLoad() { super.viewDidLoad() fetchData { //do whatever action you wish to perform on download completion mainTableView.reloadData() } } func fetchData(andOnCompletion completion:@escaping ()->()){ ref.observe(.value, with: { snapshot in print("Feed: Checking for new cards from firebase") for item in snapshot.children { // Download in memory with a maximum allowed size of 1MB (1 * 1024 * 1024 bytes) cardRef.data(withMaxSize: 1 * 1024 * 1024) { (data, error) -> Void in if (error != nil) { // Uh-oh, an error occurred! print("Feed: error occured") print(error) } else { // Data for "images/island.jpg" is returned cards.imageName = data! print("Feed: downloaded \(cards.name)") } } // add to updated list of cards updateCards.append(cards); } //call the block when done processing completion() }) } 

通过在下载中添加if语句来管理以解决我的问题,该语句检查附加到updateCards的卡的数量是否等于快照中的卡的数量。 感谢回答这个问题的两个人,因为我也使用了completion()方法,很高兴我去了解这个我不知道存在的概念。