我尝试使用CGLib创建自己的延迟加载实现,但我遇到了一些我无法解释的奇怪行为。
这就是我正在做的事 正在创建代理实例,如下所示:
public static <T> T newInstance(Long sourceId, SourceMapper<T> sourceMapper) {
Class<?> proxyTargetType = sourceMapper.getType();
//mapper will use provided sourceId in order to load real object from the DB
Function<Long, T> mapper = sourceMapper.getMapper();
return (T) Enhancer.create(proxyTargetType,
new DynamicProxy<>(sourceId, mapper));
}
以下是上述代码的用法:
Order order = new Order();
try {
//heavy object is being proxied
long customerTariffId = rs.getLong("customer_tariff_id");
order.setCustomerTariff(DynamicProxy
.newInstance(customerTariffId, CUSTOMER_TARIFF_MAPPER));
}
只有在调用任何方法时才应加载重对象:
public Object intercept(Object obj, Method method, Object[] args,
MethodProxy methodProxy) throws Throwable {
T source = this.getSource(); // loads real object using sourceId and mapper
if(source == null) return null;
return method.invoke(source, args);
}
如果this.getSource()
加载某个对象,它的效果非常好。
但是,如果我们假设,order.getCustomerTariff()
应该返回null
(this.getSource()
将返回null
)
LOG.debug("{}", order.getCustomerTariff()); //null (1)
LOG.debug("{}", order.getCustomerTariff() != null); //true (2)
我认为,由于某些原因{(1}}在第(2)行被调用,所以我得到toString()
String
而不是文字null
。这就是为什么它不等于比较条款中的文字null
。
您如何看待,有没有办法在第(2)行返回常规null
在检查期间收到null
的正确值?
修改
被代理的类看起来类似于:
false
答案 0 :(得分:0)
我假设您正在截取拦截器中的toString
方法,并且您没有获得预期的拦截链。指定仅触及要拦截的方法的方法过滤器,您应该得到预期的结果。