前言
源码地址:https://github.com/reactive-streams/reactive-streams-jvm
PS:关于源码,它实际上并不是一个实现方式,而是提供一套标准,第三方使用这套标准来实现就能够实现互通
背压(反压)backpressure
背压(反压)backpressure概念很关键。首先异步消费者会向生产者订阅接收消息,然后当有新的信息可用时,消费者会通过之前订阅时提供的回调函数被再次激活调用。如果生产者发出的信息比消费者能够处理消息最大量还要多,消费者可能会被迫一直在抓消息,耗费越来越多的资源,埋下潜在的崩溃风险。为了防止这一点,需要有一种机制使消费者可以通知生产者,降低消息的生成速度。生产者可以采用多种策略来实现这一要求,这种机制称为背压。
Reactive目标是使用非阻塞背压方式提供一个标准的异步流处理。
流数据特点是“活”的,其大小是无法预先确定的,在异步系统中需要特别关注。最突出的问题是,资源消耗需要仔细控制,使得如果有一个快速的数据源不至于压倒流的目的地(如同自来水厂水压突然增大,会冲垮水管末端的居民家的水龙头)。异步对于激活计算资源的并行使用是必要的,计算资源包括:多主机或一台机器内多个CPU核心。
Reactive Streams目标是管制流数据在跨越异步边界进行流数据交换,可以认为是将元素传递到另一个线程或线程池,同时确保在接收端不是被迫缓冲任意数量的数据。换句话说,抗压是该模型重要组成部分,设置协调线程之间的队列大小是有限制的,如果不同异步模型之间的通信是同步的将削弱异步的好处。因此必须采取谨慎措施,强制完全无阻塞的反应流能在系统的各个方面异步实施。
这个规范的目标是建立一个规则,使得很多流反应框架能够遵守规则标准,这样才能顺利实现互操作,才能发挥整个流应用上的优点。
Reactive Streams是一个基于JVM的面向流的库包的标准和规范:
1. 处理潜在的无边界限制的元素
2.顺序
3.在组件之间异步传递元素
4.使用强制性的非堵塞的抗压。
重要组件
Publisher
产生用户消费的消息(消息生产者或发布者)。其只有唯一的方法是subscribe(Subscriber),其目的应该是显而易见的,用来订阅的。当调用subscribe方法之后,Publisher应当需要调用subscribe的onSubscription方法。
Subscriber
订阅publishers(通常只有一个)并从中接收多个消息通过方法OnNext(T),错误消息通过onError(Throwable),如果只有一个消息,肯定不会没有更多的消息量使用oncomplete()。在这些任何的情况发生前,publisher需要调用onSubscription(Subscription)来激活它们。
Subscription
在单一publisher和单一subscriber之间的连接。subscriber会用它来请求更多的消息(request(long))或切断连接(cancel())。它会在Subscriber的onSubscription中作为参数传入,通过调用它的request方法开始接受指定数量的数据。
flow流程如下:
1. 创建一个Publisher和一个Subscriber
2. 使用Publisher::subscribe订阅Subscriber
3. Publisher创建Subscription 和调用Subscriber::onSubscription,这样Subscriber可以存储这个Subscription。
4. 在某个时候,subscriber 调用Subscription::request请求一批数量的消息。
5.publisher 开始传递消息给它的订阅者subscriber ,这是通过调用Subscriber::onNext实现的。它发布的消息量绝对不会超过请求所要求数量。
6.publisher发布的消息可能会某段时间后全部发布完毕或遇到麻烦,这时调用Subscriber::onCompleteor或Subscriber::onError
7.subscriber 可以在当前连接继续要求更多的消息,或取消连接Subscription::cancel
实现规则
暂未翻译……征求翻译者,原文在git项目下有。
实现者
Project Reactor(将集成到Spring 5)
Akka Streams
RxJava
引用