黑马商城微服务实战开发(服务治理)
·
1.微服务拆分远程调用
当一个服务需要调用另一个服务的数据时,我们不能直接拿到另一个服务数据,只能模拟前端,向另一个服务发送http的请求获取数据。
所以我们需要借助一个Spring为我们提供一个RestTemplate工具,可以方便的实现http请求的发送。使用步骤:

启动类
@MapperScan("com.hmall.cart.mapper")
@SpringBootApplication
public class CartApplication {
public static void main(String[] args) {
SpringApplication.run(CartApplication.class, args);
}
//spring的启动类同时也是一个配置类,我们可以配置RestTemplate
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}
}
private final RestTemplate restTemplate;
private void handleCartItems(List<CartVO> vos) {
// 1.获取商品id
Set<Long> itemIds = vos.stream().map(CartVO::getItemId).collect(Collectors.toSet());
// 2.查询商品
// List<ItemDTO> items = itemService.queryItemByIds(itemIds);
//2.1 使用restTemplate获取http响应
ResponseEntity<List<ItemDTO>> response = restTemplate.exchange(
"http://localhost:8081/items?ids={ids}",
HttpMethod.GET,
null,
new ParameterizedTypeReference<List<ItemDTO>>() {
},
Map.of("ids", CollUtil.join(itemIds, ","))
);
//2.2解析响应
if (!response.getStatusCode().is2xxSuccessful()){
throw new BizIllegalException("查询商品信息异常");
}
List<ItemDTO> items = response.getBody();
if (CollUtils.isEmpty(items)) {
return;
}
// 3.转为 id 到 item的map
Map<Long, ItemDTO> itemMap = items.stream().collect(Collectors.toMap(ItemDTO::getId, Function.identity()));
// 4.写入vo
for (CartVO v : vos) {
ItemDTO item = itemMap.get(v.getItemId());
if (item == null) {
continue;
}
v.setNewPrice(item.getPrice());
v.setStatus(item.getStatus());
v.setStock(item.getStock());
}
}
2.服务治理(注册中心)
如果有多台机器部署item-service,我们写的代码只能访问端口8081,不能实现负载均衡,而且如果这个端口挂了,跟着cart-service也不能使用这个功能,这就是RestTemplate存在的问题

2.1注册中心的原理

2.2 nacos注册中心
目前开源的注册中心框架有很多,国内比较常见的有:
- Eureka:Netflix公司出品,目前被集成在SpringCloud当中,一般用于Java应用
- Nacos:Alibaba公司出品,目前被集成在SpringCloudAlibaba中,一般用于Java应用
- Consul:HashiCorp公司出品,目前集成在SpringCloud中,不限制微服务语言
以上几种注册中心都遵循SpringCloud中的API规范,因此在业务开发使用上没有太大差异。由于Nacos是国内产品,中文文档比较丰富,而且同时具备配置管理功能(后面会学习),因此在国内使用较多,所以选择nacos。
2.3服务注册
1.在item-service的pom.xml中添加依赖:
<!--nacos 服务注册发现-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
2.配置Nacos
在item-service的application.yml中添加nacos地址配置:
spring:
application:
name: item-service # 服务名称
cloud:
nacos:
server-addr: 192.168.150.101:8848 # nacos地址
2.4服务发现
1.在cart-service的pom.xml中添加依赖:
<!--nacos 服务注册发现-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
2.配置Nacos
在cart-service的application.yml中添加nacos地址配置:
spring:
application:
name: cart-service # 服务名称
cloud:
nacos:
server-addr: 192.168.150.101:8848 # nacos地址
3.服务发现
private final DiscoveryClient discoveryClient;
// 2.查询商品
// List<ItemDTO> items = itemService.queryItemByIds(itemIds);
//2.1根据服务名称获取服务的实列列表
List<ServiceInstance> instances = discoveryClient.getInstances("item-service");
if (CollUtils.isEmpty(instances)){
return;
}
ServiceInstance serviceInstance = instances.get(RandomUtil.randomInt(instances.size()));
//2.3 使用restTemplate获取http响应
ResponseEntity<List<ItemDTO>> response = restTemplate.exchange(
serviceInstance.getUri() +"/items?ids={ids}",
HttpMethod.GET,
null,
new ParameterizedTypeReference<List<ItemDTO>>() {
},
Map.of("ids", CollUtil.join(itemIds, ","))
);
3.openfeign
3.1openfeign初步认识
上述代码,为了获取服务数据需要写大量代码,所以就出现了利用openfeign。
openfeign是一个声明式的http客户端,其作用是基于mvc注解,帮助我们优雅的发送http请求。
1.引入依赖
<!--openFeign-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>
<!--负载均衡器-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
2.启用OpenFeign
@EnableFeignClients,如果不在本包下,记得指定包

@EnableFeignClients
@MapperScan("com.hmall.cart.mapper")
@SpringBootApplication
public class CartApplication {
public static void main(String[] args) {
SpringApplication.run(CartApplication.class, args);
}
//spring的启动类同时也是一个配置类,我们可以配置RestTemplate
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}
}
3.创建客户端

4.修改代码
// private final RestTemplate restTemplate;
// private final DiscoveryClient discoveryClient;
private final ItemClient itemClient;
List<ItemDTO> items = itemClient.queryItemByIds(itemIds);`
3.2openfegin连接池

1.引入依赖

2.开启连接池功能

3.3日志

如何定制日志级别

更多推荐

所有评论(0)