【SpringBoot】自定义spring-boot-starter

news2024/9/25 21:12:13

目录

定义和目的#

命名规范#

准备阶段#

开发步骤#

一、创建 Starter 项目#

二、导入必要的依赖#

三、编写属性类#

四、自定义业务类#

五、编写自动配置类#

六、编写 spring.factories#

​编辑

七、编写配置提示文件#

八、测试 starter#

测试 starter#

一、导入自定义起步依赖

参考资料


定义和目的#

定义:Spring Boot 中的 Starter 是 Spring Boot 相对于传统的 Spring 的优势原因之一。Starter 相当于模块,它能将模块所需要的依赖进行整合并对模块内部的 Bean 根据环境进行自动配置。

使用者在使用 Spring Boot 中的 Starter 的时候,无需进行过多的配置和依赖,Spring Boot 能进行自动扫描并且为对应的模块设置默认值,做到真正的开箱即用。 针对于一些没有封装成 Starter 的依赖,往往经常出现的情况是需要使用者自行进行必要的一些配置。而对于 Starter 来说,会在开发者没有进行配置的情况下为模块中的依赖配置默认值;如果开发者想要自行配置,大多数只需要在 yml 配置文件中配置对应的键值对即可。

目的:封装 Starter 的目的主要是为了将独立于业务之外的配置模块进行集成,方便其他工程在需要使用的时候直接在 pom 中导入依赖,避免需要直接进行代码的硬拷贝而重新集成,也减少了硬拷贝可能带来的依赖版本冲突问题,让 Spring Boot 做到真正的开箱即用

命名规范#

  • Spring Boot 官方开发的 Starter 的命名规则为 spring-boot-starter-{name},例如:spring-boot-starter-web
  • 第三方的 Starter 官方推荐的命名规则为 {name}-spring-boot-starter,例如:mybatis-spring-boot-starter

准备阶段#

在这个阶段我们需要知道一些 Starter 开发中常用的注解,减少使用 xml 配置文件。Spring Boot 在自动装配的过程中是通过扫描 spring.factories 文件加载自动配置类,自动配置类中定义了各种运行时判断条件,这些判断条件的存在减少了依赖冲突的产生,也丰富了 Starter 的扩展功能。

  • 属性映射注解
    • @ConfigurationProperties:配置文件属性值和实体类的映射
    • @EnableConfigurationProperties:和 @ConfigurationProperties 配合使用,把 @ConfigurationProperties 修饰的类加入 IoC 容器。
  • 配置bean注解
    • @Configuration:标识该类为配置类,并把该类注入 ioc 容器
    • @Bean:一般在方法上使用,声明一个 Bean,bean 名称默认是方法名称,类型为返回值。
  • 条件注解
    • @Conditional:是根据条件类创建特定的 Bean ,条件类需要实现 Condition 接口,并重写 matches 接口来构造判断条件。该注解是 Spring 4 新提供的注解,按照一定的条件进行判断,满足条件给容器注册 Bean。
    • @ConditionalOnBean:容器中存在指定bean,才会实例化一个Bean
    • @ConditionalOnMissingBean:容器中不存在指定bean,才会实例化一个Bean
    • @ConditionalOnClass:系统中有指定类,才会实例化一个Bean
    • @ConditionalOnMissingClass:系统中没有指定类的 Bean 信息,才会实例化一个Bean
    • @ConditionalOnExpression:当SpEl表达式为true的时候,才会实例化一个Bean
    • @AutoConfigureAfter:在某个bean完成自动配置后实例化这个bean
    • @AutoConfigureBefore:在某个bean完成自动配置前实例化这个bean
    • @ConditionalOnJava:系统中版本是否符合要求
    • @ConditionalOnSingleCandidate:当指定的Bean在容器中只有一个,或者有多个但是指定了首选的Bean时触发实例化
    • @ConditionalOnResource:类路径下是否存在指定资源文件
    • @ConditionalOnWebApplication:是 web 应用
    • @ConditionalOnNotWebApplication:不是 web 应用
    • @ConditionalOnJndi:JNDI 指定存在项
    • @ConditionalOnProperty:配置 Configuration 的加载规则
      • prefix:配置属性名称的前缀。
      • value:数组,获取对应property名称的值,与name不可同时使用。
      • name:数组,可与prefix组合使用,组成完整的配置属性名称,与value不可同时使用。
      • havingValue:比较获取到的属性值与havingValue给定的值是否相同,相同才加载配置。
      • matchIfMissing:缺少该配置属性时是否可以加载。如果为true,没有该配置属性时也会正常加载;反之则不会生效。

