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

Spring Webflux响应式Mongo与Spring MVC Mongo性能差异排查

问题:Spring Webflux+响应式Mongo性能远低于Spring MVC+同步Mongo的原因分析

测试场景与性能结果

  • 开发两个对比应用:一个基于Spring Webflux搭配响应式Mongo驱动,另一个基于Spring MVC搭配非响应式Mongo驱动
  • 测试数据:Mongo实例中存入45000条数据
  • 性能表现:
    • MVC应用平均响应时间约200-300ms
    • 响应式应用平均响应时间约2秒,是MVC的3倍以上
    • 跨机器JMeter压测时,响应式应用性能仅为MVC的1/3
    • 使用内存仓库时,两者性能相近

环境配置

Docker部署的Mongo实例配置

mongo:
  image: mongo
  restart: always
  env_file:
    - ./env/mongo.env #仅配置用户名和密码
  ports:
    - 27017:27017
  volumes:
    - mongodb:/data/db
    - mongoconfigdb:/data/configdb

应用配置(MVC与响应式一致)

application.yml:

spring:
  data:
    mongodb:
      uri: mongodb://admin:nimda@localhost:27017
      database: data-name
      auto-index-creation: true
  application:
    name: data

Mongo实体类(两者一致)

@Document(collection = "data")
public class Data {

    @Id
    private String id;

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }
}

MVC应用实现细节

Controller

@RestController
public class BlockingController {

    private final BlockingMongoRepository blockingMongoRepository;

    public BlockingController(@Qualifier("blockingMongoRepository") BlockingMongoRepository blockingMongoRepository) {
        this.blockingMongoRepository = blockingMongoRepository;
    }

    @RequestMapping(value = "/get", method = RequestMethod.GET, produces = MediaType.APPLICATION_JSON_VALUE)
    public List<Data> getAllData() {
        return blockingMongoRepository.findAll();
    }
}

Repository

@Repository(value = "blockingMongoRepository")
public interface BlockingMongoRepository extends MongoRepository<Data, String> {
}

依赖配置(build.gradle)

dependencies {
    implementation 'org.springframework.boot:spring-boot-starter-data-mongodb'
    implementation 'org.springframework.boot:spring-boot-starter-web'
}

响应式应用实现细节

Controller

@RestController
public class ReactiveController {

    private final DataReactiveMongoRepository dataReactiveMongoRepository;

    public ReactiveController(@Qualifier("dataReactiveMongoRepository") DataReactiveMongoRepository dataReactiveMongoRepository) {
        this.dataReactiveMongoRepository = dataReactiveMongoRepository;
    }

    @RequestMapping(value = "/get", method = RequestMethod.GET, produces = MediaType.APPLICATION_JSON_VALUE)
    public Flux<Data> getAllData() {
        return dataReactiveMongoRepository.findAll();
    }
}

Repository

@Repository(value = "dataReactiveMongoRepository")
public interface DataReactiveMongoRepository extends ReactiveMongoRepository<Data, String> {
}

依赖配置(build.gradle)

dependencies {
    implementation 'org.springframework.boot:spring-boot-starter-data-mongodb-reactive'
    implementation 'org.springframework.boot:spring-boot-starter-webflux'
}

排查过程与关键发现

  • 针对响应式Controller尝试修改返回格式:返回x-ndjson、将Flux转为List,性能无提升;返回单条x-ndjson格式时性能更差
  • 手动添加@EnableReactiveMongoRepositories无效果
  • 连接Mongo Atlas免费实例时也出现相同性能差异(测试可靠性较低)
  • 关键更新发现:
    • 直接使用org.mongodb:mongodb-driver-reactivestreams的MongoClient时,性能比MVC应用高约2.3倍
    • 使用ReactiveMongoTemplate/Repository时,Blockhound检测到阻塞调用;直接用MongoClient时无此情况,推测性能损耗来自Spring Mongo Starter阻塞事件循环,但疑惑为何会影响单请求响应时间

疑问

这种情况的原因是什么?是否需要额外配置才能发挥Webflux的性能优势?


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.17 17:05:33