Spring-Cloud of Zuul routing gateway -6

  First, why the need Zuul?

  Zuul as a gateway component micro-service system for building border services (Edge Service), dedicated to dynamic routing, filtering, monitoring, security, and elastic stretch. Zuul as a routing gateway component, has a very important role in the micro-service architecture, mainly in the following six aspects.

  1) Zuul Ribbon and Eureka combined, can achieve intelligent routing and load balancing functions, Zuul able to request multiple service instances to distribute traffic to cluster state by some kind of strategy.

  2) gateway API interface for all services consistent aggregation, and unified external exposure. When the external system call API interface is the gateway of foreign exposure API interface, the external system does not need to know the complexity of the micro-service system for each service call each other. Micro-service system protects the internal micro-services API interface unit to prevent it from being called directly outside world, leading to service external exposure of sensitive information.

  3) Gateway Service can do user authentication and certification authority, prevent illegal operation requested API interface for server protection.

  4) gateway may implement monitoring, real-time log output, the request record.

  5) Gateway can be used to implement traffic monitoring. In the case of high traffic, the service downgrade.

  6) API interfaces separate from the internal service out of convenience to do the test.

  Two, Zuul works

  Zuul is achieved by Servlet, Zuul performed by custom Zuul Servlet (similar DispatcServlet] Spring MVC of the control request. Zuul core is a series of filters, may be performed during an initiation request and returns the response Http series of filters. Zuul comprises the following four filters.  

  1) PRE Filter: It is the specific service request routing prior to the execution of this type of filter can be done to verify the security such as authentication, verification and other parameters.

  2) ROUTING Filter: It is used to route the request to a specific micro-services. By default, it uses network requests Http Client.

  3) POST Filter: It is generally executed request has been routed to the micro-services, as gather statistics, index, and transmit a response to the client.

  4) ERROR filter: it is executed when an error occurs other filters.

  Zuul taken a dynamic read, compile and run these filters. Between the filter can not communicate directly, but through RequestContext shared data objects, each request creates a RequestContext object. Zuul filter has the following key features.

  1) Type (type): Type Zuul filter, the filter type determines at what stage of the requested function, e.g. Pre Post stage like.

  2) Execution Order (order of execution): specifies the execution order of the filter, the smaller the value of the Order, the first execution

  3) Criteria (standard): Filter rows required conditions.

  4) Action (action): If eligible for execution, the execution Action (ie logic code).

  Zuul request lifecycle:
  

  Request When a client request to enter Zuul gateway services gateway to enter the "pre filter , a series of verify operation or judgment and then to the" routing filter "routing forwarding , forwarding to a specific example of the service processing logic, return data after processing when a specific service, and finally processed by a "post filter after the type of processor processed, the Response message returned to the client.

  ZuulServlet is the core of Servlet Zuul, the role of ZuulServlet is to initialize ZuulFilter . And the arrangement of these sequences, a specific logic in the service () method

    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        try {
            ...

       try { this.preRoute(); } catch (ZuulException var12) { this.error(var12); this.postRoute(); return; } try { this.route(); } catch (ZuulException var13) { this.error(var13); this.postRoute(); return; } try { this.postRoute(); } catch (ZuulException var11) { this.error(var11); } } catch (Throwable var14) { this.error(new ZuulException(var14, 500, "UNHANDLED_EXCEPTION_" + var14.getClass().getName())); } finally { RequestContext.getCurrentContext().unset(); } }

  Third, the Zuul build specific applications.

  1) was added dependency:

     <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-zuul</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

  2) Start writing program plus @EnableZuulProxy comment.

package com.cetc;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.netflix.zuul.EnableZuulProxy;

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

  3) joining configuration (service port 8682):

Server: 
  Port: 8682 
the Spring: 
  the Application: 
    name: Zuul 
Eureka: 
  Client: 
    Service - url: 
      defaultzone: HTTP: // 127.0.0.1:8670/eureka/ # actual development recommended way to use the domain name 
Zuul: 
  routes: 
    the Test: 
      path : / the Test / ** 
      url: http://127.0.0.1:8673/ 
    Ribbon: 
      path: / Ribbon / ** 
      serviceId: REST 
    Feign: 
      path: / Feign / ** 
      serviceId: Feign

  Note: The above basic configuration:

  zuul.routes.test / ribbon / feign: The test / ribbon / feign custom configuration.

  path: the path for the proxy Zuul.

  serviceId: the name of the service.

  url: for the specific address, load balancing issues. (Mainly for external services added)

  4) Test: start the project include Eureka-Server, 2 Ge Eureka-Client, Ribbon of Rest, Feign and Zuul. Ports are: 8670,8673 / 8674,8675,8676,8682.

  

 

 

   Results are as follows:

  

  Test interface:

  http://127.0.0.1:8682/test/api/test/getPort

  http://127.0.0.1:8682/ribbon/api/ribbon/getPort

  http://127.0.0.1:8682/feign/api/feign/getPort

  Visible visit here: use url way no default load balancing , it is not recommended to use ribbon and feign are two ways you can perform load balancing.

  5) If you want to use the url way to do load balancing then it would have to maintain their own access list. Configuration is as follows:

