Sentinel生产环境实践

来自杨三超wiki

1、功能描述

API 限流

sentinel默认会探测所有API,但需要注意,Sentinel 会在客户端首次调用时候进行初始化,开始向控制台发送心跳包。因此需要确保客户端有访问量,才能在控制台上看到监控数据。

RPC限流粒度

可以是服务接口和服务方法两种粒度:

  • 服务接口:resourceName 为 接口全限定名,如 com.alibaba.csp.sentinel.demo.dubbo.FooService
  • 服务方法:resourceName 为 接口全限定名:方法签名,如 com.alibaba.csp.sentinel.demo.dubbo.FooService:sayHello(java.lang.String)

存在问题

1、规则持久化

支持基于 ZooKeeper / Nacos / Apollo 的数据源规则持久化,但需要改造;

2、统一异常处理;

需要自己改造;

3、监控数据持久化;

需要自己改造;

2、Dashboard改造部署

1、修改路由规则

第一步:修改dashboad.flowV1为dashboad.flow;

Sentinel生产环境实践

第二步:FlowServiceV1修改为FlowServiceV2;

Sentinel生产环境实践

2、支持规则持久化

sentinel支持限流、降级、热点、系统、授权五种规则,目前常用的功能是限流和降级、基于zookeeper实现持久化规则;

dashboad默认规则都是内存,同时需要修改对应的Controller;

Sentinel生产环境实践

Sentinel生产环境实践

 

3、监控日志持久化    

默认监控日志仅在内容保留5分钟

 

Sentinel生产环境实践

4、部署

3、服务如何使用

1、添加相关pom

1.1 springboot2.x添加pom

<!--sentinel start-->

<!-- https://mvnrepository.com/artifact/com.alibaba.cloud/spring-cloud-starter-alibaba-sentinel -->

<dependency>

    <groupId>com.alibaba.cloud</groupId>

    <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>

    <version>2.1.0.RELEASE</version>

    <exclusions>

        <exclusion>

            <artifactId>sentinel-core</artifactId>

            <groupId>com.alibaba.csp</groupId>

        </exclusion>

        <exclusion>

            <artifactId>fastjson</artifactId>

            <groupId>com.alibaba</groupId>

        </exclusion>

    </exclusions>

</dependency>

 

<!-- https://mvnrepository.com/artifact/com.alibaba.csp/sentinel-datasource-zookeeper -->

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-datasource-zookeeper</artifactId>

    <version>1.6.3</version>

    <exclusions>

        <exclusion>

            <artifactId>sentinel-datasource-extension</artifactId>

            <groupId>com.alibaba.csp</groupId>

        </exclusion>

        <exclusion>

            <artifactId>zookeeper</artifactId>

            <groupId>org.apache.zookeeper</groupId>

        </exclusion>

    </exclusions>

</dependency>

<!-- https://mvnrepository.com/artifact/com.alibaba.csp/sentinel-dubbo-adapter -->

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-dubbo-adapter</artifactId>

    <version>1.6.3</version>

</dependency>

 

<dependency>

    <groupId>org.apache.curator</groupId>

    <artifactId>curator-framework</artifactId>

    <version>2.11.0</version>

</dependency>

<dependency>

    <groupId>org.apache.curator</groupId>

    <artifactId>curator-client</artifactId>

    <version>2.11.0</version>

</dependency>

<dependency>

    <groupId>org.apache.curator</groupId>

    <artifactId>curator-recipes</artifactId>

    <version>2.11.0</version>

</dependency>

<!--sentinel end-->

 

 

1.2 springboot1.5.x添加pom

 折叠源码

<!--sentinel start-->

<!--https://mvnrepository.com/artifact/com.alibaba.cloud/spring-cloud-starter-alibaba-sentinel -->

<dependency>

    <groupId>com.alibaba.cloud</groupId>

    <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>

    <version>1.5.1.RELEASE</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-cluster-client-default</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-cluster-common-default</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-cluster-server-default</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-datasource-extension</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-parameter-flow-control</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-transport-common</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-transport-simple-http</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-web-servlet</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-core</artifactId>

    <version>1.5.1</version>

