Nepxion Discovery [explore] microservice enterprise solution

Nepxion Discovery [explore] microservice enterprise solution

The user guide for Nepxion Discovery is based on Spring Cloud Greenwich, Finchley and Hoxton versions. Users need to modify Edgware version by themselves. The main functions involved in the use guide include:

  • The gateway is the route trigger point for the full link gray routing based on Header transmission. The configuration center is used to configure the routing rule mapping, and the Header information is embedded in the gateway filter. The routing rules are transmitted to the full link service. Routing methods mainly include version and region matching routing, version and region weight routing, and machine IP address and port based routing
  • Full link gray publishing based on rule subscription. The configuration center is used to configure gray rule mapping in the whole link service, and all services subscribe to a shared configuration. The publishing methods mainly include the matching publishing of versions and regions, and the weight publishing of versions and regions
  • Full link service isolation. It includes registration isolation, consumer isolation and provider service isolation. The example only provides Group based isolation. In addition, those not covered in this article include:
    • Registration isolation: Registration isolation of IP addresses in the blacklist / whitelist, and registration isolation of the maximum number of registrations
    • Consumer isolation: consumer isolation of IP addresses in the blacklist / whitelist
  • Full link service current limiting, fusing and degrading permissions, integrating Alibaba Sentinel, organically integrating gray-scale routing, expanding the mechanism of LimitApp, and realizing combined protection mechanisms through dynamic Http Header, including protection mechanisms based on service name, gray-scale group, gray-scale version, gray-scale area, machine address and port, You can customize any combination of business parameters to realize this function. Support native flow control rules, degradation rules, authorization rules, system rules, and hotspot parameter flow control rules
  • Full link call chain. It includes header mode and log mode. Header mode is integrated within the framework, and log mode is output through MDC (it needs to be integrated by the user)
  • Dual active multi machine room switching support in the same city. It is included in "full link gray routing based on Header delivery"
  • Database gray publishing. Built in simple database gray publishing strategy, which is beyond the scope of this article
  • Automated testing of gray routing and publishing
  • Docker containerization and seamless support deployment of Kubernetes platform

[Nacos] a new generation of middleware developed by Alibaba middleware department, which integrates service registration and discovery center and configuration center. It is a service infrastructure for building "service" centered modern application architecture (such as micro service paradigm and cloud native paradigm), supports the discovery, configuration and management of almost all mainstream types of "services", and more agile and easy to build, deliver and manage micro service platform

[Sentinel] a new generation of distributed system traffic guards developed by Alibaba middleware department, which takes traffic as the starting point and protects the stability of services from multiple dimensions such as traffic control, fuse degradation and system load protection. It has undertaken the core scenarios of Alibaba's double 11 traffic promotion in recent 10 years, such as spike (i.e. sudden traffic control within the range of system capacity), message peak cutting and valley filling, cluster traffic control, real-time fusing downstream unavailable applications, etc

[Spring Cloud Alibaba] the Spring Cloud enhancement suite developed by Alibaba's middleware department is committed to providing a one-stop solution for microservice development. This project contains the necessary components for developing distributed application microservices, so that developers can easily use these components to develop distributed application services through the Spring Cloud programming model. Relying on Spring Cloud Alibaba, you only need to add some annotations and a small amount of configuration to connect Spring Cloud applications to Alibaba microservice solutions and quickly build distributed application systems through Alibaba middleware

The example takes Nacos as the service registry and configuration center (users can change to other service registries and configuration centers by themselves), integrates Spring Cloud Alibaba, calls services of two versions or regions through Gateway and Zuul, and simulates the functions of Gateway gray routing and service gray weight

If users need more powerful functions, please refer to Source Homepage . There are many rules and policies. Users are requested to choose the most suitable method for their business scenarios

catalogue

Related links

Source Homepage

Source Homepage

Guide home page

Guide home page

Document home page

Document home page

Related diagram

Deployment architecture topology

[the external chain picture transfer fails. The source station may have an anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-zuscbudp-157076884993)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/BasicTopology.jpg )]

Service governance architecture

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (IMG siuglujw-1570768850003)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/Govern.jpg )]

Gray mode difference diagram

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-0ugbfsld-157076885005)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/Difference.jpg )]

Environment construction

  • Download code
    • Git clone https://github.com/Nepxion/DiscoveryGuide.git
  • Code import IDE
  • Download Nacos server
  • Start the Nacos server
    • Under Windows environment, run startup.exe under bin directory cmd
    • Under Linux environment, run startup.exe under bin directory sh

Start service

  • In IDE, start four application services and two gateway services as follows:

Class name

Microservices

Service port

edition

region

DiscoveryGuideServiceA1.java

A1

3001

1.0

dev

DiscoveryGuideServiceA2.java

A2

3002

1.1

qa

DiscoveryGuideServiceB1.java

B1

4001

1.0

qa

DiscoveryGuideServiceB2.java

B2

4002

1.1

dev

DiscoveryGuideGateway.java

Gateway

5001

1.0

nothing

DiscoveryGuideZuul.java

Zuul

5002

1.0

nothing

Note: start up is not in sequence

Environmental validation

  • Import the test script of Postman, Script address
  • Execute "Nepxion" - > "Discovery guide Gateway interface" - > "Gateway gateway call example" under the directory structure in Postman. The call address is http://localhost:5001/discovery-guide-service-a/invoke/gateway , the relevant Header values have been preset for developers to modify. Test the call result through the Spring Cloud Gateway gateway. The result is in the following format:
gateway -> discovery-guide-service-a[192.168.0.107:3001][V=1.0][R=dev][G=discovery-guide-group] 
-> discovery-guide-service-b[192.168.0.107:4001][V=1.0][R=qa][G=discovery-guide-group]
  • Execute "Nepxion" - > "Discovery guide gateway interface" - > "Zuul gateway call example" under the directory structure in Postman. The call address is http://localhost:5002/discovery-guide-service-a/invoke/zuul , the relevant Header values have been preset for developers to modify. Test the calling result through Zuul gateway, and the result is in the following format:
zuul -> discovery-guide-service-a[192.168.0.107:3001][V=1.0][R=dev][G=discovery-guide-group] 
-> discovery-guide-service-b[192.168.0.107:4001][V=1.0][R=qa][G=discovery-guide-group]
  • The above steps are executed each time the rule policy is changed, and verify whether the result is the same as the expected value of the rule policy

Gateway gray routing strategy based on Header delivery mode

Gray routing architecture

Multi version gray routing architecture diagram

Multi region gray routing architecture

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-eig1z6ve-1570768850007)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/RouteRegion.jpg )]

Multi IP and port gray routing architecture diagram

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-soqjd6yw-1570768850008)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/RouteAddress.jpg )]

Configure gateway routing policy

In the Nacos configuration center, add the gateway gray routing strategy

Version matching gray routing strategy

