在Reactive Extensions中使用Flowable时,避免同池死锁

时间:2019-01-09 19:02:30

标签: android kotlin rx-java2 deadlock

在订阅Reactive Extensions Flowable流时,我注意到在返回128个项目之后,该流暂停/挂起(不再发射任何将来的项目,也没有返回错误)。

val download: Flowable<DownloadedRecord> = sensor.downloadRecords()
download
    .doOnComplete { Log.i( "TEST", "Finished!" ) }
    .subscribe(
        { record ->
            Log.i( "TEST", "Got record: ${record.record.id}; left: ${record.recordsLeft}" )
        },
        { error ->
            Log.i( "TEST", "Error while downloading records: $error" )
        } )

这很可能与反应式扩展有关。我发现了the default buffer size of Flowable is set to 128;不太可能是巧合。

在试图了解正在发生的事情时,我遇到了Flowable.subscribeOn上的以下文档。

  

如果链中有一个create(FlowableOnSubscribe, BackpressureStrategy)类型的源,建议将requestOn设置为false以避免同一池死锁,因为请求可能堆积在渴望/阻止发射器。

尽管我不太了解在这种情况下相同池死锁是什么,但看来我的流中正在发生类似的事情。

1。什么是Reactive Extensions中的相同池死锁?在Android上重新创建它的最小代码示例是什么?

目前无所适从,我尝试在.subscribeOn( Schedulers.io(), false )之前应用.subscribe,但并没有真正理解它的作用,但是在发送128个项目之后,流仍然锁定。

2。我该如何调试该问题,以及如何/在何处解决?

1 个答案:

答案 0 :(得分:0)

  
      
  1. 什么是Reactive Extensions中的同池死锁?
  2.   

RxJava在标准调度程序中使用单线程执行程序。当阻塞或急切的源发出项目时,它占用了该单个线程,即使下游请求更多,subscribeOn也会将这些请求安排在当前正在运行/阻塞的代码后面,然后再也不会收到有关新机会的通知。 / p>

  

在Android上重新创建它的最小代码示例是什么?

为什么要让代码陷入僵局?

  

我尝试应用.subscribeOn(Schedulers.io(),false)

您的实际流量是多少?您可能将subscribeOn应用于距源太远的位置,因此无效。最可靠的方法是将其放在create旁边。

  

我该如何调试该问题,以及如何/在哪里解决?

doOnNextdoOnRequest放在各个地方,看看信号消失的地方。