乐趣区

关于springboot:SpringBoot22升级到279遇到的问题及解决方案总结

开始

Spring Boot 最新版本曾经到了 3.1.x 版本,线上目前用的 2.1 版本官网曾经进行反对,目前打算先做肯定的技术预研,在不降级 JDK 的前提下,削减降级坡度,事后降级到 2.7.10 版本 GA 版本。

SpringBoot 官网版本反对阐明:(写这边文章时从 2.7.9 变成了 2.7.10)

官网文档:https://spring.io/projects/spring-boot#support

官网 Github Release: https://github.com/spring-projects/spring-boot/releases/tag/v2.7.10

spring cloud 版本

外面降级 jar 包,修复 logger 包的破绽,fastjson 破绽也会随着这次降级一道修复

废话不多说,间接开始:


依赖解决与性能降级

SpringBoot 主包降级

咱们将 springboot 主包从 2.1.9.RELEASE 批改为 2.7.10.

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.7.10</version>
        <relativePath/>
    </parent>

SpringCloud 组件降级

目前 Spring Cloud Alibaba 与 cloud 基于 spring boot 2.7.10 的兼容版本

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-dependencies</artifactId>
    <version>2021.0.5</version>
</dependency>

<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-alibaba-dependencies</artifactId>
    <version>2021.0.5.0</version>
</dependency>

这时候发现 SpringCloud 被逼在 2020 版本移除了对 Netflix OSS 大部分组件的反对

Spring Cloud 官网尤其着重指出 ribbon、hystrix 和 zuul 从 Spring Cloud 2020.0 正式版公布后将不再被 Spring Cloud 反对。在目前最新的 Spring Cloud 2020.0 中仅仅剩下了 Eureka。然而留给 Eureka 的工夫也不多了。

其中 ribbon 替换为 SpringCloud LoadBalance 组件,收录在 SpringCloud Commons 外面
文档如下:

参考博客:https://docs.spring.io/spring-cloud-commons/docs/current/refe…

应用上和 ribbon 没有什么不同,应用 @LoadBalanced 手动申明 RestTemplate Bean

    @ConditionalOnMissingBean(RestTemplate.class)
    @LoadBalanced
    @Bean
    public RestTemplate restTemplate(@Qualifier("myMappingJackson2HttpMessageConverter") MappingJackson2HttpMessageConverter mappingJackson2HttpMessageConverter) {RestTemplate restTemplate = new RestTemplate();
        restTemplate.getInterceptors().add(new CoreHttpRequestInterceptor());
        //RestTemplate 解决 Date 数据类型反序列化的问题,应用自定义的 MappingJackson2HttpMessageConverter 笼罩
        restTemplate.getMessageConverters().add(5, mappingJackson2HttpMessageConverter);
        return restTemplate;
    }

hystrix 能够思考应用 Spring Cloud Alibaba 的 Sentinel 做熔断和流控

上面开始做 hystirx 到 Sentinel 迁徙:
首先是 pom 替换

        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
        </dependency>
<!--        <dependency>-->
<!--            <groupId>org.springframework.cloud</groupId>-->
<!--            <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>-->
<!--        </dependency>-->
        <!--ribbon-->

我的项目外面持续应用 openfeign 做 rpc 调用,将 application.properties 外面 feign 的熔断实现配置批改为 sentinel 实现。

# 去掉
# feign.hystrix.enabled: true
# 改为如下即可
feign.sentinel.enabled: true

这里成心将 order 服务配置错,查看 rpc 调用信息,能够看到应用了 loadbalance 和 sentinel

FeignClient 基于 sentinel 对 fallbackFactory 对立降级的优化解决

因为熔断须要,业务降级时,须要手写 fallback 业务,然而并不是所有的 RPC 都须要写降级代码,所以才有了定义对立业务 Reuslt 返回 fallback 降级信息,代替框架的没有配置就 throw Exception 的逻辑。
之前 Netflix 时,是 feign 联合 hystrix 做,当初降级后,须要应用 sentinel 逻辑再改一遍。

