Spring Boot 3.x微服务升级经历
阿里云国内75折 回扣 微信号:monov8 |
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6 |
前言
Spring Boot 3.0.0 GA版已经发布好多人也开始尝试升级有人测试升级后启动速度确实快了不少如下为网络截图于是我也按捺不住的想尝试下。
历程
首先就是要把Spring Boot、Spring Cloud 相关的依赖升一下
Spring Boot3.0.0
Spring Cloud2022.0.0-RC2
统一依赖版本管理
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>2022.0.0-RC2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>3.0.0</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
现在还不能下载Spring 相关依赖包需要加入Spring 仓库。
在你的maven仓库中加入如下配置我是加在了pom.xml
中
<repository>
<id>netflix-candidates</id>
<name>Netflix Candidates</name>
<url>https://artifactory-oss.prod.netflix.net/artifactory/maven-oss-candidates</url>
<snapshots>
<enabled>false</enabled>
</snapshots>
</repository>
<repository>
<id>spring-milestones</id>
<name>Spring Milestones</name>
<url>https://repo.spring.io/milestone</url>
<snapshots>
<enabled>false</enabled>
</snapshots>
</repository>
另外Spring Boot 3.X 开始使用了Java 17将java版本调整到>17为了不必要的麻烦就选17
IDEA选择17并在pom.xml文件中指定版本
<java.version>17</java.version>
到这里我们的common 包是能正常编译了。
接下来是服务的配置
同样调整Spring Boot、Spring Cloud、Java的版本同common的配置。
碰到如下的几个问题
找不到hystrix的依赖问题
升级后找不到hystrix的版本官网也找不到这里我显式指定了版本
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
<version>2.2.9.RELEASE</version>
</dependency>
rabbitmq问题
相关的配置丢失比如如下图这边进行适当调整或者直接注释解决。
TypeVariableImpl丢失问题
原来服务中引入了sun.reflect.generics.reflectiveObjects.TypeVariableImpl
现在17中已经被隐藏无法直接使用这边为了能够先启动暂时注释后面再想办法。
Log 异常问题
由于之前我们项目中历史原因既有用log4j
也有用logback
升级后已经不行提示冲突报错如下
Exception in thread "main" java.lang.IllegalArgumentException: LoggerFactory is not a Logback LoggerContext but Logback is on the classpath. Either remove Logback or the competing implementation (class org.slf4j.helpers.NOPLoggerFactory loaded from file:/Users/chenjujun/.m2/repository/org/slf4j/slf4j-api/1.7.0/slf4j-api-1.7.0.jar). If you are using WebLogic you will need to add 'org.slf4j' to prefer-application-packages in WEB-INF/weblogic.xml: org.slf4j.helpers.NOPLoggerFactory
at org.springframework.util.Assert.instanceCheckFailed(Assert.java:713)
at org.springframework.util.Assert.isInstanceOf(Assert.java:632)
意思是要么移除Logback要么解决slf4j-api的冲突依赖这里两种方式都尝试了slf4j-api依赖的地方太多后面移除了Logback。
要排除依赖一个好办法使用Maven Helper
插件
logback依赖
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.8</version>
</dependency>
Apollo问题
使用Apollo会提示该错误需要在启动中加入--add-opens java.base/java.lang=ALL-UNNAMED
Caused by: com.ctrip.framework.apollo.exceptions.ApolloConfigException: Unable to load instance for com.ctrip.framework.apollo.spring.config.ConfigPropertySourceFactory!
at com.ctrip.framework.apollo.spring.util.SpringInjector.getInstance(SpringInjector.java:40)
at com.ctrip.framework.apollo.spring.boot.ApolloApplicationContextInitializer.<init>(ApolloApplicationContextInitializer.java:66)
... 16 more
Caused by: com.ctrip.framework.apollo.exceptions.ApolloConfigException: Unable to initialize Apollo Spring Injector!
at com.ctrip.framework.apollo.spring.util.SpringInjector.getInjector(SpringInjector.java:24)
at com.ctrip.framework.apollo.spring.util.SpringInjector.getInstance(SpringInjector.java:37)
... 17 more
Caused by: java.lang.reflect.InaccessibleObjectException: Unable to make protected final java.lang.Class java.lang.ClassLoader.defineClass(java.lang.String,byte[],int,int,java.security.ProtectionDomain) throws java.lang.ClassFormatError accessible: module java.base does not "opens java.lang" to unnamed module @16612a51
at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:354)
at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:297)
at java.base/java.lang.reflect.Method.checkCanSetAccessible(Method.java:199)
at java.base/java.lang.reflect.Method.setAccessible(Method.java:193)
at com.google.inject.internal.cglib.core.$ReflectUtils$1.run(ReflectUtils.java:52)
at java.base/java.security.AccessController.doPrivileged(AccessController.java:318)
at com.google.inject.internal.cglib.core.$ReflectUtils.<clinit>(ReflectUtils.java:42)
通过上述配置调整后能编译成功但是无法启动控制没有任何日志初步怀疑还是log依赖问题由于时间关系没有再继续问题留到以后再弄后面有新进展会持续更新该文。
javax 的依赖都变成jakarta
:
比如原来基于javax.validation包中的验证javax.validation.constraints.NotNull此类的都需要调整
Spring Boot 3.0后很多starter不能用
Spring Boot 3.0后以前的spring.factories
不能用了
只能使用META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
对于一些还没改造的starter都无法使用目前mybatisplus 已经有支持3.0 的 SNAPSHOT版本其他的druid、nacos 等还适配3.0要等等了。但我怎么会坐以待毙我尝试自己改造中间件的starter可还是报错
Failed to instantiate [org.springframework.boot.env.EnvironmentPostProcessor]: Specified class is an interface
作者其他文章
Grafana 系列文章版本OOS v9.3.1更新中
Spring Boot Admin 2 系列文章