下载 Firebase 存储数据时,DispatchGroup 未正确执行
Posted
技术标签:
【中文标题】下载 Firebase 存储数据时,DispatchGroup 未正确执行【英文标题】:DispatchGroup is not executing correctly when downloading Firebase Storage Data 【发布时间】:2021-11-07 02:08:08 【问题描述】:我有一个从 Firebase 获取用户数据的闭包,在其中我有另一个从 Firebase 存储下载图像的闭包。
在用户登录之前,我需要能够从存储中下载图像。我想我会尝试一个 DispatchGroup(),但我无法将图像数据分配给 self.photoImage,它总是返回 nil。
self.photoImage = UIImage(data: data!)
这是我第一次使用 Storage 和 GroupDispatch(),因此我们将不胜感激。
相关代码:
class AppViewModel: ObservableObject
private var db = Firestore.firestore()
@Published var userInfo: User?
@Published var signedIn: Bool = false
var handle: AuthStateDidChangeListenerHandle?
let authRef = Auth.auth()
var authHandle : AuthStateDidChangeListenerHandle?
var rootInfoCollection : CollectionReference!
var userIdRef = ""
var photoImage: UIImage?
var downloadImageTask: StorageReference?
var group = DispatchGroup()
func fetchUserData()
db.collection("Users").document("\(userIdRef)").getDocument [self] document, error in
// Check for error
if error == nil
// Check that this document exists
if document != nil && document!.exists
self.userInfo = document.map (documentSnapshot) -> User in
let data = documentSnapshot.data()
let uid = data?["uid"] as? UUID ?? UUID()
let company = data?["company"] as? String ?? ""
let name = data?["name"] as? String ?? ""
let admin = data?["admin"] as? Bool ?? false
let photoRef = data?["photoRef"] as? String ?? ""
self.downloadImageTask = Storage.storage().reference().child(photoRef)
return User(uid: uid, company: company, name: name, admin: admin, photoRef: photoRef, photoImage: nil)
group.enter()
downloadImageTask?.getData(maxSize: 6 * 1024 * 1024) data, error in
if let error = error
print("Got an error fetching data: \(error.localizedDescription)")
return
else
self.photoImage = UIImage(data: data!)
self.group.leave()
DispatchQueue.global(qos: .default).async
self.group.wait()
DispatchQueue.main.async
if photoImage != nil
print("Photo Image Is Set")
withAnimation
self.signedIn = true
【问题讨论】:
你的 DispatchGroup 的整个结构是错误的,无论如何这不是 DispatchGroup 合适或需要的情况。 我建议你去读一些关于 GCD 的东西,Ray Wenderlich 的教程很不错raywenderlich.com/… 【参考方案1】:虽然我没有测试过,但也许这对你有用:
class AppViewModel: ObservableObject
private var db = Firestore.firestore()
@Published var userInfo: User?
@Published var signedIn: Bool = false
var handle: AuthStateDidChangeListenerHandle?
let authRef = Auth.auth()
var authHandle : AuthStateDidChangeListenerHandle?
var rootInfoCollection : CollectionReference!
var userIdRef = ""
var photoImage: UIImage?
var downloadImageTask: StorageReference?
var group = DispatchGroup()
func fetchUserData()
db.collection("Users").document("\(userIdRef)").getDocument [self] document, error in
// Check for error
if error == nil
// Check that this document exists
if document != nil && document!.exists
self.userInfo = document.map (documentSnapshot) -> User in
let data = documentSnapshot.data()
let uid = data?["uid"] as? UUID ?? UUID()
let company = data?["company"] as? String ?? ""
let name = data?["name"] as? String ?? ""
let admin = data?["admin"] as? Bool ?? false
let photoRef = data?["photoRef"] as? String ?? ""
self.downloadImageTask = Storage.storage().reference().child(photoRef)
return User(uid: uid, company: company, name: name, admin: admin, photoRef: photoRef, photoImage: nil)
group.enter()
downloadImageTask?.getData(maxSize: 6 * 1024 * 1024) data, error in
if let error = error
print("Got an error fetching data: \(error.localizedDescription)")
return
else
self.photoImage = UIImage(data: data!)
self.group.leave()
group.notify(queue: .main) [self] in
if photoImage != nil
print("Photo Image Is Set")
withAnimation
self.signedIn = true
【讨论】:
以上是关于下载 Firebase 存储数据时,DispatchGroup 未正确执行的主要内容,如果未能解决你的问题,请参考以下文章
如何从 Firebase 存储下载 URL 中删除查询字符串
从Android中的firebase下载多个文件时如何管理内存
如何将多个图像上传到 Firebase 存储并返回多个下载 URL