# bs-service-a
**Repository Path**: SpringCloudTestGroup/bs-service-a
## Basic Information
- **Project Name**: bs-service-a
- **Description**: No description available
- **Primary Language**: Unknown
- **License**: Not specified
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 0
- **Created**: 2018-11-26
- **Last Updated**: 2020-12-19
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# bs-service-a
#### 项目介绍
主要演示
feign 及 Hystrix 的机制的测试
通过
bs-service-a 通过 feign 访问 bs-service-b业务
#### 软件架构
软件架构说明
#### 安装教程
1. pom.xml
```
org.springframework.cloud
spring-cloud-starter-openfeign
org.springframework.cloud
spring-cloud-starter-netflix-hystrix
```
2. 程序入口
```
package com.example.a;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.circuitbreaker.EnableCircuitBreaker;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.context.annotation.Configuration;
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients `标记启用Feign功能`
@EnableCircuitBreaker `标记启用hystrix功能`
public class ServiceAApplication {
public static void main(String[] args) {
long starTime = System.currentTimeMillis();
SpringApplication.run(ServiceAApplication.class, args);
long endTime = System.currentTimeMillis();
long time = endTime - starTime;
System.out.println("\nStart Time: " + (time / 1000) + " s");
System.out.println("...............................................................");
System.out.println("..................Service starts successfully..................");
System.out.println("...............................................................");
}
}
```
3. application.yml or bootstrap.yml
```
hystrix:
command:
default:
circuitBreaker:
forceOpen: false
#方法级的key
"ServiceBClient#doGetFromB(String,Integer)":
circuitBreaker:
#设置窗口时间内的调用失败次数, 达到次数此窗口期内所有调用走fallback
requestVolumeThreshold: 1
#设置熔断观察窗口的时间
sleepWindowInMilliseconds: 10000
execution:
isolation:
# strategy: Semaphore
thread:
#设置超时时间
timeoutInMilliseconds: 3000
fallback:
isolation:
semaphore:
maxConcurrentRequests: 1
threadpool:
#类级的key
bs-service-b:
# default:
#线程池的配置
coreSize: 10
maximumSize: 10
allowMaximumSizeToDivergeFromCoreSize: true
# maxQueueSize: 1
# queueSizeRejectionThreshold: 1
ribbon:
ConnectTimeout: 10000
ReadTimeout: 10000
feign:
hystrix:
enabled: true
eureka:
client:
registry-fetch-interval-seconds: 1
```
4. FeignClient
```
package com.example.a.client;
import com.example.a.fallback.ServiceBFallBack;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.*;
/**
* Created by liuliyun-ds on 2018/6/27.
*/`访问服务器bs-service-b,并且有返回错误熔断处理机制`
@FeignClient(name = "bs-service-b", fallback = ServiceBFallBack.class)
public interface ServiceBClient {
@RequestMapping(value = "/serviceB/test", method = RequestMethod.GET)
String doGetFromB(@RequestParam(value = "arg") String arg, @RequestParam(value = "s") Integer s);
}
```
4. FallBack类型
```
package com.example.a.fallback;
import com.example.a.client.ServiceBClient;
import org.springframework.stereotype.Component;
import org.springframework.web.bind.annotation.RequestParam;
/**
* Created by liuliyun-ds on 2018/11/26.
*/
@Component
public class ServiceBFallBack implements ServiceBClient{
@Override`同接口方法,熔断处理机制后返回信息`
public String doGetFromB(@RequestParam(value = "arg") String arg, @RequestParam(value = "s") Integer s){
return "messageFromBFallback\n";
}
}
```
5. 测试入口
```
package com.example.a.controller;
import com.example.a.client.ServiceBClient;
import com.example.a.client.ServiceCClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.web.bind.annotation.*;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
/**
* Created by liuliyun-ds on 2018/11/9.
*/
@RestController
@RequestMapping("/serviceA")
@RefreshScope
public class AController {
@Value("${test.message}")
private String message;
@Autowired
private ServiceBClient serviceBClient;
@Autowired
private ServiceCClient serviceCClient;
@GetMapping("/configTest")
public String doGetMessage(){
// return null;
return message;
}
@GetMapping("/test")
public String doGet(String arg, Integer s, String same, Integer index){
String messageA = "messageFromA\n";
Runnable runnable = new Runnable() {
@Override
public void run() {
String message = serviceBClient.doGetFromB(arg, s);
System.out.println("+++++++++++++++++++++" + message);
}
};
if ("yes".equals(same)){
ExecutorService executorService = Executors.newFixedThreadPool(10);
for(int i = 0; i<5; i++){
executorService.submit(runnable);
}
executorService.shutdown();
}else {
String messageB = serviceBClient.doGetFromB(arg, s);
System.out.println("========================" + messageA + messageB);
return messageA + messageB;
}
return messageA;
}
}
```
```
spring-cloud-starter-sleuth
跟踪原理:pom中依赖spring-cloud-starter-sleuth包后,每次链路请求都会添加一串追踪信息,格式是[server-name, main-traceId,sub-spanId,boolean]
第一个参数:服务结点名称;
第二个参数:一条链路唯一的ID,叫TraceID
第三个参数:链路中每一环的ID,叫做SpanID
第四个参数:是否将信息输出到Zipkin等服务收集和展示。
这种机制是如何实现的呢?我们知道Spring Framework微服务是通过http协议通信的(与之对立的是dubbo的RPC方式),所以Sleuth的实现也是基于http的,又不能影响正常的业务传递,所以能做文章的只能在http 的header上。
Sleuth会在每个请求的header上添加跟踪需求的重要信息,例如:
X-B3-TraceId:对应TraceID;
X-B3-SpanId:对应SpanID;
X-B3-ParentSpanId:前面一环的SpanID;
X-B3-Sampled:是否被选中抽样输出;
X-Span-Name:工作单元名称。
x-b3-spanid
x-b3-parentspanid
x-b3-sampled
x-b3-traceid
以上参考:
牛麦康纳 https://blog.csdn.net/yejingtao703/article/details/78064066
logback.xml 参考
作者:楠倏之语
链接:https://www.jianshu.com/p/6d6b52c7624f
來源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。
```
#### 使用说明
1. xxxx
2. xxxx
3. xxxx
#### 参考贡献
1. 官网:[openfeign官网](http://cloud.spring.io/spring-cloud-openfeign/single/spring-cloud-openfeign.html)
2. 新建 Feat_xxx 分支
3. 提交代码
4. 新建 Pull Request