SpringCloud-Eureka,Nacos,Ribbon

本文介绍了SpringCloud服务治理,包括Eureka的详细使用,如服务端搭建、客户端搭建及高可用配置。此外,还提到了Nacos作为注册中心和配置中心的使用,以及Ribbon在客户端负载均衡中的应用。SpringCloud与Dubbo进行了对比,讨论了它们的通信协议和适用场景。文章最后讲解了如何在Ribbon中配置和使用不同的负载均衡策略。
摘要由CSDN通过智能技术生成

Eureka注册中心,Nacos阿里注册中心,Ribbon负载均衡

SpringCloud

一系列框架的有序集合,基于SpringBoot将其整和了起来,简化开发

  • SpringCloud和Dubbo对比:
    在这里插入图片描述
  • Dubbo使用PRC通讯协议
    调用者通过配置或者注解调用注册中心的服务
<!--3.1配置dubbo包扫描,注解调用服务-->
    <!--<dubbo:annotation package="com.yh" />-->
    <!--3.2xml配置方式调用服务-->
    <dubbo:reference id="demoService" interface="com.yh.ours.UserService" />
@Reference()
    private UserService userService;
  • SpringCloud使用RESTful完成通信

Dubbo性能强,小型微服务
SpringCloud功能多,大型微服务开发

  • SpringBoot自身RPC调用
    使用RestTemplate来完成
    服务提供者:产品服务
server:
  port: 8000
# 配置服务名称
spring:
	application:
    name: product
@RestController
@RequestMapping("/product")
public class IProductController {
    @Autowired
    private IProductService iProductService;
    /*@RequestMapping("/findOne")
    public Product findById(int id){
        return iProductService.findById(id);
    }*/
    @RequestMapping("/findOne/{id}")
    public Product findById(@PathVariable("id") int id){
        return iProductService.findById(id);
    }
}

服务消费者:订单服务

server:
  port: 9000
@RestController
@RequestMapping("/orders")
public class IOrdersController {
    @Autowired
    private RestTemplate restTemplate;//用于完成RPC调用
    @Autowired
    private DiscoveryClient discoveryClient;;//该对象可以获取到注册中心中的具体的服务的信息。如服务的ip、端口信息
    @RequestMapping("/find")
    public Product find(int id){
        //通过RestTemplate来完成直接远程调用服务
        String serviceName="product";
        //方法一:根据服务发现对象获取服务信息然后完成调用。注意该方法使用条件是Nacos做注册中心
        //根据服务名获取注册的服务实例
        Lsit<ServiceInstance> serviceList=discoveryClient.getInstances(serviceName);
        //从中随机取出一个。用stram流来操作。
		ServiceInstance aervice=serviceList.stream().findAny();
		//完成RPC远程调用
		 Product forObject = restTemplate.getForObject("http://"+service.getHost()+":"+service.getPort()+"/product/findOne?id=1", Product.class);
		 //方法二:手动拼接服务信息完成调用。
       //当被调用服务没有配置spring.application.name时,直接手动拼接
        Product forObject = restTemplate.getForObject("http://localhost:8000/product/findOne?id=1", Product.class);
        return forObject;
    }
}

注入RestTemplate对象
配置类或引导类注入即可

/*RestTemplate配置类,向容器中注入一个RestTemplate对象*/
@Configuration
public class RestTemplateConfig {
    @Bean
    public RestTemplate restTemplate(){
        return new RestTemplate();
    }
}

SpringCloud服务治理

管理服务,如zookeeper的注册中心

下边三个为常用服务治理组件,其共功能相似

Eureka

在这里插入图片描述

分为服务端(即注册中心)和客户端(服务调用和地址存放者)
服务端需要自己搭建一个模块来实现

在这里插入图片描述

  • 快速入门
服务端搭建
  1. 创建eureka-service模块
    引入SpringBoot起步依赖和Web依赖
<!--导入SpringBoot起步依赖-->
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.5.RELEASE</version>
        <relativePath/>
    </parent>

<dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
  1. 引入SpringCloud和eureka-server相关依赖
<!--导入Spring-Cloud-->
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>Finchley.SR1</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
<!-- eureka-server -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
        </dependency>
  1. yaml中完成EurekaServer得相关配置
# 配置tomcat端口
server:
  port: 8761

# eureka 配置
# eureka 一共有4部分 配置
# 1. dashboard:eureka的web控制台配置
# 2. server:eureka的服务端配置
# 3. client:eureka的客户端配置
# 4. instance:eureka的实例配置


