mycat主备切换分析

https://blog.csdn.net/boonya/article/details/76039070

 

public PhysicalDatasource

 

getSource() {

switch (writeType) {  

case WRITE_ONLYONE_NODE: {  //不区分,返回当前的,当前挂了,返回下一个

return writeSources[activedIndex];

}

case WRITE_RANDOM_NODE: { // 写操作随机发送,

 

int index = Math.abs(wnrandom.nextInt()) % writeSources.length;

PhysicalDatasource result = writeSources[index];

if (!this.isAlive(result)) {  //当前是死的,找所有活着的,在其中随机找个

 

// find all live nodes

ArrayList<Integer> alives = new ArrayList<Integer>(writeSources.length - 1);

for (int i = 0; i < writeSources.length; i++) {

if (i != index) {

if (this.isAlive(writeSources[i])) {

alives.add(i);

}

}

}

 

if (alives.isEmpty()) {

result = writeSources[0];

} else {

// random select one

index = Math.abs(wnrandom.nextInt()) % alives.size();

result = writeSources[alives.get(index)];

 

}

}

 

if (LOGGER.isDebugEnabled()) {

LOGGER.debug("select write source " + result.getName()

+ " for dataHost:" + this.getHostName());

}

return result;

}

default: {

throw new java.lang.IllegalArgumentException("writeType is "

+ writeType + " ,so can't return one write datasource ");

}

}

 

}

 

switch 属性:

 1 表示不自动切换

 2 基于mysql 主从状态决定是否切换

        show slave status

3  基于mysql galary cluster 的切换机制(适合集群)

   show status like 'wsrep%'

 

 

主要通过设置  activedIndex 来达到切换目的

/**

* 主从切换

*/

public boolean switchSource(int newIndex, boolean isAlarm, String reason) {

//如果write_type 不是0 ,直接返回

if (this.writeType != PhysicalDBPool.WRITE_ONLYONE_NODE || !checkIndex(newIndex)) {

return false;

}

final ReentrantLock lock = this.switchLock;

lock.lock();

try {

int current = activedIndex;

if (current != newIndex) {

// switch index

activedIndex = newIndex;

// init again  初始化数据库连接

this.init(activedIndex);

// clear all connections

this.getSources()[current].clearCons("switch datasource");

// write log

LOGGER.warn(switchMessage(current, newIndex, false, reason));

return true;

}

} finally {

lock.unlock();

}

return false;

}

 

/*

* 初始化当前的dataSource

*/

public void init(int index) {

//检查是否合法的index

if (!checkIndex(index)) {

index = 0;

}

int active = -1;

for (int i = 0; i < writeSources.length; i++) {

int j = loop(i + index);

//初始化数据库连接,由于是新切换的需要初始化 配置中的min个数据库连接

if (initSource(j, writeSources[j])) {

                //不切换-1时,如果主写挂了   不允许切换过去

                if(dataHostConfig.getSwitchType()==DataHostConfig.NOT_SWITCH_DS&&j>0)

                {

                   break;

                }

active = j;

activedIndex = active;

initSuccess = true;

LOGGER.info(getMessage(active, " init success"));

//保存记录到文件中

if (this.writeType == WRITE_ONLYONE_NODE) {

// only init one write datasource

MycatServer.getInstance().saveDataHostIndex(hostName, activedIndex);

break;

}

}

}

if (!checkIndex(active)) {

initSuccess = false;

StringBuilder s = new StringBuilder();

s.append(Alarms.DEFAULT).append(hostName).append(" init failure");

LOGGER.error(s.toString());

}

}

 

猜你喜欢

转载自duantonghai.iteye.com/blog/2380278