zuul:
  routes:
    test-r:
      path: /test-r/**
      serviceId: test-r
test-r:
  ribbon:
    listOfServers: http://127.0.0.1:8673/, http://127.0.0.1:8674/
ribbon:
  eureka:
    enabled: false

  Description: Disables here does not affect the ribbon in front of the configured services. But it will affect the rest ribbon Zuul call or feign service , if there is load balancing these two services, then call when there is load balancing problem. It is generally recommended not to use this .

  test:

  

  6) If you want to join a specific version number, you can add the following configuration:

zuul:
  prefix: /v1

  Access way: HTTP: //127.0.0.1: 8682 / v1 / the Test / API / the Test / getPort. Join the version number in the link.

  Four, Zuul join fuse:

  The default implementation FallbackProvider interface can be added to the vessel

package org.springframework.cloud.netflix.zuul.filters.route;

import org.springframework.http.client.ClientHttpResponse;

public interface FallbackProvider {
    String getRoute();

    ClientHttpResponse fallbackResponse(String var1, Throwable var2);
}

  Implemented as:

package com.cetc.config;

import org.springframework.cloud.netflix.zuul.filters.route.FallbackProvider;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.client.ClientHttpResponse;
import org.springframework.stereotype.Component;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;

@Component
public class ZuulFallbackProvider implements FallbackProvider {

    @Override
    public String getRoute() {
        return "*";
    }

    @Override
    public ClientHttpResponse fallbackResponse(String route, Throwable cause) {
        return new ClientHttpResponse() {
            @Override
            public HttpStatus getStatusCode() throws IOException {
                return HttpStatus.OK;
            }

            @Override
            public int getRawStatusCode() throws IOException {
                return 200;
            }

            @Override
            public String getStatusText() throws IOException {
                return "OK";
            }

            @Override
            public void close() {

            }

            @Override
            public InputStream getBody() throws IOException {
                return new ByteArrayInputStream("error".getBytes());
            }

            @Override
            public HttpHeaders getHeaders() {
                HttpHeaders httpHeaders = new HttpHeaders();
                httpHeaders.setContentType(MediaType.APPLICATION_JSON_UTF8);
                return httpHeaders;
            }
        };
    }
}

  Test: Close feign test interface:

  

  Fifth, the custom filter in the Zuul:

package com.cetc.filter;

import com.netflix.zuul.ZuulFilter;
import com.netflix.zuul.context.RequestContext;
import com.netflix.zuul.exception.ZuulException;
import org.springframework.cloud.netflix.zuul.filters.support.FilterConstants;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Component; import org.springframework.util.StringUtils; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; @Component public classCustomZuulFilter the extends ZuulFilter { @Override public String filterType () { return FilterConstants.PRE_TYPE; } @Override public int filterOrder () { return 0 ; } @Override public Boolean shouldFilter () { // is turned filtering logic, run after run on ( ) The method of return to true ; } @Override public Object RUN () throws ZuulException { the requestContext requestContext = RequestContext.getCurrentContext(); HttpServletRequest request = requestContext.getRequest(); String token = request.getParameter("token"); if (StringUtils.isEmpty(token)) { HttpServletResponse response = requestContext.getResponse(); requestContext.setSendZuulResponse(false); requestContext.setResponseStatusCode(HttpStatus.UNAUTHORIZED.value()); try { response.getWriter().write("token is empty"); } catch (IOException e) { e.printStackTrace(); } } return null; } }

  test:

  

  It is not feeling a little taste of such a verification. Filtered through a custom filter can achieve the purpose of the request. Implementation process is as follows:

  

 

 

   Sixth, the common use of Zuul.

  Zuul is similar to using Spring MVC DispatchServlet achieved, using asynchronous occlusion model , so performance is worse than Nginx . Since Netflix Zuul, and other components can complement each other, seamless integration Zuul can easily achieve load balancing, intelligent routing and fuse functions. In most cases Zuul are in the form of clusters in the. Due to the lateral expansion of capacity Zuul is very good, so when the load is too high, performance bottlenecks can be solved by adding examples .

  1) A common use is to use different channels to Zuul different route , such as a mobile terminal a common gateway instance Zuul. Web gateway Zuul end with another example, other routing client Zuul with another example.

  

 

   2) Another common cluster by Ngnix Zuul and bonded to each other to do load balancing. Most exposed to the outside is Ngnix master-slave dual hot standby carried Keepalive , Ngnix through some kind of routing policy, forwards the request is routed to the cluster Zuul, Zuul request will eventually be distributed to specific services.

  

Guess you like

Origin www.cnblogs.com/ll409546297/p/11898404.html