使用者端不直接存取目標物件,需要通過第三者來實現間接存取物件
代理物件在使用者端和目標物件之間起中介作用,能夠遮蔽目標物件不想讓使用者端知道的內容,或增加額外的服務
JDK 動態代理:基於介面,利用 JDK API 動態地在記憶體中構建代理物件,從而實現目標物件的代理功能。稱為 JDK 代理或介面代理。
MapperInvocationHandler
實現 InvocationHandler
介面,實現 invoke
方法,該方法最終是代理類增強的目標類方法JDKProxyFactory
用於生成代理物件的工廠,通過呼叫 Proxy.newProxyInstance
方法生成代理物件UserMapper
目標類,JDK 代理的目標類必須實現某個介面IUserMapper
目標類介面MapperInvocationHandler
public class MapperInvocationHandler implements InvocationHandler {
// 動態的目標物件
private Object target;
public MapperInvocationHandler(Object target) {
this.target = target;
}
/**
* 增強方法
* @param proxy 代理範例
* @param method 目標方法
* @param args 目標方法引數
* @return 返回值
* @throws Throwable 異常
*/
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("=========JDK 動態代理前置增強=========");
method.invoke(target, args);
System.out.println("=========JDK 動態代理後置增強=========");
return null;
}
}
JDKProxyFactory
public class JDKProxyFactory {
// 動態的目標物件
private Object target;
public JDKProxyFactory(Object target) {
this.target = target;
}
// 為目標物件生成代理物件
public Object getTargetProxy(){
return Proxy.newProxyInstance(
// 目標物件使用的類載入器
target.getClass().getClassLoader(),
// 目標物件實現的介面
target.getClass().getInterfaces(),
// 事件處理器
new MapperInvocationHandler(target)
);
}
}
IUserMapper
public interface IUserMapper {
void save();
}
UserMapper
public class UserMapper implements IUserMapper {
@Override
public void save() {
System.out.println("儲存使用者資料");
}
}
Client
public class Client {
public static void main(String[] args) {
JDKProxyFactory jdkProxyFactory = new JDKProxyFactory(new UserMapper());
IUserMapper userMapperProxy = (IUserMapper) jdkProxyFactory.getTargetProxy();
userMapperProxy.save();
}
}
執行結果
=========JDK 動態代理前置增強=========
儲存使用者資料
=========JDK 動態代理後置增強=========
Process finished with exit code 0