简体   繁体   中英

Mysql ReplicationDriver - failure handling

I have a MySql Master/Slave replication question that google couldn't seem to answer. When using com.mysql.jdbc.ReplicationDriver, how does the driver handle failures on read replicas? Does it blacklist them, does it try just continue to try them and throw an exception each time (after whatever timeouts are configured)? From my testing it seems that my application is just hanging when I kill a read replica. I'm using tomcat and here is my context.xml....

<Resource auth="Container" 
        driverClassName="com.mysql.jdbc.ReplicationDriver" 
        defaultAutoCommit="false"
        initialSize="10" 
        minIdle="5"
        logAbandoned="false"
        maxIdle="10" 
        maxWait="10000" 
        name="jdbc/db" 
        removeAbandoned="true" 
        testOnBorrow="true"  
        removeAbandonedTimeout="86400"
        testWhileIdle="true" 
        type="javax.sql.DataSource" 
        factory="org.apache.tomcat.jdbc.pool.DataSourceFactory" 
        username="powerptc" 
        password="password"   
        url="jdbc:mysql:replication://localhost:3306,host1,host2:3306/db?allowSlavesDownConnections=true&amp;readFromMasterWhenNoSlaves=true" 
        validationQuery="/* ping */ SELECT 1"
        validationQueryTimeout="5" />

Is there a way to have the driver blacklist a failed read replica ( for x minutes ) instead of just retrying it over and over again?

In this case MySQL driver uses LoadBalanced driver for slaves and switch to master only if picking connection from LoadBalanced cluster of slaves fails. Application hanging because default value for retriesAllDown = 120 . If you set retriesAllDown = 4 , then Load Balancer will sleep 4 times for 250 milliseconds before switching to master.

By default loadBalanceBlacklistTimeout = 0 , it means that load balancer for slaves does not use blacklist. Even if you set loadBalanceBlacklistTimeout > 0 , it does not help, because strange implementation of blacklist, which is empty if all hosts are added to blacklist. But you can use next trick: Use ServerAffinityStrategy and put master hostname to slaves list, but set only slaves as affinity servers.

My working url is:

jdbc:mysql:replication://master:3306,slave1,slave2:3306/db?allowSlaveDownConnections=true&readFromMasterWhenNoSlaves=true&loadBalanceBlacklistTimeout=30000&retriesAllDown=4&loadBalanceStrategy=serverAffinity&serverAffinityOrder=slave1,slave2

In result, master will be used only if there is no available slave

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM