SpringBoot2.7升级到3.0的实践分享

springboot2,升级,实践,分享 · 浏览次数 : 44

小编点评

**1.jdk升级** * Spring Boot 3.0.x 需要jdk17以上版本才能启动。 **2.构建工具Maven升级** * Spring Boot 项目需要升级构建工具 Maven 到 3.5.x 以上版本。 **3.SpringCloud升级** * Spring Cloud 2021.0.3 升级到 2022.0.4 版本。 * 在升级过程中,需要手动设置 FeignClientFactory。 **4.Mybatis Plus升级** * Mybatis Plus 3.5.13 和 3.5.3.2 版本升级后,需要进行以下配置修改: * `id-type`从 `UUID` 变为 `ASSIGN_UUID4`。 * 拦截器路径和构造方式需要根据实际情况进行调整。 **5.redis配置升级** * `spring.redis.xxx` 更改为 `spring.data.redis.xxx`。 **6.mybatis Plus升级** * Mybatis Plus 3.5.3.2 版本升级后,需要进行以下配置修改: * `id-type`从 `UUID` 变为 `ASSIGN_UUID4`。 * 拦截器路径和构造方式需要根据实际情况进行调整。 **7.其他配置修改** * 由于版本升级带来一些配置和代码的变更,需要进行相应的配置调整。 * 请参考相关文档和日志信息,以确保升级过程顺利完成。

正文

背景

最近把项目中的技术框架做一次升级,最重要的就是SpringBoot从2.7.x升级到3.0.x,当然还会有一些周边的框架也会连带着升级,比如Mybatis Plus,SpringCloud等,话不多说直接看看有哪些事情要做。

具体事项

主要分两类,第一类是单纯的提升版本,主要如下:

1.jdk升级

SpringBoot3需要jdk17以上,看下官网的介绍。

 

2.构建工具Maven需要升级,3.5+以上。

3.SpringCloud需要升级,原来是2021.0.3,现在决定升级到2022.0.4,中途也尝试过SpringCloud暂时不升级,但是启动失败了,果断决定升级,二者的对照关系请参考https://start.spring.io/actuator/info。

4.Mybatis,Mybatis-plus需要升级,分别升级到3.5.13,3.5.3.2。

第二类是由于版本升级带来的一些配置和代码的变更,主要如下:

1. javax.需要批量替换

import javax.annotation. 替换为import jakarta.annotation.

import javax.servlet.替换为import jakarta.servlet.

这个我也是有点不解,为什么连路径都要做迁移,这个会有一些连带的改变,比如使用的一些第三方jar使用的是javax.servlet/annotation,那我们就需要找到其高版本看是否切换到了jakarta.servlet/annotation,如果不支持那我们的整体升级可能都要叫停,刚开始也想过找到一些老的jar保证编译不报错,但是运行的时候发现根本不行,因为SpringBoot,Spring等在底层使用的时候都切到了jakarta,为了适应新版本框架必须要改,庆幸的是用的第三方jar都有相应的高版本支持。

2.Spring Cloud OpenFeign升级以后,FeignContext不存在

之前有框架代码中获取FeignBean的需求,代码如下:

public static <T> T getFeignBean(String beanName, Class<T> tClass) {
      FeignContext feignContext = (FeignContext)getBean("feignContext");
      return feignContext.getInstance(beanName, tClass);
  }

需要调整为FeignClientFactory:

public static <T> T getFeignBean(String beanName, Class<T> tClass) {
    FeignClientFactory feignContext = (FeignClientFactory)getBean("feignContext");
    return feignContext.getInstance(beanName, tClass);
}

3.redis配置修改

之前是spring.redis.xxx,现在需要修改为spring.data.redis.xxx。

4.mybatis plus由3.2.0升级到3.5.3.2以后带来的几个调整

4.1 id-type: UUID调整为id-type: ASSIGN_UUID

4.2 拦截器路径以及构造方式的变化

之前如下:

@Configuration
public class MybatisPlusConfig {
  /**
   * 分页插件 
   */
  @Bean
  public PaginationInterceptor paginationInterceptor() {
    return new PaginationInterceptor();
  }

现在如下:

@Configuration
public class MybatisPlusConfig {
  /**
   * 分页插件
   */
  @Bean
  public MybatisPlusInterceptor mybatisPlusInterceptor() {
    MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
    interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL));
    return interceptor;
  }

4.3 selectCount返回值由Integer变更为Long

这个好改,直接按照idea的提示改成Math.toIntExact(xxxMapper.selectCount)。

带来的好处

先说说我最直观的一个好处,jdk由11升级到17以后空指针的异常提示清晰多了,可以明确的知道是哪个对象空,分别以jdk11和jdk17为例测试一段链式调用的NPE异常,测试代码如下:

static class User{
        int age;
        public int getAge(){
            return age;
        }
}

