I have this block of code that works fine:
return isBlacklistedToken(refreshToken, Boolean.TRUE).flatMap(isBlacklisted -> { if (isBlacklisted) return Mono.error(new UnauthorizedException(format("The user %s has already logged out.", username))); else return isBlacklistedToken(accessToken, Boolean.FALSE).flatMap(isABlacklisted -> { if (isABlacklisted) return Mono.error(new UnauthorizedException(format("The user %s has already logged out.", username))); else return blacklistTokens(username, refreshToken, accessToken); }); });
To summarize it:
- calls the
isBlacklistedToken
function (returns aMono<Boolean>
with the result of the refresh token) - If the
refresh
token is blacklisted, throws anUnauthorizedException
- If the
refresh
token is not blacklisted, does the same process for theaccess
token - If both tokens are not blacklisted, finally blacklists them.
This syntax, while it works, seems a bit sloppy. Is there a way to improve that? I wrote this piece of code, and while it throws an exception, the last part (blacklisting the tokens) always executes – peraphs my knowledge of reactive programming is a bit off.
return isBlacklistedToken(refreshToken, Boolean.TRUE) .flatMap(isBlacklisted -> isBlacklisted ? Mono.error(new UnauthorizedException(format("The user %s has already logged out.", username))) : Mono.empty()) .then(isBlacklistedToken(accessToken, Boolean.FALSE)) .flatMap(isBlacklisted -> isBlacklisted ? Mono.error(new UnauthorizedException(format("The user %s has already logged out.", username))) : Mono.empty()) .then(blacklistTokens(username, refreshToken, accessToken));
Edit: adding the isBlacklistedToken
method
private Mono<Boolean> isBlacklistedToken(final String token, final Boolean type) { return blacklistService.isBlacklisted(token, type); }
and the respective blacklistService
call (just a repository call, really simple)
public Mono<Boolean> isBlacklisted(final String token, final Boolean isRefresh) { return Mono.just(this.blacklistRepository.existsBlacklistByTokenAndIsRefresh(token, isRefresh)); }
Advertisement
Answer
I would suggest the following:
return isBlacklistedToken(refreshToken, Boolean.TRUE) .filter(isBlacklisted -> !isBlacklisted) .flatMap(isBlacklisted -> isBlacklistedToken(accessToken, Boolean.FALSE)) .filter(isBlacklisted -> !isBlacklisted) .flatMap(isBlacklisted -> blacklistTokens(username, refreshToken, accessToken)) .switchIfEmpty(Mono.error(new UnauthorizedException(format("The user %s has already logged out.", username))));
Sorry if there is some compile error but I tried this in Kotlin and needed to translate it to Java, which is become less and less easy.