当前位置:网站首页>Cglib代理-代码增强测试
Cglib代理-代码增强测试
2022-07-02 06:09:00 【一眉程序猿】
导包
<dependency>
<groupId>cglib</groupId>
<artifactId>cglib</artifactId>
<version>3.3.0</version>
</dependency>
编写方法拦截器
- 方法增强具体逻辑
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;
import java.lang.reflect.Method;
import java.util.Arrays;
/** * 自定义 cglib 代理 * * @author Ara * @since 2022/6/20 */
public class MyCglibProxyMethodInterceptor<T> implements MethodInterceptor {
/** * 目标对象 */
private final T target;
/** * 构造方法 */
public MyCglibProxyMethodInterceptor(T target) {
this.target = target;
}
/** * 获取代理对象 */
public T getProxyObject(){
Enhancer enhancer = new Enhancer();
//设置父类 因为cglib是针对指定的类生成一个子类用于其增强行为
enhancer.setSuperclass(target.getClass());
enhancer.setCallback(this);
return (T) enhancer.create();
}
// TODO 执行增强部分
@Override
public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
System.out.println("执行前 方法参数: " + Arrays.toString(objects));
Object result = method.invoke(target, objects);
System.out.println("执行后 返回值: " + result);
return result;
}
}
编写待增强测试类
- 增强目标点
/** * 文章 Service * * @author Ara * @since 2022/6/20 */
public class ArticleService {
public String saveArticle(String article) {
System.out.printf("保存文章[%s]...%n", article);
return article;
}
}
编写测试
- 检验是否能够进行增强
public class MainTest {
public static void main(String[] args) {
ArticleService articleService = new ArticleService();
//声明Cglib方法拦截增强实现类
MyCglibProxyMethodInterceptor<ArticleService> cglibProxyMethodInterceptor = new MyCglibProxyMethodInterceptor<>(articleService);
// 获取代理类
ArticleService articleServiceProxy = cglibProxyMethodInterceptor.getProxyObject();
//使用代理类调用方法
articleServiceProxy.saveArticle("Java");
}
}
验证结果
小总结
简单对比cglib与JDK动态代理:
- 这里使用cglib进行代理时,不论其目标类是否实现了接口,都可以对其进行增强。
- 但是单独使用JDK动态代理,就只能增强实现了接口的类重写的方法。
以下是对cglib和JDK动态代理是否能够增强有无接口实现的类的对比代码,感兴趣的读者可以进行测试:
public class MainTest {
public static void main(String[] args) {
cglibProxyNoInterfaceTest();
}
/** * cglib代理(代理目标类未实现接口) */
private static void cglibProxyNoInterfaceTest(){
ArticleService articleService = new ArticleService();
//声明Cglib方法拦截增强实现类
MyCglibProxyMethodInterceptor<ArticleService> cglibProxyMethodInterceptor = new MyCglibProxyMethodInterceptor<>(articleService);
// 获取代理类
ArticleService articleServiceProxy = cglibProxyMethodInterceptor.getProxyObject();
//使用代理类调用方法
articleServiceProxy.saveArticle("Java");
}
/** * cglib代理(代理目标类实现了接口) */
private static void cglibProxyHasInterfaceTest(){
UserService userService = new UserServiceImpl();
//声明Cglib方法拦截增强实现类
MyCglibProxyMethodInterceptor<UserService> cglibProxyMethodInterceptor = new MyCglibProxyMethodInterceptor<>(userService);
// 获取代理类
UserService userServiceProxy = cglibProxyMethodInterceptor.getProxyObject();
//使用代理类调用方法
userServiceProxy.add("Ara");
}
/** * JDK动态代理(代理目标类实现了接口) */
private static void jdkDynamicProxyHasInterfaceTest(){
//原对象 (接口接收参数)
UserService userService = new UserServiceImpl();
//声明增强处理程序
MyJdkProxyInvocationHandler<UserService> proxyInvocationHandler = new MyJdkProxyInvocationHandler<>(userService);
//获取代理对象
UserService proxyUserService = proxyInvocationHandler.getProxyObject();
//使用代理对象来调用方法
proxyUserService.add("Ara");
}
/** * JDK动态代理(代理目标类未实现接口) * 有误,使用JDK动态代理实现增强,必须要求代理目标实现了接口 */
private static void jdkDynamicProxyNoInterfaceTest(){
ArticleService articleService = new ArticleService();
//声明增强处理程序
MyJdkProxyInvocationHandler<ArticleService> proxyInvocationHandler = new MyJdkProxyInvocationHandler<>(articleService);
//获取代理对象
ArticleService proxyArticleService = proxyInvocationHandler.getProxyObject();
//使用代理对象来调用方法
proxyArticleService.saveArticle("Java");
}
}
边栏推荐
- Ros2 --- lifecycle node summary
- Step by step | help you easily submit Google play data security form
- LeetCode 77. 组合
- Flutter 混合开发: 开发一个简单的快速启动框架 | 开发者说·DTalk
- LeetCode 39. Combined sum
- Redis Key-Value数据库 【秒杀】
- I/o impressions from readers | prize collection winners list
- 经典文献阅读之--Deformable DETR
- LeetCode 283. 移动零
- Contest3145 - the 37th game of 2021 freshman individual training match_ H: Eat fish
猜你喜欢
从设计交付到开发,轻松畅快高效率!
Sumo tutorial Hello World
sudo提权
Monitoring uplink of VRRP
Contest3147 - game 38 of 2021 Freshmen's personal training match_ E: Listen to songs and know music
加密压缩文件解密技巧
VLAN experiment of switching technology
Contest3147 - game 38 of 2021 Freshmen's personal training match_ A: chicken
51 single chip microcomputer - ADC explanation (a/d conversion, d/a conversion)
I/o impressions from readers | prize collection winners list
随机推荐
IPv6 experiment and summary
The official zero foundation introduction jetpack compose Chinese course is coming!
Arduino Wire 库使用
Redis Key-Value数据库 【秒杀】
社区说|Kotlin Flow 的原理与设计哲学
Picture clipping plug-in cropper js
从设计交付到开发,轻松畅快高效率!
Scheme and implementation of automatic renewal of token expiration
LeetCode 78. subset
Don't use the new WP collection. Don't use WordPress collection without update
Deep learning classification network -- alexnet
Network related knowledge (Hardware Engineer)
LeetCode 78. 子集
BGP routing optimization rules and notification principles
Bgp Routing preference Rules and notice Principles
Contest3147 - game 38 of 2021 Freshmen's personal training match_ 1: Maximum palindromes
深入学习JVM底层(四):类文件结构
Common means of modeling: combination
Support new and old imperial CMS collection and warehousing tutorials
Ti millimeter wave radar learning (I)