@Test
public void testNPE(){
    List<User> list = new ArrayList();
    list.add(null);
    list.stream().filter(o -> o.getAge() >9).collect(Collectors.toList())
}

分别看下在jdk11和jdk17下的报错提示。

jdk11

java.lang.NullPointerException
  at NpeTest.lambda$testNPE$0(NpeTest.java:41)
  at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:176)
  at java.base/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1655)
  at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)
  at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)
  at java.base/java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:913)
  at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
  at java.base/java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:578)
  at NpeTest.testNPE(NpeTest.java:41)

jdk17

java.lang.NullPointerException: Cannot invoke "NpeTest$User.getAge()" because "o" is null
  at NpeTest.lambda$testNPE$0(NpeTest.java:41)
  at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:178)
  at java.base/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1625)
  at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:509)
  at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:499)
  at java.base/java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:921)
  at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
  at java.base/java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:682)

其次就是一次老生常谈的好处,比如性能提升,安全加固等,我了解的还很浅薄,待我慢慢发掘以后再跟大家分享。

推荐阅读

https://spring.io/blog/2022/05/24/preparing-for-spring-boot-3-0 

https://docs.spring.io/spring-boot/docs/3.0.10/reference/htmlsingle/#getting-help

https://github.com/spring-projects-experimental/spring-boot-migrator

https://blog.csdn.net/dreamcatcher1314/article/details/131137388

 

 

 

 

与SpringBoot2.7升级到3.0的实践分享相似的内容:

SpringBoot2.7升级到3.0的实践分享

背景 最近把项目中的技术框架做一次升级,最重要的就是SpringBoot从2.7.x升级到3.0.x,当然还会有一些周边的框架也会连带着升级,比如Mybatis Plus,SpringCloud等,话不多说直接看看有哪些事情要做。 具体事项 主要分两类,第一类是单纯的提升版本,主要如下: 1.jdk

[转帖]一次SpringBoot版本升级,引发的血案

https://z.itpub.net/article/detail/B6495288E725529E58105397659A08EB 前言 近项目组升级了SpringBoot版本,由之前的2.0.4升级到新版本2.7.5,却引出了一个大Bug。 到底是怎么回事呢? 1.案发现场 有一天,项目组的同

SpringBoot2.7集成Swagger3

1、引入pom坐标 io.springfox springfox-swagger2 3.0.0

解决SpringBoot3.X中starter配置自动注入失效问题

在自定义 starter 项目时,如果组件无法被 @ComponentScan 扫描并且想自动注册到 IOC 中,在springboot2.7之前 我们会采用 spring,factories 方式,但在3.0 之后已经被彻底移除 spring.factories介绍 spring.factorie

[转帖]springboot中使用skywalking实现日志追踪

文章目录 SkyWalking分布式追踪系统介绍主要架构 环境引入依赖配置Log4j2下载编译好的8.7.0版本包使用探针实现日志追踪启动脚本启动Java服务访问服务 使用UI切换存储方式 SkyWalking分布式追踪系统 介绍 Skywalking是一个国产的开源框架,2015年有吴晟个人开源,

EMQX配置ssl/tls双向认证+SpringBoot项目整合MQTT_真实业务实践

一.使用docker搭建Emqx 1.拉取emqx镜像 docker pull emqx/emqx:5.7 2.运行 docker run -d --name emqx emqx/emqx:5.7 3.拷贝 docker中 etc data log 到宿主机的 /opt/emqx 下 mkdir -

[转帖]Redis客户端Jedis、Lettuce、Redisson

https://www.jianshu.com/p/90a9e2eccd73 在SpringBoot2.x之后,原来使用的jedis被替换为了lettuce Jedis:采用的直连,BIO网络模型 Jedis有一个问题:多个线程使用一个连接的时候线程不安全。 解决思路是: 使用连接池,为每个请求创建

【冷启动#2】实用的springboot tutorial入门demo

跟着官方文档熟悉一遍创建spring工程的步骤 https://spring.io/guides/gs/spring-boot https://juejin.cn/post/7077958723829760008 demo简介 整个demo的预期目标是: 管理一堆玩家的数据,数据库使用的是现成的我们

Springboot整合Apollo

一、Apollo作用 随着程序功能的日益复杂,程序的配置日益增多:各种功能的开关、参数的配置、服务器的地址…… 对程序配置的期望值也越来越高:配置修改后实时生效,灰度发布,分环境、分集群管理配置,完善的权限、审核机制…… 在这样的大环境下,传统的通过配置文件、数据库等方式已经越来越无法满足开发人员对

SpringBoot+mail 轻松实现各类邮件自动推送

一、简介 在实际的项目开发过程中,经常需要用到邮件通知功能。例如,通过邮箱注册,邮箱找回密码,邮箱推送报表等等,实际的应用场景非常的多。 早期的时候,为了能实现邮件的自动发送功能,通常会使用 JavaMail 相关的 api 来完成。后来 Spring 推出的 JavaMailSender 工具,进