change line sep

This commit is contained in:
Looly
2021-01-20 17:10:45 +08:00
parent 720d24566b
commit 4e38adb32d
1450 changed files with 183940 additions and 183940 deletions

View File

@@ -1,74 +1,74 @@
package cn.hutool.aop;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.proxy.ProxyFactory;
import cn.hutool.core.util.ClassUtil;
/**
* 代理工具类
* @author Looly
*
*/
public final class ProxyUtil {
/**
* 使用切面代理对象
*
* @param <T> 切面对象类型
* @param target 目标对象
* @param aspectClass 切面对象类
* @return 代理对象
*/
public static <T> T proxy(T target, Class<? extends Aspect> aspectClass){
return ProxyFactory.createProxy(target, aspectClass);
}
/**
* 使用切面代理对象
*
* @param <T> 被代理对象类型
* @param target 被代理对象
* @param aspect 切面对象
* @return 代理对象
*/
public static <T> T proxy(T target, Aspect aspect){
return ProxyFactory.createProxy(target, aspect);
}
/**
* 创建动态代理对象<br>
* 动态代理对象的创建原理是:<br>
* 假设创建的代理对象名为 $Proxy0<br>
* 1、根据传入的interfaces动态生成一个类实现interfaces中的接口<br>
* 2、通过传入的classloder将刚生成的类加载到jvm中。即将$Proxy0类load<br>
* 3、调用$Proxy0的$Proxy0(InvocationHandler)构造函数 创建$Proxy0的对象并且用interfaces参数遍历其所有接口的方法这些实现方法的实现本质上是通过反射调用被代理对象的方法<br>
* 4、将$Proxy0的实例返回给客户端。 <br>
* 5、当调用代理类的相应方法时相当于调用 {@link InvocationHandler#invoke(Object, java.lang.reflect.Method, Object[])} 方法
*
*
* @param <T> 被代理对象类型
* @param classloader 被代理类对应的ClassLoader
* @param invocationHandler {@link InvocationHandler} ,被代理类通过实现此接口提供动态代理功能
* @param interfaces 代理类中需要实现的被代理类的接口方法
* @return 代理类
*/
@SuppressWarnings("unchecked")
public static <T> T newProxyInstance(ClassLoader classloader, InvocationHandler invocationHandler, Class<?>... interfaces) {
return (T) Proxy.newProxyInstance(classloader, interfaces, invocationHandler);
}
/**
* 创建动态代理对象
*
* @param <T> 被代理对象类型
* @param invocationHandler {@link InvocationHandler} ,被代理类通过实现此接口提供动态代理功能
* @param interfaces 代理类中需要实现的被代理类的接口方法
* @return 代理类
*/
public static <T> T newProxyInstance(InvocationHandler invocationHandler, Class<?>... interfaces) {
return newProxyInstance(ClassUtil.getClassLoader(), invocationHandler, interfaces);
}
}
package cn.hutool.aop;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.proxy.ProxyFactory;
import cn.hutool.core.util.ClassUtil;
/**
* 代理工具类
* @author Looly
*
*/
public final class ProxyUtil {
/**
* 使用切面代理对象
*
* @param <T> 切面对象类型
* @param target 目标对象
* @param aspectClass 切面对象类
* @return 代理对象
*/
public static <T> T proxy(T target, Class<? extends Aspect> aspectClass){
return ProxyFactory.createProxy(target, aspectClass);
}
/**
* 使用切面代理对象
*
* @param <T> 被代理对象类型
* @param target 被代理对象
* @param aspect 切面对象
* @return 代理对象
*/
public static <T> T proxy(T target, Aspect aspect){
return ProxyFactory.createProxy(target, aspect);
}
/**
* 创建动态代理对象<br>
* 动态代理对象的创建原理是:<br>
* 假设创建的代理对象名为 $Proxy0<br>
* 1、根据传入的interfaces动态生成一个类实现interfaces中的接口<br>
* 2、通过传入的classloder将刚生成的类加载到jvm中。即将$Proxy0类load<br>
* 3、调用$Proxy0的$Proxy0(InvocationHandler)构造函数 创建$Proxy0的对象并且用interfaces参数遍历其所有接口的方法这些实现方法的实现本质上是通过反射调用被代理对象的方法<br>
* 4、将$Proxy0的实例返回给客户端。 <br>
* 5、当调用代理类的相应方法时相当于调用 {@link InvocationHandler#invoke(Object, java.lang.reflect.Method, Object[])} 方法
*
*
* @param <T> 被代理对象类型
* @param classloader 被代理类对应的ClassLoader
* @param invocationHandler {@link InvocationHandler} ,被代理类通过实现此接口提供动态代理功能
* @param interfaces 代理类中需要实现的被代理类的接口方法
* @return 代理类
*/
@SuppressWarnings("unchecked")
public static <T> T newProxyInstance(ClassLoader classloader, InvocationHandler invocationHandler, Class<?>... interfaces) {
return (T) Proxy.newProxyInstance(classloader, interfaces, invocationHandler);
}
/**
* 创建动态代理对象
*
* @param <T> 被代理对象类型
* @param invocationHandler {@link InvocationHandler} ,被代理类通过实现此接口提供动态代理功能
* @param interfaces 代理类中需要实现的被代理类的接口方法
* @return 代理类
*/
public static <T> T newProxyInstance(InvocationHandler invocationHandler, Class<?>... interfaces) {
return newProxyInstance(ClassUtil.getClassLoader(), invocationHandler, interfaces);
}
}