</dependency>

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-annotation-aspectj</artifactId>

    <version>1.5.1</version>

</dependency>

 

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-datasource-zookeeper</artifactId>

    <version>1.5.1</version>

    <exclusions>

        <exclusion>

            <artifactId>zookeeper</artifactId>

            <groupId>org.apache.zookeeper</groupId>

        </exclusion>

    </exclusions>

</dependency>

 

<!-- https://mvnrepository.com/artifact/com.alibaba.csp/sentinel-dubbo-adapter -->

<dependency>

    <groupId>com.alibaba.csp</groupId>

    <artifactId>sentinel-dubbo-adapter</artifactId>

    <version>1.5.1</version>

</dependency>

<!--sentinel end-->

 

2、添加配置

添加配置:

cloud:

  sentinel:

    transport:

      port: 8731

      dashboard: http://127.0.0.1:9001

    datasource:

      ds:

        zk:

          path: /

          serverAddr: zookeeper:2181

          groupId: SENTINEL_GROUP

          dataId: ${spring.application.name}-flow-rules

          ruleType: FLOW

      ds1:

        zk:

          path: /

          serverAddr: zookeeper:2181

          groupId: SENTINEL_GROUP

          dataId: ${spring.application.name}-degrade-rules

          ruleType: DEGRADE

3、添加统一异常

API统一异常

@Configuration

public class MyFallbackAPIConfig {

    /**

     * URL block handler.

     */

    private static volatile UrlBlockHandler urlBlockHandler = new DefaultUrlBlockHandler();

 

    static {

        WebCallbackManager.setUrlBlockHandler(urlBlockHandler);

    }

 

    public static class DefaultUrlBlockHandler implements UrlBlockHandler {

 

        private static void writeDefaultBlockedPage(HttpServletResponse response) throws IOException {

            response.setCharacterEncoding("UTF-8");

            response.setHeader("Content-Type""application/json; charset=utf-8");

 

            Map<String, Object> responseObject = new HashMap<>(3);

            responseObject.put("code",10001);

            responseObject.put("message","系统繁忙,请稍后再试!");

            responseObject.put("body",new Object());

            JSONObject responseJSONObject = (JSONObject)JSONObject.toJSON(responseObject);

 

            PrintWriter out = response.getWriter();

            out.write(responseJSONObject.toString());

            out.flush();

            out.close();

        }

 

        @Override

        public void blocked(HttpServletRequest request, HttpServletResponse response, BlockException ex)

                throws IOException {

            // Directly redirect to the default flow control (blocked) page or customized block page.

            blockRequest(request, response);

        }

 

        public static void blockRequest(HttpServletRequest request, HttpServletResponse response) throws IOException {

            StringBuffer url = request.getRequestURL();

 

            if ("GET".equals(request.getMethod()) && StringUtil.isNotBlank(request.getQueryString())) {

                url.append("?").append(request.getQueryString());

            }

 

            if (StringUtil.isBlank(WebServletConfig.getBlockPage())) {

                writeDefaultBlockedPage(response);

            else {

                String redirectUrl = WebServletConfig.getBlockPage() + "?http_referer=" + url.toString();

                // Redirect to the customized block page.

                response.sendRedirect(redirectUrl);

            }

        }

    }

}

 

dubbo统一异常

@Component

public class MyFallbackDubboConfig  {

    /**

     * URL block handler.

     */

    private static volatile DefaultDubboBlockHandler dubboFallback = new DefaultDubboBlockHandler();

 

    static {

        DubboFallbackRegistry.setConsumerFallback(dubboFallback);

    }

 

    public static class DefaultDubboBlockHandler implements DubboFallback {

 

        @Override

        public Result handle(Invoker<?> invoker, Invocation invocation, BlockException e) {

            return new RpcResult(null);

        }

    }

 

}