Add the grayscale policy of Spring Cloud Gateway based on version matching routing. The Group is discovery guide Group and the Data Id is discovery guide gateway. The policy content is as follows. All calls initiated from Spring Cloud Gateway follow the service with version 1.0:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <strategy>
        <version>1.0</version>
    </strategy>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-fk6uaan2-157076885009)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide2-1.jpg )]

The version of each service call can be specified by itself. See article 2 below. When all services choose the same version, it can be simplified to the first item below

1. <version>1.0</version>
2. <version>{"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.0"}</version>

If the above expression does not meet the requirements, wildcards can also be used (for specific usage, refer to Spring AntPathMatcher)

* - Indicates that the call scope is all versions of all services
1.* - Indicates that the call scope is all versions beginning with 1 of all services

perhaps

"discovery-guide-service-b":"1.*;1.2.?"

Indicates the version of the discovery-guide-service-b service. The calling range is all versions beginning with 1 or all versions beginning with 1.2 (the end must be 1 character)

Version weight gray routing strategy

Add the gray-scale policy of version weight based routing for Spring Cloud Gateway. The Group is discovery guide Group and the Data Id is discovery guide gateway. The policy contents are as follows. The traffic calls of version 1.0 and 1.1 initiated from Spring Cloud Gateway are 90% and 10%:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <strategy>
        <version-weight>1.0=90;1.1=10</version-weight>
    </strategy>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-1ierevj4-1570768850014)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide2-2.jpg )]

The version weight of each service call can be specified by itself, as shown in Article 2 below. When all services choose the same version weight, it can be simplified to the first item below

1. <version-weight>1.0=90;1.1=10</version-weight>
2. <version-weight>{"discovery-guide-service-a":"1.0=90;1.1=10", "discovery-guide-service-b":"1.0=90;1.1=10"}</version-weight>

Region matching gray routing strategy

Zuul's gray-scale policy based on region matching routing is added. The Group is discovery guide Group and the Data Id is discovery guide zuul. The content of the policy is as follows to realize that all calls initiated from zuul go through the service with region dev:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <strategy>
        <region>dev</region>
    </strategy>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (IMG lwcoweox-1570768850016)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide2-3.jpg )]

The region of each service call can be specified by itself, as shown in Article 2 below. When all services are selected in the same region, it can be simplified to the first item below

1. <region>dev</region>
2. <region>{"discovery-guide-service-a":"dev", "discovery-guide-service-b":"dev"}</region>

If the above expression does not meet the requirements, wildcards can also be used (for specific usage, refer to Spring AntPathMatcher)

* - Indicates that the call scope is all regions of all services
d* - Indicates that the call scope is all services d All areas at the beginning

perhaps

"discovery-guide-service-b":"d*;q?"

Indicates that the region calling range of the discovery-guide-service-b service is all regions starting with d or all regions starting with q (the end must be 1 character)

Regional weight gray routing strategy

Add Zuul's gray-scale strategy based on area weight routing. The Group is discovery guide Group and the Data Id is discovery guide Zuul. The content of the strategy is as follows. The calls initiated from Zuul are 85% for dev area traffic calls and 15% for qa area traffic calls:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <strategy>
        <region-weight>dev=85;qa=15</region-weight>
    </strategy>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-gdxry0vf-1570768850019)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide2-4.jpg )]

The area weight of each service call can be specified by itself, as shown in Article 2 below. When all services select the same area weight, it can be simplified to the first item below

1. <region-weight>dev=85;qa=15</region-weight>
2. <region-weight>{"discovery-guide-service-a":"dev=85;qa=15", "discovery-guide-service-b":"dev=85;qa=15"}</region-weight>

Set the gateway gray routing policy through other methods

In addition to publishing gray scale routing rules through the configuration center above, there are three ways:

Incoming gray level routing policy through front end

The gray-scale routing strategy is transmitted through the front-end (Postman) mode instead of the configuration center mode to transmit the full link routing strategy. Note: when both the configuration center and the interface are configured, the interface input takes precedence

  • For version matching policy, choose one of the following Header formats:
1. n-d-version=1.0
2. n-d-version={"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.0"}
  • For version weight policy, choose one of the following Header formats:
1. n-d-version-weight=1.0=90;1.1=10
2. n-d-version-weight={"discovery-guide-service-a":"1.0=90;1.1=10", "discovery-guide-service-b":"1.0=90;1.1=10"}
  • For region matching policy, choose one of the following Header formats:
1. n-d-region=qa
2. n-d-region={"discovery-guide-service-a":"qa", "discovery-guide-service-b":"qa"}
  • For the region weight policy, choose one of the following Header formats:
1. n-d-region-weight=dev=99;qa=1
2. n-d-region-weight={"discovery-guide-service-a":"dev=99;qa=1", "discovery-guide-service-b":"dev=99;qa=1"}
  • Machine IP address and port policy:
n-d-address={"discovery-guide-service-a":"127.0.0.1:3001", "discovery-guide-service-b":"127.0.0.1:4002"}

When the external value Header is passed, the gateway also sets and passes the Header with the same name. It needs to decide which Header to pass to the subsequent service. It needs to be controlled by the following switches:

# When the external value Header is passed, the gateway also sets and passes the Header with the same name. It needs to decide which Header to pass to the subsequent service. If the following switch is true, the gateway setting takes precedence; otherwise, the externally transmitted value takes precedence. If it is missing, it defaults to true
spring.application.strategy.gateway.header.priority=false
# When the gateway is set as the priority, the gateway does not configure the Header, but the external Header is configured, and the external Header is still ignored. If it is missing, it defaults to true
spring.application.strategy.gateway.original.header.ignored=true

# When the external value Header is passed, the gateway also sets and passes the Header with the same name. It needs to decide which Header to pass to the subsequent service. If the following switch is true, the gateway setting takes precedence; otherwise, the externally transmitted value takes precedence. If it is missing, it defaults to true
spring.application.strategy.zuul.header.priority=false
# When the gateway is set as the priority, the gateway does not configure the Header, but the external Header is configured, and the external Header is still ignored. If it is missing, it defaults to true
spring.application.strategy.zuul.original.header.ignored=true

Customize the gray routing policy in the gateway filter through service parameters

The whole link gray-scale routing strategy is transmitted by transmitting Http Header through gateway filter. The following code is only applicable to Zuul and Spring Cloud Gateway gateways. This method is not required for Service microservices

  • Custom way of mapping built-in policy resolution to filter

Add the resolution policy of Spring Cloud Gateway, with Group as discovery guide Group and Data Id as discovery guide gateway, or add the resolution policy of Spring Cloud Gateway, with Group as discovery guide Group and Data Id as discovery guide zuul. See the following XML content for the policy content, which expresses the functional logic:

1. When an external call with Http Header Values in a=1 meanwhile b=2
   <condition>In node header="a=1;b=2"Corresponding version-id="version-route1",Find below
   <route>In node id="version-route1" type="version"Then the route is:
   {"discovery-guide-service-a":"1.1", "discovery-guide-service-b":"1.1"}

2. When an external call with Http Header Values in a=1
   <condition>In node header="a=1"Corresponding version-id="version-route2",Find below
   <route>in id="version-route2" type="version"Then the route is:
   {"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.1"}

3. When an external call with Http Header None of the values in the hit, find the above
   <strategy>The global default route in the node, then the route is:
   {"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.0"}

4. A total of 5 types of policy resolution are supported, which can be used alone or multiple combinations:
   1)version Version routing
   2)region Regional routing
   3)address Machine address routing
   4)version-weight Version weight routing
   5)region-weight Area weight routing
<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <!-- be based on Http Header Policy route for delivery, global default route -->
    <strategy>
        <version>{"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.0"}</version>
    </strategy>

    <!-- be based on Http Header The delivered policy routing, customized control, and binding with business parameters. If not, the above global default route is executed -->
    <strategy-customization>
        <conditions>
            <condition id="condition1" header="a=1" version-id="version-route2"/>
            <condition id="condition2" header="a=1;b=2" version-id="version-route1"/>
        </conditions>

        <routes>
            <route id="version-route1" type="version">{"discovery-guide-service-a":"1.1", "discovery-guide-service-b":"1.1"}</route>
            <route id="version-route2" type="version">{"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.1"}</route>
        </routes>
    </strategy-customization>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-6wy7dqik-1570768850021)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide2-7.jpg )]

  • User override filter customization

Inherit the GatewayStrategyRouteFilter or ZuulStrategyRouteFilter, override one or more of the following methods, and override the built-in filter class of the framework through @ Bean

protected String getRouteVersion();

protected String getRouteRegion();

protected String getRouteAddress();

GatewayStrategyRouteFilter example

Select different routing paths according to different headers in the code

// It is applicable to A/B Testing or determine the gray routing path according to a service parameter. The A/B paths can be configured separately in combination with the configuration center, which can be dynamically changed and notified
// When the user from the Header is Zhang San, execute a routing path; For Li Si, execute another routing path
public class MyGatewayStrategyRouteFilter extends DefaultGatewayStrategyRouteFilter {
    private static final String DEFAULT_A_ROUTE_VERSION = "{\"discovery-guide-service-a\":\"1.0\", \"discovery-guide-service-b\":\"1.1\"}";
    private static final String DEFAULT_B_ROUTE_VERSION = "{\"discovery-guide-service-a\":\"1.1\", \"discovery-guide-service-b\":\"1.0\"}";

    @Value("${a.route.version:" + DEFAULT_A_ROUTE_VERSION + "}")
    private String aRouteVersion;

    @Value("${b.route.version:" + DEFAULT_B_ROUTE_VERSION + "}")
    private String bRouteVersion;

    @Override
    public String getRouteVersion() {
        String user = strategyContextHolder.getHeader("user");

        if (StringUtils.equals(user, "zhangsan")) {
            return aRouteVersion;
        } else if (StringUtils.equals(user, "lisi")) {
            return bRouteVersion;
        }

        return super.getRouteVersion();
    }
}

In the configuration class, create the filter class in @ Bean mode to override the built-in filter class of the framework

@Bean
public GatewayStrategyRouteFilter gatewayStrategyRouteFilter() {
    return new MyGatewayStrategyRouteFilter();
}

ZuulStrategyRouteFilter example

Select different routing paths according to different headers in the code

// It is applicable to A/B Testing or determine the gray routing path according to a service parameter. The A/B paths can be configured separately in combination with the configuration center, which can be dynamically changed and notified
// When the user from the Header is Zhang San, execute a routing path; For Li Si, execute another routing path
public class MyZuulStrategyRouteFilter extends DefaultZuulStrategyRouteFilter {
    private static final String DEFAULT_A_ROUTE_VERSION = "{\"discovery-guide-service-a\":\"1.0\", \"discovery-guide-service-b\":\"1.1\"}";
    private static final String DEFAULT_B_ROUTE_VERSION = "{\"discovery-guide-service-a\":\"1.1\", \"discovery-guide-service-b\":\"1.0\"}";

    @Value("${a.route.version:" + DEFAULT_A_ROUTE_VERSION + "}")
    private String aRouteVersion;

    @Value("${b.route.version:" + DEFAULT_B_ROUTE_VERSION + "}")
    private String bRouteVersion;

    @Override
    public String getRouteVersion() {
        String user = strategyContextHolder.getHeader("user");

        if (StringUtils.equals(user, "zhangsan")) {
            return aRouteVersion;
        } else if (StringUtils.equals(user, "lisi")) {
            return bRouteVersion;
        }

        return super.getRouteVersion();
    }
}

In the configuration class, create the filter class in @ Bean mode to override the built-in filter class of the framework

@Bean
public ZuulStrategyRouteFilter zuulStrategyRouteFilter() {
    return new MyZuulStrategyRouteFilter();
}

Customize the gray routing policy in the policy class through service parameters

Customize the gray routing policy by policy. The following code is applicable to both Zuul and Spring Cloud Gateway gateways and Service microservices. At the same time, this method must be added to gateways and services in the whole link

// It realizes the combination policy, version routing policy + area routing policy + IP and port routing policy + user-defined policy
public class MyDiscoveryEnabledStrategy extends DefaultDiscoveryEnabledStrategy {
    private static final Logger LOG = LoggerFactory.getLogger(MyDiscoveryEnabledStrategy.class);

    // Policy the Header parameter (e.g. mobile) passed from the Rest call
    @Override
    public boolean apply(Server server) {
        String mobile = strategyContextHolder.getHeader("mobile");
        String serviceId = pluginAdapter.getServerServiceId(server);
        String version = pluginAdapter.getServerVersion(server);
        String region = pluginAdapter.getServerRegion(server);

        LOG.info("Load balancing user customization trigger: mobile={}, serviceId={}, version={}, region={}", mobile, serviceId, version, region);

        if (StringUtils.isNotEmpty(mobile)) {
            // The mobile phone number starts with mobile 138 and is routed to the 1.0 service
            if (mobile.startsWith("138") && StringUtils.equals(version, "1.0")) {
                return true;
                // The mobile phone number starts with Unicom 133 and is routed to the service of version 2.0
            } else if (mobile.startsWith("133") && StringUtils.equals(version, "1.1")) {
                return true;
            } else {
                // In other cases, refuse the request directly
                return false;
            }
        }

        return true;
    }
}

Create a policy class in the configuration class in @ Bean mode

@Bean
public DiscoveryEnabledStrategy discoveryEnabledStrategy() {
    return new MyDiscoveryEnabledStrategy();
}

