springcloud 中服务间两种restful调用方式
1、RestTemplate
2、Feign
以订餐系统为例:
RestTemplate的三种方法:
第一种方式(直接使用RestTemplate):
product系统代码:端口 -Dserver.port=8080
@RestController
public class ServerController {
@GetMapping("/msg")
public String msg() {
return "this is product' msg";
}
}
order系统代码:端口-Dserver.port=8081
@RestController
public class ServerController {
@GetMapping("/getProductMsg")
public String getProductMsg() {
//第一种方式
RestTemplate restTemplate = new RestTemplate();
String response = restTemplate.getForObject("http://localhost:8080/msg",String.class);
return response ;
}
}
启动两个应用,访问:http://localhost:8081/getProductMsg
这种方式的缺点:
1、调用url在代码里面是固定写死的,线上的时候eureka上面会有多台服务器,IP地址肯定是不知道的。这样子访问肯定是不行的。
2、对方有多个地址,起了多个实例,做不了负载均衡。
第二种方式(通过LoadBalancerClient这个对象通过应用名字PRODUCT获取的其中任意一个url,再使用RestTemplate):
product系统代码和第一种方式一样。
order系统代码:
@RestController
public class ServerController {
@Autowired
private LoadBalancerClient loadBalancerClient;
@GetMapping("/getProductMsg")
public String getProductMsg() {
//第二种方式
RestTemplate restTemplate = new RestTemplate();
ServiceInstance serviceInstance = loadBalancerClient.choose("PRODUCT");
String url = String.format("http://%s:%s",serviceInstance.getHost,serviceInstance.getPort() + "/msg");
String response = restTemplate.getForObject(url,String.class);
return response ;
}
}
第三种方式:(利用@LoadBalanced注解,可在restTemplate里面应用名字)
product系统代码和第一种方式一样。
order系统代码:
@Component
public class RestTemplateConfig {
@Bean
@LoadBalanced
public RestTemplate restTemplate(){
return new RestTemplate();
}
}
@RestController
public class ServerController {
@Autowired
private RestTemplate restTemplate ;
@GetMapping("/getProductMsg")
public String getProductMsg() {
//第三种方式
String response = restTemplate.getForObject("http://PRODUCT/msg",String.class);
return response ;
}
}
Feign
orider系统代码:
@RestController
public class ServerController {
@GetMapping("/msg")
public String msg() {
return "this is product' msg";
}
}
1、首先要在调用方增加依赖
<dependency>
<groundId>org.springframework.cloud</groundId>
<artifactId>spring-cloud-starter-feign</artifactId>
</dependency>
2、然后在启动类添加注解:@EnableFeignClients
3、定义好需要调用的接口, produceMsg方法命名和orider系统msg方法命名没关系,他们是通过@GetMapping("/msg")来联系的。
@FeignClient(name="product")
public interface ProductClient{
@GetMapping("/msg")
String produceMsg();
}
@RestController
public class ServerController {
@Autowired
private ProductClient productClient;
@GetMapping("/getProductMsg")
public String getProductMsg() {
String response = productClient.produceMsg();
return response ;
}
}
Feign是声明式REST客户端(伪RPC),采用了基于接口的注释。