View File

@@ -1,49 +1,49 @@
package cn.hutool.aop.aspects;
import java.lang.reflect.Method;
/**
* 切面接口
*
* @author looly
* @author ted.L
* @since 4.18
*/
public interface Aspect {
/**
* 目标方法执行前的操作
*
* @param target 目标对象
* @param method 目标方法
* @param args 参数
* @return 是否继续执行接下来的操作
*/
boolean before(Object target, Method method, Object[] args);
/**
* 目标方法执行后的操作
* 如果 target.method 抛出异常且
*
* @param target 目标对象
* @param method 目标方法
* @param args 参数
* @param returnVal 目标方法执行返回值
* @return 是否允许返回值(接下来的操作)
* @see Aspect#afterException 返回true,则不会执行此操作
* 如果
* @see Aspect#afterException 返回false,则无论target.method是否抛出异常均会执行此操作
*/
boolean after(Object target, Method method, Object[] args, Object returnVal);
/**
* 目标方法抛出异常时的操作
*
* @param target 目标对象
* @param method 目标方法
* @param args 参数
* @param e 异常
* @return 是否允许抛出异常
*/
boolean afterException(Object target, Method method, Object[] args, Throwable e);
}
package cn.hutool.aop.aspects;
import java.lang.reflect.Method;
/**
* 切面接口
*
* @author looly
* @author ted.L
* @since 4.18
*/
public interface Aspect {
/**
* 目标方法执行前的操作
*
* @param target 目标对象
* @param method 目标方法
* @param args 参数
* @return 是否继续执行接下来的操作
*/
boolean before(Object target, Method method, Object[] args);
/**
* 目标方法执行后的操作
* 如果 target.method 抛出异常且
*
* @param target 目标对象
* @param method 目标方法
* @param args 参数
* @param returnVal 目标方法执行返回值
* @return 是否允许返回值(接下来的操作)
* @see Aspect#afterException 返回true,则不会执行此操作
* 如果
* @see Aspect#afterException 返回false,则无论target.method是否抛出异常均会执行此操作
*/
boolean after(Object target, Method method, Object[] args, Object returnVal);
/**
* 目标方法抛出异常时的操作
*
* @param target 目标对象
* @param method 目标方法
* @param args 参数
* @param e 异常
* @return 是否允许抛出异常
*/
boolean afterException(Object target, Method method, Object[] args, Throwable e);
}

View File

@@ -1,33 +1,33 @@
package cn.hutool.aop.aspects;
import java.io.Serializable;
import java.lang.reflect.Method;
/**
* 简单切面类,不做任何操作<br>
* 可以继承此类实现自己需要的方法即可
*
* @author Looly, ted.L
*/
public class SimpleAspect implements Aspect, Serializable {
private static final long serialVersionUID = 1L;
@Override
public boolean before(Object target, Method method, Object[] args) {
//继承此类后实现此方法
return true;
}
@Override
public boolean after(Object target, Method method, Object[] args, Object returnVal) {
//继承此类后实现此方法
return true;
}
@Override
public boolean afterException(Object target, Method method, Object[] args, Throwable e) {
//继承此类后实现此方法
return true;
}
}
package cn.hutool.aop.aspects;
import java.io.Serializable;
import java.lang.reflect.Method;
/**
* 简单切面类,不做任何操作<br>
* 可以继承此类实现自己需要的方法即可
*
* @author Looly, ted.L
*/
public class SimpleAspect implements Aspect, Serializable {
private static final long serialVersionUID = 1L;
@Override
public boolean before(Object target, Method method, Object[] args) {
//继承此类后实现此方法
return true;
}
@Override
public boolean after(Object target, Method method, Object[] args, Object returnVal) {
//继承此类后实现此方法
return true;
}
@Override
public boolean afterException(Object target, Method method, Object[] args, Throwable e) {
//继承此类后实现此方法
return true;
}
}

