Writing in the front

In my previous article, “Getting Started with Microservices Architecture: Flow Control and Fuse downgrading solutions —-,” I gave a brief introduction to the use of Sentinel. However, one problem remains that the Sentinel configuration information has not been persisted and will be lost after the service restarts. In this article, we will tackle this problem.

Nacos was used as the Sentinel configuration information data source

In the default sentinel, the configuration information is stored directly in local memory and will be lost when the server restarts. In addition, fine-grained configurations require individual configuration operations for each resource, which is not conducive to the reuse of configuration information.

Sentinel dynamic rule configuration

In the sentinel data source extension, the following two modes are provided:

  • Pull mode: Clients regularly poll pull rules to a rule manager, such as RDBMS, files, or even VCS. The way to do this is simple, but the disadvantage is that changes cannot be captured in a timely manner;
  • Push mode: the rule center pushes the rules uniformly, and the client monitors the changes constantly by registering listeners, such as using Nacos and Zookeeper configuration centers. This method has better real-time performance and consistency assurance.

We will use the Nacos learned in the previous article as the data source of Sentinel configuration information (push pattern) to achieve persistent and dynamic configuration of Sentinel configuration information.

Before that, if you haven’t studied Nacos, then you need to learn first Nacos content, you can read my previous article introduction to the micro service architecture service registry findings and configuration center | Spring Cloud Alibaba Nacos “.

Introduction of depend on

First of all, we need to add sentinel’s NACOS data source dependency to the existing dependencies.

	<dependency>
        <groupId>com.alibaba.csp</groupId>
        <artifactId>sentinel-datasource-nacos</artifactId>
        <version>1.5.2</version>
    </dependency>
Copy the code

Add the configuration

server:
  port: 9004
  tomcat:
    uri-encoding: UTF-8
spring:
  application:
    name: sentinel-demo
  cloud:
    nacos:
      server-addr: 172.17172.49.: 8848
    sentinel:
      transport:
        dashboard: 127.0. 01.: 8080
      datasource:
# Whatever your name is
        ds1:
          nacos:
            server-addr: ${spring.cloud.nacos.server-addr}
            dataId: ${spring.application.name}-sentinel
            groupId: DEFAULT_GROUP
# rule type, here is the limiting rule
            # see values: org. Springframework. Cloud. Alibaba. Sentinel. The datasource. RuleType
            rule-type: flow
        ds2:
          nacos:
            server-addr: ${spring.cloud.nacos.server-addr}
            dataId: ${spring.application.name}-sentinel-degrade
            groupId: DEFAULT_GROUP
# Demotion rule
            rule-type: degrade
        ds3:
          nacos:
            server-addr: ${spring.cloud.nacos.server-addr}
            dataId: ${spring.application.name}-sentinel-param-flow
            groupId: DEFAULT_GROUP
            # Hotspot parameter flow limiting rule
            rule-type: param-flow
        ds4:
          nacos:
            server-addr: ${spring.cloud.nacos.server-addr}
            dataId: ${spring.application.name}-sentinel-system
            groupId: DEFAULT_GROUP
            System adaptive current limiting
            rule-type: system
        ds5:
          nacos:
            server-addr: ${spring.cloud.nacos.server-addr}
            dataId: ${spring.application.name}-sentinel-authority
            groupId: DEFAULT_GROUP
            # Whitelist configuration
            rule-type: authority

Copy the code

Add the corresponding Sentinel rule configuration in NACOS

Current limiting rules

[{"resource": "/test/info"."limitApp": "default"."grade": 1."count": 3."strategy": 0."controlBehavior": 0."clusterMode": false}]Copy the code

Description of configuration information:

  • resource: Resource name, which is the object of the traffic limiting rule
  • limitApp: Call source for flow control. If it is default, the call source is not identified
  • grade: Traffic limiting threshold type (QPS or number of concurrent threads);0Represents limiting traffic according to the number of concurrent requests,1Represents flow control according to QPS
  • count: Indicates the traffic limiting threshold
  • strategy: Invokes the relational traffic limiting policy. 0 indicates direct, 1 indicates association, and 2 indicates link.
  • controlBehavior: Flow control effect (0 direct rejection, 1 Warm Up, 2 uniform queuing)
  • clusterMode: Indicates whether the cluster mode is used

Fuse downgrading rules

[{"resource": "/test/info"."grade": 2."count": 3."timeWindow": 10."minRequestAmount": 1."statIntervalMs": 1000}]Copy the code

