Spring Cloud简介
Spring Cloud是一个基于Spring Boot实现的云应用开发工具,它为基于JVM的云应用开发中的配置管理、服务发现、断路器、智能路由、微代理、控制总线、全局锁、决策竞选、分布式会话和集群状态管理等操作提供了一种简单的开发方式。
Spring Cloud包含了多个子项目(针对分布式系统中涉及的多个不同开源产品),比如:Spring Cloud Config、Spring Cloud Netflix、Spring Cloud CloudFoundry、Spring Cloud AWS、Spring Cloud Security、Spring Cloud Commons、Spring Cloud Zookeeper、Spring Cloud CLI等项目。
本文将介绍基于springBoot2.1.4的springCloud的微服务搭建以及需要注意的细节.
1.服务注册与发现
在简单介绍了Spring Cloud和微服务架构之后,下面回归本文的主旨内容,如何使用Spring Cloud搭建服务注册与发现模块。
这里我们会用到Spring Cloud Netflix,该项目是Spring Cloud的子项目之一,主要内容是对Netflix公司一系列开源产品的包装,它为Spring Boot应用提供了自配置的Netflix OSS整合。通过一些简单的注解,开发者就可以快速的在应用中配置一下常用模块并构建庞大的分布式系统。它主要提供的模块包括:服务发现(Eureka),断路器(Hystrix),智能路有(Zuul),客户端负载均衡(Ribbon)等。
所以,我们这里的核心内容就是服务发现模块:Eureka。下面我们动手来做一些尝试。
创建“服务注册中心”
1.1 创建springboot项目
使用Spring Initalizr 快速构建springboot项目
1.2 修改pom文件,添加spring cloud eureka依赖如下
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- springCloud注测中心服务 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<!-- springCloud 配置 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
1.3 在启动类上加上注解 如下
通过@EnableEurekaServer注解启动一个服务注册中心提供给其他应用进行对话。这一步非常的简单,只需要在一个普通的Spring Boot应用中添加这个注解就能开启此功能,比如下面的例子:
1.4 配置文件application.yml
在默认设置下,该服务注册中心也会将自己作为客户端来尝试注册它自己,所以我们需要禁用它的客户端注册行为,只需要在application.yml中问增加如下配置:
为了与后续要进行注册的服务区分,这里将服务注册中心的端口通过server.port属性设置为1111。
启动工程后,访问:http://localhost:1111/
可以看到下面的页面,其中还没有发现任何服务:
2.1 创建springboot项目同上
2.2 修改pom.xml文件,添加spring cloud 服务端
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
2.3 在启动类上加上注解 如下
最后在主类中通过加上@EnableEurekaClient 注解,该注解能激活Eureka中的对注册中心注册服务实现,才能实现Controller中对服务信息的输出。
2.4 配置文件application.yml
通过spring.application.name属性,我们可以指定微服务的名称后续在调用的时候只需要使用该名称就可以进行服务的访问。
eureka.client.serviceUrl.defaultZone属性对应服务注册中心的配置内容,指定服务注册中心的位置。
为了在本机上测试区分服务提供方和服务注册中心,使用server.port属性设置不同的端口。
2.5 启动该项目
再次访问:http://localhost:1111/
可以看到,我们定义的服务被注册了。如下图所示:
3 spring cloud 路由网关服务—Zuul
在使用Zuul之前,我们先构建一个服务注册中心、以及两个简单的服务,比如:我构建了一个sc-demo-service,一个sc-demo1-service。然后启动eureka-server和这两个服务。通过访问eureka-server,我们可以看到sc-demo-service和sc-demo1-service已经注册到了服务中心。
如何构建sc-demo1-service服务,请参考上面的服务端构建
需要注意的是:
1.spring.application.name :可以是跟sc-demo-service中的spring.application.name一致
2.端口号不能一致。
3.pom文件的依赖是跟sc-demo-service一样的,启动类也是需要加上@EnableEurekaClient 注解
启动服务成功显示如下:
本文中sc-demo1-service只修改了端口号,端口号是3333
接下来可以在两个服务中创建Controller,如下图
创建完以上的Controller就可以测试一下了:http://localhost:3333/info
3.1接下来搭建-----路由网关服务—Zuul
3.2修改pom.xml文件,添加spring cloud Zuul依赖如下
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<!-- springCloud 配置 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-zuul</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
3.3 在启动类上加上注解 如下
应用主类使用@EnableZuulProxy注解开启Zuul
这里用了@SpringCloudApplication注解,之前没有提过,通过源码我们看到,它整合了@SpringBootApplication、@EnableEurekaClient、@EnableCircuitBreaker,主要目的还是简化配置。
3.4配置application.yml文件
#表示要通过Zull访问sc-demo-service服务中的Controller地址是:http://localhost:9999/test/info
3.5 启动项目 测试
输入地址:http://localhost:9999/test/info
每次刷新访问都会在下面结果轮询显示:
这就简单实现了springCloud的负载均衡.
3.5 服务过滤
在完成了服务路由之后,我们对外开放服务还需要一些安全措施来保护客户端只能访问它应该访问到的资源。所以我们需要利用Zuul的过滤器来实现我们对外服务的安全控制。
在服务网关中定义过滤器只需要继承ZuulFilter抽象类实现其定义的四个抽象函数就可对请求进行拦截与过滤。
第一步:自定义过滤器继承ZuulFilter抽象类
重写run,shouldFilter,filterOrder,filterType
run方法是写具体的过滤逻辑
其中shouldFilter方法表示是否执行该过滤器,此处为true,说明需要过滤
filterOrder方法表示优先级,数字越大,优先级越低
filterType 方法表示在什么时候调用
pre:可以在请求被路由之前调用
route:在路由请求时候被调用
post:在route和error过滤器之后被调用
error:处理请求时发生错误时被调用
在实现了自定义过滤器之后,还需要实例化该过滤器才能生效,我们只需要在应用主类中增加如下内容:
@Bean
public AccessFilter accessFilter(){
return new AccessFilter();
}