开发步骤#

一、创建 Starter 项目#

注意:在创建 Initializr 项目之后,要删除 main 启动类和 test 文件夹。

在选择起步的时候的依赖时,不需要勾选任何依赖。

https://start.spring.io/

二、导入必要的依赖#

注意:在第一步删除了启动类之后,需要去除 pom 文件中 maven 打包插件 spring-boot-maven-plugin。

这一部分中,为了适配大多数的项目,建议将 JDK 版本设置为 1.8。

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.3.3</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.marion.demo</groupId>
    <artifactId>demo-spring-boot-starter</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>demo-spring-boot-starter</name>
    <description>自定义spring-boot-start封装</description>
    <url/>
    <licenses>
        <license/>
    </licenses>
    <developers>
        <developer/>
    </developers>
    <scm>
        <connection/>
        <developerConnection/>
        <tag/>
        <url/>
    </scm>
    <properties>
        <java.version>8</java.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>

        <!-- Spring Boot 的自动装配所需要的依赖 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-autoconfigure</artifactId>
        </dependency>

        <!-- 配置文件点击可以跳转实体,主要是为了适配 IDEA -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-configuration-processor</artifactId>
            <optional>true</optional>
        </dependency>
    </dependencies>
</project>

三、编写属性类#

我们需要对 Starter 进行配置信息类进行定义,为了和配置文件进行映射,能够读取 yml 或者 properties 文件中的配置属性。

主要用到的注解是 @ConfigurationProperties ,该注解能够帮我们完成映射工作。

package com.marion.demo.springbootstarter.config;

import org.springframework.boot.context.properties.ConfigurationProperties;

@ConfigurationProperties(prefix = "demo.config")
public class DemoProperties {

    private String name = "Hello Starter!";

    private int age = 8;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
}

四、自定义业务类#

在这一部分可以自定义一些用于获取配置文件信息进行业务操作的业务类。

package com.marion.demo.springbootstarter.config;

import org.springframework.boot.context.properties.ConfigurationProperties;

@ConfigurationProperties(prefix = "demo.config")
public class DemoProperties {

    private String name = "Hello Starter!";

    private int age = 8;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
}

五、编写自动配置类#

注意:这里配置一个 web 应用才能注入,并且 demo.config.flag 的值是否为 true 或者不配置该 key 才能注入 DemoService 服务。自动配置类遵循的命名规范是 XxxAutoConfiguration。

package com.marion.demo.springbootstarter;

import com.marion.demo.springbootstarter.config.DemoProperties;
import com.marion.demo.springbootstarter.service.DemoService;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration(proxyBeanMethods = false)
// 当存在某个类时,此自动配置类才会生效
@ConditionalOnClass(value = {DemoService.class})
// 导入我们自定义的配置类,供当前类使用
@EnableConfigurationProperties(value = DemoProperties.class)
// 只有非web应用程序时此自动配置类才会生效
@ConditionalOnWebApplication
// 判断demo.config.flag的值是否为“true”, matchIfMissing = true:没有该配置属性时也会正常加载
@ConditionalOnProperty(prefix = "demo.config", name = "flag", havingValue = "true", matchIfMissing = true)
public class DemoAutoConfiguration {
    /**
     * @param demoProperties 直接方法签名入参注入DemoProperties,也可以使用属性注入
     * @return DemoService 类
     */
    @Bean
    @ConditionalOnMissingBean(DemoService.class)
    //@ConditionalOnProperty(prefix = "demo.config", name = "flag", havingValue = "true", matchIfMissing = true)
    public DemoService demoService(DemoProperties demoProperties) {
        DemoService demoService = new DemoService();
        //把获取的信息注入
        demoService.setName(demoProperties.getName());
        demoService.setAge(demoProperties.getAge());
        return demoService;
    }
}

