源码分析 dynamic-datasource-spring-boot-starter 组件负载均衡策略

dynamic-datasource-spring-boot-starter 组件自带了两个负载均衡算法1

  • LoadBalanceDynamicDataSourceStrategy 轮询。

  • RandomDynamicDataSourceStrategy 随机。

其中轮询是默认算法。

这两个算法类都实现了 DynamicDataSourceStrategy 接口:

所以如果需要自定义负载均衡算法,就可以实现DynamicDataSourceStrategy 接口。该接口只定义了一个determineDataSource方法,用于决定多个数据源的选择策略:


public interface DynamicDataSourceStrategy {

 /**

 * determine a database from the given dataSources

 *

 * @param dataSources given dataSources

 * @return final dataSource

 */

 DataSource determineDataSource(List dataSources);

}

(1)轮询算法


public class LoadBalanceDynamicDataSourceStrategy implements DynamicDataSourceStrategy {

 /**

 * 负载均衡计数器

 */

 private final AtomicInteger index = new AtomicInteger(0);

 @Override

 public DataSource determineDataSource(List dataSources) {

 return dataSources.get(Math.abs(index.getAndAdd(1) % dataSources.size()));

 }

}

这里利用 AtomicInteger 类创建了一个线程安全2的 Integer作为计数器,默认为 0。

然后在 determineDataSource 实现方法中,利用 AtomicInteger#getAndAdd() 累加该计算器,接着把结果值除以数据源总数,求余数。

这里的 Math.abs() 似乎没有必要,因为被除数与除数肯定大于 0。

可以改造如下:


/**

* 计数器增长量

 */

public static final int INCREASE_AMOUNT = 1;

/**

* 计数器

 */

private final AtomicInteger counter = new AtomicInteger(0);

@Override

public DataSource determineDataSource(List dataSources) {

 int newValue = counter.getAndAdd(INCREASE_AMOUNT);

 int nextIndex = newValue % dataSources.size();

 return dataSources.get(nextIndex);

}

(2)随机算法


public class RandomDynamicDataSourceStrategy implements DynamicDataSourceStrategy {

 @Override

 public DataSource determineDataSource(List dataSources) {

 return dataSources.get(ThreadLocalRandom.current().nextInt(dataSources.size()));

 }

}

这里使用了ThreadLocalRandom 来生成线程安全的随机数3,current() 方法是其静态工厂。


  1. 动态数据源自定义负载均衡策略.

  2. 原子操作类AtomicInteger详解.

  3. ThreadLocalRandom.

你可能感兴趣的:(源码分析 dynamic-datasource-spring-boot-starter 组件负载均衡策略)