Description of configuration information:

  • resource: resource name
  • grade: Fuse breaker policy, supporting slow call ratio (0)/ Abnormal ratio (1)/ Abnormal number policy (2)
  • count: In slow call ratio mode, it is slow call critical RT (beyond this value, it is slow call); In exception ratio/Number of exceptions mode, the corresponding threshold is set
  • timeWindow: Fuse duration, in unit of s
  • minRequestAmount: Minimum number of requests triggered by fuses. If the number of requests is less than this value, fuses will not be triggered even if the abnormal ratio exceeds the threshold (introduced in 1.7.0)
  • statIntervalMs: Statistics duration (unit: ms). For example, 60 x 1000 indicates the minute level (introduced in 1.8.0).
  • slowRatioThreshold: Slow call ratio threshold, valid only in slow call ratio mode (introduced in 1.8.0)

Hotspot parameter traffic limiting configuration:

[{"resource": "/test/getInfoById"."count": 3."durationInSec": 1."controlBehavior": 0."maxQueueingTimeMs": 3000."paramIdx": 0}]Copy the code

Description of configuration information:

  • resource: resource name
  • count: Indicates the traffic limiting threshold
  • durationInSec: Statistics window duration (in seconds), supported by version 1.6.0
  • controlBehavior: Flow control effect (support fast failure and uniform queuing mode), supported by version 1.6.0
  • maxQueueingTimeMs: Maximum queuing duration (available only in uniform queuing mode). Version 1.6.0 is supported
  • paramIdx: Parameter index value, from0start

The system ADAPTS to traffic limiting

[{"highestSystemLoad": 3
    },
    {
        "highestCpuUsage": 0.8
    },
    {
        "avgRt": 10
    },
    {
        "qps": 20
    },
    {
        "maxThread": 20}]Copy the code

Description of configuration information:

  • The Load adaptive(Only for Linux/ UNIX-like machines) : Load1 of the system is used as an inspiration indicator for adaptive system protection. System protection (BBR phase) is triggered when system load1 exceeds the set heuristics value and the current number of concurrent threads in the system exceeds the estimated system capacity. System capacity is determined by the systemmaxQps * minRtEstimated. The setting reference value is generallyCPU cores * 2.5.
  • CPU Usage (version 1.5.0+) : When the CPU usage exceeds the threshold, system protection is triggered (value range: 0.0 to 1.0).
  • Average RT: System protection is triggered when the average RT of all inlet traffic on a single machine reaches a threshold, in milliseconds.
  • Number of concurrent threads: System protection is triggered when the number of concurrent threads for all incoming traffic on a single machine reaches a threshold.
  • Inlet QPS: System protection is triggered when the QPS of all inlet flows on a single machine reaches the threshold.

Blacklist and whitelist configuration:

[{"resource": "/test/info"."limitApp": "sentinel-demo-client"."strategy": 0
    }
    
Copy the code

Description of configuration information:

  • resource: resource name
  • limitApp: Indicates the corresponding blacklist/whitelist. Different origin is used.Space, such asappA,appB.
  • strategy: Indicates the list type. 0 indicates the whitelist and 1 indicates the blacklist. The default mode is whitelist.

Start and test

  1. Start nacOS, Sentinel and this module

  2. Access interface

  1. Check the Sentinel console to see if it receives a push message from NACOS

Flow control rules

Fuse downgrading rules

Hotspot parameter Traffic limiting rule

The system ADAPTS to traffic limiting rules

Access rules

You can see that Sentinel has received a push from NACOS.

This section describes how to modify traffic control rules

  1. The change rule in the Sentinel console: only exists in the memory of the service, the configuration value in Nacos will not be modified, and the original value will be restored after the restart.

  2. Change rules in the Nacos console: The in-memory rules of the service are updated, as are the persistent rules in Nacos, which remain unchanged after a restart.

Custom degrade message prompt

Sentinel provides the @SentinelResource annotation for defining resources and an extension to AspectJ for automatically defining resources, handling blockexceptions, and so on

Attribute Description:

  • Value: resource name, required (cannot be empty)

  • EntryType: Entry type, optional (default entrytype.out)

  • BlockHandler/blockHandlerClass: Specifies the name of the function that processes blockExceptions. This parameter is optional. The blockHandler function must have a public access scope, a return type that matches the original method, a parameter type that matches the original method and an extra parameter of type BlockException at the end. The blockHandler function needs to be in the same class as the original method by default. If you want to use a function of another Class, you can specify blockHandlerClass as the Class object of the corresponding Class. Note that the corresponding function must be static; otherwise, it cannot be parsed.

  • Fallback /fallbackClass: Optional fallback function name that provides fallback handling logic when an exception is thrown. The fallback function handles all types of exceptions except those excluded from exceptionsToIgnore. Fallback function signature and position requirements:

    • The return value type must be the same as that of the original function;
    • The method argument list needs to be the same as the original function, or it can be an extra oneThrowableType to receive the corresponding exception.
    • The fallback function needs to be in the same class as the original method by default. You can specify if you want to use a function from another classfallbackClassOf the corresponding classClassObject, note that the corresponding function must be static, otherwise it cannot be parsed.
  • DefaultFallback (since 1.6.0) : The default, optional fallback function name, usually used for generic fallback logic (that is, for many services or methods). The default fallback function can be used for all types of exceptions except exceptionsToIgnore

    The type of exception that is excluded). If both fallback and defaultFallback are configured, only fallback takes effect. DefaultFallback signature requirements:

    • The return value type must be the same as that of the original function;
    • The method parameter list needs to be empty, or you can have an extra parameterThrowableType to receive the corresponding exception.
    • DefaultFallback needs to be in the same class as the original method by default. You can specify if you want to use a function from another classfallbackClassOf the corresponding classClassObject, note that the corresponding function must be static, otherwise it cannot be parsed.
  • ExceptionsToIgnore (since 1.6.0) : Specifies which exceptions are excluded and are not counted in the exception statistics or fallback logic. Instead, it is thrown as is.