In the gateway and service, the user-defined grayscale routing policy based on Rest Header is supported. In addition, the service also supports the user-defined grayscale routing policy based on Rpc method parameter transmission, which includes interface name, method name, parameter name or parameter value. The following example shows that the user-defined combined gray routing policy based on Rest Header transfer and Rpc method parameter transfer is enabled in the service at the same time

// It realizes the combination policy, version routing policy + area routing policy + IP and port routing policy + user-defined policy
public class MyDiscoveryEnabledStrategy implements DiscoveryEnabledStrategy {
    private static final Logger LOG = LoggerFactory.getLogger(MyDiscoveryEnabledStrategy.class);

    @Autowired
    private PluginAdapter pluginAdapter;

    @Autowired
    private ServiceStrategyContextHolder serviceStrategyContextHolder;

    @Override
    public boolean apply(Server server) {
        boolean enabled = applyFromHeader(server);
        if (!enabled) {
            return false;
        }

        return applyFromMethod(server);
    }

    // Select the service instance that executes the call request according to the Header parameter (e.g. mobile) passed from the Rest call
    private boolean applyFromHeader(Server server) {
        String mobile = serviceStrategyContextHolder.getHeader("mobile");
        String serviceId = pluginAdapter.getServerServiceId(server);
        String version = pluginAdapter.getServerVersion(server);
        String region = pluginAdapter.getServerRegion(server);

        LOG.info("Load balancing user customization trigger: mobile={}, serviceId={}, version={}, region={}", mobile, serviceId, version, region);

        if (StringUtils.isNotEmpty(mobile)) {
            // The mobile phone number starts with mobile 138 and is routed to the 1.0 service
            if (mobile.startsWith("138") && StringUtils.equals(version, "1.0")) {
                return true;
                // The mobile phone number starts with Unicom 133 and is routed to the service of version 2.0
            } else if (mobile.startsWith("133") && StringUtils.equals(version, "1.1")) {
                return true;
            } else {
                // In other cases, refuse the request directly
                return false;
            }
        }

        return true;
    }

    // Select the service instance to execute the call request according to the method parameters (such as interface name, method name, parameter name or parameter value) passed from the RPC call
    // This example only works on the discovery-guide-service-a service
    @SuppressWarnings("unchecked")
    private boolean applyFromMethod(Server server) {
        Map<String, Object> attributes = serviceStrategyContextHolder.getRpcAttributes();
        String serviceId = pluginAdapter.getServerServiceId(server);
        String version = pluginAdapter.getServerVersion(server);
        String region = pluginAdapter.getServerRegion(server);

        LOG.info("Load balancing user customization trigger: attributes={}, serviceId={}, version={}, region={}", attributes, serviceId, version, region);

        if (attributes.containsKey(ServiceStrategyConstant.PARAMETER_MAP)) {
            Map<String, Object> parameterMap = (Map<String, Object>) attributes.get(ServiceStrategyConstant.PARAMETER_MAP);
            String value = parameterMap.get("value").toString();
            if (StringUtils.isNotEmpty(value)) {
                // The input value contains dev, which is routed to the service in the dev area
                if (value.contains("dev") && StringUtils.equals(region, "dev")) {
                    return true;
                    // The input value contains qa and is routed to the service in the qa area
                } else if (value.contains("qa") && StringUtils.equals(region, "qa")) {
                    return true;
                } else {
                    // In other cases, directly through the request
                    return true;
                }
            }
        }

        return true;
    }
}

The function needs to be turned on through the following switches

# When starting and closing the routing policy, the call of RPC mode is intercepted. If it is missing, it defaults to false
spring.application.strategy.rpc.intercept.enabled=true

Configure front-end gray-scale gateway gray-scale routing combined strategy

When multiple versions of current end (e.g. APP) and back-end microservices exist at the same time, the "front-end grayscale & gateway grayscale routing combined strategy" can be implemented

For example, there are versions 1.0 and 2.0 in the front end and versions 1.0 and 2.0 in the microservice. Due to the incompatibility of versions (version 1.0 in the front end can only call version 1.0 of the microservice, and version 2.0 in the front end can only call version 2.0 of the microservice), when the front end calls the gateway, it can pass its version number to the gateway through the Header. According to the version number of the front end, To route the corresponding version of microservices

This scenario can be solved by the scheme of "customizing gray routing policy in gateway filter through service parameters", as follows:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <strategy-customization>
        <conditions>
            <condition id="condition1" header="app-version=1.0" version-id="version-route1"/>
            <condition id="condition2" header="app-version=2.0" version-id="version-route2"/>
        </conditions>

        <routes>
            <route id="version-route1" type="version">{"discovery-guide-service-a":"1.0", "discovery-guide-service-b":"1.0"}</route>
            <route id="version-route2" type="version">{"discovery-guide-service-a":"1.1", "discovery-guide-service-b":"1.1"}</route>
        </routes>
    </strategy-customization>
</rule>

The above configuration simulates two independent and undisturbed call paths in the whole link:

1. APP v1.0 -> gateway -> A service v1.0 -> B service v1.0
2. APP v1.1 -> gateway -> A service v1.1 -> B service v1.1

Full link gray Publishing Rules Based on subscription

In the Nacos configuration center, add full link gray Publishing Rules Note: this function will overlap with the gateway gray routing and gray weight functions. In order not to affect the demonstration effect, please clear the gateway gray routing policy first

Configure full link gray matching rules

Version matching grayscale rule

Add the grayscale rule for version matching. The Group is discovery guide Group, and the Data Id is discovery guide Group (global publishing, both are Group names). The content of the rule is as follows: version 1.0 of a service can only access version 1.0 of b service, and version 1.1 of a service can only access version 1.1 of b service:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <version>
            <service consumer-service-name="discovery-guide-service-a" provider-service-name="discovery-guide-service-b" consumer-version-value="1.0" provider-version-value="1.0"/>
            <service consumer-service-name="discovery-guide-service-a" provider-service-name="discovery-guide-service-b" consumer-version-value="1.1" provider-version-value="1.1"/>
        </version>
    </discovery>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-8noczb6r-1570768850022)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide3-1.jpg )]

Region matching gray rule

Add gray rules for region matching. The Group is discovery guide Group, and the Data Id is discovery guide Group (global publishing, both are Group names). The rules are as follows: a service in dev region can only access b service in dev region, and a service in qa region can only access b service in qa region:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <region>
            <service consumer-service-name="discovery-guide-service-a" provider-service-name="discovery-guide-service-b" consumer-region-value="dev" provider-region-value="dev"/>
            <service consumer-service-name="discovery-guide-service-a" provider-service-name="discovery-guide-service-b" consumer-region-value="qa" provider-region-value="qa"/>
        </region>
    </discovery>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-txms36fo-1570768850029)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide3-2.jpg )]

Configure full link gray weight rules

