Java如何实现一个动态代理

2020-07-17  本文已影响0人  阿汐爹

1.编写两个接口

UserDao

import java.util.List;

public interface UserDao {
    List findAllUser();
    int getUser();
}

PersonDao

import java.util.List;

public interface PersonDao {
    List getAllPerson();
    int remove();
}

2.编写两个接口的实现类

UserDaoImpl

import com.dj.proxy.dao.UserDao;
import java.util.List;

public class UserDaoImpl implements UserDao {
    @Override
    public List findAllUser() {
        System.out.println("获取user全部用户");
        return null;
    }

    @Override
    public int getUser() {
        System.out.println("获取user");
        return 0;
    }
}

3.编写任务类

Plugin

public class Plugin {
    public void doStart(){
        System.out.println("start:我是事前工作方法");
    }
    public void doAfter(){
        System.out.println("after:我是事后工作方法");
    }
}

4.编写动态代理类

MyProxy

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

/**
 * 动态代理
 * 1.实现InvocationHandler接口
 * 2.新增一个方法bind(名称可以随意取),方法返回Object,返回值要用Proxy.newProxyInstance完成
 * 3.invoke方法里实现需要增加的动态代理的功能,返回值需是method.invoke(object,args)的返回值
 */
public class MyProxy implements InvocationHandler {
    //动态代理中增加的额外操作的类
    Plugin plugin;
    //原始类
    Object object;

    public Object bind(Object object,Plugin plugin){
        this.object = object;
        this.plugin = plugin;
        //对Object类实现代理
        return Proxy.newProxyInstance(object.getClass().getClassLoader(),object.getClass().getInterfaces(),this);
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        //额外的操作1
        plugin.doStart();
        //原始类的方法调用
        Object invoke = method.invoke(object,args);
        //额外的操作2
        plugin.doAfter();
        //返回原始类
        return invoke;
    }
}

重点在于:

1.类要实现InvocationHandler接口

2.bind方法要返回Proxy.newProxyInstance

3.invoke方法要返回原始类的方法调用返回的Object

5.使用代理

ProxyTest

import com.dj.proxy.dao.PersonDao;
import com.dj.proxy.dao.UserDao;
import com.dj.proxy.impl.PersonDaoImpl;
import com.dj.proxy.impl.UserDaoImpl;

public class ProxyTest {
    public static void main(String[] args) {
        Plugin plugin = new Plugin();
        MyProxy proxy = new MyProxy();

        //对UserDao动态代理
        UserDao userDao = (UserDao) proxy.bind(new UserDaoImpl(),plugin);
        userDao.findAllUser();
        userDao.getUser();

        System.out.println();

        //对PersonDao动态代理
        PersonDao personDao = (PersonDao) proxy.bind(new PersonDaoImpl(),plugin);
        personDao.getAllPerson();
        personDao.remove();
    }
}

最终打印

start:我是事前工作方法
获取user全部用户
after:我是事后工作方法
start:我是事前工作方法
获取user
after:我是事后工作方法

start:我是事前工作方法
获取person全部用户
after:我是事后工作方法
start:我是事前工作方法
删除person
after:我是事后工作方法
上一篇 下一篇

猜你喜欢

热点阅读