eureka:
  instance:
    hostname: localhost # 主机名
  client:
    service-url:
      defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信

    register-with-eureka: false # 是否将自己的路径 注册到eureka上。eureka server 不需要的,eureka provider client 需要
    fetch-registry: false # 是否需要从eureka中抓取路径。eureka server 不需要的,eureka consumer client 需要

  1. 启动该模块:该模块即为注册中心
    运行该模块引导类
    引导类:必须添加@EnableEurekaServer注解来激活Eureka Server,新版本不需要
@SpringBootApplication
// 启用EurekaServer
@EnableEurekaServer
public class EurekaApp {
    public static void main(String[] args) {
        SpringApplication.run(EurekaApp.class,args);
    }
}
  1. 通过ip:8761访问
    http://localhost:8761/在这里插入图片描述
客户端搭建

建立与EurekaServer得连接并将服务注册到Eureka上

  1. 创建消费者模块,引入SpringBoot和web依赖
<!--导入SpringBoot起步依赖-->
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.5.RELEASE</version>
        <relativePath/>
    </parent>

<dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
  1. 引入SpringCloud和eureka-client相关依赖
<!--导入Spring-Cloud-->
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>Finchley.SR1</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
<!-- eureka-client -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>
  1. yaml中完成对eureka的配置
server:
  port: 9000

# eureka客户端配置
eureka:
  instance:
    hostname: localhost # 主机名
  client:
    service-url:
      defaultZone: http://localhost:8761/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信
#配置应用名,在获取时需要使用
spring:
  application:
    name: eureka-consumer # 设置当前应用的名称。将来会在eureka中Application显示。将来需要使用该名称来获取路径

  1. 完成基于eureka动态的RPC调用
    除了要配置RestTemplate对象实现PRC,还需要直接注入DiscoveryClient对象来获取服务的动态ip和端口
    RestTemplate配置类:
/*RestTemplate配置类,向容器中注入一个RestTemplate对象*/
@Configuration
public class RestTemplateConfig {
    @Bean
    public RestTemplate restTemplate(){
        return new RestTemplate();
    }
}

Controller调用类

@RestController
@RequestMapping("/orders")
public class IOrdersController {
    //注入RestTemplate,用来实现远程调用
    @Autowired
    private RestTemplate restTemplate;
    //注入DiscoveryClient对象,用于动态获取服务ip和host
    @Autowired
    private DiscoveryClient discoveryClient;
	//第一种访问时用?id=1来访问http://localhost:9000/orders/find?id=1
/*    @GetMapping("/find")
    public Product find(int id){
    }*/
    
	//第二种访问时用/1来访问http://localhost:9000/orders/find/1
    @GetMapping("/find/{id}")
    public Product find(@PathVariable("id") int id){
        //演示discoveryClient 使用
        //返回是集合是因为集群环境时同一服务可能被部署多份
        List<ServiceInstance> instances = discoveryClient.getInstances("EUREKA-PROVIDER");//EUREKA-PROVIDER为eureka中注册得服务名

        //判断集合是否有数据
        if(instances == null || instances.size() == 0){
            //集合没有数据
            return null;
        }
        //获取单个服务实例
        ServiceInstance instance = instances.get(0);
        String host = instance.getHost();//获取ip
        int port = instance.getPort();//获取端口

        System.out.println(host);
        System.out.println(port);

        String url = "http://"+host+":"+port+"/ /product/findOne/"+id;

        //String url=;//"http://localhost:8000/product/findOne?id=1"原来不变得写法
        //通过RestTemplate来完成直接远程调用服务
        Product forObject = restTemplate.getForObject(url, Product.class);
        return forObject;
    }
}
  • 配置
  1. server服务端配置
server:
  port: 8761

# eureka 配置
# eureka 一共有4部分 配置
# 1. dashboard:eureka的web控制台配置
# 2. server:eureka的服务端配置
# 3. client:eureka的客户端配置
# 4. instance:eureka的实例配置


eureka:
  instance:
    hostname: localhost # 主机名
  client:
    service-url:
      defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信
    register-with-eureka: false # 是否将自己的路径 注册到eureka上。eureka server 不需要的,eureka provider client 需要
    fetch-registry: false # 是否需要从eureka中抓取路径。eureka server 不需要的,eureka consumer client 需要
  server:
    enable-self-preservation: false # 关闭自我保护机制
    eviction-interval-timer-in-ms: 3000 # 检查服务的时间间隔

  1. 实例(客户端)配置
server:
  port: 8001


