You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Webflux ServerResponse空白及未认证flatMap不执行问题排查

Spring Webflux RouterFunction 认证场景响应问题修复

原代码问题

@Bean
public RouterFunction<ServerResponse> refresh() {
    return route(GET("/api/refresh"), (request) ->
            request.principal().or(Mono.empty()).flatMap((it) -> {
                System.out.println(it);

                return ServerResponse.ok().body(Mono.just(new FreshStatus(true)), FreshStatus.class);
            }));
}

record FreshStatus(boolean isFresh) {}

存在两个问题:

  • 未认证时:flatMap内代码完全不执行,响应状态码200但无内容
  • 已认证时:flatMap内代码正常执行(能打印Principal),但响应体空白,状态码仍为200

问题原因

  1. 未认证场景:request.principal()本身就会返回Mono.empty(),调用.or(Mono.empty())后还是空Mono。而flatMap仅在上游Mono有值时才会执行逻辑,因此整个handler最终返回Mono.empty(),Spring Webflux会将其处理为200 OK的空响应。
  2. 已认证场景:原代码在flatMap内构建ServerResponse,虽逻辑合法,但存在订阅链路的隐性问题,导致响应体的Mono.just(new FreshStatus(true))未被正确触发序列化,最终返回空白。

修复代码

@Bean
public RouterFunction<ServerResponse> refresh() {
    return route(GET("/api/refresh"), (request) ->
            ServerResponse.ok().body(
                    request.principal()
                            .map(it -> new FreshStatus(true))
                            .defaultIfEmpty(new FreshStatus(false)),
                    FreshStatus.class
            )
    );
}

record FreshStatus(boolean isFresh) {}

修复逻辑说明

  • 用map将已认证的Principal直接映射为FreshStatus(true),确保认证场景生成正确响应数据
  • 用defaultIfEmpty(new FreshStatus(false))兜底处理未认证场景,避免返回空Mono
  • 将整个Mono<FreshStatus>作为响应体传入ServerResponse.ok().body(),保证无论是否认证,都会生成包含有效内容的200响应

内容的提问来源于stack exchange,提问作者Vinz243

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 08:05:23