3.负载均衡-LoadBalance

1.背景引入

1.1问题描述

java 复制代码
List<ServiceInstance> instances = discoveryClient.getInstances("product-service");
 //服务可能有多个, 获取第⼀个
EurekaServiceInstance instance = (EurekaServiceInstance) instances.get(0);

针对某个服务,我们启动多个实例进行观察

访问eureka后,可以看到注册的实例

但是发现一个问题,每次进行数据访问时,都是同一台机器

我们启动多个实例, 是希望可以分担其他机器的负荷

1.2负载均衡

负载均衡(Load Balance) , 是⾼并发, ⾼可⽤系统必不可少的关键组件.当服务流量增⼤时, 通常会采⽤增加机器的⽅式进⾏扩容, 负载均衡就是⽤来在多个机器或者其他资源中, 按照⼀定的规则合理分配负载

1.3服务端负载均衡

在服务端进⾏负载均衡的算法分配.

⽐较有名的服务端负载均衡器是Nginx. 请求先到达Nginx负载均衡器, 然后通过负载均衡算法, 在多个服务器之间选择⼀个进⾏访问.

1.4客户端负载均衡

在客⼾端进⾏负载均衡的算法分配.

把负载均衡的功能以库的⽅式集成到客⼾端, ⽽不再是由⼀台指定的负载均衡设备集中提供.

⽐如Spring Cloud的Ribbon, 请求发送到客⼾端, 客⼾端从注册中⼼(⽐如Eureka)获取服务列表, 在发

送请求前通过负载均衡算法选择⼀个服务器,然后进⾏访问.

2.Spring Cloud LoadBalancer

2.1使⽤Spring Cloud LoadBalancer实现负载均衡

(1)给 RestTemplate 这个Bean添加 @LoadBalanced 注解

java 复制代码
@Configuration
public class BeanConfig {
    @Bean
    @LoadBalanced
    public RestTemplate restTemplate(){
        return new RestTemplate();
    }
}

(2)修改IP端⼝号为服务名称

java 复制代码
    public OrderInfo selectOrderById(Integer orderId){
        OrderInfo orderInfo = orderMapper.selectOrderById(orderId);

        String url="http://product-service/product/"+orderInfo.getProductId();

        log.info("远程调用url{}",url);
        ProductInfo productInfo = restTemplate.getForObject(url, ProductInfo.class);
        orderInfo.setProductInfo(productInfo);
        return orderInfo;
    }

2.2负载均衡策略

负载均衡策略是⼀种思想, ⽆论是哪种负载均衡器, 它们的负载均衡策略都是相似的. Spring Cloud LoadBalancer 仅⽀持两种负载均衡策略: 轮询策略 和 随机策略

  • 轮询: 轮询策略是指服务器轮流处理⽤⼾的请求. 这是⼀种实现最简单, 也最常⽤的策略. ⽣活中也有类似的场景, ⽐如学校轮流值⽇, 或者轮流打扫卫⽣.
  • 随机选择: 随机选择策略是指随机选择⼀个后端服务器来处理新的请求.

Spring Cloud LoadBalancer 默认负载均衡策略是轮询策略,如果服务的消费者如果想采⽤随机的负载均衡策略, 也⾮常简单

(1)定义随机算法对象, 通过 @Bean 将其加载到 Spring 容器中

java 复制代码
public class CustomLoadBalancerConfiguration {

    @Bean
    ReactorLoadBalancer<ServiceInstance> randomLoadBalancer(Environment environment,
                                                            LoadBalancerClientFactory loadBalancerClientFactory) {
        String name = environment.getProperty(LoadBalancerClientFactory.PROPERTY_NAME);
        return new RandomLoadBalancer(loadBalancerClientFactory
                .getLazyProvider(name, ServiceInstanceListSupplier.class),
                name);
    }
}

(2)使⽤ @LoadBalancerClient 或者 @LoadBalancerClients 注解

在 RestTemplate 配置类上⽅, 使⽤ @LoadBalancerClient 或 @LoadBalancerClients 注解, 可以对不同的服务提供⽅配置不同的客⼾端负载均衡算法策略

java 复制代码
//name指定这个配置针对的服务名称是"product-service",configuration指定自定义的负载均衡配置类
@LoadBalancerClient(name = "product-service",configuration = CustomLoadBalancerConfiguration.class)
@Configuration
public class BeanConfig {
    @Bean
    @LoadBalanced
    public RestTemplate restTemplate(){
        return new RestTemplate();
    }
}

2.3LoadBalancer原理

LoadBalancer 的实现, 主要是 LoadBalancerInterceptor , 这个类会对 RestTemplate 的请求进⾏拦截, 然后从Eureka根据服务id获取服务列表,随后利⽤负载均衡算法得到真实的服务地址信息,替换服务id

3.服务部署(Linux)

3.1准备数据

  • 安装mysql
  • 数据初始化
  • 修改配置文件,主要包括用户名和密码

3.2服务构建打包

采用Maven打包,对所以服务进行打包

3.3启动服务

java 复制代码
#后台启动eureka-server, 并设置输出⽇志到logs/eureka.log
nohup java -jar eureka-server.jar >logs/eureka.log &
#其他服务同理

#再多启动两台实例
#启动实例, 指定端⼝号为9091
nohup java -jar product-service.jar --server.port=9091 >logs/product-9091.log &
#启动实例, 指定端⼝号为9092
nohup java -jar product-service.jar --server.port=9092 >logs/product-9092.log &

3.4开放端口号

对于不同的服务厂商,开放端口号的方法不同,这里以阿里云为例

相关推荐
第二只羽毛2 小时前
外卖订餐管理系统
java·大数据·开发语言·算法
毕设源码-赖学姐2 小时前
【开题答辩全过程】以 高校篮球社团管理系统 为例,包含答辩的问题和答案
java·eclipse
挫折常伴左右2 小时前
初学HTML2
java·开发语言
2401_831501732 小时前
Devops之Docker安装和使用
运维·docker·devops
invicinble2 小时前
java--se数据处理
java·开发语言
码界奇点2 小时前
基于Django与Zabbix集成的运维故障管理系统设计与实现
运维·django·毕业设计·zabbix·源代码管理
longxibo2 小时前
Ubuntu datasophon1.2.1 二开之二:解决三大监控组件安装后,启动失败:报缺失common.sh
大数据·linux·运维·ubuntu
小尧嵌入式2 小时前
Linux的shell命令
linux·运维·服务器·数据库·c++·windows·算法
码界奇点2 小时前
基于Django与Ansible的自动化运维管理系统设计与实现
运维·python·django·毕业设计·ansible·源代码管理