自定义springboot start,springboot自定义starter原理

写的比较早,我们每次构建Spring应用,都不想从零开始实现带有“横切关注点”的内容;相反,我们希望一次性实现这些功能,并根据需要将它们包含在我们想要构建的任何应用程序中。 横切

写的比较早,我们每次构建Spring应用,都不想从零开始实现带有“横切关注点”的内容;相反,我们希望一次性实现这些功能,并根据需要将它们包含在我们想要构建的任何应用程序中。

横切关注点

横切关注点:指一些跨越多个模块的行为(从维基百科引入),即可以被多个项目或模块使用的内容,比如一个SDK。

在Spring Boot,用来表示提供这种横切关注点的模块的术语是starter。依靠starter,您可以轻松地使用它的一些功能特性。无论你是否会在工作中打造自己的首发,你都要有打造“首发”的想法。本文将结合Spring Boot官方标准构建一个简单的启动器。

定制启动器在我们进一步了解如何定制启动器之前,为了更好地理解我们在每一步都在做什么以及启动器是如何工作的,我们先从宏观的角度来看一下启动器的结构。

通常一个完整的起动机需要包括以下两个部件:

自动配置模块Starter模块如果你看下面两个组件的解释,有点抽象,你就可以了解了。看完这篇文章,回头看这里,你会豁然开朗。

自动配置模块

自动配置模块是包含自动配置类的MavenGradle模块。通过这种方式,我们可以构建能够自动贡献给应用程序上下文的模块,并添加一个特性或提供对外部库的访问。

起动机模块

Spring Boot启动器是一个Maven或Gradle模块,其唯一目的是提供& # 34;开始& # 34;功能所需的所有依赖关系。您可以包括一个或多个自动配置模块依赖项,以及您可能需要的任何其他依赖项。这样,在Spring startup应用程序中,我们只需要添加这个starter依赖项就可以使用它的特性。

Spring官方参考手册建议将自动配置分开,将每个自动配置启动到一个独立的Maven或Gradle模块中,从而将自动配置与依赖管理分开。如果您没有为成千上万的用户构建一个开源库,您也可以将它们合并到一个模块中,如果您不需要分离两个关注点,您可以将自动配置代码和依赖性管理合并到一个模块中。

名字

来自Spring官方的启动器都是用spring-boot-starter启动的,比如:

spring-boot-starter-webspring-boot-starter-AOP如果我们将starter函数的名称定义为acme,那么我们的名称如下:

acme-spring-Boot-starter acme-Spring-Boot-Auto Configure如果在Starter中使用了配置键,还应该注意不要使用Spring Boot使用的命名空 room,比如(server,management,Spring)。

父模块创建

让我们来看看项目的整体结构:一级目录结构:

。├──POM . XML├───ryb-spring-boot-auto configure├───ryb-spring-boot-sample└───ryb-spring-boot-starter二级目录结构:

。├──pom.xml├──rgy b-spring-boot-auto configure│├──pom.xml│└──src├──rgy b-spring-boot-sample│├──POM . XML│└──src└──rgy b-spring-boot-starter├──p om . XML└──src创建一个Maven模块,也就是空之父,主要提供依赖管理,这样子模块就不需要单独维护依赖版本号,从而可以查看POM . XML内容:

& lt依赖关系管理&gt。& lt依赖关系& gt& lt依赖性& gt& ltgroupId & gtorg . spring framework . boot & lt;/groupId & gt;& ltartifactId & gtspring-boot-dependencies/artifact id & gt;& lt版本& gt$ { spring-boot . version } & lt;/version & gt;& lttype & gtpom & lt/type & gt;& lt范围& gt导入& lt/scope & gt;& lt/dependency & gt;& lt/dependencies & gt;& lt!-在此添加其他全局依赖关系管理。默认情况下,子模块不会引入这些依赖关系,所以需要显式指定-& gt;& lt/dependency management & gt;自动配置模块结构

