Firestore 数据不显示在列表视图中。可识别设置不正确?
Firestore data is not displayed in listview. Identifiable not set up correctly?
我正在尝试从 firebase 文档中获取一些数据并将其显示在 ListView 中。获取数据并将其解码到我自己的结构中工作正常(通过让控制台打印它进行测试),但它不会显示在实际的 ListView 中。我尝试创建 2 个示例数据集以查看我的 struct and/or ListView 的实现是否有任何问题,但这些数据集显示得很好。
我最好的猜测是 ListView 对我从 firebase 文档中获得的 id 不满意。
这是我获取数据的方式(请暂时忽略 checkAvailablePkgs() 中丑陋的解决方案,它会改变):
class firebaseController : ObservableObject {
let databaseFIRB = Firestore.firestore()
@Published var forUserAvailablePkgs : [DLPackage] = []
func checkAvailablePkgs() {
if Auth.auth().currentUser != nil {
var allAccessiblePkgs : [String] = []
let userUID = Auth.auth().currentUser!.uid
databaseFIRB.collection("user-access").document(userUID).getDocument { (document, error) in
if let document = document, document.exists {
let dataDescription = document.data().map(String.init(describing:)) ?? "nil"
let pkgArr = dataDescription.components(separatedBy: ", ")
for partString in pkgArr {
var tmpStringSlicing : String
tmpStringSlicing = partString.replacingOccurrences(of: "\": <null>", with: "")
tmpStringSlicing = tmpStringSlicing.replacingOccurrences(of: "[\[\]\"]", with: "", options: .regularExpression)
allAccessiblePkgs.append(tmpStringSlicing)
}
self.checkIndividualPkgInformation(pkgIDs: allAccessiblePkgs)
} else {
print("Document does not exist")
}
}
}
}
func checkIndividualPkgInformation(pkgIDs: [String]) {
for id in pkgIDs {
databaseFIRB.collection("download-pkgs").document(id).getDocument { (document, error) in
if let document = document, document.exists {
let result = Result {
try document.data(as: DLPackage.self)
}
switch result {
case .success(let pkg):
if let pkg = pkg {
// A `Package` value was successfully initialized from the DocumentSnapshot.
print("Package: \(pkg)")
self.forUserAvailablePkgs.append(pkg)
} else {
// A nil value was successfully initialized from the DocumentSnapshot,
// or the DocumentSnapshot was nil.
print("Document does not exist")
}
case .failure(let error):
// A `City` value could not be initialized from the DocumentSnapshot.
print("Error decoding package: \(error)")
}
} else {
print("Package-Document does not exist")
}
}
}
}
}
这是我要将其保存为的结构:
struct DLPackage: Identifiable, Codable {
@DocumentID var id = UUID().uuidString
var name : String = ""
var size : String = ""
var contentpaths : [String] = [""]
}
这里是拒绝显示获取数据的ListView:
struct FIRBauthView: View {
let firebaseCtrl: firebaseController = firebaseController()
var body: some View {
VStack() {
List(firebaseCtrl.forUserAvailablePkgs) {item in
HStack() {
Text(String(item.name)).font(.custom("Avenir", size: 26))
Spacer()
Text(String(item.size)).font(.custom("Avenir", size: 26))
}
}
Button {
firebaseCtrl.checkAvailablePkgs()
} label: {
Text("Check")
}
}
}
}
我可以给我的 firebaseControler().forUserAvailablePkgs 一个初始值:
forUserAvailablePkgs.append(contentsOf: [DLPackage(name: "Example", size: "1GB", contentpaths: ["hello","something"]),DLPackage(name: "Nr2", size: "1GB", contentpaths: ["hello","something else"])])
他们会出现的。
这是我从加载到 forUserAvailablePkgs 数组的 firebase 数据打印出来的:
[Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("CDB68E0C-DCE2-4FAA-AD55-872322A55E56")), name: "Example", size: "1GB", contentpaths: ["hello", "something"]),
Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("DCAAF136-24FE-470A-B897-2D178AEDB3A0")), name: "Nr2", size: "1GB", contentpaths: ["hello", "something else"]),
Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("package2")), name: "Bewährte Klassiker", size: "3.4GB", contentpaths: ["placeholder for another path", "placeholder for a different path"]),
Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("package1")), name: "Basic", size: "7.3GB", contentpaths: ["placeholder for path", "placeholder for path 2"])]
我尝试将结构的 ID 更改为:
@DocumentID var id: String?
因为我在网上的教程中找到了它,但是代码并没有那样编译。
我也尝试在从数据库中获取数据后用生成的 UUID 覆盖 firebase 数据中的 id,但我仍然无法让 ListView 显示它。
感谢任何帮助。
经过一夜安眠,我的暂时性失明痊愈了,但我发现在我看来我缺少@ObservedObject 属性。
struct FIRBauthView: View {
@ObservedObject var firebaseCtrl: firebaseController = firebaseController()
而不是
struct FIRBauthView: View {
let firebaseCtrl: firebaseController = firebaseController()
现在数据按预期显示。
我正在尝试从 firebase 文档中获取一些数据并将其显示在 ListView 中。获取数据并将其解码到我自己的结构中工作正常(通过让控制台打印它进行测试),但它不会显示在实际的 ListView 中。我尝试创建 2 个示例数据集以查看我的 struct and/or ListView 的实现是否有任何问题,但这些数据集显示得很好。 我最好的猜测是 ListView 对我从 firebase 文档中获得的 id 不满意。
这是我获取数据的方式(请暂时忽略 checkAvailablePkgs() 中丑陋的解决方案,它会改变):
class firebaseController : ObservableObject {
let databaseFIRB = Firestore.firestore()
@Published var forUserAvailablePkgs : [DLPackage] = []
func checkAvailablePkgs() {
if Auth.auth().currentUser != nil {
var allAccessiblePkgs : [String] = []
let userUID = Auth.auth().currentUser!.uid
databaseFIRB.collection("user-access").document(userUID).getDocument { (document, error) in
if let document = document, document.exists {
let dataDescription = document.data().map(String.init(describing:)) ?? "nil"
let pkgArr = dataDescription.components(separatedBy: ", ")
for partString in pkgArr {
var tmpStringSlicing : String
tmpStringSlicing = partString.replacingOccurrences(of: "\": <null>", with: "")
tmpStringSlicing = tmpStringSlicing.replacingOccurrences(of: "[\[\]\"]", with: "", options: .regularExpression)
allAccessiblePkgs.append(tmpStringSlicing)
}
self.checkIndividualPkgInformation(pkgIDs: allAccessiblePkgs)
} else {
print("Document does not exist")
}
}
}
}
func checkIndividualPkgInformation(pkgIDs: [String]) {
for id in pkgIDs {
databaseFIRB.collection("download-pkgs").document(id).getDocument { (document, error) in
if let document = document, document.exists {
let result = Result {
try document.data(as: DLPackage.self)
}
switch result {
case .success(let pkg):
if let pkg = pkg {
// A `Package` value was successfully initialized from the DocumentSnapshot.
print("Package: \(pkg)")
self.forUserAvailablePkgs.append(pkg)
} else {
// A nil value was successfully initialized from the DocumentSnapshot,
// or the DocumentSnapshot was nil.
print("Document does not exist")
}
case .failure(let error):
// A `City` value could not be initialized from the DocumentSnapshot.
print("Error decoding package: \(error)")
}
} else {
print("Package-Document does not exist")
}
}
}
}
}
这是我要将其保存为的结构:
struct DLPackage: Identifiable, Codable {
@DocumentID var id = UUID().uuidString
var name : String = ""
var size : String = ""
var contentpaths : [String] = [""]
}
这里是拒绝显示获取数据的ListView:
struct FIRBauthView: View {
let firebaseCtrl: firebaseController = firebaseController()
var body: some View {
VStack() {
List(firebaseCtrl.forUserAvailablePkgs) {item in
HStack() {
Text(String(item.name)).font(.custom("Avenir", size: 26))
Spacer()
Text(String(item.size)).font(.custom("Avenir", size: 26))
}
}
Button {
firebaseCtrl.checkAvailablePkgs()
} label: {
Text("Check")
}
}
}
}
我可以给我的 firebaseControler().forUserAvailablePkgs 一个初始值:
forUserAvailablePkgs.append(contentsOf: [DLPackage(name: "Example", size: "1GB", contentpaths: ["hello","something"]),DLPackage(name: "Nr2", size: "1GB", contentpaths: ["hello","something else"])])
他们会出现的。
这是我从加载到 forUserAvailablePkgs 数组的 firebase 数据打印出来的:
[Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("CDB68E0C-DCE2-4FAA-AD55-872322A55E56")), name: "Example", size: "1GB", contentpaths: ["hello", "something"]),
Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("DCAAF136-24FE-470A-B897-2D178AEDB3A0")), name: "Nr2", size: "1GB", contentpaths: ["hello", "something else"]),
Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("package2")), name: "Bewährte Klassiker", size: "3.4GB", contentpaths: ["placeholder for another path", "placeholder for a different path"]),
Light_Player.DLPackage(_id: FirebaseFirestoreSwift.DocumentID<Swift.String>(value: Optional("package1")), name: "Basic", size: "7.3GB", contentpaths: ["placeholder for path", "placeholder for path 2"])]
我尝试将结构的 ID 更改为:
@DocumentID var id: String?
因为我在网上的教程中找到了它,但是代码并没有那样编译。
我也尝试在从数据库中获取数据后用生成的 UUID 覆盖 firebase 数据中的 id,但我仍然无法让 ListView 显示它。
感谢任何帮助。
经过一夜安眠,我的暂时性失明痊愈了,但我发现在我看来我缺少@ObservedObject 属性。
struct FIRBauthView: View {
@ObservedObject var firebaseCtrl: firebaseController = firebaseController()
而不是
struct FIRBauthView: View {
let firebaseCtrl: firebaseController = firebaseController()
现在数据按预期显示。