RxSwift Объединить массив наблюдаемых с массивом объектов - PullRequest
0 голосов
/ 07 апреля 2020

Я пытаюсь получить данные из Firebase, используя RxSwift. Я использую this для выполнения вызовов API.

Поэтому моя БД выглядит так: Collection Category (у нее есть свойства: title, about et c) внутри есть еще одна коллекция под названием Manifests . Чтобы получить Манифесты Мне нужно использовать documentId из Категория коллекция. Так что это два разных вызова API, но я хочу объединить результаты

Это то, что я имею до сих пор:

    func fetchCategories() -> Observable<[ManifestCategory]> {
        let ref = self.db.collection(FirebaseCollection.manifestCategories.collectionPath)

        return ref.rx.getDocuments().map({ snapshot in
            return snapshot.documents.map({ doc in
                var category = ManifestCategory.init(JSON: doc.data())

                category?.documentId = doc.documentID

                return category
                }).compactMap({ $0 })
        })
    }

    func fetchManifests(categoryId: String) -> Observable<[Manifest]> {
        let ref = self.db.collection(FirebaseCollection.manifests(categoryId: categoryId).collectionPath)

        return ref.rx.getDocuments().map({ snapshot in
            return snapshot.documents.map({ doc in
                var manifest = Manifest.init(JSON: doc.data())

                manifest?.documentId = doc.documentID

                return manifest
            }).compactMap({ $0 })
        })
    }

Можно ли как-нибудь добавить массив Manifests в категорию объект?

Спасибо!

1 Ответ

1 голос
/ 07 апреля 2020

Вы должны попробовать что-то вроде этого:

func fetchCategories() -> Observable<[ManifestCategory]> {
    let ref = self.db.collection(FirebaseCollection.manifestCategories.collectionPath)

    return ref.rx.getDocuments()
        .map { snapshot in
            return snapshot.documents
                .map { doc in
                    var category = ManifestCategory.init(JSON: doc.data())
                    category?.documentId = doc.documentID
                    return category
                }
                .compactMap { $0 }
        }
        .flatMapLatest { [weak self] categories -> Observable<[ManifestCategory]> in
            guard let self = self else {
                return .empty()
            }

            let observables = categories.map { category -> ([Manifest], String) in
                self.fetchManifests(categoryId: category.documentId)
                    .map { ($0, category.documentId) }
            }

            return Observable.zip(observables)
                .map { tuple -> [ManifestCategory] in
                    tuple.compactMap { manifests, id in
                        if var category = categories.first(where: { $0.documentId == id }) {
                            category.manifests = manifests
                            return category
                        }
                        return nil
                    }
                }
        }
}
...