RestTemplate 跳过SSL证书验证

在使用RestTemplate请求接口的过程中,遇到HTTPS请求又没有证书的情况,只能通过配置来忽略证书验证了

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
package com.ewei.custom.yto.config

import org.springframework.context.annotation.Bean
import org.springframework.context.annotation.Configuration
import org.springframework.http.client.ClientHttpRequestFactory
import org.springframework.http.client.SimpleClientHttpRequestFactory
import org.springframework.web.client.RestTemplate
import java.net.HttpURLConnection
import java.security.SecureRandom
import java.security.cert.X509Certificate
import javax.net.ssl.HttpsURLConnection
import javax.net.ssl.SSLContext
import javax.net.ssl.SSLSocketFactory
import javax.net.ssl.X509TrustManager


/**
* @author wuwenze
* @date 2019-06-21
*/
@Configuration
class RestTemplateClientConfig {

@Bean
fun restTemplate(factory: ClientHttpRequestFactory): RestTemplate {
return RestTemplate(factory)
}

@Bean
fun simpleClientHttpRequestFactory(): ClientHttpRequestFactory {
val factory = SkipSSLSimpleClientHttpRequestFactory()
factory.setReadTimeout(30000)
factory.setConnectTimeout(30000)
return factory
}

class SkipSSLSimpleClientHttpRequestFactory : SimpleClientHttpRequestFactory() {
override fun prepareConnection(connection: HttpURLConnection, httpMethod: String) {
if (connection is HttpsURLConnection) {
try {
connection.setHostnameVerifier { _, _ -> true }
connection.sslSocketFactory = createSslSocketFactory()
} catch (e: Throwable) {
// ignore
}
}
super.prepareConnection(connection, httpMethod)
}

private fun createSslSocketFactory(): SSLSocketFactory {
val context: SSLContext = SSLContext.getInstance("TLS")
context.init(null, arrayOf(SkipX509TrustManager()), SecureRandom())
return context.socketFactory
}

class SkipX509TrustManager : X509TrustManager {
override fun getAcceptedIssuers(): Array<X509Certificate> = arrayOf()
override fun checkClientTrusted(chain: Array<out X509Certificate>?, authType: String?) {}
override fun checkServerTrusted(chain: Array<out X509Certificate>?, authType: String?) {}
}
}
}

SpringBoot与VUE前后端分离最佳实践

前后端分离的开发模式大家都很清楚了,甚是麻烦:

  • 前端启动webpack-dev-server
  • 后端启动接口服务
  • 开启代理服务器,前端通过代理服务器请求后端接口(解决跨域问题)

但是这些东西对于后端来说,太麻烦了,直接把前端打包好的dist文件丢到后端静态服务器里面就好了。
至于前端的webpack-dev-server热部署特性,改完前端代码立即在浏览器生效,对于后端来说有什么用呢?

  • 配置前端项目打包Task
  • 配置后端项目启动Task(执行前端编译、拷贝编译后的静态文件、启动后端)
  • 一键启动

Swagger2在SpringBoot中的集成指南

引入依赖Swagger2及Swagger2 UI

1
2
3
4
5
6
7
8
9
10
11
12
<!-- swagger -->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger2</artifactId>
<version>2.7.0</version>
</dependency>
<!-- swagger-ui -->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger-ui</artifactId>
<version>2.7.0</version>
</dependency>

构建配置文件(基于JavaConfig)

SpringBoot Admin 集成指南(v2.1.1)

SpringBoot Admin用于管理和监控SpringBoot应用程序。 应用程序作为Spring Boot Admin Client向为Spring Boot Admin Server注册(通过HTTP)或使用SpringCloud注册中心(例如Eureka,Consul)发现。

其常见的功能如下:

  • 显示健康状况
  • 显示详细信息,例如
    • JVM和内存指标
    • micrometer.io指标
    • 数据源指标
    • 缓存指标
  • 显示构建信息编号
  • 关注并下载日志文件
  • 查看jvm系统和环境属性
  • 查看Spring Boot配置属性
  • 支持Spring Cloud的postable / env-和/ refresh-endpoint
  • 轻松的日志级管理
  • 与JMX-beans交互
  • 查看线程转储
  • 查看http跟踪
  • 查看auditevents
  • 查看http-endpoints
  • 查看计划任务
  • 查看和删除活动会话(使用spring-session)
  • 查看Flyway / Liquibase数据库迁移
  • 下载heapdump文件
  • 状态变更通知(通过电子邮件,Slack,Hipchat,……)
  • 状态更改的事件日志(非持久性)

    开始使用

使用Docker容器部署SpringBoot项目

Docker简介

Docker是基于Go语言实现的云开源项目,诞生于2013年初,最初发起者是dotClouw公司。Docker 自开源后受到广泛的关注和讨论,目前已有多个相关项目,逐断形成了围Docker的生态体系。dotCloud 公司后来也改名为Docker Ine。

Docker是一个开源的容器引擎,它有助于更快地交付应用。 Docker可将应用程序和基础设施层隔离,并且能将基础设施当作程序一样进行管理。使用 Docker可更快地打包、测试以及部署应用程序,并可以缩短从编写到部署运行代码的周期。

