前言
SpringBoot最强大的功能就是把我们常用的场景抽取成了一个个 Starter (场景启动器),我们通过引入SpringBoot为我提供的这些场景启动器,再进行少量的配置就能使用相应的功能。即使是这样,SpringBoot也不能囊括我们所有的使用场景,往往我们需要自定义 Starter,来简化我们对SpringBoot的使用。
模式探索
我们参考mybatis-spring-boot-starter来探索所需要的模式:
pom文件如下:
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-autoconfigure</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis-spring</artifactId>
</dependency>
</dependencies>
其中有一个重要的依赖mybatis-spring-boot-autoconfigure:
它的pom文件中引用了很多mybatis框架所需要的依赖。
模式总结
- 启动器starter是一个空的 jar 文件,仅仅提供辅助性依赖管理,这些依赖可能用于自动装配或其他类库
- 需要专门写一个类似spring-boot-autoconfigure的配置模块
- 用的时候只需要引入启动器starter,就可以使用自动配置了
命令规范
官方启动器的命名
- 前缀:spring-boot-starter-
- 模式:spring-boot-starter-模块名
- 举例:spring-boot-starter-web、spring-boot-starter-jdbc
自定义启动器的命名
- 后缀:-spring-boot-starter
- 模式:模块-spring-boot-starter
- 举例:mybatis-spring-boot-starter
自定义启动器
我们以 xxl-job 开源框架为例子,自定义一个job-scheduler-spring-boot-starter,首先创建job-scheduler-spring-boot项目,内部包含两个模块,一个是job-scheduler-spring-boot-starter模块,一个是job-scheduler-spring-boot-autoconfigure模块。
其中job-scheduler-spring-boot-starter模块是一个空项目,只需要在pom文件中加如下依赖:
<dependencies>
<dependency>
<groupId>com.ambition.spring.boot</groupId>
<artifactId>job-scheduler-spring-boot-autoconfigure</artifactId>
<version>1.0.0-SNAPSHOT</version>
</dependency>
</dependencies>
job-scheduler-spring-boot-autoconfigure模块是真正做事的模块,需要引入 xxl-job 框架,pom文件如下:
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-autoconfigure</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-autoconfigure-processor</artifactId>
<optional>true</optional>
</dependency>
<!-- xxl-job-core -->
<dependency>
<groupId>com.xuxueli</groupId>
<artifactId>xxl-job-core</artifactId>
<version>2.2.0</version>
</dependency>
</dependencies>
然后需要有灵活配置的配置参数,可以自定义一个配置参数类,一般配置参数类以Properties结尾:
@ConfigurationProperties(prefix = JobSchedulerProperties.JOB_SCHEDULER_PREFIX)
public class JobSchedulerProperties {
public static final String JOB_SCHEDULER_PREFIX = "job.scheduler";
private String registryAddresses;
private String accessToken;
private Executor executor;
public static class Executor {
private String name;
private String address;
private String ip;
private Integer port;
private String logPath;
private Integer logRetentionDays;
}
}
再定义一个配置类,读取配置参数中的配置,将我们需要的容器注入到Spring容器中:
@Configuration
@EnableConfigurationProperties(JobSchedulerProperties.class)
public class JobSchedulerAutoConfiguration {
private static final Logger LOGGER = LoggerFactory.getLogger(JobSchedulerAutoConfiguration.class);
@Autowired
private JobSchedulerProperties properties;
@Bean
public XxlJobSpringExecutor xxlJobExecutor() {
if (null == properties || null == properties.getExecutor()) {
LOGGER.error("can not initialize job scheduler, missing required properties");
throw new BeanInitializationException("can not initialize job scheduler");
}
XxlJobSpringExecutor springExecutor = new XxlJobSpringExecutor();
springExecutor.setAdminAddresses(properties.getRegistryAddresses());
springExecutor.setAccessToken(properties.getAccessToken());
springExecutor.setAppname(properties.getExecutor().getName());
springExecutor.setAddress(properties.getExecutor().getAddress());
springExecutor.setIp(properties.getExecutor().getIp());
springExecutor.setPort(properties.getExecutor().getPort());
springExecutor.setLogPath(properties.getExecutor().getLogPath());
springExecutor.setLogRetentionDays(properties.getExecutor().getLogRetentionDays());
return springExecutor;
}
}
最后也是最重要的一步,定义 spring.factories 文件,将上面的配置类设置为自动配置,委托SpringBoot框架读取并处理配置类:
# Auto Configure
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
com.ambition.spring.boot.autoconfigure.JobSchedulerAutoConfiguration
这样就成功的定义了一个自定义的启动器,使用就很简单了:
- 1、对项目 job-scheduler-spring-boot-autoconfigure 执行打包命令
- 2、对项目 job-scheduler-spring-boot-starter 执行打包命令
- 3、将依赖添加到项目中
<dependency>
<groupId>com.ambition.spring.boot</groupId>
<artifactId>job-scheduler-spring-boot-starter</artifactId>
<version>1.0.0-SNAPSHOT</version>
</dependency>
- 4、配置调度中心参数
job:
scheduler:
# 调度中心部署跟地址,如调度中心集群部署存在多个地址则用逗号分隔
# 执行器将会使用该地址进行"执行器心跳注册"和"任务结果回调"
registry-addresses: http://127.0.0.1:8080/xxl-job-admin/
access-token:
# 执行器配置
# 名称是执行器心跳注册分组依据
# 地址信息用于"调度中心请求并触发任务"和"执行器注册"
# 执行器默认端口为9999,执行器IP默认为空表示自动获取IP,多网卡时可手动设置指定IP,该IP不会绑定Host仅作为通讯实用
# 单机部署多个执行器时,注意要配置不同执行器端口
executor:
name: ${spring.application.name}
address:
ip:
port: 8848
# 执行器运行日志文件存储的磁盘位置,需要对该路径拥有读写权限
log-path: /app/log/xxl-job/jobhandler
# 执行器Log文件定期清理功能,指定日志保存天数,日志文件过期自动删除
# 限制至少保持3天,否则功能不生效
log-retention-days: 30
- 5、启动项目
这样就完成了自定义的SpringBootStarter,job-scheduler项目地址在这里,需要自取。
上海米哈游内推,福利好待遇高,五险二金,早晚餐零食水果下午茶烧烤,吃货天堂,还有奶茶咖啡券,旅游基金,内推奖励,看我这么卖力打广告就知道奖励力度有多大了,更有周年礼物年会抽奖等你来拿,欢迎大家自荐和推荐:https://app.mokahr.com/recommendation-apply/mihoyo/26460?recommendCode=NTAKBmA#/jobs?from=genPoster