- Sentinel服务熔断环境搭建
- 一、共用类commons
- 二、服务提供者9003,90004搭建
- 二、服务消费者8084模块搭建
- @SentinelResource注解
- 属性
- fallback用法
- blockHolder和fallbackHolder的区别
为了测试熔断保护机制,首先搭建一个服务环境,服务环境如下:
springcloud的依赖版本记得选2.2.X
搭建方式跟之前差不多
服务cloudalibaba-commons,后面9003和9004会引用这个类
package com.cloud.cloudalibabacommons.entity; import lombok.AllArgsConstructor; import lombok.Data; import lombok.NoArgsConstructor; @Data @AllArgsConstructor @NoArgsConstructor public class JsonResult二、服务提供者9003,90004搭建{ private Integer code; private T data; }
9003和9004项目结构、代码相同,只是端口号不一样
pom依赖:
com.alibaba.cloud spring-cloud-starter-alibaba-nacos-discovery com.cloud cloudalibaba-commons 0.0.1-SNAPSHOT
application.yml
server:
port: 9003
spring:
application:
name: nacos-provider
cloud:
nacos:
discovery:
server-addr: localhost:8848
management:
endpoints:
web:
exposure:
include: '*'
启动类记得添加@EnableDiscoveryClient注解
控制器类:
package com.cloud.cloudalibabaprovider9004.controller;
import com.cloud.cloudalibabacommons.entity.JsonResult;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.HashMap;
@RestController
@RequestMapping("data")
public class DataController {
@Value("${server.port}")
private String serverPort;
public static HashMap dataMap = new HashMap<>();
//模仿数据库存储数据
static{
dataMap.put(1L,"鼠标");
dataMap.put(2L,"键盘");
dataMap.put(3L,"耳机");
}
@GetMapping("info/{id}")
public JsonResult info(@PathVariable("id") Long id){
return new JsonResult(200,serverPort+": "+dataMap.get(id));
}
}
二、服务消费者8084模块搭建
pom依赖
com.alibaba.cloud
spring-cloud-starter-alibaba-nacos-discovery
com.alibaba.cloud
spring-cloud-starter-alibaba-sentinel
com.cloud
cloudalibaba-commons
0.0.1-SNAPSHOT
配置文件application.yml
server:
port: 8084
spring:
application:
name: naocs-customer
cloud:
nacos:
discovery:
server-addr: localhost:8848
sentinel:
transport:
#默认8719端口,假如被占用会自动从8719开始依次+1扫描,直至找到未被占用的端口
port: 8719
#配置Sentinel dashboard地址
dashboard: 8080
# 消费者将要去访问的微服务名称(注册成功进nacos的微服务提供者)
service-url:
nacos-user-service: http://nacos-provider
启动类
@SpringBootApplication
@EnableDiscoveryClient
public class CloudalibabaCustomer8084Application {
public static void main(String[] args) {
SpringApplication.run(CloudalibabaCustomer8084Application.class, args);
}
@Bean
@LoadBalanced
public RestTemplate getRestTemplate(){
return new RestTemplate();
}
}
Controller类
@RestController
@RequestMapping("demo")
public class DemoController {
@Autowired
private RestTemplate restTemplate;
@Value("${service-url.nacos-user-service}")
private String SERVICE_URL;
@GetMapping("info/{id}")
public JsonResult fallbackInfo(@PathVariable("id") Long id){
JsonResult jsonResult = restTemplate.getForObject(SERVICE_URL+"/data/info/"+id,JsonResult.class);
return jsonResult;
}
}
@SentinelResource注解
属性
@SentinelResource官方文档说明
- value 资源名称,必需项(不能为空)
- blockHandler / blockHandlerClass: blockHandler 对应处理 BlockException 的函数名称,可选项。之前有提到过blockHandler和blockHanlderClass用法
- fallback:fallback 函数名称,可选项,用于在抛出异常的时候提供 fallback 处理逻辑。fallback 函数可以针对所有类型的异常。
- exceptionsToIgnore:用于指定哪些异常被排除掉,不会计入异常统计中,也不会进入 fallback 逻辑中,而是会原样抛出。
@RestController
@RequestMapping("demo")
public class DemoController {
@Autowired
private RestTemplate restTemplate;
@Value("${service-url.nacos-user-service}")
private String SERVICE_URL;
@GetMapping("info/{id}")
@SentinelResource(value = "info", fallback = "fallBackHandler", exceptionsToIgnore = {NullPointerException.class})
public JsonResult fallbackInfo(@PathVariable("id") Long id){
if(id<3){
JsonResult jsonResult = restTemplate.getForObject(SERVICE_URL+"/data/info/"+id,JsonResult.class);
return jsonResult;
}else if(id>10){
throw new RuntimeException("----------RuntimeException----------");
}
throw new NullPointerException("没有查询到该数据");
}
public JsonResult fallBackHandler(Long id,Throwable e){
return new JsonResult(441,"NullPointerException");
}
}
为了提高服用性,避免多个@SentinelResource指定方法带来重复,也可以使用fallbackClass指定一个固定的类来处理
@GetMapping("info/{id}")
@SentinelResource(value = "info",
fallback = "exceptionHandler",
fallbackClass = {FallbackHandler.class})
public JsonResult fallbackInfo(@PathVariable("id") Long id){
if(id<3){
JsonResult jsonResult = restTemplate.getForObject(SERVICE_URL+"/data/info/"+id,JsonResult.class);
return jsonResult;
}
throw new NullPointerException("没有查询到该数据");
}
处理异常的类
package com.cloud.cloudalibabacustomer8084.hanlder;
import com.cloud.cloudalibabacommons.entity.JsonResult;
import lombok.extern.slf4j.Slf4j;
@Slf4j
public class FallbackHandler {
public static JsonResult exceptionHandler(Long id,Throwable e){
log.info("fffffff");
return new JsonResult(446,"访问异常");
}
}
blockHolder和fallbackHolder的区别



