SpringCloud——Nacos

1. 基础入门

1.1. 简介

官网:Nacos 快速开始 | Nacos 官网

Nacos /nɑ:kəʊs/ 是 Dynamic Naming and Configuration Service的首字母简称,一个更易于构建云原生应用的动态服务发现、配置管理和服务管理平台。

1.2. 安装

  • Docker 安装
docker run -d -p 8848:8848 -p 9848:9848 -e MODE=standalone --name nacos nacos/nacos-server:v2.4.3

2. 注册中心

2.1. 依赖引入

<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>

2.2. 整合配置

1、在 application.properties中配置如下

spring.cloud.nacos.discovery.server-addr=127.0.0.1:8848

#暂未用到配置中心功能,需要关闭配置检查
#spring.cloud.nacos.config.import-check.enabled=false

2、开启服务注册/发现功能

@EnableDiscoveryClient //核心注解
@SpringBootApplication
public class OrderMainApplication {

	public static void main(String[] args) {
		SpringApplication.run(OrderMainApplication.class, args);
	}

}

2.3. 服务注册

2.3.1. 查看效果

访问:http://localhost:8848/nacos 可以看到服务已经注册上来;

2.3.2. 注册更多
  1. 创建 service-product服务
  2. 引入 nacos依赖
  3. 配置 nacos地址信息
    1. 注意:每个微服务端口不一样
  1. 启动应用,查看是否注册成功

2.3.3. 启动集群

service-order为例,启动 movie 的三个服务。

  1. idea 搜索 services面板,添加 SpringBoot 项目。
  2. 复制 OrderMainApplication三份,每个启动命令重新指定端口

2.3.4. 查看集群

2.4. 服务发现(官方或第三方配置好的组件,直接注入使用)

2.4.1. DiscoveryClient
@Autowired
DiscoveryClient discoveryClient;
@Test
void discoveryClientTest(){
    for (String service : discoveryClient.getServices()) {
        System.out.println("service = " + service);
        //获取ip+port
        List<ServiceInstance> instances = discoveryClient.getInstances(service);
        for (ServiceInstance instance : instances) {
            System.out.println("ip:"+instance.getHost()+";"+"port = " + instance.getPort());
        }
    }
}

2.4.2. NacosServiceDiscovery
@Autowired
NacosServiceDiscovery nacosServiceDiscovery;
@Test
void  nacosServiceDiscoveryTest() throws NacosException {
    for (String service : nacosServiceDiscovery.getServices()) {
        System.out.println("service = " + service);
        List<ServiceInstance> instances = nacosServiceDiscovery.getInstances(service);
        for (ServiceInstance instance : instances) {
            System.out.println("ip:"+instance.getHost()+";"+"port = " + instance.getPort());
        }
    }
}

2.5. 远程调用

2.5.1. 配置 RestTemplate(全局可唯一使用,直接注入Bean)
@Configuration
public class UserConfiguration {

    @Bean
    RestTemplate restTemplate() {
        return new RestTemplate();
    }
}
2.5.2. 测试调用
	@Autowired
	RestTemplate restTemplate;


	@Test
	void testRestTemplate() {
			String forObject = restTemplate.getForObject("http://localhost:8080/movie", String.class);
			System.out.println(forObject);
			System.out.println("-----------------------------");

	}

2.5.3. 小结
  1. 使用 RestTemplate 可以获取到远程数据
  2. 必须精确指定地址和端口
  3. 如果远程宕机将不可用

期望:可以负载均衡调用,不用担心远程宕机

2.6. 负载均衡

2.6.1. 依赖导入
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>

2.6.2. LoadBalancerClient
    // 进阶2:完成负载均衡发送请求
    private Product getProductFromRemoteWithLoadBalance(Long productId){
        //1、获取到商品服务所在的所有机器IP+port
        ServiceInstance choose = loadBalancerClient.choose("service-product");
        //远程URL
        String url = "http://"+choose.getHost() +":" +choose.getPort() +"/product/"+productId;
        log.info("远程请求:{}",url);
        //2、给远程发送请求
        Product product = restTemplate.getForObject(url, Product.class);
        return product;
    }

2.6.3. 注解式负载均衡
@Configuration
public class UserConfiguration {
    
    @LoadBalanced
    @Bean
    RestTemplate restTemplate() {
        return new RestTemplate();
    }
    
}

    // 进阶3:基于注解的负载均衡
    private Product getProductFromRemoteWithLoadBalanceAnnotation(Long productId){

        String url = "http://service-product/product/"+productId;
        //2、给远程发送请求; service-product 会被动态替换
        Product product = restTemplate.getForObject(url, Product.class);
        return product;
    }
2.6.4.
2.6.5. 小结
  1. 负载均衡调用只需要传入服务名
  2. 请求发起之前会自动去注册中心确定微服务地址
  3. 如果微服务宕机,会自动剔除在线名单,请求将不会发过去

2.7. 深入探索

经典面试题:

如果注册中心宕机,远程调用是否可以成功?

  1. 从未调用过,如果宕机,调用会立即失败
  2. 调用过,如果宕机,因为会缓存名单,调用会成功
  3. 调用过,如果注册中心和对方服务宕机,因为会缓存名单,调用会阻塞后失败(Connection Refused)

3. 配置中心

主要提示:

3.1. 整合配置

3.1.1. 依赖引入
<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>
3.1.2. 配置文件

application.properties

# 指定配置中心地址
spring.cloud.nacos.server-addr=localhost:8848
spring.config.import=nacos:service-order.properties

3.1.3. 配置集-dataId

3.2. 动态刷新

3.2.1. @RefreshScope
@RefreshScope//自动刷新
@RestController
public class OrderController {


    @Autowired
    OrderService orderService;

   @Value("${order.timeout}")
   String orderTimeout;
   @Value("${order.auto-confirm}")
   String orderAutoConfirm;

    @Autowired
    OrderProperties orderProperties;

    @GetMapping("/config")
    public String config(){
        return "order.timeout="+orderProperties.getTimeout()+"; " +
                "order.auto-confirm="+orderProperties.getAutoConfirm() +";"+
                "order.db-url="+orderProperties.getDbUrl();
    }
}

3.2.2. ConfigurationProperties

无需 @RefreshScope,自动绑定配置,动态更新

@Component
@ConfigurationProperties(prefix = "order") //配置批量绑定在nacos下,可以无需@RefreshScope就能实现自动刷新
@Data
public class OrderProperties {

    String timeout;

    String autoConfirm;

    String dbUrl;
}

3.3. NacosConfigManager配置监听

	@Bean
	ApplicationRunner applicationRunner(NacosConfigManager manager){
		return args -> {
			ConfigService configService = manager.getConfigService();
			configService.addListener("service-order.properties", "DEFAULT_GROUP", new Listener() {
				@Override
				public Executor getExecutor() {
					return Executors.newFixedThreadPool(4);
				}

				@Override
				public void receiveConfigInfo(String configInfo) {
					System.out.println("configInfo = " + configInfo);
				}
			});
		};
	}

3.4.

3.5. namespace、dataId、group

3.5.1. namespace

命名空间:实现多环境隔离,如:开发、测试、预发、生产等

3.5.2. dataId

数据集id:就是以前配置文件的名字。完整写法:名字.后缀 如:common.properties

3.5.3. groupId

分组id:一般可以用微服务的名字作为自己的组。

3.5.4. 推荐用法

 

后续将讲解OpenFeign如何更简化远程调用开发

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值