我正在重新考虑我们的 Spring MVC 应用程序行为,无论是从数据库中提取(Java8 Stream)数据还是让数据库推送(Reactive / Observable)数据并使用背压来控制数量更好。
现在的情况:
User
请求最近的 30 篇文章Service
进行数据库查询并将 30 个结果放入List
Jackson
迭代List
并生成 JSON 响应
为什么要切换实现?
这非常消耗内存,因为我们一直将这 30 个对象保存在内存中。这不是必需的,因为应用程序一次处理一个对象。尽管应用程序应该能够检索一个对象、对其进行处理、将其丢弃并获取下一个对象。
Java8 流?(拉)
这java.util.Stream
很容易:Service
创建一个Stream
,它在幕后使用数据库游标。并且每次Jackson
为 的一个元素写入 JSON 字符串时Stream
,它会请求下一个元素,然后触发数据库游标返回下一个条目。
RxJava / 反应式 / 可观察?(推)
这里我们有相反的情况:数据库必须逐个推送条目,并且Jackson
必须为每个元素创建 JSON 字符串,直到onComplete
调用该方法。
即Controller
告诉Service
:给我一个Observable<Article>
。然后Jackson
可以请求尽可能多的数据库条目,因为它可以处理。
分歧和担忧:
在请求下一个数据库条目和检索/处理它Streams
之间总是有一些延迟。如果网络连接速度较慢或必须发出大量数据库请求来完成响应,这可能会减慢 JSON 响应时间。
使用RxJava
应该始终有可用于处理的数据。如果它太多,我们可以使用背压来减慢从数据库到应用程序的数据传输。在最坏的情况下,缓冲区/队列将包含所有请求的数据库条目。那么内存消耗将等于我们当前使用List
.
我为什么要问/我要什么?
我错过了什么?还有其他优点/缺点吗?
Stream
如果每个数据库请求/响应之间总是存在(短)延迟,为什么(特别是)Spring Data Team 扩展他们的 API 以支持来自数据库的响应?对于大量请求的条目,这可能会导致一些明显的延迟。是否建议在
RxJava
这种情况下使用(或其他一些反应式实现)?还是我错过了任何缺点?