美文网首页
API网关服务 Spring Cloud Zuul 入门

API网关服务 Spring Cloud Zuul 入门

作者: zbsong | 来源:发表于2020-04-01 21:31 被阅读0次

什么是API网关服务?
个人理解:
简单直白点说主要就是为了解决各个微服务应用中的冗余逻辑,比如用户状态校验、签名校验等等,假设一个系统有十个应用服务,每个里面都维护着相同的用户状态校验和签名校验的逻辑,如果发现一个BUG需要需改,那我们还得去十个应用里面挨个修改,这对于后续的维护会产生很大的负担,而且伴随着的是也会对测试工作产生倍数的增长,毕竟每个应用改完都得重新覆盖测试,所以产生了API网关的概念。
所有的外部请求都经过API网关进行调度和过滤,比如我们把用户校验、签名校验的相关逻辑从各个应用中分离出来,单独创建一个应用服务,在API网关上统一调用来对微服务接口做前置过滤。它的存在就像是整个微服务架构的门面一样,所有的外部客户端访问都需要经过它来调度和过滤。主要实现了请求路由、负载均衡、校验过滤、熔断、聚合等等一系列高级功能。

Spring Cloud提供了基于Netflix Zuul实现的API网关组件Spring Cloud Zuul,主要有请求路由、请求过滤、服务路由配置、路径匹配、本地跳转、过滤器、动态加载、Hystrix和Ribbon支持等等功能,太多了,不多啰嗦,本节先看实现一个入门例子,先来了解Spring Cloud Zuul中封装的API网关是怎么使用的,怎么应用到微服务架构中的。

本节先用一个简单的例子,使用服务路由配置,来实API网关将求转发到具体实例的功能。

  • 我们先创建一个接口服务,方便等会测试
    1.新建一个Spring Boot工程,命名为zuul-consumer(随意)
    2.编辑pom.cml,添加主要依赖
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>

3.编辑application.yml

spring:
  application:
    name: zuul-consumer
server:
  port: 9002
eureka:
  client:
    service-url:
      defaultZone: http://peer1:1111/eureka/

4.编辑主类,添加@EnableDiscoveryClient注解,把该服务注册到注册中心

@SpringBootApplication
@EnableDiscoveryClient
public class ZuulApplication {

    public static void main(String[] args) {
        SpringApplication.run(ZuulApplication.class, args);
    }

}

5.添加ZuulController,提供一个接口,等会就用这个接口测试

@RestController
@RequestMapping(value = "/zuul")
public class ZuulController {

    @GetMapping(value = "/test")
    public String feignConsumer() {
        System.out.println("zuul测试");
        return "zuul测试";
    }
}
  • 创建API网关服务
    1.新建一个Spring Boot工程,命名为zuui-api-gateway(随意)
    2.编辑pom.cml,添加spring-cloud-starter-netflix-zuul依赖
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-netflix-zuul</artifactId>
</dependency>
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>

3.查看spring-cloud-starter-netflix-zuul包可以看到该包包含了hystrix、ribbon、actuator重要依赖。
spring-cloud-starter-netflix-hystrix:在网关服务中实现对微服务转发时候的保护机制,通过线程隔离和断路器来防止微服务的故障引发API网关资源无法释放而影响别的应用的对外服务。
spring-cloud-starter-netflix-ribbon:实现在网关服务中进行路由转发时候的客户端负载均衡和请求重试。
spring-boot-starter-actuator:提供常规的微服务管理端点。

image.png
4.编辑application.yml
spring:
  application:
    name: zuul-api-gateway
server:
  port: 9000
eureka:
  client:
    service-url:
      defaultZone: http://peer1:1111/eureka/
#配置服务路由
zuul:
  routes:
    zuul-consumer: /zuul-test/**

zuul.routes.zuul-consumer=/zuul-test/**的作用是配置服务路由
配置方式是 zuul.routes.<serviceId>=<path>
<serviceId>代表具体的服务实例地址,不区分大小写

image.png <path>配置请求的表达式
我们配置文件中的zuul.routes.zuul-consumer=/zuul-test/**代表将符合/zuul-test/**规则的请求路径转发zuul-consumer的服务实例上。
比如请求我们刚刚创建的API网关服务:http://localhost:9000/zuul-test/zuul/test,符合了我们配置的/zuul-test/**的规则,则API网关会把请求转发到http://localhost:9002/zuul/test
API网关服务和接口服务都注册到了服务中心,所以API网关可以获取到服务注册中心的所有实例信息,然后可以通过我们刚刚说的<serviceId>找到服务实例具体的地址。
/zuul-test/****代表通配符,有三种
:匹配任意单个字符,比如可以匹配/zuul-test/a、/zuul-test/b
*:匹配任意数量的字符,比如/zuul-test/a、/zuul-test/aaa、
**:匹配任意数量的字符,且支持多级目录,比如/zuul-test/aaa/bbb、/zuul-test/bb/c

5.编辑主类,添加@EnableDiscoveryClient注解,把该服务注册到注册中心,添加@EnableZuulProxy注解,开启zuul的API网关服务功能

@SpringBootApplication
@EnableDiscoveryClient
@EnableZuulProxy
public class ZuulApplication {

    public static void main(String[] args) {
        SpringApplication.run(ZuulApplication.class, args);
    }

}

下面启动服务注册中心(这里就不讲怎么搭建服务注册中心了)、zuul-consumer、zuui-api-gateway三个服务。

image.png
可以看到zuul-consumer、zuui-api-gateway两个服务都注册到了服务注册中心。
下面我们访问API服务:http://localhost:9000/zuul-test/zuul/test
image.png
正常返回了我们接口服务的/zuul/test接口的内容,说明API网关服务根据我们配置的服务路由配置生效了,将http://localhost:9000/zuul-test/zuul/test的请求成功转发到了http://localhost:9002/zuul/test地址。

服务路由配置规则还可以使用
zuul.routes.<route>.pathzuul.routes.<route>.serviceId实现
拿我们上面的例子来讲,也可以写成:
zuul.routes.zuul-consumer.path=/zuul-test/**
zuul.routes.zuul-consumer.serviceId=zuul-consumer
还有一点需要注意的是当API网关服务和Eurake整合以后,网关服务会为Eurake中的每个服务都创建一个默认的路由规则,这些默认的规则的path会使用serviceId配置的服务名作为请求前缀,比如我们上面的例子,其实还自动生成了一套路由规则,如下
zuul.routes.zuul-consumer.path=/zuul-consumer/**
zuul.routes.zuul-consumer.serviceId=zuul-consumer
我们可以测试一下,我们清楚的是在配置文件中并没有配置/zuul-consumer/**的路由规则,现在我们请求一下http://localhost:9000/zuul-consumer/zuul/test

image.png
发现一样请求成功,这样可能会使得一些不希望对外开放的服务也能被外部访问,针对这个问题,我们可以使用ignored-services来设置哪些服务不自动创建默认路由规则,也可以将ignored-services设置为*,对所有服务不创建,然后自己通过我们上面讲的,对我们希望对外提供的服务单独添加路由规则。

测试一下ignored-services,修改zuui-api-gateway工程的application.yml,添加
ignored-services: "*"

zuul:
  routes:
    zuul-consumer: /zuul-test/**
  ignored-services: "*"

重启,然后在访问一下http://localhost:9000/zuul-consumer/zuul/test

image.png
可以看到通过默认路由规则已经访问不到了。

相关文章

网友评论

      本文标题:API网关服务 Spring Cloud Zuul 入门

      本文链接:https://www.haomeiwen.com/subject/eptguhtx.html