美文网首页
负载均衡是怎么做的?

负载均衡是怎么做的?

作者: 育王净量 | 来源:发表于2019-03-05 20:16 被阅读0次

负载均衡

负载均衡是实现分布式系统高可用的方式之一;负载均衡策略实现了把高并发的流量分摊在其后的服务器集群上;常见的,有基于F5硬件负载均衡设备、基于DNS的负载均衡设备(根据请求IP,选择就近的服务集群提供服务,DNS的缓存不能使负载均衡策略立即生效)、基于软件LVS的负载均衡设备(分两种:七层应用层的Nginx负载均衡、四层传输层的流量分发)。

负载均衡算法

常见负载均衡算法有:轮询策略(顺序轮询和随机轮询)、负载度策略、响应策略、哈希策略。实际项目中使用轮询策略的居多;

基于轮询策略的负载均衡算法实现

public interface LoadBalanceSelector<N, C> {
    N select(C c);
}

@RequiredArgsConstructor
public abstract class AbstractLoadBalanceSelector<N, C> implements LoadBalanceSelector<N, C> {
    
    private final Supplier<List<N>> supplier;
    private final Predicate<N> predicate;
    
    @Override
    public N select(C c) {
        List<N> candidates = supplier.get();
        if (CollectionUtils.isEmpty(candidates)) {
            return null;
        } else if (candidates.size() == 1) {
            return predicate.test(candidates.get(0)) ? candidates.get(0) : null;
        }
        
        N candidate = null;
        int idx = getIndex(candidates);
        for (int i = 0; i < candidates.size(); i++) {
            N n = candidates.get((i + idx) % candidates.size());
            if (predicate.test(n)) {
                candidate = n;
            }
        }
        return candidate;
    }
    
    abstract protected int getIndex(List<N> candidates);
}

public class RandomLoadBalanceSelector<N, C> extends AbstractLoadBalanceSelector<N, C> {
    
    public RandomLoadBalanceSelector(Supplier<List<N>> supplier, Predicate<N> predicate) {
        super(supplier, predicate);
    }
    
    @Override
    protected int getIndex(List<N> candidates) {
        return (int) (ThreadLocalRandom.current().nextDouble() * candidates.size());
    }
}

public class RoundRobinLoadBalanceSelector<N, C> extends AbstractLoadBalanceSelector<N, C> {
    
    private static AtomicInteger idx = new AtomicInteger(0);
    
    public RoundRobinLoadBalanceSelector(Supplier<List<N>> supplier, Predicate<N> predicate) {
        super(supplier, predicate);
    }
    
    @Override
    protected int getIndex(List<N> candidates) {
        return 0x7fffffff & idx.incrementAndGet();
    }
}

public enum LoadBalanceStrategyEnums {
    
    RoundRobin,
    
    RANDOM,
}

public final class LoadBalanceSelectors {
    
    private LoadBalanceSelectors() {
    
    }
    
    public static <N, C> LoadBalanceSelector<N, C> of(Supplier<List<N>> supplier, Predicate<N> predicate,
                                                      LoadBalanceStrategyEnums loadBalanceStrategy) {
        
        if (loadBalanceStrategy == LoadBalanceStrategyEnums.RANDOM) {
            return new RandomLoadBalanceSelector<N,C>(supplier, predicate);
        }
        return new RoundRobinLoadBalanceSelector<N,C>(supplier, predicate);
    }
}

完整版代码

参考文章:

  1. 分布式系统关注点——如何去实施「负载均衡」

  2. 不懂高性能的负载均衡设计?没关系,架构师带你飞

相关文章

网友评论

      本文标题:负载均衡是怎么做的?

      本文链接:https://www.haomeiwen.com/subject/jiqauqtx.html