View File

@@ -1,33 +1,33 @@
package cn.hutool.aop.aspects;
import cn.hutool.core.date.TimeInterval;
import cn.hutool.core.lang.Console;
import java.lang.reflect.Method;
/**
* 通过日志打印方法的执行时间的切面
*
* @author Looly
*/
public class TimeIntervalAspect extends SimpleAspect {
private static final long serialVersionUID = 1L;
private final TimeInterval interval = new TimeInterval();
@Override
public boolean before(Object target, Method method, Object[] args) {
interval.start();
return true;
}
@Override
public boolean after(Object target, Method method, Object[] args, Object returnVal) {
Console.log("Method [{}.{}] execute spend [{}]ms return value [{}]",
target.getClass().getName(), //
method.getName(), //
interval.intervalMs(), //
returnVal);
return true;
}
}
package cn.hutool.aop.aspects;
import cn.hutool.core.date.TimeInterval;
import cn.hutool.core.lang.Console;
import java.lang.reflect.Method;
/**
* 通过日志打印方法的执行时间的切面
*
* @author Looly
*/
public class TimeIntervalAspect extends SimpleAspect {
private static final long serialVersionUID = 1L;
private final TimeInterval interval = new TimeInterval();
@Override
public boolean before(Object target, Method method, Object[] args) {
interval.start();
return true;
}
@Override
public boolean after(Object target, Method method, Object[] args, Object returnVal) {
Console.log("Method [{}.{}] execute spend [{}]ms return value [{}]",
target.getClass().getName(), //
method.getName(), //
interval.intervalMs(), //
returnVal);
return true;
}
}

View File

@@ -1,7 +1,7 @@
/**
* 切面实现,提供一些基本的切面实现
*
* @author looly
*
*/
/**
* 切面实现,提供一些基本的切面实现
*
* @author looly
*
*/
package cn.hutool.aop.aspects;

View File

@@ -1,60 +1,60 @@
package cn.hutool.aop.interceptor;
import cn.hutool.aop.aspects.Aspect;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
import java.io.Serializable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* Cglib实现的动态代理切面
*
* @author looly, ted.L
*/
public class CglibInterceptor implements MethodInterceptor, Serializable {
private static final long serialVersionUID = 1L;
private final Object target;
private final Aspect aspect;
/**
* 构造
*
* @param target 被代理对象
* @param aspect 切面实现
*/
public CglibInterceptor(Object target, Aspect aspect) {
this.target = target;
this.aspect = aspect;
}
public Object getTarget() {
return this.target;
}
@Override
public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
final Object target = this.target;
Object result = null;
// 开始前回调
if (aspect.before(target, method, args)) {
try {
// result = proxy.invokeSuper(obj, args);
result = proxy.invoke(target, args);
} catch (InvocationTargetException e) {
// 异常回调(只捕获业务代码导致的异常,而非反射导致的异常)
if (aspect.afterException(target, method, args, e.getTargetException())) {
throw e;
}
}
}
// 结束执行回调
if (aspect.after(target, method, args, result)) {
return result;
}
return null;
}
}
package cn.hutool.aop.interceptor;
import cn.hutool.aop.aspects.Aspect;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
import java.io.Serializable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* Cglib实现的动态代理切面
*
* @author looly, ted.L
*/
public class CglibInterceptor implements MethodInterceptor, Serializable {
private static final long serialVersionUID = 1L;
private final Object target;
private final Aspect aspect;
/**
* 构造
*
* @param target 被代理对象
* @param aspect 切面实现
*/
public CglibInterceptor(Object target, Aspect aspect) {
this.target = target;
this.aspect = aspect;
}
public Object getTarget() {
return this.target;
}
@Override
public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
final Object target = this.target;
Object result = null;
// 开始前回调
if (aspect.before(target, method, args)) {
try {
// result = proxy.invokeSuper(obj, args);
result = proxy.invoke(target, args);
} catch (InvocationTargetException e) {
// 异常回调(只捕获业务代码导致的异常,而非反射导致的异常)
if (aspect.afterException(target, method, args, e.getTargetException())) {
throw e;
}
}
}
// 结束执行回调
if (aspect.after(target, method, args, result)) {
return result;
}
return null;
}
}

