使用Kotlin Flow做HTTP轮询(三)

其实做HTTP轮询也相当简单,比如,我们现在在《如何在android开发中使用Kotlin Flow(二)》
基础上改成一个HTTP轮询:


class CommentRepository(private val apiService: GetCommentService) {

    var isClosed = false
    private val dispatcher = Dispatchers.IO
    suspend fun getCommentWithId(id: Int): Flow<CommentModel> {
        
        return channelFlow {
            while (!isClosed) {

                val data = apiService.getCommentWithId(id)
                send(data)
                delay(5000)
            }
        }.flowOn(dispatcher)


//        flow {
//            val data = apiService.getCommentWithId(id)
//            emit(data)
//        }.flowOn(Dispatchers.IO)
    }
    
    fun close() {
        dispatcher.cancel()
    }
}

这样就完成了一个5秒请求一次HTTP的功能了。我现在来谈谈这个channelFlow。

public fun <T> channelFlow(@BuilderInference block: suspend ProducerScope<T>.() -> Unit): Flow<T> =
    ChannelFlowBuilder(block)

它会创建一个冷流对象ChannelFlowBuilder请添加图片描述

它最终也是一个Flow对象。我们传给我们的函数,就是上图中的block,最终它会提供一个ProducerScope:
在这里插入图片描述
它会给我们提供SendChannel对象,我们用它在我们的block里发送生产出来的数据。在channelFlow里,我们让运行在不同协程上下文的代码生产数据,或者让它们并发生产数据,不管怎么样,这些产生的数据都可以用SendChannel来发送,如(这两个例子是来自官方的):

fun <T> Flow<T>.merge(other: Flow<T>): Flow<T> = channelFlow {
    // collect from one coroutine and send it
    launch {
        collect { send(it) }
    }
    // collect and send from this coroutine, too, concurrently
    other.collect { send(it) }
}

fun <T> contextualFlow(): Flow<T> = channelFlow {
    // send from one coroutine
    launch(Dispatchers.IO) {
        send(computeIoValue())
    }
    // send from another coroutine, concurrently
    launch(Dispatchers.Default) {
        send(computeCpuValue())
    }
}

因为channelFlow产生的是一个冷流,所以它的启动,也只有在collect末端操作符作用上来时,才会启动。channelFlow是线程安全的,不用担心它会因并发而产生不好的结果。

我们block里的代码,一执行完,channelFlow产生的Flow对象也就结束了。因为它是冷流的原因,为了让它保持工作,上面我用了while循环让它一直工作。

如果想结束它,可以拿到它的协程上下文进行取消操作,如上面的close方法。

大概就这么多先吧。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值