Spring Boot 2.0.8.RELEASE集成WebFlux与Integration启动失败求助
webFluxConversionService与integrationConversionService Bean冲突问题 在Spring Boot 2.0.8.RELEASE里同时引入spring-boot-starter-webflux和spring-boot-starter-integration依赖时,确实会触发这个Bean冲突问题——两个ConversionService类型的Bean(webFluxConversionService和integrationConversionService)会被自动注册,导致依赖注入时Spring找不到唯一匹配的Bean,最终启动失败。
先看下你遇到的错误信息:
APPLICATION FAILED TO START
描述:de.test.service.SomeServiceAdapterImpl构造方法的参数1需要单一Bean,但找到2个:
- webFluxConversionService:由org.springframework.web.reactive.config.DelegatingWebFluxConfiguration中的方法'webFluxConversionService'定义
- integrationConversionService:定义为null
建议:考虑将其中一个Bean标记为@Primary,更新消费者以接受多个Bean,或使用@Qualifier指定要使用的Bean。
问题原因
WebFlux和Spring Integration这两个模块都会自动注册各自的ConversionService Bean,当你的代码直接依赖ConversionService接口类型时,Spring无法判断该注入哪一个,因此抛出了Bean歧义异常。另外注意你代码里用了Lombok的@RequiredArgsConstructor,字段上的@Qualifier不会自动同步到生成的构造方法参数上,这也是为什么你加了@Qualifier却依然报错的核心原因。
解决办法
1. 修正@Qualifier的使用方式(适配你的代码)
因为Lombok生成的构造方法不会继承字段上的@Qualifier注解,所以需要让@Qualifier直接作用在构造方法参数上。有两种方式:
- 手动编写构造方法,给参数加上
@Qualifier:
@Component public class SomeServiceAdapterImpl { private final ConversionService conversionService; public SomeServiceAdapterImpl(@Qualifier("webFluxConversionService") ConversionService conversionService) { this.conversionService = conversionService; } // 业务方法 }
- 依然使用Lombok,但通过
onConstructor_属性把@Qualifier加到构造方法上(需要Lombok 1.18.4及以上版本):
@Component @RequiredArgsConstructor(onConstructor_ = {@Qualifier("webFluxConversionService")}) public class SomeServiceAdapterImpl { private final ConversionService conversionService; // 业务方法 }
2. 标记其中一个Bean为@Primary
如果你的项目多数场景下都用同一个ConversionService,可以通过配置类把它标记为@Primary,让Spring默认优先注入这个Bean:
@Configuration public class ConversionServiceConfig { @Primary @Bean public ConversionService primaryConversionService(@Qualifier("webFluxConversionService") ConversionService webFluxConversionService) { return webFluxConversionService; } }
这样之后,代码里直接依赖ConversionService类型时,Spring会自动注入被标记为@Primary的实例。
3. 自定义整合式ConversionService
如果需要同时用到两个模块的转换规则,可以自定义一个ConversionService,把两个内置的转换器整合到一起:
@Configuration public class CombinedConversionServiceConfig { @Bean @Primary public ConversionService combinedConversionService( @Qualifier("webFluxConversionService") ConversionService webFluxConversionService, @Qualifier("integrationConversionService") ConversionService integrationConversionService) { GenericConversionService combinedService = new GenericConversionService(); // 加入WebFlux的所有转换器 if (webFluxConversionService instanceof GenericConversionService) { ((GenericConversionService) webFluxConversionService).getConverters().forEach(combinedService::addConverter); } // 加入Spring Integration的所有转换器 if (integrationConversionService instanceof GenericConversionService) { ((GenericConversionService) integrationConversionService).getConverters().forEach(combinedService::addConverter); } return combinedService; } }
内容的提问来源于stack exchange,提问作者Eli

