Избавление от вложенного типа задачи

Можно ли избавиться от вложенных обобщений задач?

Для каждого continueWith заявление, новый Task добавляется в типе. Каждое продолжение является частью типа. В идеале я бы возвратил одну задачу, которая последовательно выполняет каждую задачу и успешно или неудачно завершается.

пример

Первые операции запрашивают группы пользователя

private fun getGroupsSnapshot(): Task<QuerySnapshot> {
    val userId = Auth.currentUser()!!.uid
    val query = userGroupsQuery(groupsCollection, userId)
    return query.get()
}

Вторая операция запрашивает альбомы в этих группах.

fun getAlbums(): Task<Task<List<Album>>> {
    return getGroupsSnapshot().continueWith { task ->
        val documentSnapshots = TaskUtils.getResult(task)
        val albums = mutableListOf<Album>()
        val fetchAlbumTasks = documentSnapshots.documents.map { document ->
            Log.d(TAG, document["name"].toString())
            document.reference.collection("albums").get().addOnCompleteListener { queryTask ->
                albums.addAll(toObjects(Album::class.java, queryTask))
            }
        }
        return@continueWith Tasks.whenAll(fetchAlbumTasks).continueWith allTasks@ {
            return@allTasks albums as List<Album>
        }
    }
}

Однако я хотел бы, чтобы эта операция возвращала тип Task<List<Album>> поддерживать интерфейс в чистоте.

1 ответ

Решение

Для составления нескольких Task вы должны использовать continueWithTask вместо continueWith, Он принимает Continuation<TResult, Task<TContinuationResult> в качестве параметра, который существенно выравнивает возвращаемый Task и избегает вложения. Вы должны думать об этом как map против flatMap операция в монаде (т.е. List), в этом случае, continueWithTask будет эквивалентно flatMap если вы используете List в качестве контейнера вместо Task (Помните, с flatMap вы трансформируете каждый элемент List к новому Listи сгладить полученную List)

Другие вопросы по тегам