zoukankan      html  css  js  c++  java
  • [zebra源码]GroupDataSource读库的负载均衡

    GroupDataSource的物理结构
    image.png

    负载均衡的对象

    zebra的负载均衡是在GroupDataSource的读库 readDataSource( LoadBalanceDataSource) 中进行的, 它内部包含多个读库节点的SingleDataSource

    LoadBalanceDataSource#getConnection() -> router.select(context);

    关键对象DataSourceRouter 数据源路由器

    负载均衡由 DataSourceRouter 数据源路由器实现具体的逻辑 => 它是个套娃

    image.png

    包含 中心路由、idc路由、区域路由和权重, 这几个负载均衡算法是嵌套执行的, 从范围大到小逐层进行

    默认的 routerStrategy=“WeightRouter" 即 WeightDataSourceRouter 在最里层同机房范围内的多个读库是根据权重来选择的
    image.png

    了解更多,官方文档 zebra路由设计

    区域、中心、机房,最后都会走向基于权重的路由 WeightDataSourceRouter#select()

    public RouterTarget select(Set<RouterTarget> excludeTargets) {
    	if (!this.targets.isEmpty()) {
    		TreeSet<RouterTarget> weights = this.targets;
    		int tmpGroupDataSourceTargetSize = this.groupDataSourceTargetSize;
    
    		if (excludeTargets != null && !excludeTargets.isEmpty()) {
    			// 需要排除某些GroupDataSourceTarget的话,就重新copy一个weights
    			TreeSet<RouterTarget> copyWeights = new TreeSet<RouterTarget>();
    			tmpGroupDataSourceTargetSize = 0;
    			for (RouterTarget routerTarget : weights) {
    				if (excludeTargets.contains(routerTarget)) {
    					continue;
    				}
    				// 先将节点先放入到排序集合中
    				// 假设  节点1 -> weight=2, 节点2 -> weight=3
    				// 则在排序树中 节点1 -> sort=2, 节点2 -> sort = 2+3
    				int weight = routerTarget.getWeight();
    				tmpGroupDataSourceTargetSize += weight;
    				copyWeights.add(new RouterTarget(routerTarget.getId(), weight, tmpGroupDataSourceTargetSize - 1));
    			}
    			weights = copyWeights;
    		}
    
    		if (weights.isEmpty() || tmpGroupDataSourceTargetSize <= 0) {
    			return null;
    		}
    		// 取一个随机数
    		int randomNum = random.nextInt(tmpGroupDataSourceTargetSize);
    		RouterTarget tempForSearch = new RouterTarget(null, -1, randomNum);
    		//排序集合中最靠近随机数的entry则为目标节点
    		return weights.ceiling(tempForSearch);
    	} else {
    		return null;
    	}
    }
    }
    
    

    想要查看具体执行细节 ,可以debug 源码里 com.dianping.zebra.group.router 包下的 DataSourceRouter 单测

    完整目录:数据库中间件zebra源码分析

    本文来自博客园,作者:mushishi,转载请注明原文链接:https://www.cnblogs.com/mushishi/p/15022077.html

  • 相关阅读:
    Meta标签详解
    Python: 什么是*args和**kwargs
    如何进行 WebSocket 协议的压测
    在Mac上使用Microsoft Remote Desktop
    报表测试方法与注意事项
    Linux服务部署Yapi项目(安装Node Mongdb Git Nginx等) Linux服务部署Yapi
    mac安装brew(亲测)
    Linux下查看系统配置
    iTerm--比Terminal(终端)更好用的命令行工具
    协方差矩阵
  • 原文地址:https://www.cnblogs.com/mushishi/p/15022077.html
Copyright © 2011-2022 走看看