汕头网站制作后缀,学做网站论坛可信吗,济南网站建设vashine,app制作网站收费吗服务引用代理类在Stackoverflow中有一个有趣的问题 #xff0c;关于Spring Bean如何获得对由Spring创建的代理的引用以处理事务#xff0c;Spring AOP#xff0c;缓存#xff0c;异步流等。需要对代理的引用#xff0c;因为如果存在对自身的调用通过代理bean#xff… 服务引用代理类 在Stackoverflow中有一个有趣的问题 关于Spring Bean如何获得对由Spring创建的代理的引用以处理事务Spring AOP缓存异步流等。需要对代理的引用因为如果存在对自身的调用通过代理bean此调用将完全绕过代理。 考虑一个InventoryService接口 public interface InventoryService{public Inventory create(Inventory inventory);public ListInventory list();public Inventory findByVin(String vin);public Inventory update(Inventory inventory);public boolean delete(Long id);public Inventory compositeUpdateService(String vin, String newMake);
} 还请考虑该服务的默认实现并假定最后一个方法CompositeUpdateService内部在Bean本身上调用两个方法如下所示 public Inventory compositeUpdateService(String vin, String newMake) {logger.info(composite Update Service called);Inventory inventory this.findByVin(vin);inventory.setMake(newMake);this.update(inventory);return inventory;
} 如果我现在创建一个方面来建议对InventoryService的任何调用以跟踪每个方法调用花费的时间Spring AOP将为InventoryService Bean创建一个动态代理 但是对CompositeUpdateService的调用将仅在此方法的级别上记录时间即CompositeUpdateService内部对findByVin的调用更新绕过了代理因此不会被跟踪 一个好的解决方法是使用AspectJ的全部功能– AspectJ会更改DefaultInventoryService的所有方法的字节码以包括对建议的调用。 我们制定的解决方法是将对代理本身的引用注入到bean中而不是调用this.findByVin和this.update而是调用proxy.findByVin和proxy.update 因此现在我们如何干净地将对代理的引用注入到bean中-我提供的解决方案是创建一个接口以标记对自己的代理感兴趣的bean public interface ProxyAwareT {void setProxy(T proxy);
} 感兴趣的接口及其实现如下所示 public interface InventoryService extends ProxyAwareInventoryService{
...
}public class DefaultInventoryService implements InventoryService{ ...private InventoryService proxy;Overridepublic void setProxy(InventoryService proxy) {this.proxy proxy;}
} 然后定义一个BeanPostProcessor注入这个代理 public class ProxyInjectingBeanPostProcessor implements BeanPostProcessor, Ordered {Overridepublic Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {return bean;}Overridepublic Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {if (AopUtils.isAopProxy((bean))){try {Object target ((Advised)bean).getTargetSource().getTarget();if (target instanceof ProxyAware){((ProxyAware) target).setProxy(bean);}} catch (Exception e) {return bean;}}return bean;}Overridepublic int getOrder() {return Integer.MAX_VALUE;}
} 不是最干净的实现但是可以 参考 http : //blog.springsource.org/2012/05/23/understanding-proxy-usage-in-spring/ 参考 all和杂项博客中 JCG合作伙伴 Biju Kunjummen 引用了代理课程中的动态代理 。 翻译自: https://www.javacodegeeks.com/2012/07/reference-to-dynamic-proxy-in-proxied.html服务引用代理类