webflux 是不是很容易写出回调地狱啊
话说原本很简单的一个场景,查询 User 和 UserInfo 的信息,然后复制给 OperInfo
webflux 写出来总感觉怪怪的
// mvc
User user = userRepository.findById(xxx);
UserInfo userInfo = userInfoRepository.findById(xxx);
OperInfo operInfo = new OperInfo();
BeanUtils.copyProperties(user, operInfo);
BeanUtils.copyProperties(userInfo, operInfo);
return operInfo;
我 webflux 写成了下面,不知道应该怎么写才是最佳实践
// webflux
Mono<User> user = userRepository.findById(xxx);
Mono<UserInfo> userInfo = userInfoRepository.findById(xxx);
return Mono.zip(user, userInfo).flatmap(data -> {
User user = data.getT1();
UserInfo userInfo = data.getT2();
OperInfo operInfo = new OperInfo();
BeanUtils.copyProperties(user, operInfo);
BeanUtils.copyProperties(userInfo, operInfo);
return operInfo;
})
1
myCupOfTea OP 而且我中间一旦有很多外部调用,回调写到爆炸,好难受
|
2
JamesChen 2021-09-23 08:05:45 +08:00
webflux 不容易写出回调地狱。我写了几十 W 行 reactor-core ( webflux 的底层异步实现),基本都没写出过回调地狱。如果有略微“接近”回调地狱的代码,那也是为了减少中间 Publisher ( Mono/Flux )中间对象与对象传递时的开销,如果不关心这些开销,拆成扁平结构也都是没问题的。
具体操作而言,可以把大块的回调函数拆成多个函数,或拆除多个代码逻辑块。如果要看具体代码,可以参考下面这个超长函数,该函数涉及多个异步操作,但是并没有出现回调地狱,代码都比较扁平: https://github.com/turms-im/turms/blob/9e9cd17e3a1bb5fb3cc32519082885b2ac9f0dba/turms-service/src/main/java/im/turms/service/workflow/access/servicerequest/dispatcher/ServiceRequestDispatcher.java#L152 另外,webflux 没人带,或者自己不怎么想深入专研,不太推荐使用,因为很容易就用错了,而且你还不知道。可以考虑等等 loom (估计 2 年后的时)。 |
3
zhenjiachen 2021-09-23 10:50:19 +08:00
如果不想写回调地狱可以看看 kotlin 的 coroutines,在方法上加个 suspend 配合 reactor 就像写同步代码一样。
|
4
myCupOfTea OP @JamesChen 好的,谢谢拉,我只是要改造 spring cloud gateway 不得已要写
|