前言
还记得吗,我们在创建maven项目的时候,曾经使用过qucikstart,webapp等这些maven archetype。使用archetype可以快速创建出具有一定组织结构或者一定功能的项目。比如:qucikstart 可以src/main/java,src/main/resources等这些目录,webapp 可以快速创建出符合web应用目录规范的项目。
现在让我们想一下开发微服务项目的时候我们创建一个微服务一般是怎么做的?
- 第一种方式
1)创建一个普通maven工程
2)编写pom.xml导入springboot ,nacos,feign,sleuth,zipkin等依赖
3)创建编写application.yml或者bootstrap.yml配置文件
4)创建启动类
- 第二种方式
通过spring initializr创建项目
创建编写application.yml或者bootstrap.yml配置文件,编写启动类。
问题:
上述两种创建的过程有没有重复性工作呢?
nacos,sleuth一些配置能不能也一块随着项目创建出来呢?
项目中的一些自己个性化的东东可不可以也随之创建呢 ?
接下来我们自己创建一个mavne archetype模板,以后用我们自己的模板创建项目。解决上述问题。是不是有点脚手架的感觉。。
创建cloud maven archetype
- 创建一个普通maven项目
File–>new module—>maven–>next - 展示;
- module的名字我由于已经创建了,这里飘红。可忽略。
点击finish完成。 - 编写pom.xml
1)定义版本号
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<junit.version>4.12</junit.version>
<log4j.version>1.2.17</log4j.version>
<lombok.version>1.16.18</lombok.version>
<mysql.version>5.1.47</mysql.version>
<druid.version>1.1.16</druid.version>
<mybatis.spring.boot.version>1.3.0</mybatis.spring.boot.version>
</properties>
我这里为了看着方便,spring boot和cloud的版本号没有去引用properties.
spring boot和cloud的版本怎么选择呢?这里可以看一下官网提供的对应关系。访问这个网址:
https://start.spring.io/actuator/info
<dependencyManagement>
<dependencies>
<!--spring boot 2.2.2-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.2.1.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--spring cloud Hoxton.SR1-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Hoxton.SR1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--spring cloud alibaba 2.1.0.RELEASE-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>2.1.0.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>${druid.version}</version>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>${mybatis.spring.boot.version}</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>${log4j.version}</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
<optional>true</optional>
</dependency>
</dependencies>
</dependencyManagement>
```引入你自己认为需要的依赖。
<denpendencies>
<!--引入自己需要的-->
</dependencies>
- 配置你application.yml
1. #配置常用的配置,用的时候稍做改动
server:
port: 8882
spring:
application:
name: consumer
eureka:
client:
serviceUrl:
defaultZone: http://localhost:8761/eureka/
register-with-eureka: false
instance:
instance-id: consumer/${random.int}
prefer-ip-address: true
…
此处省略1000字…
4.添加你的工具类等,你想添加的
比如:这是我的一个服务调用工具类
public final class Rests {
private static final Logger LOGGER = LoggerFactory.getLogger(Rests.class);
private Rests(){};
private static DefaultHanlder defaultHanlder = new DefaultHanlder();
/**
* 执行服务调用,并判断返回状态
* @param callable
* @return
*/
public static <T> T exc(Callable<T> callable){
return exc(callable, defaultHanlder);
}
public static <T> T exc(Callable<T> callable,ResultHandler handler){
T result = sendReq(callable);
return handler.handle(result);
}
public static String toUrl(String serviceName,String path){
return "http://" + serviceName + path;
}
public static class DefaultHanlder implements ResultHandler {
@Override
public <T> T handle(T result) {
int code = 1;
String msg = "";
try {
// code = (Integer)FieldUtils.readDeclaredField(result, "code", true);
// msg = (String)FieldUtils.readDeclaredField(result, "msg", true);
} catch (Exception e) {
//ignore
}
if (code != 0) {
throw new RestException("Get erroNo " + code + " when execute rest call with errorMsg " +msg);
}
return result;
}
}
public interface ResultHandler{
<T> T handle(T result);
}
public static <T> T sendReq(Callable<T> callable){
T result = null;
try {
result = callable.call();
} catch (Exception e) {
throw new RestException("sendReq error by " + e.getMessage());
}finally {
LOGGER.info("result={}",result);
}
return result;
}
添加一些你的常用config,比如:
@Configuration
@ConditionalOnClass({HttpClient.class})
@EnableConfigurationProperties(HttpClientProperties.class)
public class HttpClientAutoConfiguration {
private final HttpClientProperties properties;
public HttpClientAutoConfiguration(HttpClientProperties properties){
this.properties = properties;
}
@Autowired
private LogbookHttpRequestInterceptor logbookHttpRequestInterceptor;
@Autowired
private LogbookHttpResponseInterceptor logbookHttpResponseInterceptor;
/**
* httpclient bean 的定义
* @return
*/
@Bean
@ConditionalOnMissingBean(HttpClient.class)
public HttpClient httpClient() {
RequestConfig requestConfig = RequestConfig.custom()
.setConnectTimeout(properties.getConnectTimeOut())
.setSocketTimeout(properties.getSocketTimeOut()).build();// 构建requestConfig
HttpClient client = HttpClientBuilder.create().setDefaultRequestConfig(requestConfig)
.setUserAgent(properties.getAgent())
.setMaxConnPerRoute(properties.getMaxConnPerRoute())
.setMaxConnTotal(properties.getMaxConnTotaol())
.addInterceptorFirst(logbookHttpRequestInterceptor)
.addInterceptorFirst(logbookHttpResponseInterceptor)
.build();
return client;
}
}
自己可以个性化的添加,我就不把代码都贴出来了。
制作archetype
archetype:create-from-project
执行:
执行成功之后,回来target目录生成一些文件。
E:\work\cloud\hkd-cloudbasic-archetype\target\generated-sources\archetype
切换到这个目录执行:
mvn install
成功后会发现该目录多了一个
同时在你的本地maven 仓库中,有这样一个配置文件
使用archetype创建项目
1)首先看一下你刚才创建的archetype的maven坐标:
<groupId>com.hkd.archetype</groupId>
<artifactId>hkd-cloudbasic-archetype</artifactId>
<version>1.0</version>
点击ok,
是不是多了一个选项。后面创建项目的步骤我就不啰嗦了,你看一下你创建的项目是不是你刚才写的东西都在呢,只要稍微改吧改吧是不是就可以使用了呢。