参考博客:https://blog.csdn.net/qq_40592377/article/details/105142856

cloud 的 openfeign 和 alibaba 的 sentinel 包外面移除了如下包依赖,测底和 hystrix 辞别了

<dependency>
      <groupId>io.github.openfeign</groupId>
      <artifactId>feign-hystrix</artifactId>
      <version>10.4.0</version>
      <scope>compile</scope>
    </dependency>

这里是从新批改后的代码
批改处 1 应用反射结构 SentinelInvocationHandler 是因为他不提供 public 构造方法
批改处 2 应用了我本人定义的对立 Result 业务谬误 Result 的 FeignFallback。

Feign 对于上游参数的透传 TODO

之前是自定义 HystrixConcurrencyStrategy 实现,在微服务之间 RPC 调用时,实现申请的业务 header 值,跨线程池透递
目前改用 sentinel 之后,还没有钻研透彻,有待后续优化。

Bean 循环援用的问题

重启零碎,发现报错如下,因为 SpringBoot 2.6 开始默认禁止循环援用,这时候改业务就有麻烦,先批改为强制批准。

> 
Description:

  The dependencies of some of the beans in the application context form a cycle:
  略
  ↓
  sqlSessionFactory defined in class path resource [com/suike/config/database/MyBatisConfig.class]
  ┌─────┐
  | dataSource defined in class path resource [com/suike/config/database/MyBatisConfig.class]
  ↑ ↓
  | dataSourceDev defined in class path resource [com/suike/config/database/dataSource/DruidDBConfigDev.class]
  ↑ ↓
  | dataSourceInitializer
  └─────┘

在我的项目 Starter 文件中批改 setAllowCircularReferences(Boolean.TRUE);

    public static void main(String[] args) {log.info(">>>>>>>> steamcdk-activitys 启动开始 >>>>>>>>>");
        SpringApplication application = new SpringApplication(ActivityStarter.class);
        // 临时先容许循环援用,前面再清理业务。做标准
        application.setAllowCircularReferences(Boolean.TRUE);
        application.run(args);
        log.info(">>>>>>>> steamcdk-activitys 启动实现 >>>>>>>>>");
    }

参考:https://blog.csdn.net/Dug_Zhang/article/details/122225331

依赖组件 Nacos Server 版本升级

重启我的项目,再次报错:

ErrCode:-401, ErrMsg:Client not connected,current status:STARTING

询问度娘得悉,Alibaba2.2.7 中 nacos client 依赖的 server 必须也是 2.x 以上, 而我这边我的项目之前用的是 nacos-servcer-1.4.1
没辙,去 nacos 官网查 1.x 降级 2.x 降级文档:

nacos git 地址:https://github.com/alibaba/nacos/releases
nacos2.0 降级文档:https://nacos.io/zh-cn/docs/2.0.0-upgrading.html

覆盖文件,而后批改下配置就好了,双写先开着,老零碎还在用。

ErrCode:-400, ErrMsg:Could not initialize class com.alibaba.nacos.common.remote.client.grpc.GrpcSdkClient

nacos 升级成 2.2.0,以下是 alibaba 官网版本匹配

Springfox 降级为 Springdoc

重启一下,T T,持续!

网上说如果要持续用 Springfox,只须要加一段配置

spring.mvc.pathmatch.matching-strategy=ant_path_matcher

然而前面必定还会有兼容性问题,再次求助得悉:Spring 基于 Swagger3 本人做了一套基于 openapi3 标准的文档我的项目,叫 springDoc.

参考:https://zhuanlan.zhihu.com/p/439255980

忙活了半天,还是决定替换成 SpringDoc,首先是 springfox 曾经很久没有更新了
其实,改版后发现 Springdoc 的确做的比 springfox 更适宜 spring 体系。

文档地址:https://springdoc.org/#demos

替换注解,重写 OpenAPI 的配置文件,参考文档,胜利平滑替换

Redis 线程池改变

