在 Java 中,Proxy(代理) 通常指两种含义:
下面从适用场景角度系统说明,并区分 JDK 动态代理 和 CGLIB / 静态代理 的适用边界。
最常见的场景,如:
public Object invoke(Object proxy, Method method, Object[] args) {
logBefore();
Object result = method.invoke(target, args);
logAfter();
return result;
}
✅ 典型框架:Spring AOP(默认使用 JDK 动态代理)
JDK 动态代理只能代理接口
适用:
Proxy.newProxyInstance(
interface.getClassLoader(),
new Class[]{UserService.class},
handler
);
将远程服务“伪装”为本地接口:
UserService userApi = Proxy.newProxyInstance(...);
userApi.getUser(1); // 实际是网络请求
代理对象在真正调用方法时才创建真实对象:
方法调用前查缓存,未命中再调用真实对象:
if (cache.contains(key)) return cache.get(key);
return method.invoke(target, args);
在代理层统一开启/提交事务,避免业务代码耦合。
❌ 目标类没有接口
class UserServiceImpl { } // 不能被 JDK 代理
解决方式:
无论是静态代理、JDK 动态代理、CGLIB,都适用于:
| 场景 | 说明 |
|---|---|
| 访问控制 | 控制是否允许调用 |
| 延迟加载 | 用的时候再创建 |
| 日志 / 监控 | 无侵入增强 |
| 事务管理 | 统一控制 |
| 远程代理 | 本地调用远程 |
| 保护代理 | 权限校验 |
| 智能引用 | 引用计数、缓存 |
| 对比项 | JDK Proxy | CGLIB |
|---|---|---|
| 基于 | 接口 | 继承类 |
| 性能 | 稍慢(反射) | 更快(字节码) |
| 限制 | 必须有接口 | 不能代理 final |
| Spring 默认 | 有接口时用 | 无接口时用 |
Java Proxy 适合:基于接口的、无侵入的、横切逻辑的增强场景,尤其是 AOP、RPC、日志、事务和缓存。
如果你愿意,我也可以:
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。