В первом примере getDocument возвращает DocumentSnapshot, который является подмножеством DocumentSnapshot? который является необязательным, поэтому его можно использовать с объектом Results .flatmap.
Во втором примере getDocuments не возвращает DocumentSnapshot, он возвращает QueryDocumentSnapshot:
Гарантия QueryDocumentSnapshots что их содержимое всегда ненулевое
Это означает, что оно не является необязательным и не может использоваться с .flatmap, поскольку его нельзя развернуть.
Документация Firebase показывает QueryDocumentSnapshot является подклассом DocumentSnapshot, DocumentSnapshot является необязательным, QueryDocumentSnapshot не является.
В этом случае .flatmap используется для развертывания DocumentSnapshot (необязательный) - происходит то, что объект в Result будет быть необязательным без него. Таким образом .flatmap разворачивает его один раз, а затем if let city = city {
снова разворачивает его, и в итоге он становится просто объектом города.
Вот что я хотел бы сделать ... Заменить этот код чем-то вроде
func getCities() {
let docRef = db.collection("cities")
docRef.getDocuments { (querySnapshot, error) in
if let snapshotDocuments = querySnapshot?.documents {
for document in snapshotDocuments {
do {
if let city = try document.data(as: City.self) {
print(city.name)
}
} catch let error as NSError {
print("error: \(error.localizedDescription)")
}
}
}
}
}
EDIT
Я собираюсь позаимствовать это у github, потому что это делает использование результатов (как показано в документации) намного более понятным.
There are thus three cases to handle, which Swift lets us describe
nicely with built-in sum types:
Result
/\
Error Optional<City>
/\
Nil City //<- we get the actual city with `if let city = city {`