特地留神,spring date redis 依赖的 commons-pool2 2.9.0 会报错,须要另外申明为最新

<dependency>
    <groupId>org.apache.commons</groupId>
    <artifactId>commons-pool2</artifactId>
    <version>2.11.1</version>
</dependency>

在 Springboot 2x 当前,底层拜访 redis 曾经不再是 jedis 了,而是 lettuce

这边配置批改为应用 lettuce 链接池

MYSQL 连接器 版本升级

MySQL 的链接驱动,从 8.0.31 开始,从原来的 mysql:mysql-connector-java 改为 com.mysql:mysql-connector-j

网关中,对于 exclude Url 匹配规定降级

> org.springframework.web.util.pattern.PatternParseException: No more pattern data allowed after {*...} or ** pattern element

谬误直观展现是门路统配问题,可是之前没有问题啊,起初通过一通查找发现是 spring 降级到 5.3 之后门路统配产生了变动,官网给出的解释是“In Spring MVC, the path was previously analyzed by AntPathMatcher, but it was changed to use PathPatternParser introduced in WebFlux from Spring 5.3.0.”。

2、具体解决是把/**/*.html 改为 /*/*.html,我的项目中可能波及多个文件,都要改:

OK, 批改完重启。不出所料再次遇到问题

网关应用 Loadbalancer 代替 Ribbon 实现负载平衡

拜访服务网关进行路由时,找不到服务

gateway 配置一切正常,鉴权也没有问题,nacos 也失常注册,然而路由的时候就是找不到服务

解决办法:在 pom.xml 文件中增加如下依赖:


<!-- 客户端负载平衡 loadbalancer-->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>

起因:因为 springcloud2020 弃用了 Ribbon,因而 Alibaba 在 2021 版本 nacos 中删除了 Ribbon 的 jar 包,因而无奈通过 lb 路由到指定微服务,呈现了 503 状况。
所以只须要引入 springcloud loadbalancer 包即可

fastJson 重大破绽,降级为 1.2.83 版本

我的项目启动时,退出如下代码

    /*
 * Fastjson 存在近程代码执行破绽 降级到最新版本 1.2.83  关上 autotype 性能
 * @see https://github.com/alibaba/fastjson/wiki/enable_autotype
 */
ParserConfig.getGlobalInstance().addDeny("com.rush.gameup");

非必须降级

Mybatis-plus 从 3.2 降级到 3.5

mybatis-plus 能够说是用 lambda 预发写 sql,体感十分丝滑。
在 3.5 中,次要改变是代码生成器的 api 降级,变得更弱小了。

这里我通过 mybatis-generator 生成时指定我形象出的一套扩大父类,能够放慢不少开发速度
更进阶的话,手挫 100% 符合本人业务的 vm、ftl 模板, 设想空间很大。

也能够体验下 @EnumValue,@TableLogic 的“花活”。

文档地址 https://baomidou.com/pages/24112f/

Gateway 应用 knife4j 聚合 swagger 文档并优化 ui

降级后的 spring doc 的 UI 好看了一些

然而当初有一个国人开源的更弱小的 UI 插件:knife4j

界面成果如下图, 下拉框里会列出 nacos 外面注册的所有服务,knife4j 会主动拆卸进来,选中即可查看文档

<dependency>
    <groupId>com.github.xiaoymin</groupId>
    <artifactId>knife4j-gateway-spring-boot-starter</artifactId>
    <version>4.1.0</version>
</dependency>

最新 4.1 版本 Gateway 只须要如下的简略配置,就能够主动注册和聚合所有微服务的 swagger 文档,比我之前手动写个聚合页应用体验要强上许多。

knife4j:
  gateway:
    # 指定服务发现的模式聚合微服务文档,并且是默认 `default` 分组
    strategy: discover
    discover:
      # 指定版本号(Swagger2|OpenAPI3)
      version: openapi3
      enabled: true
    enabled: true

参考文档:https://doc.xiaominfo.com/docs/changelog/x/4.1

退出移动版