eureka:
  instance:
    hostname: localhost # 主机名
    prefer-ip-address: true # 将当前实例的ip注册到eureka server 中。默认是false 注册主机名
    ip-address: 127.0.0.1 # 设置当前实例的ip,自定义
    instance-id: ${eureka.instance.ip-address}:${spring.application.name}:${server.port} # 设置web控制台显示的 实例id
    lease-renewal-interval-in-seconds: 3 # 每隔3 秒发一次心跳包
    lease-expiration-duration-in-seconds: 9 # 如果9秒没有发心跳包,服务器呀,你把我干掉吧~
  client:
    service-url:
      defaultZone: http://localhost:8761/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信
spring:
  application:
    name: eureka-provider # 设置当前应用的名称。将来会在eureka中Application显示。将来需要使用该名称来获取路径


instance-id
在这里插入图片描述

eurake的自我保护机制
eurekaServer默认开启,即当某注册的服务因网络等问题挂了,服务端在一定时间内保留该服务的一种保护机制

Eurake高可用

在这里插入图片描述

搭建多个EurakeServer,即搭建集群
搭建步骤:

  1. 创建2个eurekaServer模块

  2. 导入SpringgBoot起步依赖和SpringCloud依赖以及eurekaServer依赖和web依赖

<!--导入SpringBoot起步依赖-->
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.5.RELEASE</version>
        <relativePath/>
    </parent>
<dependencies>
<!--导入Spring-Cloud-->
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>Finchley.SR1</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!-- eureka-server -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
        </dependency>
    </dependencies>
  1. 修改yaml配置文件
    互相注册
    修改hostname: eureka-server-1时需要更改hosts文件
    在这里插入图片描述
    添加两个Server的配置
127.0.0.1       eureka-server-1
127.0.0.1       eureka-server-2

eurakeServer1:

# 配置tomcat端口
server:
  port: 8761

# eureka高可用配置

eureka:
  instance:
    hostname: eureka-server-1 # 主机名
  client:
    service-url:
      defaultZone: http://eureka-server-2:8762/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信

    register-with-eureka: true # 是否将自己的路径 注册到eureka上。eureka server 不需要的,eureka provider client 需要
    fetch-registry: true # 是否需要从eureka中抓取路径。eureka server 不需要的,eureka consumer client 需要

#配置eureka名
spring:
  application:
    name: eureka-server-ha

eurakeServer2:

# 配置tomcat端口
server:
  port: 8762

# eureka高可用配置

eureka:
  instance:
    hostname: eureka-server-2 # 主机名
  client:
    service-url:
      defaultZone: http://eureka-server-1:8761/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信

    register-with-eureka: true # 是否将自己的路径 注册到eureka上。eureka server 不需要的,eureka provider client 需要
    fetch-registry: true # 是否需要从eureka中抓取路径。eureka server 不需要的,eureka consumer client 需要

#配置eureka名
spring:
  application:
    name: eureka-server-ha



  1. 启动两个Server服务

  2. 修改客户端配置文件
    两个EurekaServer服务端分别注册

server:
  port: 9000

# eureka客户端配置
eureka:
  instance:
    hostname: localhost # 主机名
  client:
    service-url:
      defaultZone: http://eureka-server-2:8762/eureka,http://eureka-server-1:8761/eureka
      #defaultZone: http://localhost:8761/eureka # eureka服务端地址,将来客户端使用该地址和eureka进行通信
#配置应用名,在获取时需要使用
spring:
  application:
    name: eureka-consumer # 设置当前应用的名称。将来会在eureka中Application显示。将来需要使用该名称来获取路径

Consul

Nacos

注册中心+配置中心

  1. 解压缩
    链接:https://pan.baidu.com/s/1QzeChU9VVMcObBCPUD4g_w
    提取码:led9
  2. bin目录下启动startup.cmd
  3. 浏览器访问服务端http://localhost:8848/nacos

在这里插入图片描述
客户端配置
4. 导入依赖nacos–俩


    <dependencies>
<!--导入Spring-Cloud-->
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>Finchley.SR1</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
        <!--nacos-->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
            <version>0.2.2.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>com.alibaba.nacos</groupId>
            <artifactId>nacos-client</artifactId>
            <version>1.1.0</version>
        </dependency>


        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-actuator</artifactId>
        </dependency>



    </dependencies>
  1. 消费端配置注册中心
server:
  port: 8000

# nacos配置
spring:
  cloud:
    nacos:
      discovery:
        server-addr:  127.0.0.1:8848 # 配置nacos 服务端地址
  application:
    name: nacos-provider # 服务名称

  1. 消费端获取已注册的服务
    RestTemplate执行RPC
    DiscoveryClient来动态获取ip和端口
@RestController
@RequestMapping("/orders")
public class IOrdersController {
    //注入RestTemplate,用来实现远程调用
    @Autowired
    private RestTemplate restTemplate;
    //注入DiscoveryClient对象,用于动态获取服务ip和host
    @Autowired
    private DiscoveryClient discoveryClient;
    @GetMapping("/find/{id}")
    public Product find(@PathVariable("id") int id){
        //演示discoveryClient 使用
        //返回是集合是因为集群环境时同一服务可能被部署多份
        List<ServiceInstance> instances = discoveryClient.getInstances("nacos-provider");//EUREKA-PROVIDER为eureka中注册得服务名

        //判断集合是否有数据
        if(instances == null || instances.size() == 0){
            //集合没有数据
            return null;
        }
        //获取单个服务实例
        ServiceInstance instance = instances.get(0);
        String host = instance.getHost();//获取ip
        int port = instance.getPort();//获取端口

        System.out.println(host);
        System.out.println(port);

        String url = "http://"+host+":"+port+"/ /product/findOne/"+id;

        //String url=;//"http://localhost:8000/product/findOne?id=1"原来不变得写法
        //通过RestTemplate来完成直接远程调用服务
        Product forObject = restTemplate.getForObject(url, Product.class);
        return forObject;
    }
}

Ribbon客户端负载均衡

客户端存放负载均衡策略
基于eureka学习

  • 简化远程调用
    原过程:RestTemplate调用getForObject方法传入url和class文件实现RPC而DiscoveryClient则根据注册中心中服务的名称来动态的获取注册中心中服务的ip和host端口号
    简化:不在使用DiscoveryClient来动态获取ip和host
  1. 在配置类中声明RestTemplate时,添加注解@LoadBalanced
/*RestTemplate配置类,向容器中注入一个RestTemplate对象*/
@Configuration
public class RestTemplateConfig {
    @Bean
    @LoadBalanced
    public RestTemplate restTemplate2(){
        return new RestTemplate();
    }
}
  1. 在使用RestTemplate对象发起RPC请求时,将ip:host部分替换为服务提供方的应用名称即可
 //注入RestTemplate,用来实现远程调用
    @Autowired
    private RestTemplate restTemplate;
 /*使用ribbon来简化RPC*/
    @GetMapping("/find2/{id}")
    public Product find2(@PathVariable("id") int id){
        //演示discoveryClient 使用
        String url = "http://EUREKA-PROVIDER/ /product/findOne/"+id;
        //String url=;//"http://localhost:8000/product/findOne?id=1"原来不变得写法
        //通过RestTemplate来完成直接远程调用服务
        Product forObject = restTemplate.getForObject(url, Product.class);
        return forObject;
    }
  • 负载均衡

提供了7种负载均衡策略:
在这里插入图片描述

需要指定负载均衡策略服务提供方的应用名称
实现:

  1. 配置类实现:配置负载均衡策略
/*Ribbon负载均衡策略配置类*/
@Configuration
public class MyRule {
    @Bean
    public IRule iRule(){
    //随机策略
        return new RandomRule();
    }
}

引导类
使用注解@RibbonClient来指定服务提供方的应用名称和设置负载均衡的Bean的配置类

/*启动类*/
@SpringBootApplication
@EnableEurekaClient //该注解 在新版本中可以省略
/*
    配置Ribbon的负载均衡策略
    * name:设置 服务提供方的 应用名称
    * configuration:设置负载均衡Bean
 */
@RibbonClient(name="EUREKA-PROVIDER",configuration = MyRule.class)
public class CustomerApp {
    public static void main(String[] args) {
        SpringApplication.run(CustomerApp.class);
    }
}
  1. 配置实现
    消费客户端配置:
server:
  port: 9000


eureka:
  instance:
    hostname: localhost # 主机名
  client:
    service-url:
      #defaultZone:  http://eureka-server1:8761/eureka,http://eureka-server2:8762/eureka  # eureka服务端地址,将来客户端使用该地址和eureka进行通信
      defaultZone: http://localhost:8761/eureka
spring:
  application:
    name: eureka-consumer # 设置当前应用的名称。将来会在eureka中Application显示。将来需要使用该名称来获取路径


# 配置的方式设置Ribbon的负载均衡策略
EUREKA-PROVIDER: # 设置的服务提供方的 应用名称
  ribbon:
    NFloadBalancerRuleClassName: com.netflix.loadbalancer.RandomRule # 策略类
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值