Note:

  1. @ SentinelResource does not supportprivatemethods
  2. 1.6.0The previous version of the fallback function only worked with degraded exceptions (DegradeException) for processing,Service exceptions cannot be handled.
  3. If blockHandler and Fallback are configured, they are thrown due to traffic limiting degradationBlockExceptionWill only enterblockHandlerProcessing logic.
  4. If not configuredblockHandler,fallbackdefaultFallback, will be degraded by traffic limitingBlockException Direct selling(If the method itself does not define throws BlockException, it is wrapped by the JVMUndeclaredThrowableException).

Using the step

Introduction of depend on

If the AOP processing of Sentinel is used, the following dependencies need to be introduced

	<dependency>
        <groupId>com.alibaba.csp</groupId>
        <artifactId>sentinel-annotation-aspectj</artifactId>
    </dependency>
Copy the code

use

/** Test interface *@authorLaifeng [email protected] *@version 1.0
 * @date2020/10/26 he * /
@RestController
@RequestMapping("/test")
public class DemoController {

    /** ** function *@return map
     */
    @SentinelResource(value = "/test/info", blockHandler = "blockExceptionHandler", fallback = "infoFallback", exceptionsToIgnore = RuntimeException.class )
    @GetMapping("/info")
    public Map info(a) {
        HashMap<String, Object> map = new HashMap<>(3);
        map.put("code".0);
        map.put("msg"."Wxb: Java Development Practices");
        return map;
    }

    /** the fallback function has the same signature as the original function or adds a Throwable parameter@return* /
    public Map infoFallback(a) {
        HashMap<String, Object> map = new HashMap<>(3);
        map.put("code".501);
        map.put("msg"."Busy, please try again later.");
        return map;
    }

    /** handle exceptions * Block exception processing function, the last parameter more than a BlockException, the rest of the same as the original function@return* /
    public Map backExceptionhandler(BlockException e){
        HashMap<String, Object> map = new HashMap<>(3);
        map.put("code".500);
        map.put("msg"."The system is busy. Please try again later.");
        returnmap; }}Copy the code

Start and test

Quick access to the interface in the browser

Note: 1. If the exception is intercepted by @ExceptionHandler, this will cause an error in the de-escalation policy of the Sentinel configuration. Exceptions processed by @ExceptionHandler will not be counted in the statistics

##Sentinel support for RestTemplate ·@SentinelRestTemplate

In the example above, we configure the limiting and degrading handlers so that they can be handled when limiting and degrading occur. However, it can be seen that the format of the two methods is mandatory, so it is difficult to reuse these two methods. If you want to reuse, you have to unify the parameters and return the results. Or write corresponding stream limiting and degradation handlers for each sentinel resource, which is obviously not realistic.

Sentinel enables the definition of degradation policies upstream of the service (service callers) and the writing of uniform degradation handling methods.

Implementation steps

Let’s create a new module, Sentinel-Demo-client, to demonstrate service invocation.

1. Add dependencies

 <dependencies>
        <! -- NacOS service Discovery -->
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
        </dependency>
        <! -- NacOS Configuration Center -->
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
        </dependency>
        <! -- Sentinel Service Flow Control -->
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
        </dependency>

        <dependency>
            <groupId>com.alibaba.csp</groupId>
            <artifactId>sentinel-annotation-aspectj</artifactId>
        </dependency>


        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

    </dependencies>
Copy the code

2. Write startup classes

/ * * *@authorLaifeng [email protected] *@version 1.0
 * @date2020/10/30 20:22 * /
@SpringBootApplication(scanBasePackages = "pers.lbf.spring.cloud.alibaba.demo.sentinel.demo.client")
@EnableDiscoveryClient
public class ClientApp {

  public static void main(String[] args) { SpringApplication.run(ClientApp.class,args); }}Copy the code

3. Write configurations

server:
  port: 8010
spring:
  application:
    name: sentinel-demo-client
  cloud:
    nacos:
      server-addr: 172.17172.49.: 8848
    sentinel:
      transport:
        dashboard: 127.0. 01.: 8080
Copy the code

4. Write flow limiting and degradation processing logic

/** Class **sentinel@authorLaifeng [email protected] *@version 1.0
 * @dateRose 2020/10/30 * /
public class SentinelUtils {


    /** * stream limiting function *@param request
     * @param body
     * @param execution
     * @param ex
     * @return* /
    public static SentinelClientHttpResponse handleException(HttpRequest request,
                                                             byte[] body, ClientHttpRequestExecution execution, BlockException ex) {
       
        System.err.println("Fallback: Service traffic restricted" );
        return new SentinelClientHttpResponse("The system is busy. Please try again later.");
    }

    /** * Service degradation handler *@param request
     * @param body
     * @param execution
     * @param ex
     * @return* /
      public static SentinelClientHttpResponse defaultFallbackMethod(HttpRequest request,
                                                        byte[] body, ClientHttpRequestExecution execution, BlockException ex) {
          System.err.println("Fallback: Service downgraded" );
          return new SentinelClientHttpResponse("The system is busy. Please try again later."); }}Copy the code

5 configuration RestTemplate

We need to configure the Sentinel supported RestTemplate so that the service provider can handle downscaling and limiting traffic. The configuration is as simple as marking the @SentinelResttemlpate annotation when injecting the RestTemplate.

/ * * *@authorLaifeng [email protected] *@version 1.0
 * @date2020/10/30 20:22 * /
@SpringBootApplication(scanBasePackages = "pers.lbf.spring.cloud.alibaba.demo.sentinel.demo.client")
@EnableDiscoveryClient
public class ClientApp {

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

  @Bean
  @SentinelRestTemplate(fallbackClass = SentinelUtils.class, fallback = "defaultFallbackMethod", blockHandlerClass = SentinelUtils.class, blockHandler = "handleException")
  public RestTemplate restTemplate(a) {
      return newRestTemplate(); }}Copy the code
SentinelRestTemlpateParameter Description:
  • fallbackClass: Class of the degrade handler
  • fallback: Specifies the name of the degradation handler
  • blockHandlerClass: Class of the current limiting function
  • blockHandler: current limiting function

Note: The method signatures and method return types of the fallback and BlockHandler methods are fixed, and they must be static methods

6. Write test interfaces and invoke services

/** test interface, responsible for demonstrating calling service *@authorLaifeng [email protected] *@version 1.0
 * @date2020/10/30 20:52 * /
@RestController
public class TestController {

    @Autowired
    private RestTemplate restTemplate;

    @GetMapping("/test")
    public ResultVO test(a) throws Exception{

        ResultVO resultVO = restTemplate.getForObject("http://127.0.0.1:9004/test/info", ResultVO.class);

        System.out.println(Objects.requireNonNull(resultVO).toString());

        returnresultVO; }}Copy the code

7 Start the nacOS, Sentinel, and sentinel test modules and add the service degradation configuration

Add degrade configuration:

It is important to note here that we add degrade configuration to the invoked service at the service caller, and when the trigger degrade (fuse) condition is reached, the degrade logic will be performed and no remote service invocation will take place. In addition, when the call is made again after the fuse break period expires, if an exception occurs again, the fuse break mechanism will be triggered again.

Testing:

You can see that on the second batch access, a circuit breaker occurs again because the first request did not succeed

Write in the last

That’s all we have to say about getting started with Sentine.

If you find this article helpful, please give it a thumbs up. If there is any mistake, please feel free to comment. Here, thank you folks!

In the next Spring Cloud Alibaba series, we’ll start learning about service invocation of microservices.

** This article code link: **github.com/code81192/a…