Global version weight gray rule

Gray level rule for adding global version weight. The Group is discovery guide Group, and the Data Id is discovery guide Group (global publishing, both are Group names). The content of the rule is as follows: the service with version 1.0 provides 90% traffic, and the service with version 1.1 provides 10% traffic:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <weight>
            <version provider-weight-value="1.0=90;1.1=10"/>
        </weight>
    </discovery>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-jpmzeaty-1570768850030)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide4-1.jpg )]

Local version weight gray rule

Gray level rules that add the weight of local versions. The Group is discovery guide Group, and the Data Id is discovery guide Group (global publishing, both are Group names). The rules are as follows: version 1.0 of a service provides 90% of the traffic, and version 1.1 provides 10% of the traffic; b service version 1.0 provides 20% traffic and version 1.1 provides 80% traffic:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <weight>
            <service provider-service-name="discovery-guide-service-a" provider-weight-value="1.0=90;1.1=10" type="version"/>
            <service provider-service-name="discovery-guide-service-b" provider-weight-value="1.0=20;1.1=80" type="version"/>
        </weight>
    </discovery>
</rule>

Global region weight gray rule

The grayscale rule for increasing the weight of the global region. The Group is discovery guide Group, and the Data Id is discovery guide Group (global publishing, both are Group names). The content of the rule is as follows: the region provides 90% traffic for dev services and 10% traffic for qa services:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <weight>
            <region provider-weight-value="dev=90;qa=10"/>
        </weight>
    </discovery>
</rule>

Local area weight gray rule

Gray scale rule for adding local area weight. Group is discovery guide group and Data Id is discovery guide group (global publishing, both are group names). The content of the rule is as follows: a service dev area provides 90% traffic and qa area provides 10% traffic; The b service dev area provides 20% of the traffic, and the qa area provides 80% of the traffic:

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <weight>
            <service provider-service-name="discovery-guide-service-a" provider-weight-value="dev=90;qa=10" type="region"/>
            <service provider-service-name="discovery-guide-service-b" provider-weight-value="dev=20;qa=80" type="region"/>
        </weight>
    </discovery>
</rule>

Note: local weight priority is higher than global weight, and version weight priority is higher than regional weight

Please execute Postman operation, and carefully observe the probability that the service is called by random weight

Configure the combination rule of full link gray weight and gray version

A combined gray rule is added. The Group is discovery guide Group and the Data Id is discovery guide Group (global publishing, both are Group names). The rule contents are as follows and the functions are realized:

  • a service version 1.0 provides 90% traffic to the gateway, and version 1.1 provides 10% traffic to the gateway
  • a service version 1.0 can only access b service version 1.0, and 1.1 can only access b service version 1.1

The meaning of this function is that the gateway invokes the service with random weight, and the service link invokes it according to version matching

<?xml version="1.0" encoding="UTF-8"?>
<rule>
    <discovery>
        <version>
            <service consumer-service-name="discovery-guide-service-a" provider-service-name="discovery-guide-service-b" consumer-version-value="1.0" provider-version-value="1.0"/>
            <service consumer-service-name="discovery-guide-service-a" provider-service-name="discovery-guide-service-b" consumer-version-value="1.1" provider-version-value="1.1"/>
        </version>

        <weight>
            <service consumer-service-name="discovery-guide-gateway" provider-service-name="discovery-guide-service-a" provider-weight-value="1.0=90;1.1=10" type="version"/>
            <service consumer-service-name="discovery-guide-zuul" provider-service-name="discovery-guide-service-a" provider-weight-value="1.0=90;1.1=10" type="version"/>
        </weight>
    </discovery>
</rule>

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-e4r3ub9t-1570768850036)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide5-1.jpg )]

Graphical interface verification

  • download Source Homepage And import the IDE
  • Start the discovery spring cloud example console / consoleapplication under the source code project
  • Start the discovery console desktop / consolelauncher under the source code project
  • Log in through admin/admin and click "display service topology" to display the following interface [external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-groekf6w-1570768850038)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide5-2.jpg )]
  • Before adding the above rules, select the gateway node, right-click "execute gray routing", add "discovery-guide-service-a" and "discovery-guide-service-b" in order in the pop-up routing interface, and click "execute routing" to display the following interface
  • After adding the above rules, click "execute route" again in the routing interface to display the following interface

Full link service isolation

Group in metadata represents system ID or system logical grouping in a certain sense. Group based policy means that only services in the same system can be called

Registration service isolation

Based on the Group blacklist / whitelist policy, that is, the Group where the current service is located can be registered only if it is not in the blacklist or whitelist of the Group. Just open the following configuration at the gateway or server:

# Start and close registered service isolation (Group blacklist / whitelist based policy). If it is missing, it defaults to false
spring.application.strategy.register.isolation.enabled=true

The blacklist / whitelist is configured as follows:

spring.application.strategy.register.isolation.group.blacklist=
spring.application.strategy.register.isolation.group.whitelist=

Consumer service isolation

Based on whether the Group is the same strategy, that is, the provider list obtained by the consumer must have the same Group. Just open the following configuration at the gateway or server:

# Start and close service isolation on the consumer side (based on whether the Group has the same policy). If it is missing, it defaults to false
spring.application.strategy.consumer.isolation.enabled=true

By changing the Group name of discovery-guide-service-b to another name and executing the Postman call, it will be found that any instance of discovery-guide-service-b cannot be obtained from discovery-guide-service-a. This means that the consumer side of discovery-guide-service-a is isolated

Provide end-to-end service isolation

Based on the policy of whether the Group is the same, that is, if the server is called by the consumer, the groups of the two must be the same, otherwise the call is rejected, and the heterogeneous system can pass the n-d-service-group value through the Header for matching. Just open the following configuration on the server (not applicable to the gateway):

# Start and close service isolation on the provider side (based on whether the Group has the same policy). If it is missing, it defaults to false
spring.application.strategy.provider.isolation.enabled=true

# When implementing the gray-scale routing strategy, you need to specify the scanning path for the business RestController class. This configuration is used for RPC call interception and service isolation at the consumer
spring.application.strategy.scan.packages=com.nepxion.discovery.guide.service.feign

In the Postman call, execute http://localhost:4001/invoke/abc , to call the discovery-guide-service-b service, the following exception will appear. This means that the discovery-guide-service-b provider is isolated

Reject to invoke because of isolation with different service group

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-bo2jls40-1570768850046)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide6-1.jpg )] If the Header of n-d-service-Group = discovery guide Group is added, the two groups remain the same, and the call passes. This is a means to solve the isolation of microservices called by heterogeneous systems [external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-spl5msao-1570768850047)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide6-2.jpg )]

Sentinel based full link service current limiting fuse degradation authority and gray fusion

By integrating Sentinel, this function is realized on the server