六、编写 spring.factories#

在 resource/META-INF/ 下面创建 spring.factories 文件,把自动配置类 DemoAutoConfiguration 配置到 org.springframework.boot.autoconfigure.EnableAutoConfiguration 的 key 下,Spring Boot 启动时会自动加载该文件并根据条件装配。

org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ com.marion.demo.springbootstarter.DemoAutoConfiguration

如果使用springboot2.7以上

创建META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports

com.marion.demo.springbootstarter.DemoAutoConfiguration

七、编写配置提示文件#

additional-spring-configuration-metadata.json

配置 additional-spring-configuration-metadata.json 文件后,在开发人员的 IDE 工具使用个人编写的配置读取很有效的在application.propertiesapplication.yml文件下完成提示。

配置详细格式参数可查看文档

{
  "properties": [
    {
      "name": "demo.config.name",
      "type": "java.lang.String",
      "defaultValue": "hello 默认值!这里配置的是提示,真正默认值在Properties里面",
      "description": "这是字符串名称啊."
    },
    {
      "name": "demo.config.age",
      "defaultValue": 18,
      "description": "这是int类型的年龄啊.",
      "deprecation": {
        "reason": "过时原因.",
        "replacement": "替代key是:demo.config.age22",
        "level": "warning"
      }
    }
  ]
}

spring-configuration-metadata.json

spring-configuration-metadata.json 代码量挺大的,为了方便我们可以通过IDE来生成,这里使用的是idea。

在 IDEA 设置中搜索 Annotation Processors,接下来勾住 Enable annonation processing 就完成了。 在编译打包后的文件中看到自动生成的 **spring-configuration-metadata.json** 。这个文件不用我们编写。

八、测试 starter#

编写完毕之后,我们在 maven 控制台执行 clean、compiler、package、install 的操作。

在这一步发现一些问题,在进行打包的时候,发现 test 文件夹下的类提示没有依赖。直接将 test 文件夹删除即可。

新建项目:demo-test-spring-boot-starter 进行测试。

测试 starter#

编写完毕之后,我们在 maven 控制台执行 clean、compiler、package、install 的操作。

在这一步发现一些问题,在进行打包的时候,发现 test 文件夹下的类提示没有依赖。直接将 test 文件夹删除即可。

新建项目:demo-test-spring-boot-starter 进行测试。

一、导入自定义起步依赖

直接运行测试项目的启动类,提示错误:没有定义好 DemoService 的类,推荐定义一个同名的 Bean。

参考资料

【Spring】-springboot 自定义starter封装

spring-boot-starter ~ 封装 简要版_springboot 封装starter-CSDN博客

Spring Boot 3.x 自动配置详解-腾讯云开发者社区-腾讯云

在SpringBoot3中spring.factories配置不起作用的原因和解决方法_springboot3 spring.factories-CSDN博客

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2073611.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

如何玩转CentOS Linux内核升级?手把手教你内核编译升级至最新版本

文章目录 如何玩转CentOS Linux内核升级&#xff1f;手把手教你内核编译升级至最新版本1 升级环境2 升级需求2.1 升级前的内核版本2.2 升级后的内核版本 3 升级步骤3.1 安装编译环境3.2 更新GCC版本3.2.1 多GCC版本共存3.2.2 永久替换旧的GCC 3.3 下载内核源代码并解压3.4 配置…

《数据结构》(408代码题及应用题)(王道收编真题)

