如何从 rxjava 平面映射调用协程用例

How to call a coroutine usecase from a rxjava flat map

提问人:BRDroid 提问时间:1/8/2021 最后编辑:BRDroid 更新时间:1/9/2021 访问量:3430

问:

嗨,我有一个 rxjava 平面图,我想在其中调用协程用例 onStandUseCase,这是一个 api 调用

最初,该用例也是基于 rxjava 的,它曾经返回并且工作正常 现在我将用法更改为基于协程,它只返回Observable<GenericResponse>GenericResponse

请如何修改平面图以与协程用例一起正常工作

        subscriptions += view.startFuellingObservable
        .onBackpressureLatest()
        .doOnNext { view.showLoader(false) }
        .flatMap {
            if (!hasOpenInopIncidents()) {
                //THIS IS WHERE THE ERROR IS IT RETURNS GENERICRESPONSE
                onStandUseCase(OnStandUseCase.Params("1", "2", TimestampedAction("1", "2", DateTime.now()))) {
                    
                }
               
            } else {
                val incidentOpenResponse = GenericResponse(false)
                incidentOpenResponse.error = OPEN_INCIDENTS
                Observable.just(incidentOpenResponse)
            }
        }
        .subscribe(
            { handleStartFuellingClicked(view, it) },
            { onStartFuellingError(view) }
        )

OnStandUseCase.kt (英语)

class OnStandUseCase @Inject constructor(
    private val orderRepository: OrderRepository,
    private val serviceOrderTypeProvider: ServiceOrderTypeProvider
) : UseCaseCoroutine<GenericResponse, OnStandUseCase.Params>() {

    override suspend fun run(params: Params) = orderRepository.notifyOnStand(
        serviceOrderTypeProvider.apiPathFor(params.serviceType),
        params.id,
        params.action
    )

    data class Params(val serviceType: String, val id: String, val action: TimestampedAction)
}

用例协程

abstract class UseCaseCoroutine<out Type, in Params> where Type : Any {

    abstract suspend fun run(params: Params): Type

    operator fun invoke(params: Params, onResult: (type: Type) -> Unit = {}) {
        val job = GlobalScope.async(Dispatchers.IO) { run(params) }
        GlobalScope.launch(Dispatchers.Main) { onResult(job.await()) }
    }
}

startFuellingObservable 是

val startFuellingObservable: Observable<Void>

这是错误的图像

enter image description here

关于如何解决此问题的任何建议,请

提前致谢 R

Android Kotlin RX-Java Kotlin-Coroutines 用例

评论

0赞 George Leung 1/8/2021
使用集成库。然后写.由于您不需要可观察对象,因此您可以编写 .rxSingle { ... }.toObservable()concatMapSingleflatMap
0赞 BRDroid 1/9/2021
你好@GeorgeLeung一个开始FuellingObservable仍然是一个可观察的,我不想改变那一边
0赞 George Leung 1/9/2021
Observable#concatMapSingle s an .通过“不需要可观察对象”,我的意思是挂起函数对应于 a 而不是 .returnObservableSingleObservable
0赞 BRDroid 1/9/2021
你能建议如何改变我的代码吗,我对此很陌生

答:

6赞 George Leung 1/9/2021 #1

有一个链接 RxJava 和 Kotlin 协程的集成库

rxSingle可用于将挂起函数转换为 Single。OP 想要一个 ,所以我们可以调用转换。ObservabletoObservable()

.flatMap {
    if (!hasOpenInopIncidents()) {
        rxSingle {
            callYourSuspendFunction()
        }.toObservable()
    } else {
        val incidentOpenResponse = GenericResponse(false)
        incidentOpenResponse.error = OPEN_INCIDENTS
        Observable.just(incidentOpenResponse)
    }
}

请注意,两个分支中的 s 只包含一个元素。我们可以通过使用 Observable#concatMapSingle 使这一事实更加明显。Observable

.concatMapSingle {
    if (!hasOpenInopIncidents()) {
        rxSingle { callYourSuspendFunction() }
    } else {
        val incidentOpenResponse = GenericResponse(false)
        incidentOpenResponse.error = OPEN_INCIDENTS
        Single.just(incidentOpenResponse)
    }
}