官网地址:(https://docs.docker.com/) 中文:(http://www.docker.org.cn/)

Docker架构

Docker daemon:运行在宿主机(DOCKER-HOST)的后台进程,可通过 Docker 客户端与之通信。

Images:一个只读的镜像模板,可以自己创建一个镜像也可以从网站上下载镜像供自己使用,镜像包含了一个RFS,一个镜像可以创建很多容器。

Container:由Docker Client通过镜像创建的实例,用户在容器中运行应用,一旦创建后就可以看做是一个简单的RFS,每个应用运行在隔离的容器中,享用独自的权限,用户,网络。确保安全与互相干扰 两者在创建后,都是一堆layer的统一视角,唯一的却别是镜像最上面那一层是只读的,不可以修改,但是容器最上面一层是rw的,提供给用户操作。

Repository:镜像仓库。

Spring5响应式WEB编程-Webflux示例

Spring WebFlux简介

Spring WebFlux是随Spring 5推出的响应式Web框架:



(左侧为基于spring-webmvc的技术栈,右侧为基于spring-webflux的技术栈)

服务端技术栈

  • Spring WebFlux是基于响应式流的,因此可以用来建立异步的、非阻塞的、事件驱动的服务。它采用Reactor作为首选的响应式流的实现库,不过也提供了对RxJava的支持;
  • 由于响应式编程的特性,Spring WebFlux和Reactor底层需要支持异步的运行环境,比如NettyUndertow;也可以运行在支持异步I/O的Servlet 3.1的容器之上,比如Tomcat(8.0.23及以上)和Jetty(9.0.4及以上);
  • 从图的纵向上看,spring-webflux上层支持两种开发模式:
    • 类似于Spring WebMVC的基于注解(@Controller@RequestMapping)的开发模式;
    • Java 8 lambda 风格的函数式开发模式;
  • 响应式的WebSocket服务端开发;

    客户端技术栈

使用Mybatis Plus优雅实现多租户架构

在进行多租户架构(Multi-tenancy)实现之前,先了解一下相关的定义吧:

什么是多租户

多租户技术或称多重租赁技术,简称SaaS,是一种软件架构技术,是实现如何在多用户环境下(此处的多用户一般是面向企业用户)共用相同的系统或程序组件,并且可确保各用户间数据的隔离性。

简单讲:在一台服务器上运行单个应用实例,它为多个租户(客户)提供服务。从定义中我们可以理解:多租户是一种架构,目的是为了让多用户环境下使用同一套程序,且保证用户间数据隔离。那么重点就很浅显易懂了,多租户的重点就是同一套程序下实现多用户数据的隔离。

数据隔离方案

多租户在数据存储上存在三种主要的方案,分别是:

在SpringBoot中优雅的集成Dubbo

在springboot中集成dubbo示例(非注解),废话少说,直入正题。

pom

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>

<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>

<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.8.4</version>
<exclusions>
<exclusion>
<artifactId>spring</artifactId>
<groupId>org.springframework</groupId>
</exclusion>
</exclusions>
</dependency>

<dependency>
<groupId>org.apache.zookeeper</groupId>
<artifactId>zookeeper</artifactId>
<version>3.4.6</version>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
</exclusion>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
</exclusions>
</dependency>

<dependency>
<groupId>com.github.sgroschupf</groupId>
<artifactId>zkclient</artifactId>
<version>0.1</version>
</dependency>

使用MockMvc在SpringBoot中进行单元测试

在开发好常规的RESTful接口后,难免会依次进行单元测试,一般来说使用Postman即可, 但是依然是不太方便,有没有更方便,更优雅的方式呢?

MockMvc

org.springframework.test.web.servlet.MockMvc

MockMvc是由Spring提供的,作用是在单元测试代码中,伪造一套MVC环境,常见的方法如下:

Method Remark
perform 执行一个RequestBuilder请求,会自动执行SpringMVC的流程并映射到相应的控制器执行处理;
get/post/delete/put 声明发送一个get请求的方法。MockHttpServletRequestBuilder get(String urlTemplate, Object… urlVariables):根据uri模板和uri变量值得到一个GET请求方式的。另外提供了其他的请求的方法,如:post、put、delete等。
param 添加request的参数
content 添加requestBody的参数
contentType 设置contentType属性
header 设置header属性
andExpect 添加ResultMatcher验证规则,验证控制器执行完成后结果是否正确(对返回的数据进行的判断);
andDo 添加ResultHandler结果处理器,比如调试时打印结果到控制台(对返回的数据进行的判断);
andReturn 最后返回相应的MvcResult;然后进行自定义验证/进行下一步的异步处理(对返回的数据进行的判断);

使用Consul代替Spring Cloud Eureka

随着Eureka 2.0 开源工作宣告停止,其实是可以考虑转战其他方式来实现注册中心了(如:Zookeeper、Redis、Consul等)

本文通过简单的描述,快速将Consul集成到SpringCloud环境中。

Consul环境搭建

官网:https://www.consul.io/

官网提供了(macOS、FreeBSD、Linux、Solaris、Windows)全平台的相关包,下面以Windows为例:

  1. 下载 https://releases.hashicorp.com/consul/1.2.0/consul_1.2.0_windows_amd64.zip
  2. 解压,并创建快速启动脚本:
1
2
consul agent -dev
pause

  1. 启动,然后浏览器访问:http://localhost:8500, 出现UI界面则搭建成功。
Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×