View File

@@ -1,66 +1,66 @@
package cn.hutool.aop.interceptor;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.core.util.ClassUtil;
import cn.hutool.core.util.ReflectUtil;
import java.io.Serializable;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* JDK实现的动态代理切面
*
* @author Looly
* @author ted.L
*/
public class JdkInterceptor implements InvocationHandler, Serializable {
private static final long serialVersionUID = 1L;
private final Object target;
private final Aspect aspect;
/**
* 构造
*
* @param target 被代理对象
* @param aspect 切面实现
*/
public JdkInterceptor(Object target, Aspect aspect) {
this.target = target;
this.aspect = aspect;
}
public Object getTarget() {
return this.target;
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
final Object target = this.target;
final Aspect aspect = this.aspect;
Object result = null;
// 开始前回调
if (aspect.before(target, method, args)) {
ReflectUtil.setAccessible(method);
try {
result = method.invoke(ClassUtil.isStatic(method) ? null : target, args);
} catch (InvocationTargetException e) {
// 异常回调(只捕获业务代码导致的异常,而非反射导致的异常)
if (aspect.afterException(target, method, args, e.getTargetException())) {
throw e;
}
}
}
// 结束执行回调
if (aspect.after(target, method, args, result)) {
return result;
}
return null;
}
}
package cn.hutool.aop.interceptor;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.core.util.ClassUtil;
import cn.hutool.core.util.ReflectUtil;
import java.io.Serializable;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* JDK实现的动态代理切面
*
* @author Looly
* @author ted.L
*/
public class JdkInterceptor implements InvocationHandler, Serializable {
private static final long serialVersionUID = 1L;
private final Object target;
private final Aspect aspect;
/**
* 构造
*
* @param target 被代理对象
* @param aspect 切面实现
*/
public JdkInterceptor(Object target, Aspect aspect) {
this.target = target;
this.aspect = aspect;
}
public Object getTarget() {
return this.target;
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
final Object target = this.target;
final Aspect aspect = this.aspect;
Object result = null;
// 开始前回调
if (aspect.before(target, method, args)) {
ReflectUtil.setAccessible(method);
try {
result = method.invoke(ClassUtil.isStatic(method) ? null : target, args);
} catch (InvocationTargetException e) {
// 异常回调(只捕获业务代码导致的异常,而非反射导致的异常)
if (aspect.afterException(target, method, args, e.getTargetException())) {
throw e;
}
}
}
// 结束执行回调
if (aspect.after(target, method, args, result)) {
return result;
}
return null;
}
}

View File

