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

Micronaut 3.10.3对比3.10.2的哪些变更引发SSLHandshake失败?

升级Micronaut BOM至3.10.3后SSL握手失败问题分析

问题描述

仅将Micronaut BOM从3.10.2升级至3.10.3后,所有应用出现SSL连接错误,错误堆栈如下:

io.micronaut.http.client.exceptions.HttpClientException: <JKS_URL_HERE_works_fine_from_browser>: Connect Error: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
at com.td.vsx.common.mn.ErrorTracingHttpClientFilter$DelegatingPublisher.replaceExceptionIncludingUrl(ErrorTracingHttpClientFilter.java:101)
at com.td.vsx.common.mn.ErrorTracingHttpClientFilter$DelegatingPublisher$1.onError(ErrorTracingHttpClientFilter.java:80)
at reactor.core.publisher.FluxMap$MapSubscriber.onError(FluxMap.java:134)
at reactor.core.publisher.FluxOnErrorResume$ResumeSubscriber.onError(FluxOnErrorResume.java:106)
at reactor.core.publisher.Operators.error(Operators.java:198)
at reactor.core.publisher.MonoError.subscribe(MonoError.java:53)
at reactor.core.publisher.Mono.subscribe(Mono.java:4576)
at reactor.core.publisher.FluxOnErrorResume$ResumeSubscriber.onError(FluxOnErrorResume.java:103)
at reactor.core.publisher.FluxMap$MapSubscriber.onError(FluxMap.java:134)
at reactor.core.publisher.MonoNext$NextSubscriber.onError(MonoNext.java:93)
at reactor.core.publisher.MonoNext$NextSubscriber.onError(MonoNext.java:93)
at io.micronaut.core.async.propagation.ReactivePropagation$2.onError(ReactivePropagation.java:129)
at io.micronaut.http.reactive.execution.FlowAsMono$SubscriptionImpl.forward(FlowAsMono.java:132)
at io.micronaut.http.reactive.execution.FlowAsMono$SubscriptionImpl.lambda$request$0(FlowAsMono.java:119)
at io.micronaut.core.execution.ImperativeExecutionFlowImpl.onComplete(ImperativeExecutionFlowImpl.java:132)
at io.micronaut.core.execution.DelayedExecutionFlowImpl$OnComplete.apply(DelayedExecutionFlowImpl.java:383)
at io.micronaut.core.execution.DelayedExecutionFlowImpl.work(DelayedExecutionFlowImpl.java:54)
at io.micronaut.core.execution.DelayedExecutionFlowImpl.complete0(DelayedExecutionFlowImpl.java:75)
at io.micronaut.core.execution.DelayedExecutionFlowImpl.completeExceptionally(DelayedExecutionFlowImpl.java:87)
at io.micronaut.http.client.netty.PoolResizer$PendingRequest.tryCompleteExceptionally(PoolResizer.java:429)
at io.micronaut.http.client.netty.ConnectionManager$Pool.onNewConnectionFailure(ConnectionManager.java:1243)
at io.micronaut.http.client.netty.ConnectionManager$Pool$1.onNewConnectionFailure(ConnectionManager.java:1205)
at io.micronaut.http.client.netty.InitialConnectionErrorHandler.channelInactive(InitialConnectionErrorHandler.java:48)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:303)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:281)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelInactive(AbstractChannelHandlerContext.java:274)
at io.netty.channel.ChannelInboundHandlerAdapter.channelInactive(ChannelInboundHandlerAdapter.java:81)
at io.netty.handler.ssl.ApplicationProtocolNegotiationHandler.channelInactive(ApplicationProtocolNegotiationHandler.java:167)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:303)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:281)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelInactive(AbstractChannelHandlerContext.java:274)
at io.netty.handler.codec.ByteToMessageDecoder.channelInputClosed(ByteToMessageDecoder.java:412)
at io.netty.handler.codec.ByteToMessageDecoder.channelInactive(ByteToMessageDecoder.java:377)
at io.netty.handler.ssl.SslHandler.channelInactive(SslHandler.java:1192)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:303)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:281)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelInactive(AbstractChannelHandlerContext.java:274)
at io.netty.channel.DefaultChannelPipeline$HeadContext.channelInactive(DefaultChannelPipeline.java:1352)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:301)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelInactive(AbstractChannelHandlerContext.java:281)
at io.netty.channel.DefaultChannelPipeline.fireChannelInactive(DefaultChannelPipeline.java:850)
at io.netty.channel.AbstractChannel$AbstractUnsafe$7.run(AbstractChannel.java:811)
at io.netty.util.concurrent.AbstractEventExecutor.runTask(AbstractEventExecutor.java:173)
at io.netty.util.concurrent.AbstractEventExecutor.safeExecute(AbstractEventExecutor.java:166)
at io.netty.util.concurrent.SingleThreadEventExecutor.runAllTasks(SingleThreadEventExecutor.java:472)
at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:566)
at io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:998)
at io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
at java.base/java.lang.Thread.run(Thread.java:842)

可能的原因分析

1. Netty版本升级带来的SSL验证逻辑变更

Micronaut 3.10.3大概率升级了底层依赖的Netty版本,新版本的Netty SSL Handler对证书链的验证逻辑更严格:

  • 不再默认信任不完整的证书链(如服务器未正确返回中间证书)
  • 对证书扩展字段(如Subject Alternative Name)的验证要求更高
  • 修改了PKIX路径构建规则,导致JVM默认信任库无法匹配证书路径

2. Micronaut HTTP客户端SSL默认配置调整

3.10.3版本可能调整了HTTP客户端的默认SSL配置:

  • 默认启用严格的证书验证模式,关闭了3.10.2中可能存在的宽松兼容选项
  • 修改了信任库加载逻辑,不再自动加载系统信任库之外的自定义证书
  • 调整micronaut.http.client.ssl下的默认属性值,比如trust-all默认改为false

3. 证书路径构建逻辑优化

Micronaut在3.10.3中修改了PKIX证书路径构建的实现:

  • 不再自动尝试补充缺失的中间证书
  • 对证书有效性检查更全面,比如拒绝过期或吊销状态的证书(即使之前版本未严格校验)

排查与解决建议

  • 验证证书链完整性:检查目标服务器返回的证书链是否包含所有必要的中间证书,可通过浏览器查看证书详情确认;若缺失,需将中间证书添加到应用的信任库或服务器配置中。
  • 对比版本配置差异:查看Micronaut 3.10.3的发布说明,确认是否有micronaut.http.client.ssl相关的默认配置变更,针对性调整应用配置。
  • 临时宽松验证排查:添加配置micronaut.http.client.ssl.insecure=true(仅用于测试),若连接恢复正常,说明是验证逻辑变严格导致的问题,需补充对应证书到信任库。
  • 检查自定义SSL配置:若应用使用了自定义信任库或SSL上下文,确认3.10.3版本中加载逻辑是否正常,比如文件路径、权限是否符合要求。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.13 03:50:06