CGLIB proxy error after spring bean definition loading into XmlWebApplicationContext at runtime
I load additional singleton beans definitions at runtime from external jar file into existing 开发者_Python百科XmlWebApplicationContext of my application:
BeanFactory beanFactory = xmlWebApplicationContext.getBeanFactory();
DefaultListableBeanFactory defaultFactory = (DefaultListableBeanFactory)beanFactory;
final URL url = new URL("external.jar");
final URL[] urls = {url};
ClassLoader loader = new URLClassLoader(urls, this.getClass().getClassLoader());
defaultFactory.setBeanClassLoader(loader);
final ClassPathBeanDefinitionScanner scanner = new ClassPathBeanDefinitionScanner(defaultFactory);
final DefaultResourceLoader resourceLoader = new DefaultResourceLoader();
resourceLoader.setClassLoader(loader);
scanner.setResourceLoader(resourceLoader);
scanner.scan("com.*");
Object bean = xmlWebApplicationContext.getBean("externalBean");
After all above xmlWebApplicationContext contains all external definitions of beans. But when i am trying to get bean from context exception is thrown:
Couldn't generate CGLIB proxy for class ...
I saw in debug mode that in the bean initialization process first time proxy is generated by
org.springframework.aop.aspectj.autoproxy.AspectJAwareAdvisorAutoProxyCreator
and than it is tried to generate proxy with
org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator
but fails with mentioned exception.
Make sure the bean:
- isn't
final
- has a non-private constructor
Cause was determined. Second proxy creator definition was founded in spring-common-manager.xml:
"org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator" which intercepts beans with names DAO, Dao, *ManagerTarget.
During my external bean creation, proxy bean classLoader was set to system class loader. So proxy creator couldn't find class definition for external bean.
It seems that without refresh class loader, which added to default factory is invisible for some utility beans such proxy creators.
My Solution is to obtain proxy creator bean and to set implicitly class loader to it, but maybe some better way exists to resolve this problem.
精彩评论