【发布时间】:2021-05-05 09:10:23
【问题描述】:
给定以下方法:
private Mono<UserProfileUpdate> upsertUserIdentifier(UserProfileUpdate profileUpdate, String id){
return userIdentifierRepository.findUserIdentifier(id)
.switchIfEmpty(Mono.defer(() -> {
profileUpdate.setNewUser(true);
return createProfileIdentifier(profileUpdate.getType(), id);
}))
.map(userIdentifier -> {
profileUpdate.setProfileId(userIdentifier.getProfileId());
return profileUpdate;
});
}
switchIfEmpty 和 map 运算符会改变 profileUpdate 对象。在switchIfEmpty 运算符中进行变异是否安全?关于map,如果我理解正确的话,这是不安全的,对象profileUpdate 必须是不可变的,对吧?例如:
private Mono<UserProfileUpdate> upsertUserIdentifier(UserProfileUpdate profileUpdate, String id){
return userIdentifierRepository.findUserIdentifier(id)
.switchIfEmpty(Mono.defer(() -> {
profileUpdate.setNewUser(true);
return createProfileIdentifier(profileUpdate.getType(), id);
}))
.map(userIdentifier -> profileUpdate.withProfileId(userIdentifier.getProfileId()));
}
在链的后面,另一个方法改变了对象:
public Mono<UserProfileUpdate> transform(UserProfileUpdate profUpdate) {
if (profUpdate.isNewUser()) {
profUpdate.getAttributesToSet().putAll(profUpdate.getAttributesToSim());
} else if (!profUpdate.getAttributesToSim().isEmpty()) {
return userProfileRepository.findUserProfileById(profUpdate.getProfileId())
.map(profile -> {
profUpdate.getAttributesToSet().putAll(
collectMissingAttributes(profUpdate.getAttributesToSim(), profile.getAttributes().keySet()));
return profUpdate;
});
}
return Mono.just(profUpdate);
}
上述方法调用如下:
Mono.just(update)
.flatMap(update -> upsertUserIdentifier(update, id))
.flatMap(this::transform)
【问题讨论】:
-
正如下面的答案中所指出的,这取决于。如果您的代码示例是安全的。很确定。它是否使代码易于遵循。我会说不。这使得很难理解您的对象处于什么状态,并且如果在某个地方做错了,状态可能会以一种可能导致难以发现错误和问题的方式发生变化。我会避免它,但这就是我,我会尝试在设计一切时考虑到不变性。
标签: java reactive-programming spring-webflux project-reactor