SpringCloud组件之Zuul路由网关

1、什么是Zuul?

1、Spring Cloud Zuul 是整合了NetFlix公司的Zuul开源项目(一笔带过、了解即可)
2、其中Zuul包含了对请求路由校验过滤两个最主要的功能:
(1)其中”请求路由功能“负责将请求转发到相应的微服务实例上(下面的例子我们将会讲到:只要带有“/product/**"请求的,都会转发到 microservice-cloud-08-provider-product-hystrix-8001 服 务。),是实现外部访问、统一入口的基础;
(2)而过滤功能则是将请求的处理过程进行干预,是实现请求校验功能的基础。
3、Zuul和Eureka进行结合,将Zuul自身注册为Eureka服务治理中的服务,同时他也从Eureka中获取其他微服务的信息,也就是说以后所有访问微服务都是通过Zuul跳转后获得的;

2、我们在实战中如何使用Zuul?

(1)首先,我们新建一个Zuul的模块,引入相应的依赖:

 <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
<!--    因为要把自己注册进Eureka中,所以我们得先添加一个eureka-client的依赖-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        <version>2.1.2.RELEASE</version>
    </dependency>
<!--    添加一个路由网关依赖-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-zuul</artifactId>
    </dependency>
    <dependency>
        <groupId>org.slf4j</groupId>
        <artifactId>slf4j-api</artifactId>
    </dependency>
</dependencies>

(2)对yml文件进行配置;其中包括端口号服务器名;

server:
  port: 7001 #该服务端口为7001
spring:   #给该服务命名
  application:
    name: microserver-zuul-gateway

eureka:
  client:
    register-with-eureka: true #因为该路由服务也得将自己注册进服务中心,故得打开
    fetch-registry: true  #服务发现:路由服务也需要从服务中心获取到其他服务的信息
    service-url:  #客户端(服务提供者)注册到哪个eureka Server服务注册中心,存在多个就用逗号隔开
      defaultZone:
        http://eureka6001.com:6001/eureka,http://eureka6002.com:6002/eureka

  instance:
    instance-id: ${spring.application.name}:${server.port} #指定实例ID,就不会在Eureka注册中心显示主机名
    prefer-ip-address: true #访问路径可选择IP地址
zuul:
  routes:
    provider-product:      #路由名称,名称任意,保持所有路由名称唯一
      path: /product/** #访问路径:这里表示只要接收到/product开头的路径就会转发到microservice-cloud-08-provider-product-hystrix-8001服务
      serviceId: microservice-product #指定需要被路由管理的服务ID,会自动从Eureka中找到此服务器的IP和端口
      stripPrefix: false #代理转发去掉前缀,false:表明代理转发时不去掉前缀:例如:为true时,请求/product/get/1,代理转发到/get/1
#这里我们开始添加Zuul的配置

(3)接下来我们对启动类进行配置,使用@EnableZuulProxy注解标注启动类,开启Zuul功能;

@EnableZuulProxy //开启Zuul功能(注意我们开启的是zuul代理)
@SpringBootApplication
public class ZuulServer_7001 {
    public static void main(String[] args) {
        SpringApplication.run(ZuulServer_7001.class, args);
    }
}

(4)一切准备工作就绪之后,我们开始新建一个过滤器类;Zuul的核心就说过滤器类,通过过滤器实现请求过滤(转发)和身份验证;
4.1. 自定义过滤器类需要继承自Zuulfilter,ZuulFilter是一个抽象类,需要覆盖里面的方法,如下:
**filterType():**返回字符串代表过滤器的类型,返回值有:
pre:在请求路由之前执行
route:在请求路由时调用
post:请求路由之后调用, 也就是在route和errror过滤器之后调用
error:处理请求发生错误时调用
**filterOrder():**此方法返回整型数值,通过此数值来定义过滤器的执行顺序,数字越小优先级越高。
**shouldFilter():**返回Boolean值,判断该过滤器是否执行。返回true表示要执行此过虑器,false不执行。
**run():**过滤器的业务逻辑
贴上代码更直观理解:

/**
 * Zuul核心时过滤器,通过过滤器实现请求过滤和身份验证
 * 自定义过滤器类需要继承ZuulFilter,Zuulfilter时一个抽象类
 * 需要覆盖其中的四个方法
 */
@Component //这里我们需要把该类注入进容器中
public class LoginFilter extends ZuulFilter {
    //在开发过程中,我们往往需要打印日志信息,就需要在类的第一行写上如下代码:
    Logger logger =  LoggerFactory.getLogger(getClass());

    @Override
    public String filterType() {
        return "pre"; //请求路由前调用
    }

    @Override
    public int filterOrder() {
        return 1; //int值来定义过滤器的执行顺序,数值越小优先级越高
    }

    @Override
    public boolean shouldFilter() {
        return true;//该过滤器是否执行,True为执行,反之不执行
    }

    @Override
    public Object run() throws ZuulException {
        //这里我们添加一个身份验证的逻辑
        RequestContext context = RequestContext.getCurrentContext();
        HttpServletRequest request = context.getRequest();
        //获取请求参数Token的值
        String token = request.getParameter("token");
        if (token == null) {
            logger.warn("此操作需要先登录系统");
            //logger.warining("此操作需要先登录系统"); //这个是其他依赖的写法
            context.setSendZuulResponse(false);//是否拒绝访问:否
            context.setResponseStatusCode(200); //设置响应状态码
            //响应结果
            try {
                context.getResponse().getWriter().write("token is null");

            } catch (IOException e) {
                e.printStackTrace();
            }
            return null;

        }
        logger.info("ok了!!!");
        return null;
    }
}

(这里得强调一下,我们这里导入依赖的时候一定得导入正确!就像这句话: Logger logger = LoggerFactory.getLogger(getClass());没有正确的依赖,运行起来就报错!)

在这里插入图片描述

(5)至此,我们可以开始测试我们写好的Zuul以及过滤器类;
5.1. 首先启动Eureka集群
5.2. 启动我们其中的服务提供者(也就是我们请求转发的测试服务)
5.3. 启动我们的路由服务
5.4. 这时候,我们可以发现通过路由(7001)直接访问会弹出”token为空“的字样,是因为我们写了一个自定义过滤器类,里面添加了这一逻辑!在这里插入图片描述
5.5. 于是我们在访问的URL后面随机带一个字符串表示其为Token,保证其不为空就能访问成功!
在这里插入图片描述

发布了26 篇原创文章 · 获赞 9 · 访问量 745

猜你喜欢

转载自blog.csdn.net/z19950712/article/details/104007544