package net.sinofool.dbpool;
import java.util.List;
import java.util.Map;
import java.util.Timer;
import java.util.TimerTask;
import javax.sql.DataSource;
import net.sinofool.dbpool.config.DBConfig;
import net.sinofool.dbpool.config.DBServer;
import net.sinofool.dbpool.config.DBSource;
import net.sinofool.dbpool.idl.DBPoolClientPrx;
import net.sinofool.dbpool.idl.DBPoolClientPrxHelper;
import net.sinofool.dbpool.idl.DBPoolServerPrx;
import net.sinofool.dbpool.idl.DBPoolServerPrxHelper;
import net.sinofool.dbpool.idl._DBPoolClientDisp;
import org.apache.commons.configuration.Configuration;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class ZeroCIceProvider implements ConfigProvider {
private static final Logger logger = LoggerFactory.getLogger(ZeroCIceProvider.class);
@SuppressWarnings("serial")
private class DBClient extends _DBPoolClientDisp {
@Override
public boolean pushDBInstanceDict(Map<String, net.sinofool.dbpool.idl.DBServer[]> dict, Ice.Current __current) {
logger.info("pushDBInstanceDict start");
List<DBServer> changes = dbconfig.reloadConfig(dict);
for (DBServer change : changes) {
dbsource.closeDataSource(change);
}
logger.info("pushDBInstanceDict finish");
return true;
}
}
private DBConfig dbconfig = new DBConfig();
private DBSource dbsource = new DBSource();
@Override
public DataSource getDataSource(String instance, int access, String pattern) {
DBServer ds = dbconfig.getDBServer(instance, access, pattern);
if (ds != null) {
return dbsource.getDataSource(ds);
}
return null;
}
private Ice.Communicator ic;
private Ice.ObjectAdapter adapter;
private DBPoolClientPrx clientPrx;
private DBPoolServerPrx serverPrx;
private Timer keepAliveTimer = new Timer();
/*
* @param proxy: format like "M:default -h 127.0.0.1 -p 10000"
*/
@Override
public void initialize(final Configuration props) {
Ice.InitializationData initData = new Ice.InitializationData();
initData.properties = Ice.Util.createProperties();
initData.properties.setProperty("Ice.IPv6", "0");
ic = Ice.Util.initialize(initData);
adapter = ic.createObjectAdapterWithEndpoints("DBPoolClient", "default");
clientPrx = DBPoolClientPrxHelper.uncheckedCast(adapter.add(new DBClient(), ic.stringToIdentity("C")));
adapter.activate();
String proxy = props.getString("dbpool.provider.zerocice.proxy", "M:default -h 127.0.0.1 -p 10000");
logger.info("Connecting to " + proxy);
// set timeout 1000, so if the trans data is big we can still get it
serverPrx = DBPoolServerPrxHelper.uncheckedCast(ic.stringToProxy(proxy).ice_timeout(1000));
dbconfig.reloadConfig(serverPrx.getDBInstanceDict());
serverPrx.registerClient(clientPrx);
keepAliveTimer.scheduleAtFixedRate(new TimerTask() {
@Override
public void run() {
try {
// also get config after register to make sure client can
// get
// the change in the period of client lost connection with
// server
logger.debug("Run communicate with server start");
serverPrx.registerClient(clientPrx);
dbconfig.reloadConfig(serverPrx.getDBInstanceDict());
logger.debug("Run communicate with server finish");
} catch (Throwable e) {
logger.warn("Run communicate with server get exception " + e);
}
}
}, 15 * 1000L, 15 * 1000L);
}
@Override
public void close() {
ic.shutdown();
ic.destroy();
}
}