基于maven
打包方式通常采用的jar包,使用springboot的默认方式便可;java
使用maven命令:web
mvn clean package -Dmaven.test.skip=true
执行成功以后,能够在对应的target目录下找到对应的包,好比: eg-zuul-0.0.1-SNAPSHOT.jar spring
springboot内置了web container容器 tomcat, 能够直接使用 java -jar命令运行;shell
例如:apache
java -jar xxx/target/eg-zuul-0.0.1-SNAPSHOT.jar
也可以使用war的方式,使用外置的tomcat运行,不过代码须要改造一下:
1 改造打包方式
打包方式改成 war包;
在pom.xml中,在version标签的下面添加配置:segmentfault
<package>war</package>
2 添加改造启动代码 api
package com.springbootpractice.egzuul; import org.springframework.boot.builder.SpringApplicationBuilder; import org.springframework.boot.web.servlet.support.SpringBootServletInitializer; /** * @author <a href="mailto:505847426@qq.com">carterbrother</a> * @description 经过外置的容器运行springboot * @date 2019年06月21日 15:32 * @Copyright (c) carterbrother */ public class ServletInitializer extends SpringBootServletInitializer { @Override protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) { return builder.sources(EgZuulApplication.class); } }
原理是: 从servlet3.1开始,运行无web.xml的web程序,只须要实现ServletContainerInitializer接口,而SpringBootServletInitializer扩展了该类,因此能够实现无xml启动;tomcat
3 配置外置tomcat springboot
4 忽略打包检查网络
<plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-war-plugin</artifactId> <version>2.3</version> <configuration> <failOnMissingWebXml>false</failOnMissingWebXml> </configuration> </plugin>
开发的时候用到, spring-boot-devtools ;
引入依赖:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <optional>true</optional> </dependency>
暴露的配置信息能够配置更多细节方面的处理:
基于junit 和 mockito (消除各类环境对于http带来的困难)
package com.springbootpractice.eguser; import com.springbootpractice.api.user.dto.UserPro; import com.springbootpractice.eguser.service.UserService; import org.junit.Assert; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.boot.test.web.client.TestRestTemplate; import org.springframework.test.context.junit4.SpringRunner; import java.util.Map; @RunWith(SpringRunner.class) @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) public class EgUserApplicationTests { @Autowired private UserService userService; @Autowired private TestRestTemplate testRestTemplate; @Test public void testUserService() { UserPro userPro = new UserPro(); userPro.setId(1L); userPro.setUserName("xxxaaa"); final Map<String, Object> map = userService.insertUser(userPro); Assert.assertEquals("插入失败",true,map.get("success")); final UserPro userProReturn = userService.getUserPro(1L); Assert.assertEquals(userPro,userProReturn); } @Test public void testUserRest() { UserPro userPro = new UserPro(); userPro.setId(2L); userPro.setUserName("BBBB"); Map map = testRestTemplate.postForObject("/insert", userPro, Map.class); Assert.assertEquals("插入失败",true,map.get("success")); UserPro userProReturn = testRestTemplate.getForObject("/user/{id}", UserPro.class, 2L); Assert.assertEquals(userPro,userProReturn); } }
当依赖的服务尚未开发完毕,而须要测试的功能却强烈依赖,可使用Mock来测试;
package com.springbootpractice.egproduct; import com.springbootpractice.api.user.UserApi; import com.springbootpractice.api.user.dto.UserPro; import org.junit.Assert; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.BDDMockito; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.boot.test.mock.mockito.MockBean; import org.springframework.test.context.junit4.SpringRunner; @RunWith(SpringRunner.class) @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) public class EgProductApplicationTests { @MockBean private UserApi userApi; @Test public void mockUserApiTest() { UserPro mockUserPro = new UserPro(); mockUserPro.setId(1L); mockUserPro.setUserName("xxxx"); BDDMockito.given(userApi.getUserPro(1L)).willReturn(mockUserPro); UserPro userProReturn = userApi.getUserPro(1L); Assert.assertEquals(userProReturn,mockUserPro); } }
基于 actuator ,监控运行状态,进行一些简单的管理
引入依赖:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency> <dependency> <groupId>org.springframework.hateoas</groupId> <artifactId>spring-hateoas</artifactId> <version>0.24.0.RELEASE</version> </dependency>
默认只开放了 health , info ;
若是要开放全部的监控点:
management.endpoint.web.exposure.include=*
常见的监控点有:
url | 监控说明 |
---|---|
health | 监控信息 |
info | |
beans | 容器中的Bean |
mappings | url mapping |
env | 配置参数 |
shutdown | 关闭服务 |
conditions | 自动装配相关的信息 |
对敏感的配置信息,可使用spring-security来控制保护起来;
shutdown端点默认是关闭的,开启的配置属性是:
management.endpoint.shutdown.enabled=true
开启以后 访问 /actuator/shutdown 须要是post请求才能调用;
通常的配置端点开关的方式是:
//默认全部的端点都是关闭的,而后选择一些须要暴露的端点进行打开
management.endpoints.enabled-by-default=false
标注@Endpoint注解类,
@ReadOperation标注方法 标识GET方法
@WriteOperation 标识POST方法
@DeleteOperation 标识Delete方法
package com.springbootpractice.egproduct.endpoint; import org.springframework.boot.actuate.endpoint.annotation.Endpoint; import org.springframework.boot.actuate.endpoint.annotation.ReadOperation; import org.springframework.stereotype.Component; /** * @author <a href="mailto:505847426@qq.com">carterbrother</a> * @description 新增actuator的一个端点 * @date 2019年06月21日 18:42 * @Copyright (c) carterbrother */ @Endpoint(id = "dbCheck",enableByDefault = true) @Component public class DBCheckEndpoint { @ReadOperation public String test(){ return "db check ok"; } }
actuator内置了不少的健康指标 须要配置才能显示,配置方法:
management.endpoint.health.show-details=_always_
package com.springbootpractice.egproduct.health; import org.springframework.boot.actuate.health.AbstractHealthIndicator; import org.springframework.boot.actuate.health.Health; import org.springframework.stereotype.Component; import java.io.IOException; import java.net.InetAddress; /** * @author <a href="mailto:505847426@qq.com">carterbrother</a> * @description 进行网络检查 * @date 2019年06月21日 18:30 * @Copyright (c) carterbrother */ @Component public class WWWHealthIndicator extends AbstractHealthIndicator { @Override protected void doHealthCheck(Health.Builder builder) throws Exception { if (ping()){ builder.withDetail("message","能够正常链接互联网").up(); return; } builder.withDetail("message","没法链接互联网").unknown(); } private boolean ping() { try { return InetAddress.getByName("www.baidu.com").isReachable(3000); } catch (IOException e) { return false; } } }
相对于http监控,也提供了jmx的监控方式;
典型使用方式使用的是jdk的 jconsole,使用jmx协议链接本地的jvm,进行监控,MBean下的Health下能够查看到返回信息;以此来进行监控。
原创不易,转载请注明出处,欢迎沟通交流。