@@ -1,65 +1,65 @@
package cn.hutool.aop.interceptor;
import cn.hutool.aop.aspects.Aspect;
import org.springframework.cglib.proxy.MethodInterceptor;
import org.springframework.cglib.proxy.MethodProxy;
import java.io.Serializable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* Spring-cglib实现的动态代理切面
*
* @author looly
*/
public class SpringCglibInterceptor implements MethodInterceptor, Serializable {
private static final long serialVersionUID = 1L;
private final Object target;
private final Aspect aspect;
/**
* 构造
*
* @param target 被代理对象
* @param aspect 切面实现
*/
public SpringCglibInterceptor(Object target, Aspect aspect) {
this.target = target;
this.aspect = aspect;
}
/**
* 获得目标对象
*
* @return 目标对象
*/
public Object getTarget() {
return this.target;
}
@Override
public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
final Object target = this.target;
Object result = null;
// 开始前回调
if (aspect.before(target, method, args)) {
try {
// result = proxy.invokeSuper(obj, args);
result = proxy.invoke(target, args);
} catch (InvocationTargetException e) {
// 异常回调(只捕获业务代码导致的异常,而非反射导致的异常)
if (aspect.afterException(target, method, args, e.getTargetException())) {
throw e;
}
}
}
// 结束执行回调
if (aspect.after(target, method, args, result)) {
return result;
}
return null;
}
}
package cn.hutool.aop.interceptor;
import cn.hutool.aop.aspects.Aspect;
import org.springframework.cglib.proxy.MethodInterceptor;
import org.springframework.cglib.proxy.MethodProxy;
import java.io.Serializable;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
/**
* Spring-cglib实现的动态代理切面
*
* @author looly
*/
public class SpringCglibInterceptor implements MethodInterceptor, Serializable {
private static final long serialVersionUID = 1L;
private final Object target;
private final Aspect aspect;
/**
* 构造
*
* @param target 被代理对象
* @param aspect 切面实现
*/
public SpringCglibInterceptor(Object target, Aspect aspect) {
this.target = target;
this.aspect = aspect;
}
/**
* 获得目标对象
*
* @return 目标对象
*/
public Object getTarget() {
return this.target;
}
@Override
public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
final Object target = this.target;
Object result = null;
// 开始前回调
if (aspect.before(target, method, args)) {
try {
// result = proxy.invokeSuper(obj, args);
result = proxy.invoke(target, args);
} catch (InvocationTargetException e) {
// 异常回调(只捕获业务代码导致的异常,而非反射导致的异常)
if (aspect.afterException(target, method, args, e.getTargetException())) {
throw e;
}
}
}
// 结束执行回调
if (aspect.after(target, method, args, result)) {
return result;
}
return null;
}
}

View File

@@ -1,7 +1,7 @@
/**
* 代理拦截器实现
*
* @author looly
*
*/
/**
* 代理拦截器实现
*
* @author looly
*
*/
package cn.hutool.aop.interceptor;

View File

@@ -1,7 +1,7 @@
/**
* JDK动态代理封装提供非IOC下的切面支持
*
* @author looly
*
*/
/**
* JDK动态代理封装提供非IOC下的切面支持
*
* @author looly
*
*/
package cn.hutool.aop;

View File

@@ -1,25 +1,25 @@
package cn.hutool.aop.proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.interceptor.CglibInterceptor;
import net.sf.cglib.proxy.Enhancer;
/**
* 基于Cglib的切面代理工厂
*
* @author looly
*
*/
public class CglibProxyFactory extends ProxyFactory{
private static final long serialVersionUID = 1L;
@Override
@SuppressWarnings("unchecked")
public <T> T proxy(T target, Aspect aspect) {
final Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(target.getClass());
enhancer.setCallback(new CglibInterceptor(target, aspect));
return (T) enhancer.create();
}
}
package cn.hutool.aop.proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.interceptor.CglibInterceptor;
import net.sf.cglib.proxy.Enhancer;
/**
* 基于Cglib的切面代理工厂
*
* @author looly
*
*/
public class CglibProxyFactory extends ProxyFactory{
private static final long serialVersionUID = 1L;
@Override
@SuppressWarnings("unchecked")
public <T> T proxy(T target, Aspect aspect) {
final Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(target.getClass());
enhancer.setCallback(new CglibInterceptor(target, aspect));
return (T) enhancer.create();
}
}

View File

@@ -1,22 +1,22 @@
package cn.hutool.aop.proxy;
import cn.hutool.aop.ProxyUtil;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.interceptor.JdkInterceptor;
/**
* JDK实现的切面代理
*
* @author looly
*/
public class JdkProxyFactory extends ProxyFactory {
private static final long serialVersionUID = 1L;
@Override
public <T> T proxy(T target, Aspect aspect) {
return ProxyUtil.newProxyInstance(//
target.getClass().getClassLoader(), //
new JdkInterceptor(target, aspect), //
target.getClass().getInterfaces());
}
}
package cn.hutool.aop.proxy;
import cn.hutool.aop.ProxyUtil;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.interceptor.JdkInterceptor;
/**
* JDK实现的切面代理
*
* @author looly
*/
public class JdkProxyFactory extends ProxyFactory {
private static final long serialVersionUID = 1L;
@Override
public <T> T proxy(T target, Aspect aspect) {
return ProxyUtil.newProxyInstance(//
target.getClass().getClassLoader(), //
new JdkInterceptor(target, aspect), //
target.getClass().getInterfaces());
}
}

View File