一、线性表 1、线性表的线性表示 分析&#xff1a; “循环”左移&#xff0c;那这个循环就应该是我们需要重点思考的点。先考虑最简单的我们可以设置两个数组&#xff0c;其中一个数组保存的是原数据&#xff0c;另一个初始为空。接着想要实现循环左移就只需要找出相对应的位…

2002-2023年中债国债3年期到期收益率

国债是一种政府发行的债券&#xff0c;它为投资者提供了一种相对安全的投资渠道&#xff0c;因为背后有国家信用的支撑。国债的发行可以帮助政府筹集资金&#xff0c;用于公共支出、基础设施建设、社会福利等项目。国债通常分为两种形式&#xff1a;固定利率国债和浮动利率国债…

PHP 7.4.21 development server 源码泄露漏洞复现

原漏洞地址&#xff1a;https://blog.projectdiscovery.io/php-http-server-source-disclosure/ 版本&#xff1a;PHP<7.4.21 漏洞成因&#xff1a; 通过&#xff1a;PHP -s 开启的内置web服务器存在源码泄露漏洞&#xff0c;可以将PHP文件作为静态代码直接输出源码 POC&…

【区间dp】 P1775 石子合并(弱化版) 题解

题目描述 设有 N ( N ≤ 300 ) N(N \le 300) N(N≤300) 堆石子排成一排&#xff0c;其编号为 1 , 2 , 3 , ⋯ , N 1,2,3,\cdots,N 1,2,3,⋯,N。每堆石子有一定的质量 m i ( m i ≤ 1000 ) m_i\ (m_i \le 1000) mi​ (mi​≤1000)。现在要将这 N N N 堆石子合并成为一堆。每…

20240825 每日AI必读资讯

超6亿&#xff01;文心大模型日调用量半年增长超10倍&#xff0c;AI成百度最强加速引擎 - 文心大模型日调用量超过6亿次&#xff0c;日均处理Tokens文本超1万亿。与23年Q4公布的5000万次日均调用量相比&#xff0c;半年增长超10倍。 - 第二季度&#xff0c;百度云业务营收51亿…

【计算机网络】socket网络编程 --- 实现简易UDP网络程序之字符串回响

&#x1f466;个人主页&#xff1a;Weraphael ✍&#x1f3fb;作者简介&#xff1a;目前正在学习c和算法 ✈️专栏&#xff1a;Linux &#x1f40b; 希望大家多多支持&#xff0c;咱一起进步&#xff01;&#x1f601; 如果文章有啥瑕疵&#xff0c;希望大佬指点一二 如果文章对…

【北京仁爱堂】脖子歪斜,拉扯疼痛怎么办?规律的生活让痉挛性斜颈的恢复事半功倍!

痉挛性斜颈是一种肌张力障碍性疾病&#xff0c;也是一种让人非常痛苦不堪的疾病&#xff0c;他不仅影响患者的外貌&#xff0c;也会对患者的身体和心理造成双重的打击&#xff0c;严重影响正常的生活&#xff0c;社交和工作。 痉挛性斜颈的病因尚不明确&#xff0c;因为做任何仪…

Java Web —— 第八天(登录功能)

基础登录功能 LoginController 类 RestController //用于处理 HTTP 请求 Slf4j //记录日志 RequestMapping("/login") public class LoginController {Autowiredprivate EmpService empService;PostMappingpublic Result login(RequestBody Emp emp){log.info(&quo…

FFmpeg的入门实践系列六(编程入门之常见处理流程)

欢迎诸位来阅读在下的博文~ 在这里&#xff0c;在下会不定期发表一些浅薄的知识和经验&#xff0c;望诸位能与在下多多交流&#xff0c;共同努力 文章目录 前期博客参考书籍一、FFmpeg常见的处理流程复制编解码器的参数完整代码 二、创建并写入音视频文件三、总结附页 前期博客…

《黑神话:悟空》中的实景三维建模

这几天&#xff0c;国产游戏《黑神话:悟空》终于面世&#xff0c;迅速引爆了全球游戏市场。作为一款以《西游记》为背景的3A级动作角色扮演游戏&#xff0c;《黑神话:悟空》不仅在文化表达上极具吸引力&#xff0c;其背后的技术实力更是令人瞩目。本文将深入探讨&#xff0c;3A…