Encapsulate NacosDataSource and Apollo DataSource, support two remote configuration centers, Nacos and Apollo, and realize sentinel function with zero code. For more remote configuration centers, please refer to Sentinel's official DataSource and integrate by yourself

1. Nacos of Key Format: Group Configured for metadata[Group name],Data Id by[service name]-[Rule type]
2. Apollo of Key Format:[Group name]-[service name]-[Rule type]

Support the reading logic of remote configuration center and local rule file, that is, read the remote configuration first. If there is no rule or error, read the local rule file. Dynamically realize the hot refresh of rules in the remote configuration center

The following switches are supported to turn on the kinetic energy, which is off by default

# Start and close Sentinel current limiting, degraded fuse authority and other functions. If it is missing, it defaults to false
spring.application.strategy.sentinel.enabled=true

Native Sentinel annotation

Referring to the following code, add @ SentinelResource annotation for the interface method, value is sentinel resource, and blockHandler and fallback are the methods to be executed after protection

@RestController
@ConditionalOnProperty(name = DiscoveryConstant.SPRING_APPLICATION_NAME, havingValue = "discovery-guide-service-b")
public class BFeignImpl extends AbstractFeignImpl implements BFeign {
    private static final Logger LOG = LoggerFactory.getLogger(BFeignImpl.class);

    @Override
    @SentinelResource(value = "sentinel-resource", blockHandler = "handleBlock", fallback = "handleFallback")
    public String invoke(@PathVariable(value = "value") String value) {
        value = doInvoke(value);

        LOG.info("Call path:{}", value);

        return value;
    }

    public String handleBlock(String value, BlockException e) {
        return value + "-> B server sentinel block, cause=" + e.getClass().getName() + ", rule=" + e.getRule() + ", limitApp=" + e.getRuleLimitApp();
    }

    public String handleFallback(String value) {
        return value + "-> B server sentinel fallback";
    }
}

Native Sentinel rules

For the usage of native Sentinel rules, please refer to Sentinel official documents

Flow control rules

Add a rule for service discovery-guide-service-b. the Group is discovery guide Group, and the Data Id is discovery-guide-service-b-sentinel-flow. The content of the rule is as follows:

[
    {
        "resource": "sentinel-resource",
        "limitApp": "default",
        "grade": 1,
        "count": 1,
        "strategy": 0,
        "refResource": null,
        "controlBehavior": 0,
        "warmUpPeriodSec": 10,
        "maxQueueingTimeMs": 500,
        "clusterMode": false,
        "clusterConfig": null
    }
]

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-2cyqzcmx-1570768850048)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide7-1.jpg )]

Degradation rule

Add a rule for service discovery-guide-service-b. the Group is discovery guide Group, and the Data Id is discovery-guide-service-b-sentinel-grade. The content of the rule is as follows:

[
    {
        "resource": "sentinel-resource",
        "limitApp": "default",
        "count": 2,
        "timeWindow": 10,
        "grade": 0,
        "passCount": 0
    }
]

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-nh61wfh9-1570768850049)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide7-2.jpg )]

Authorization rules

Add a rule for service discovery-guide-service-b. the Group is discovery guide Group, and the Data Id is discovery-guide-service-b-sentinel-authority. The content of the rule is as follows:

[
    {
        "resource": "sentinel-resource",
        "limitApp": "discovery-guide-service-a",
        "strategy": 0
    }
]

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-j8ojymqc-1570768850052)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide7-3.jpg )]

System rules

Add the rule of service discovery-guide-service-b. the Group is discovery guide Group, and the Data Id is discovery guide-service-b-sentinel-system. The content of the rule is as follows:

[
    {
        "resource": null,
        "limitApp": null,
        "highestSystemLoad": -1.0,
        "highestCpuUsage": -1.0,
        "qps": 200.0,
        "avgRt": -1,
        "maxThread": -1
    }
]

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-qjopr4db-1570768850054)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide7-4.jpg )]

Hot spot parameter flow control rules

Add a rule for service discovery-guide-service-b. the Group is discovery guide Group, and the Data Id is discovery-guide-service-b-sentinel-param-flow. The content of the rule is as follows:

[
    {
        "resource": "sentinel-resource",
        "limitApp": "default",
        "grade": 1,
        "paramIdx": 0,
        "count": 1,
        "controlBehavior": 0,
        "maxQueueingTimeMs": 0,
        "burstCount": 0,
        "durationInSec": 1,
        "paramFlowItemList": [],
        "clusterMode": false
    }
]

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-cct3gfa1-1570768850056)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/DiscoveryGuide7-5.jpg )]

Protection mechanism based on gray routing and sentinel limitapp extension

This method is effective for all the above five rules, which are described here in terms of authorization rules

In authorization rules, if there are multiple limitapps, they can be separated by ",". "Strategy": 0 means white list, "strategy": 1 means blacklist

Protection mechanism based on service name

Modify the configuration item Sentinel Request Origin Key as the Header name of the service name, and modify limitApp in the authorization rules as the corresponding service name to realize the protection mechanism based on the service name

Configuration item. This configuration item defaults to n-d-service-id and can not be configured

spring.application.strategy.service.sentinel.request.origin.key=n-d-service-id

Add a rule for service discovery-guide-service-b. the Group is discovery-guide-group, and the Data Id is discovery-guide-service-b-sentinel-authority. The content of the rule is as follows, indicating that all discovery-guide-service-a services are allowed to access the discovery-guide-service-b service

[
    {
        "resource": "sentinel-resource",
        "limitApp": "discovery-guide-service-a",
        "strategy": 0
    }
]

Protection mechanism based on gray group

Modify the configuration item Sentinel Request Origin Key as the Header name of the gray-scale group, and modify the limitApp in the authorization rule as the corresponding group name to realize the protection mechanism based on the group name

Configuration item

spring.application.strategy.service.sentinel.request.origin.key=n-d-service-group

The rule of service discovery-guide-service-b is added. The Group is discovery-guide-group, and the Data Id is discovery-guide-service-b-sentinel-authority. The content of the rule is as follows, indicating that all services belonging to my Group are allowed to access service discovery-guide-service-b

[
    {
        "resource": "sentinel-resource",
        "limitApp": "my-group",
        "strategy": 0
    }
]

Protection mechanism based on gray version

Modify the configuration item Sentinel Request Origin Key to the Header name of the grayscale version, and modify the limitApp in the authorization rules to the corresponding version, so as to realize the version based protection mechanism

Configuration item

spring.application.strategy.service.sentinel.request.origin.key=n-d-service-version

The rule of service discovery-guide-service-b is added. The Group is discovery guide Group, and the Data Id is discovery-guide-service-b-sentinel-authority. The content of the rule is as follows, indicating that all services with version 1.0 are allowed to access service discovery-guide-service-b

[
    {
        "resource": "sentinel-resource",
        "limitApp": "1.0",
        "strategy": 0
    }
]