@@ -1,73 +1,73 @@
package cn.hutool.aop.proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.core.util.ReflectUtil;
import cn.hutool.core.util.ServiceLoaderUtil;
import java.io.Serializable;
/**
* 代理工厂<br>
* 根据用户引入代理库的不同,产生不同的代理对象
*
* @author looly
*/
public abstract class ProxyFactory implements Serializable {
private static final long serialVersionUID = 1L;
/**
* 创建代理
*
* @param <T> 代理对象类型
* @param target 被代理对象
* @param aspectClass 切面实现类,自动实例化
* @return 代理对象
* @since 5.3.1
*/
public <T> T proxy(T target, Class<? extends Aspect> aspectClass) {
return proxy(target, ReflectUtil.newInstanceIfPossible(aspectClass));
}
/**
* 创建代理
*
* @param <T> 代理对象类型
* @param target 被代理对象
* @param aspect 切面实现
* @return 代理对象
*/
public abstract <T> T proxy(T target, Aspect aspect);
/**
* 根据用户引入Cglib与否自动创建代理对象
*
* @param <T> 切面对象类型
* @param target 目标对象
* @param aspectClass 切面对象类
* @return 代理对象
*/
public static <T> T createProxy(T target, Class<? extends Aspect> aspectClass) {
return createProxy(target, ReflectUtil.newInstance(aspectClass));
}
/**
* 根据用户引入Cglib与否自动创建代理对象
*
* @param <T> 切面对象类型
* @param target 被代理对象
* @param aspect 切面实现
* @return 代理对象
*/
public static <T> T createProxy(T target, Aspect aspect) {
return create().proxy(target, aspect);
}
/**
* 根据用户引入Cglib与否创建代理工厂
*
* @return 代理工厂
*/
public static ProxyFactory create() {
return ServiceLoaderUtil.loadFirstAvailable(ProxyFactory.class);
}
}
package cn.hutool.aop.proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.core.util.ReflectUtil;
import cn.hutool.core.util.ServiceLoaderUtil;
import java.io.Serializable;
/**
* 代理工厂<br>
* 根据用户引入代理库的不同,产生不同的代理对象
*
* @author looly
*/
public abstract class ProxyFactory implements Serializable {
private static final long serialVersionUID = 1L;
/**
* 创建代理
*
* @param <T> 代理对象类型
* @param target 被代理对象
* @param aspectClass 切面实现类,自动实例化
* @return 代理对象
* @since 5.3.1
*/
public <T> T proxy(T target, Class<? extends Aspect> aspectClass) {
return proxy(target, ReflectUtil.newInstanceIfPossible(aspectClass));
}
/**
* 创建代理
*
* @param <T> 代理对象类型
* @param target 被代理对象
* @param aspect 切面实现
* @return 代理对象
*/
public abstract <T> T proxy(T target, Aspect aspect);
/**
* 根据用户引入Cglib与否自动创建代理对象
*
* @param <T> 切面对象类型
* @param target 目标对象
* @param aspectClass 切面对象类
* @return 代理对象
*/
public static <T> T createProxy(T target, Class<? extends Aspect> aspectClass) {
return createProxy(target, ReflectUtil.newInstance(aspectClass));
}
/**
* 根据用户引入Cglib与否自动创建代理对象
*
* @param <T> 切面对象类型
* @param target 被代理对象
* @param aspect 切面实现
* @return 代理对象
*/
public static <T> T createProxy(T target, Aspect aspect) {
return create().proxy(target, aspect);
}
/**
* 根据用户引入Cglib与否创建代理工厂
*
* @return 代理工厂
*/
public static ProxyFactory create() {
return ServiceLoaderUtil.loadFirstAvailable(ProxyFactory.class);
}
}

View File

@@ -1,25 +1,25 @@
package cn.hutool.aop.proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.interceptor.SpringCglibInterceptor;
import org.springframework.cglib.proxy.Enhancer;
/**
* 基于Spring-cglib的切面代理工厂
*
* @author looly
*
*/
public class SpringCglibProxyFactory extends ProxyFactory{
private static final long serialVersionUID = 1L;
@Override
@SuppressWarnings("unchecked")
public <T> T proxy(T target, Aspect aspect) {
final Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(target.getClass());
enhancer.setCallback(new SpringCglibInterceptor(target, aspect));
return (T) enhancer.create();
}
}
package cn.hutool.aop.proxy;
import cn.hutool.aop.aspects.Aspect;
import cn.hutool.aop.interceptor.SpringCglibInterceptor;
import org.springframework.cglib.proxy.Enhancer;
/**
* 基于Spring-cglib的切面代理工厂
*
* @author looly
*
*/
public class SpringCglibProxyFactory extends ProxyFactory{
private static final long serialVersionUID = 1L;
@Override
@SuppressWarnings("unchecked")
public <T> T proxy(T target, Aspect aspect) {
final Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(target.getClass());
enhancer.setCallback(new SpringCglibInterceptor(target, aspect));
return (T) enhancer.create();
}
}