创建一个新类GreetingAutoConfiguration

@ configuration public class greeting auto configuration { @ Bean public greeting service greeting service(greeting properties greeting properties){ return new greeting service(greeting properties . get members());}}我们使用@Configuration注释标签类GreetingAutoConfiguration作为启动器的入口点。这个配置包含了我们提供starter特性所需的所有@Bean定义。在本例中,为了简单起见,我们只将GreetingService Bean添加到应用程序上下文中。

欢迎服务的内容如下:

@ AllArgsConstructorpublic class greeting service { private List & lt;字符串& gtmembers = new ArrayList & lt& gt();public void say hello(){ members . foreach(s-& gt;system . out . println(& # 34;你好& # 34;+s));}}在resources目录下新建一个文件META-INF/spring.factors(如果META-INF目录不存在,需要手动创建),写入文件:

org . spring framework . boot . auto configure . enable auto configuration = \ Top。达亚奇。自动配置。greeting auto configuration Spring将启动其类路径中的所有spring.factoreis文件,并在其中加载声明的配置。当问候自动配置类准备就绪时,我们的Spring Boot启动器将有一个自动激活的入口点。

这里这个& # 34;不完整的启动器& # 34;已经可以用了。但是因为是自动激活的,为了让它灵活,我们需要根据自己的意愿来激活,所以需要条件注释来帮助。

条件配置

向类中添加两个条件注释:

@ Configuration @ conditional property(value = & # 34;rgyb . greeting . enable & # 34;,具有值= & # 34;真& # 34;)@ conditional class(dummy mail . class)public class问候语自动配置{…}通过使用annotation @ conditional属性,我们告诉Spring,只有当属性rgyb.greeting.enable的值设置为true时,GreetingAutoConfiguration(及其声明的所有bean)才会包含在应用程序上下文中。通过使用@ConditionalOnClass注释,我们告诉Spring,只有当类DummyEmail.class存在于类路径中时,才会将GreetingAutoConfiguration(及其声明的所有bean)包含在应用程序上下文中。多个条件为and/ AND,只有满足所有条件时才会加载GreetingAutoConfiguration。

如果不清楚条件注释的用法,可以查看我之前的文章:@条件注释,Spring Boot的灵活配置。

配置属性管理

上面使用了@ConditionalOnProperty注释,实际的starter中可能有很多属性,所以我们需要集中管理这些属性:

@Data@ConfigurationProperties(前缀= & # 34;rgyb.greeting & # 34)public class问候语属性{/* * *问候语属性开关*/boolean enable = false;/* * *需要打招呼的成员列表*/list

& lt依赖性& gt& ltgroupId & gtorg . spring framework . boot & lt;/groupId & gt;& ltartifactId & gt弹簧引导配置处理器& lt/artifact id & gt;& lt可选& gttrue & lt/可选& gt& lt/dependency & gt;这样我们mvn编译的时候就会生成一个名为Spring-Configuration-Metadata的文件。JSON,如下所示:

自定义springboot start,springboot自定义starter原理

生成的内容用在下面的内容里,看看。

提升开始时间

对于类路径上的每个自动配置类,Spring Boot必须计算@Conditional… condition值,该值用于决定是否加载自动配置及其需要的所有类。根据Spring启动应用程序中启动器的大小和数量,这可能是一个非常昂贵的操作,并且会影响启动时间。为了缩短启动时间,我们需要在pom.xml中添加另一个依赖项:

& lt依赖性& gt& ltgroupId & gtorg . spring framework . boot & lt;/groupId & gt;& ltartifactId & gtspring-boot-自动配置-处理器& lt/artifact id & gt;& lt可选& gttrue & lt/可选& gt& lt/dependency & gt;这个注释将生成一个名为Spring-Autoconfigure-metadata的属性文件。属性,其内容如下:

自定义springboot start,springboot自定义starter原理

这样,Spring Boot可以在启动时读取这些元数据,并且可以在不实际检查这些类的情况下过滤掉不符合条件的配置,从而提高启动速度。

至此,自动配置模块已经构建完毕,我们需要继续构建启动模块。

起动机模块结构

启动模块的结构非常简单。你可以把它想象成一个空模块。除了依赖自动配置模块之外,它唯一的功能是提供使用starter特性所需的所有依赖关系,因此我们将以下内容添加到Starter模块的pom.xml文件中:

& lt依赖关系& gt& lt依赖性& gt& ltgroupId & gttop . day arch . learning & lt。/groupId & gt;& ltartifactId & gtrgy b-spring-boot-auto configure & lt;/artifact id & gt;& lt版本& gt1.0.0 .发布& lt/version & gt;& lt/dependency & gt;& lt!-在此添加其他必要的依赖项,以确保启动程序可用-& gt;& lt/dependencies & gt;同样,在resources目录下创建一个新文件META-INF/spring.providers,内容如下:

providers:rgy b-spring-boot-auto configure这个文件的主要作用是解释starter模块的依赖信息。用逗号分隔多个依赖关系即可。该文件不会影响starter的使用,并且是可选的。

启动模块就这么简单。将这两个模块安装到本地Maven存储库中,然后我们将创建一个示例模块来介绍这个starter依赖项,它将从本地Maven存储库中提取。

创建示例模块我们可以通过Spring Initializr正常初始化一个Spring Boot项目(RYB-Spring-Boot-Sample),引入我们刚刚创建的starter依赖项,在sample pom.xml中添加依赖项:

& lt依赖性& gt& ltgroupId & gttop . day arch . learning & lt。/groupId & gt;& ltartifactId & gtrgy b-spring-boot-starter & lt;/artifact id & gt;& lt版本& gt1.0.0 .发布& lt/version & gt;& lt/dependency & gt;接下来,配置application.yml属性。

RYB:问候:启用:真实成员:-李磊-韩梅梅当我们配置YAML时,会出现如下提示,会更友好。当然,为了规范起见,属性描述最好用英文描述,这里用中文描述来说明问题:

自定义springboot start,springboot自定义starter原理

编写测试类

我们编写测试用例:

@ Autowired(required = false)private greeting service greeting service;@ test public void test greeting(){ greeting service . say hello();测试结果如下:

你好李磊你好韩梅梅总结,完整的首发开发到此结束。希望大家能了解它的构建流程,目录结构,命名标准,以便大家在有相应的业务需求时,开发自己的启动器,供他人应用。

启动器开发完成后,其他人可以手动添加依赖项来引入启动器的相关功能。那么如何才能像Spring Initializer一样通过下拉菜单选择我们的starter,从而直接初始化整个项目呢?在下面的文章中,我们将模仿Spring初始化器来定制我们自己的初始化器。

知识点描述

依赖选项

为什么自动配置模块的依赖项都是可选的=真?这就涉及到Maven传递依赖的问题。详见Maven对及物性依赖的透彻理解。

春天.工厂

Spring Boot是如何加载这个文件并找到我们的配置类的?下图是Spring Boot应用程序启动的调用堆栈的一部分,我添加了断点:

自定义springboot start,springboot自定义starter原理

打开SpringFactoriesLoader类,这就是您看到的内容:

自定义springboot start,springboot自定义starter原理

这两张图应该足够说明问题了。它们是SPI的一种加载方法。更多详情请自行了解。

实际案例

建议查一下mybatis-spring-boot-starter的非官方案例,从中我们:

模仿它的目录结构、设计概念和编码规范。

自定义springboot start,springboot自定义starter原理

主题测试文章,只做测试使用。发布者:rekoe,转转请注明出处:https://www.mulub.com/8634.html

(0)
上一篇 2024-04-09
下一篇 2024-04-09

相关推荐

发表回复

登录后才能评论
关注微信
捐助我们