Protection mechanism based on gray region

Modify the configuration item Sentinel Request Origin Key as the Header name of the gray area, and modify the limitApp in the authorization rule as the corresponding area to realize the area based protection mechanism

Configuration item

spring.application.strategy.service.sentinel.request.origin.key=n-d-service-region

The rule of service discovery-guide-service-b is added. The Group is discovery-guide-group, and the Data Id is discovery-guide-service-b-sentinel-authority. The content of the rule is as follows, indicating that all services in the region dev are allowed to access service discovery-guide-service-b

[
    {
        "resource": "sentinel-resource",
        "limitApp": "dev",
        "strategy": 0
    }
]

Protection mechanism based on machine address and port

Modify the configuration item Sentinel Request Origin Key as the Header name of the gray area, and modify the limitApp in the authorization rule as the corresponding area value to realize the protection mechanism based on the machine address and port

Configuration item

spring.application.strategy.service.sentinel.request.origin.key=n-d-service-address

The rule of service discovery-guide-service-b is added. The Group is discovery guide Group, and the Data Id is discovery guide-service-b-sentinel-authority. The content of the rule is as follows, indicating that services with addresses and ports of 192.168.0.88:8081 and 192.168.0.88:8082 are allowed to access service discovery-guide-service-b

[
    {
        "resource": "sentinel-resource",
        "limitApp": "192.168.0.88:8081,192.168.0.88:8082",
        "strategy": 0
    }
]

Combined protection mechanism for user-defined business parameters

The combined protection mechanism of user-defined business parameters is realized through the adaptation class

// User defined version number + user name to realize combined fusing
public class MyServiceSentinelRequestOriginAdapter extends DefaultServiceSentinelRequestOriginAdapter {
    @Override
    public String parseOrigin(HttpServletRequest request) {
        String version = request.getHeader(DiscoveryConstant.N_D_SERVICE_VERSION);
        String user = request.getHeader("user");

        return version + "&" + user;
    }
}

Create an adaptation class in the configuration class in @ Bean mode

@Bean
public ServiceSentinelRequestOriginAdapter ServiceSentinelRequestOriginAdapter() {
    return new MyServiceSentinelRequestOriginAdapter();
}

The rule of service discovery-guide-service-b is added. The Group is discovery-guide-group, and the Data Id is discovery-guide-service-b-sentinel-authority. The content of the rule is as follows, indicating that the version is 1.0 and the user of the incoming Http Header = Zhangsan. All services meeting these two conditions are allowed to access service discovery-guide-service-b

[
    {
        "resource": "sentinel-resource",
        "limitApp": "1.0&zhangsan",
        "strategy": 0
    }
]

Operation effect

  • When user=zhangsan in the Http Header passed, and when the full link call is in progress, the API gateway load balancing discovery-guide-service-a service reaches version 1.0, then call the discovery-guide-service-b service, and finally the call succeeds
  • When user=lisi in the delivered Http Header does not meet the conditions, the final call is rejected on the discovery-guide-service-b server
  • When user=zhangsan in the Http Header passed, one of the conditions is met. In the whole link call, the API gateway load balancing discovery-guide-service-a service reaches version 1.1 and then calls the discovery-guide-service-b service, which does not meet the condition of version=1.0. Finally, the call is rejected at the discovery-guide-service-b server

Full link service current limiting fuse and gray fusion based on Hystrix

By introducing the Hystrix component to realize the function of service current limiting and fusing, when performing gray publishing and routing, calling in the thread pool isolation mode will lose the context, so the following steps are required to avoid this situation. The following steps are applicable to both gateway and server

  • Pom introduction
<!-- For service Hystrix When thread isolation is performed, the following packages need to be imported -->
<dependency>
    <groupId>com.nepxion</groupId>
    <artifactId>discovery-plugin-strategy-starter-hystrix</artifactId>
    <version>${discovery.version}</version>
</dependency>
  • Configuration on
# When you enable the server to implement the Hystrix thread isolation mode for service isolation, you must put spring application. strategy. Hystrix. threadlocal. Set supported to true and introduce the discovery plugin strategy starter Hystrix package. Otherwise, the ThreadLocal context object will be lost during thread switching. If it is missing, it defaults to false
spring.application.strategy.hystrix.threadlocal.supported=true

Full link call chain

The gray level call chain mainly includes the following 6 parameters. The user can define the call chain parameters to be passed, such as traceId, spanId, etc; You can also define the business call chain parameters to be passed, such as mobile, user, etc

1. n-d-service-group - Group or application to which the service belongs
2. n-d-service-type - Service type, divided into "gateway" and "service"
3. n-d-service-id - service ID
4. n-d-service-address - Service address, including Host and Port
5. n-d-service-version - Service version
6. n-d-service-region - Service area

Grayscale call chain output is divided into Header mode and log mode

Header output mode

Header mode framework internal integration

  • The gateway of Spring Cloud Gateway will transmit the Header value by itself (refer to AbstractGatewayStrategyRouteFilter.java in the source code of Discovery)
  • Zuul gateway will transmit Header value by itself (refer to AbstractZuulStrategyRouteFilter.java in Discovery source code)
  • The server transmits the Header value through Feign and RestTemplate interceptors (refer to FeignStrategyInterceptor.java and RestTemplateStrategyInterceptor.java in the Discovery source code)

Log output mode

  • Spring Cloud Gateway

Inherits gatewaystrategytracer Java, in the trace method, 6 parameters (refer to the debugTraceHeader method in the parent class) or more are output to the log through MDC

// The custom call chain and gray call chain are output to the log through MDC. During user integration, focus on MDC in trace method MDC in put and release methods The clear code part is enough
public class MyGatewayStrategyTracer extends DefaultGatewayStrategyTracer {
    @Override
    public void trace(ServerWebExchange exchange) {
        super.trace(exchange);
        
        // Output to log
        MDC.put("traceid", "traceid=" + strategyContextHolder.getHeader("traceid"));
        ...

        MDC.put(DiscoveryConstant.N_D_SERVICE_GROUP, "Service group name=" + strategyContextHolder.getHeader(DiscoveryConstant.N_D_SERVICE_GROUP));
        ...
    }

    @Override
    public void release(ServerWebExchange exchange) {
        MDC.clear();
    }
}

Create the call chain class in the configuration class in @ Bean mode, which overrides the built-in call chain class of the framework

@Bean
@ConditionalOnProperty(value = StrategyConstant.SPRING_APPLICATION_STRATEGY_TRACE_ENABLED, matchIfMissing = false)
public GatewayStrategyTracer gatewayStrategyTracer() {
    return new MyGatewayStrategyTracer();
}
  • Zuul gateway

Inherit zuulstrategytracer Java, in the trace method, 6 parameters (refer to the debugTraceHeader method in the parent class) or more are output to the log through MDC