View File

@@ -1,7 +1,7 @@
/**
* 代理实现
*
* @author looly
*
*/
/**
* 代理实现
*
* @author looly
*
*/
package cn.hutool.aop.proxy;

View File

@@ -1,3 +1,3 @@
cn.hutool.aop.proxy.CglibProxyFactory
cn.hutool.aop.proxy.SpringCglibProxyFactory
cn.hutool.aop.proxy.CglibProxyFactory
cn.hutool.aop.proxy.SpringCglibProxyFactory
cn.hutool.aop.proxy.JdkProxyFactory

View File

@@ -1,88 +1,88 @@
package cn.hutool.aop.test;
import cn.hutool.aop.ProxyUtil;
import cn.hutool.aop.aspects.TimeIntervalAspect;
import cn.hutool.core.lang.Console;
import lombok.Data;
import org.junit.Assert;
import org.junit.Test;
/**
* AOP模块单元测试
*
* @author Looly
*/
public class AopTest {
@Test
public void aopTest() {
Animal cat = ProxyUtil.proxy(new Cat(), TimeIntervalAspect.class);
String result = cat.eat();
Assert.assertEquals("猫吃鱼", result);
cat.seize();
}
@Test
public void aopByAutoCglibTest() {
Dog dog = ProxyUtil.proxy(new Dog(), TimeIntervalAspect.class);
String result = dog.eat();
Assert.assertEquals("狗吃肉", result);
dog.seize();
}
interface Animal {
String eat();
void seize();
}
/**
* 有接口
*
* @author looly
*/
static class Cat implements Animal {
@Override
public String eat() {
return "猫吃鱼";
}
@Override
public void seize() {
Console.log("抓了条鱼");
}
}
/**
* 无接口
*
* @author looly
*/
static class Dog {
public String eat() {
return "狗吃肉";
}
public void seize() {
Console.log("抓了只鸡");
}
}
@Test
public void testCGLIBProxy() {
TagObj target = new TagObj();
//目标类设置标记
target.setTag("tag");
TagObj proxy = ProxyUtil.proxy(target, TimeIntervalAspect.class);
//代理类获取标记tag (断言错误)
Assert.assertEquals("tag", proxy.getTag());
}
@Data
public static class TagObj{
private String tag;
}
}
package cn.hutool.aop.test;
import cn.hutool.aop.ProxyUtil;
import cn.hutool.aop.aspects.TimeIntervalAspect;
import cn.hutool.core.lang.Console;
import lombok.Data;
import org.junit.Assert;
import org.junit.Test;
/**
* AOP模块单元测试
*
* @author Looly
*/
public class AopTest {
@Test
public void aopTest() {
Animal cat = ProxyUtil.proxy(new Cat(), TimeIntervalAspect.class);
String result = cat.eat();
Assert.assertEquals("猫吃鱼", result);
cat.seize();
}
@Test
public void aopByAutoCglibTest() {
Dog dog = ProxyUtil.proxy(new Dog(), TimeIntervalAspect.class);
String result = dog.eat();
Assert.assertEquals("狗吃肉", result);
dog.seize();
}
interface Animal {
String eat();
void seize();
}
/**
* 有接口
*
* @author looly
*/
static class Cat implements Animal {
@Override
public String eat() {
return "猫吃鱼";
}
@Override
public void seize() {
Console.log("抓了条鱼");
}
}
/**
* 无接口
*
* @author looly
*/
static class Dog {
public String eat() {
return "狗吃肉";
}
public void seize() {
Console.log("抓了只鸡");
}
}
@Test
public void testCGLIBProxy() {
TagObj target = new TagObj();
//目标类设置标记
target.setTag("tag");
TagObj proxy = ProxyUtil.proxy(target, TimeIntervalAspect.class);
//代理类获取标记tag (断言错误)
Assert.assertEquals("tag", proxy.getTag());
}
@Data
public static class TagObj{
private String tag;
}
}