新“冰桶挑战”风靡奥运年,荣耀让科技有温度

巴黎奥运会落幕之后&#xff0c;残奥会即将在8月28日正式开赛&#xff0c;“超越自我&#xff0c;挑战极限”的拼搏精神仍在延续。 而挑战精神&#xff0c;不分场上或台下&#xff0c;存在于生活中的每个角落。 2024年不仅是奥运年&#xff0c;也是“冰桶挑战”的十周年&…

DMP调研(Data Management Platform-数据管理平台)

基础概念 数据资产 CRM、DMP、CDP 定义 Customer Data Platform&#xff08;CDP,客户数据平台&#xff09;&#xff1a;对于企业来说&#xff0c;CDP是作为全链路运营的核心数据系统。是汇集所有客户数据并将数据存储在统一的、可多部门访问的数据平台中&#xff0c;让企业各…

【Remi Pi使用HDMI屏幕显示QT界面】将QT工程在Ubuntu虚拟机交叉编译好拷贝到开发板并运行

开发板和Ubuntu虚拟机ssh连接 可以成功点亮hdmi屏幕&#xff08;默认是运行的mxapp2程序显示如下&#xff09; 可以在开发板上运行自己的qt程序界面 手动配置开发板以太网ip ip addr add 192.168.43.101/24 brd dev eth0 ip link set eth0 &#xff08;2&#xff09;虚拟机…

Vue3.0项目实战(一)——Vue3 大事件管理系统项目搭建

目录 1. 大事件项目介绍和创建 1.1 Vue3 大事件管理系统 1.2 pnpm 包管理器 - 创建项目 1.3 创建项目 2. Eslint 配置代码风格 2.1 环境同步 2.2 Eslint 配置代码风格 3. 基于 husky 的代码检查工作流 3.1 提交前做代码检查 3.2 暂存区 eslint 校验 3.3 总结 4. 目…

i.MX6裸机开发(9):CCM时钟控制模块

本章参考资料&#xff1a;《IMX6ULRM》&#xff08;参考手册&#xff09;。 学习本章时&#xff0c;配合《IMX6ULRM》第18章Clock Controller Module (CCM)&#xff0c;效果会更佳&#xff0c;特别是涉及到寄存器说明的部分。 本章我们主要讲解时钟部分&#xff0c;芯片内部的…

TensorFlow实现Softmax回归

原理 模型 相比线性回归&#xff0c;Softmax只多一个分类的操作&#xff0c;即预测结果由连续值变为离散值&#xff0c;为了实现这样的结果&#xff0c;我们可以使最后一层具有多个神经元&#xff0c;而输入不变&#xff0c;其结构如图所示&#xff1a; 为了实现分类&#xf…

AI编程简介

文章目录 AI 编程的特点常见编程工具copilot的工作原理AI编程常用技巧 AI 编程的特点 AI 编程是指利用人工智能技术来辅助开发过程的一种编程方式。包括但不限于&#xff1a;代码生成、优化、调试、审查&#xff0c;文档生成、测试自动化。 编程能力是大模型各项能力的天花板&…

可用于便携音箱的18V同步升压变换器TPS61288

在音频市场中,便携式音箱因其自带电源、方便携带深受消费者喜爱。便携式音箱通常配备2节可充电锂离子电池,当输出功率要求高于10W时,电池电压不足以为音频功放提供足够的功率,一般需要升压电路将电池电压升压至12V~18V以满足功率要求。 TPS61288是德州仪器公司推出的一款最…

力扣2025.分割数组的最多方案数

力扣2025.分割数组的最多方案数 哈希表 前缀和 用两个哈希表分别存元素(之后会遍历)左侧和右侧的前缀和 typedef long long LL;class Solution {public:int waysToPartition(vector<int>& nums, int k) {int n nums.size(),ans 0;vector<LL> sum(n);unor…