更改Firebase Observer Swift 4后,功能返回



我正在重写我的firebase函数,以将其自身函数放入通过数据库获取数据的实时部分,因此我从.observe(.childAdded, with: {(snapshot) in转换为.observeSingleEvent(of: .value, with: { (snapshot) in,以引用数据库。现在,该功能现在在guard let data = snapshot.value as? [String :String] else { return }上返回。快照相同时发生了什么变化?我自己看不到的任何解释都是很棒的。一如既往地感谢。

这是函数的两个版本:

旧观察者:

func displayAlerts(setCompletion: @escaping (Bool) -> ()) {
        self.mapView.removeAnnotations(mapView.annotations)
        MapArray.alertNotificationCoordinatesArray.removeAll()
        self.userAlertNotificationArray.removeAll()
        print("                     MapArray.alertNotificationCoordinatesArray before snapshot is: (MapArray.alertNotificationCoordinatesArray)")
        print("                     self.userAlertNotificationArray before snapshot is: (self.userAlertNotificationArray)")
        ref = Database.database().reference()
        databaseHandle = ref?.child("Continent").child("Europe").child("Country").child("Italy").child("Region").child("Emilia-Romagna").child("City").child("Bologna").child("Community").child("Alert Notifications").observe(.childAdded, with: { (snapshot) in

            //            self.mapView.removeAnnotations(self.mapView.annotations) //
            print("         snapshot is: (snapshot)")
            guard let data = snapshot.value as? [String:String] else { return }
            guard let firebaseKey = snapshot.key as? String else { return }
            //                let date = data!["Date"]
            //                let time = data!["Time"]
            let dataLatitude = data["Latitude"]!
            let dataLongitude = data["Longitude"]!
            let type = data["Description"]!
            let id = Int(data["Id"]!)
            let doubledLatitude = Double(dataLatitude)
            let doubledLongitude = Double(dataLongitude)
            let recombinedCoordinate = CLLocationCoordinate2D(latitude: doubledLatitude!, longitude: doubledLongitude!)
            print("Firebase alerts posts retrieved")
            let userAlertAnnotation = UserAlert(type: type, coordinate: recombinedCoordinate, firebaseKey: firebaseKey, title: type,id: id!)
            self.userAlertNotificationArray.append(userAlertAnnotation)  // array of notifications coming from Firebase
            //            print("userAlertNotificationArray after retrieving from Firebase is : (self.userAlertNotificationArray)")
            MapArray.alertNotificationCoordinatesArray.append(recombinedCoordinate) // array for checkig alerts on route

            print("                 MapArray.alertNotificationCoordinatesArray after snapshot is: (MapArray.alertNotificationCoordinatesArray)")
            print("                     self.userAlertNotificationArray after snapshot is: (self.userAlertNotificationArray)")
            setCompletion(true)
            self.mapView.addAnnotations(self.userAlertNotificationArray)
        })
    }

新观察者:

func displayAlerts(setCompletion: @escaping (Bool) -> ()) {
    print("                     MapArray.alertNotificationCoordinatesArray before newer displayAlert snapshot is: (MapArray.alertNotificationCoordinatesArray)")
    print("                     self.userAlertNotificationArray before displayAlert snapshot is: (self.userAlertNotificationArray)")
    if self.userAlertNotificationArray.count == 0 {
       ref = Database.database().reference()
        ref?.child("Continent").child("Europe").child("Country").child("Italy").child("Region").child("Emilia-Romagna").child("City").child("Bologna").child("Community").child("Alert Notifications").observeSingleEvent(of: .value, with: { (snapshot) in

            //            self.mapView.removeAnnotations(self.mapView.annotations) //
            print("         snapshot is: (snapshot)")
            guard let data = snapshot.value as? [String :Any] else { return }
            guard let firebaseKey = snapshot.key as? String else { return }
            //                let date = data!["Date"]
            //                let time = data!["Time"]
            let dataLatitude = data["Latitude"] as! Double
            let dataLongitude = data["Longitude"] as! Double
            let type = data["Description"] as! String
            let id = Int(data["Id"] as! String)
            let doubledLatitude = Double(dataLatitude)
            let doubledLongitude = Double(dataLongitude)
            let recombinedCoordinate = CLLocationCoordinate2D(latitude: doubledLatitude, longitude: doubledLongitude)
                        print("Firebase alerts posts retrieved")
            let userAlertAnnotation = UserAlert(type: type, coordinate: recombinedCoordinate, firebaseKey: firebaseKey, title: type,id: id!)
            self.userAlertNotificationArray.append(userAlertAnnotation)  // array of notifications coming from Firebase
            MapArray.alertNotificationCoordinatesArray.append(recombinedCoordinate) // array for checkig alerts on route

            print("                 MapArray.alertNotificationCoordinatesArray after newer displayAlert snapshot is: (MapArray.alertNotificationCoordinatesArray)")
            print("                     self.userAlertNotificationArray after newer displayAlert snapshot is: (self.userAlertNotificationArray)")
            self.mapView.addAnnotations(self.userAlertNotificationArray)
            setCompletion(true)
        })
    }
}

编辑:

这是快照的印刷品,以查看两个版本的结果:

观察Levent快照:

snapshot is: Snap (Alert Notifications) {
    "-LZtTuFSKMhhXFwyT-7K" =     {
        Description = "Ciclabile chiusa";
        Id = 0;
        Latitude = "44.50139187990401";
        Longitude = "11.33592981426992";
    };
    "-LZtUV8MOxVrvPnEfi4g" =     {
        Description = "Lavori in corso";
        Id = 1;
        Latitude = "44.5013918797401";
        Longitude = "11.335929814371545";
    };
    "-LZtV7sJJrOQjAimszTm" =     {
        Description = "Pericoli sulla ciclabile";
        Id = 2;
        Latitude = "44.50139187974223";
        Longitude = "11.335929814367324";
    };
}

和儿童的快照:

snapshot is: Snap (-LZtTuFSKMhhXFwyT-7K) {
    Description = "Ciclabile chiusa";
    Id = 0;
    Latitude = "44.50139187990401";
    Longitude = "11.33592981426992";
}
snapshot is: Snap (-LZtUV8MOxVrvPnEfi4g) {
    Description = "Lavori in corso";
    Id = 1;
    Latitude = "44.5013918797401";
    Longitude = "11.335929814371545";
}
snapshot is: Snap (-LZtV7sJJrOQjAimszTm) {
    Description = "Pericoli sulla ciclabile";
    Id = 2;
    Latitude = "44.50139187974223";
    Longitude = "11.335929814367324";
}

更改

guard let data = snapshot.value as? [String :String] else { return }

to

guard let data = snapshot.value as? [String :[String:String]] else { return } 
data.values.forEach {  
    print($0["Latitude"]) 
    print($0["Longitude"])  
}

您是否可以向数据库中存储的JSON显示出一个榜样?用

.observe(.childAdded, with: {(snapshot) in

您只收到添加的孩子,并带有

.observeSingleEvent(of: .value, with: { (snapshot) in

您会收到整个节点,所以也许节点不是[字符串:字符串]可能比一个项目更多,因此应该是[字符串:任何],然后您可以从其中得到每个孩子。

这只是一个部分答案,但是经过许多不同的尝试,在SH_KHAN的帮助下,我们必须使其正常工作。问题是在guard let data = snapshot.value as? [String :Any] else { return }行中,需要是guard let data = snapshot.value as? [String : [String : String] else { return }

因此,该功能必须写为:

func displayAlerts(setCompletion: @escaping (Bool) -> ()) {
        print("                     MapArray.alertNotificationCoordinatesArray before displayAlert snapshot is: (MapArray.alertNotificationCoordinatesArray)")
        print("                     self.userAlertNotificationArray before displayAlert snapshot is: (self.userAlertNotificationArray)")
        if self.userAlertNotificationArray.count == 0 {
           ref = Database.database().reference()
            ref?.child("Continent").child("Europe").child("Country").child("Italy").child("Region").child("Emilia-Romagna").child("City").child("Bologna").child("Community").child("Alert Notifications").observeSingleEvent(of: .value, with: { (snapshot) -> Void in
                print("         snapshot is: (snapshot)")
                guard let data = snapshot.value as? [String :[String:String]] else { return }
                guard let firebaseKey = snapshot.key as? String else { return }
                data.values.forEach {
//                    let firebaseKey = data.keys[]
                    let dataLatitude = $0["Latitude"]!
                    let dataLongitude = $0["Longitude"]!
                    let type = $0["Description"]!
                    let id = Int($0["Id"]!)
                    print("firebaseKey is:(firebaseKey)")
                    print("dataLatitude is: (dataLatitude)")
                    print("dataLongitude is: (dataLongitude)")
                    print("type is: (type)")
                    print("id is: (id)")
                    print("Key is: (firebaseKey)")
                    print("data is: (data)")
                    let doubledLatitude = Double(dataLatitude)
                    let doubledLongitude = Double(dataLongitude)
                    let recombinedCoordinate = CLLocationCoordinate2D(latitude: doubledLatitude!, longitude: doubledLongitude!)
                    let userAlertAnnotation = UserAlert(type: type, coordinate: recombinedCoordinate, firebaseKey: firebaseKey, title: type,id: id!)
                    self.userAlertNotificationArray.append(userAlertAnnotation)  // array of notifications coming from Firebase
                    MapArray.alertNotificationCoordinatesArray.append(recombinedCoordinate)
                }

                            print("Firebase alerts posts retrieved")
                print("                 MapArray.alertNotificationCoordinatesArray after  displayAlert snapshot is: (MapArray.alertNotificationCoordinatesArray)")
                print("                     self.userAlertNotificationArray after  displayAlert snapshot is: (self.userAlertNotificationArray)")
                self.mapView.addAnnotations(self.userAlertNotificationArray)
                setCompletion(true)
            })
        }
    }

现在我要解决两件事。首先:如何获取子键,因为guard let firebaseKey = snapshot.key as? String else { return }行给了我节点的名称?第二:我创建的较新功能只是为了获得使用.observe(.childAdded, with: { (snapshot) in的Neweralerts,添加了一个新的孩子。我应该问新问题还是继续这里?

谢谢

最新更新