// The custom call chain and gray call chain are output to the log through MDC. During user integration, focus on MDC in trace method MDC in put and release methods The clear code part is enough
public class MyZuulStrategyTracer extends DefaultZuulStrategyTracer {
    @Override
    public void trace(RequestContext context) {
        super.trace(context);
        
        // Output to log
        MDC.put("traceid", "traceid=" + strategyContextHolder.getHeader("traceid"));
        ...

        MDC.put(DiscoveryConstant.N_D_SERVICE_GROUP, "Service group name=" + strategyContextHolder.getHeader(DiscoveryConstant.N_D_SERVICE_GROUP));
        ...
    }

    @Override
    public void release(RequestContext context) {
        MDC.clear();
    }
}

Create the call chain class in the configuration class in @ Bean mode, which overrides the built-in call chain class of the framework

@Bean
@ConditionalOnProperty(value = StrategyConstant.SPRING_APPLICATION_STRATEGY_TRACE_ENABLED, matchIfMissing = false)
public ZuulStrategyTracer zuulStrategyTracer() {
    return new MyZuulStrategyTracer();
}
  • Service Service

Inherits servicestrategytracer Java, in the trace method, 6 parameters (refer to the debugTraceLocal method in the parent class) or more are output to the log through MDC

// The custom call chain and gray call chain are output to the log through MDC. During user integration, focus on MDC in trace method MDC in put and release methods The clear code part is enough
public class MyServiceStrategyTracer extends DefaultServiceStrategyTracer {
    @Override
    public void trace(ServiceStrategyTracerInterceptor interceptor, MethodInvocation invocation) {
        super.trace(interceptor, invocation);
        
        // Output to log
        MDC.put("traceid", "traceid=" + strategyContextHolder.getHeader("traceid"));
        ...

        MDC.put(DiscoveryConstant.N_D_SERVICE_GROUP, "Service group name=" + pluginAdapter.getGroup());
        ...
    }

    @Override
    public void release(ServiceStrategyTracerInterceptor interceptor, MethodInvocation invocation) {
        MDC.clear();
    }
}

Create the call chain class in the configuration class in @ Bean mode, which overrides the built-in call chain class of the framework

@Bean
@ConditionalOnProperty(value = StrategyConstant.SPRING_APPLICATION_STRATEGY_TRACE_ENABLED, matchIfMissing = false)
public ServiceStrategyTracer serviceStrategyTracer() {
    return new MyServiceStrategyTracer();
}

Refer to the results printed in the IDE console [external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-gx4rhnh4-1570768850063)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/Tracer.jpg )]

The opening and closing of the call chain function need to be controlled by the following switches:

# Start and close the call chain. If it is missing, it defaults to false
spring.application.strategy.trace.enabled=true
# Start and close the Debug log printing of the call chain. Note that each call will be printed, which will affect the performance. It is recommended to close the pressure test environment and production environment. If it is missing, it defaults to false
spring.application.strategy.trace.debug.enabled=true

Full link Header delivery

The framework will transfer the relevant headers by default for the whole link, which can be configured as follows. In addition, for any Header starting with "n-d -", the framework will default to full link delivery

# When the routing policy is started and closed, calls to REST mode are intercepted. If it is missing, it defaults to true
spring.application.strategy.rest.intercept.enabled=true
# Start and turn off the Debug log printing passed by the Header. Note that each call will print once, which will affect the performance. It is recommended to turn off the pressure test environment and production environment. If it is missing, it defaults to false
spring.application.strategy.rest.intercept.debug.enabled=true
# If you want to pass the Header parameters (used for the built-in context Header of the framework, such as traceid, spanid, etc.) from the outside to the service when calling and intercepting the REST mode (Feign or RestTemplate calls are supported), configure the following values. If more than one is used, ";" Separated, no spaces allowed
spring.application.strategy.context.request.headers=traceid;spanid
# If you want to pass the externally customized Header parameter (used for the business system sub definition Header, such as mobile) to the service when calling and intercepting the REST mode (Feign or RestTemplate calls are supported), configure the following values. If more than one is used, ";" Separated, no spaces allowed
spring.application.strategy.business.request.headers=user;mobile

The native Feign Header transfer can be implemented using the RequestInterceptor interceptor, and the native RestTemplate Header transfer can be implemented using the ClientHttpRequestInterceptor interceptor interceptor

This framework also uses these native interceptors as the transmission of Header in gray function. In order to avoid users creating another layer of interceptors, the framework abstracts two interception adapters. Their usage is consistent with the two native interceptors, which can help users realize the transmission of custom headers

Custom feign header delivery

Implement feignstrategyinterceptoradapter Java, add a custom Header transfer in the apply method

// Customize Header delivery in Feign interceptor
public class MyFeignStrategyInterceptorAdapter extends DefaultFeignStrategyInterceptorAdapter {
    @Override
    public void apply(RequestTemplate requestTemplate) {
        requestTemplate.header("n-d-my-id", "123");
    }
}

Create interception adapter in configuration class in @ Bean mode

@Bean
public FeignStrategyInterceptorAdapter feignStrategyInterceptorAdapter() {
    return new MyFeignStrategyInterceptorAdapter();
}

Custom resttemplate header delivery

Implement resttemplatestrategyinterceptoradapter Java, add a custom Header transfer in the intercept method

// Header passing in custom RestTemplate interceptor
public class MyRestTemplateStrategyInterceptorAdapter extends DefaultRestTemplateStrategyInterceptorAdapter {
    @Override
    public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException {
        HttpHeaders headers = request.getHeaders();
        headers.add("n-d-my-id", "456");

        return execution.execute(request, body);
    }
}

Create interception adapter in configuration class in @ Bean mode

@Bean
public RestTemplateStrategyInterceptorAdapter restTemplateStrategyInterceptorAdapter() {
    return new MyRestTemplateStrategyInterceptorAdapter();
}

Docker containerization and Kubernetes platform

Docker containerization

  • Build Docker environment under Windows10 operating system or Linux operating system
  • Fully automatically deploy and run Docker services. Under the root directory
    • Run install docker gateway with one click Bat or sh, automatically deploy and run the Spring Cloud Gateway
    • Run install docker Zuul.com with one click Bat or sh, deploy and run the Zuul gateway automatically
    • Run install docker service XX with one click Bat or sh, automatically deploy and run microservices. Note that you must run in sequence, that is, you can't execute the next one until the previous one is deployed

[external chain picture transfer failed. The source station may have anti-theft chain mechanism. It is recommended to save the picture and upload it directly (img-zqy2sfjz-1570768850064)( https://github.com/Nepxion/Docs/raw/master/discovery-doc/Docker.jpg )]

Kubernetes platform

Please study by yourself

Added by mydimension on Thu, 06 Jan 2022 10:47:32 +0200