/* ==================================================================
* Created [2009-4-27 下午11:32:55] by Jon.King
* ==================================================================
* TSS
* ==================================================================
* mailTo:jinpujun@hotmail.com
* Copyright (c) Jon.King, 2009-2012
* ==================================================================
*/
package com.jinhe.tss.core.cachepool.proxy;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import com.jinhe.tss.core.cachepool.Cacheable;
import com.jinhe.tss.core.cachepool.IPool;
import com.jinhe.tss.core.cachepool.TimeWrapper;
import com.jinhe.tss.core.cachepool.strategy.CacheConstants;
/**
* <p>
* Disabler.java
* </p>
* 用动态代理来管理缓存池的缓存策略停用/启用两种状态下存取数据操作的差异。
* </p><p>
* 加入了一个mixin功能,扩展了缓存池的动态代理类的功能,</p><p>
* 其可以直接停用/启用,而不要调用Cachestrategy.setDisabled()。
* </p><p>
* 通过调用本动态代理类,用户可以不去设置IPool接口的</p><p>
* 各个实现类的getObject,putObject,check-out,check-in操作相应的关于停用/启用的处理。</p><p>
*
* @author Jon.King 2006-8-13
*/
public class Disabler{
public static Object disableWrapper(final Object object) {
/*
* 对ThreadPool不进行拦截,因为需要对它进行向下强制转换类型,代理后就不能转换了。if(object instanceof ThreadPool) return object;
* 改进:ThreadPool已实现了IThreadPool接口,动态代理后可以自由转换为IThreadPool接口,上诉的问题不复存在 */
// IPool的实现类都有一个抽象的父类
Class<?>[] interfaces = ProxyUtil.getInterfaces(object.getClass());
if(object instanceof IPool){
Class<?>[] temp = new Class[interfaces.length + 1];
for(int i = 0; i < interfaces.length; i++){
temp[i] = interfaces[i];
}
temp[temp.length - 1] = IDisable.class; //将mixin的IDisable的接口也加进来
interfaces = temp;
}
return Proxy.newProxyInstance(object.getClass().getClassLoader(), interfaces, new InvocationHandler(){
Object target = object;
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
if(target instanceof IPool){
/* 如果调用方法是属于IDisable的,则将目标对象切换new DisableMixin();*/
IPool pool = (IPool)target;
if(method.getDeclaringClass().equals(IDisable.class)){
target = new DisableMixin(pool);
}
/*
* 如果缓存策略已经关闭:
* 取数据时则不从池中获取而重新加载数据;
* 存数据则不将数据放到缓存池中,直接返回null
*/
if(CacheConstants.TRUE.equals(pool.getCacheStrategy().getDisabled())){
//不进行初始化
if (method.getName().equals("init"))
return null;
//如果是调用getObject方法则调用载入器重新载入。参数args[0]为key值
if (method.getName().equals("getObject"))
return pool.reload(new TimeWrapper(args[0], null));
if (method.getName().equals("putObject"))
return null;
//如果是调用checkOut 方法则调用池算法器创建一个
if (method.getName().equals("checkOut"))
return pool.getArithmetic().create(pool.getCacheStrategy().getCyclelife());
if (method.getName().equals("checkIn")){
pool.getArithmetic().destroy((Cacheable) args[0]);
return null;
}
}
}
try {
return method.invoke(target, args);
} catch (InvocationTargetException e) {
throw e.getTargetException();
}
}
});
}
}