JAVA常用负载均衡算法实现

一、负载均衡的概念



      在大型的分布式架构中,对于负载较高的服务来说,往往对应着多台机器组成的集群,当请求到来的时候,为了将请求均衡的分配给后端服务器需要有相应的负载均衡算法来支持,通过相应的负载均衡算法选取一台机器来处理客户端请求,这个过程称为服务的负载均衡。


二、常用负载均衡算法实现


       常用的负载均衡算法主要有随机法,轮询法,加权随机,加权轮询,最小连接数,一致性hash等。随机法,轮询法都比较简单,随机算法不考虑服务器的负载实际中很少使用,轮询算法在服务的上线下线时无法及时感应到也较少使用,下面重点介绍比较常用的加权轮询和一致性hash。 

 2.1 负载均衡接口
 
import java.util.List;
 
import cn.fzjh.vo.ServiceInstance;
 
public interface LoadBalance {
     
    //根据请求选择一个服务实例
    ServiceInstance chooseServerInstance();
 
    /**
     * 设置服务的信息
     * 
     * @param serviceName 服务名
     * @param version 服务版本
     */
    void setService(String serviceName, String version);
     
    /**
     * 初始化
     */
    void init();
     
    /**
     * 获取全部服务列表
     * 
     * @return
     */
    List<serviceinstance> getServiceInstanceList();
     
    /**
     * 更新服务实例列表
     */
    void updateServerInstanceList();
     
    /**
     * 隔离一个服务实例
     * 
     * @param server
     */
    void isolateServerInstance(String server);
 
    /**
     * 恢复一个服务实例
     * 
     * @param server
     */
    void resumeServerInstance(String server);
}

    2.2 抽象负载均衡基类

   

import java.util.List;
import java.util.Random;
 
import javax.annotation.Resource;
 
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
 
import cn.fzjh.jk.LoadBalance;
import cn.fzjh.rule.DynamicUploadRule;
import cn.fzjh.vo.ServiceInstance;
 
//抽象的负载均衡基类,提供基本的服务信息和相关服务实例列表的管理
public abstract class AbstractLoadBalance implements LoadBalance {
 
    protected final Logger logger = LoggerFactory
            .getLogger(AbstractLoadBalance.class);
     
    @Resource(name="dynamicUploadRule")
    private transient DynamicUploadRule dynamicUploadRule;
 
    protected String serviceName;
 
    protected String version;
 
    // 特定版本的服务的标识
    private transient String serviceKey;
 
    protected List<serviceinstance> serviceInstanceList;
 
    @Override
    public void setService(String serviceName, String version) {
        this.serviceName = serviceName;
        this.version = version;
        this.serviceKey = genKey(serviceName, version);
    }
 
    // 随机算法获取可利用的服务列表
    @Override
    public ServiceInstance chooseServerInstance() {
        List<serviceinstance> allServiceList = getAllServiceInstanceList();
        if (null == allServiceList) {
            return null;
        }
        ServiceInstance serviceInstance = null;
        int indexOfLoop = 0;
        Random random = new Random();
        if (null != allServiceList && allServiceList.size() > 0) {
            int serviceCount = allServiceList.size();
            while (null == serviceInstance && indexOfLoop < serviceCount * 5) {// 由于是随机选取,不能在serverCount内选出
                int index = random.nextInt(serviceCount);
                serviceInstance = allServiceList.get(index);
                logger.info("随机选择算法获取可用的服务:" + serviceInstance.getServerName());
                if (serviceInstance.isIsolated()) {
                    logger.info("选择的服务暂时不可用:" + serviceInstance.getServerName()
                            + ",重新选择");
                    indexOfLoop++;
                    serviceInstance = null;
                }
            }
        }
        return serviceInstance;
    }
 
    @Override
    public void init() {
        // 拿到所有的服务器列表
        List<serviceinstance> serviceInstances = getAllServiceInstanceList();
        setServiceInstanceList(serviceInstances);
    }
 
    @Override
    public List<serviceinstance> getServiceInstanceList() {
        return serviceInstanceList;
    }
  • 4
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值