Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Spring logs FactoryBean type check warning in case of factory method with arguments [SPR-12900] #17499

Closed
spring-issuemaster opened this issue Apr 9, 2015 · 1 comment

Comments

Projects
None yet
2 participants
@spring-issuemaster
Copy link
Collaborator

commented Apr 9, 2015

Andrei opened SPR-12900 and commented

I have two configuration files:

@Configuration
public class FactoryBeansContext {

    @Bean
    public HessianProxyFactoryBean deviceServiceHessianProxyFactoryBean(final Environment env) {
        final HessianProxyFactoryBean factory = new HessianProxyFactoryBean();
        factory.setProxyFactory(miHessianProxyFactoy(env));
        factory.setServiceUrl(env.getProperty(PropertyConstants.URL));
        factory.setServiceInterface(com.mi.eas.service.DeviceService.class);
        factory.setOverloadEnabled(true);
        return factory;
    }

    @Bean
    public static MIHessianProxyFactory miHessianProxyFactoy(final Environment env) {
        final MIHessianProxyFactory bean = new MIHessianProxyFactory();
        bean.setUserName(env.getProperty(PropertyConstants.USER_ID));
        bean.setEncryptedPassword(env.getProperty(PropertyConstants.ENCRYPTED_PASSWORD));
        return bean;
    }

}
@Configuration
@ComponentScan(some package here)

public class Context {

    @Autowired
    private Environment env;

    @Autowired
    private FactoryBeansContext factoryBeansContext;

    @Bean 
    public DeviceService deviceService() {
        return (DeviceService)this.factoryBeansContext.deviceServiceHessianProxyFactoryBean(this.env).getObject();
    }

}

Here MIHessianProxyFactory extends com.caucho.hessian.client.HessianProxyFactory

When i run my application Spring tries to create deviceServiceHessianProxyFactoryBean.

It goes to AbstractAutowireCapableBeanFactory#getSingletonFactoryBeanForTypeCheck and execute method #beforeSingletonCreation.

In #beforeSingletonCreation method it puts bean name "deviceServiceHessianProxyFactoryBean" in singletonsCurrentlyInCreation List.

Than it goes to AbstractAutowireCapableBeanFactory#createBeanInstance() method and tries to create deviceServiceHessianProxyFactoryBean bean.

But inside #createBeanInstance() method Srping calls #beforeSingletonCreation() method one more time and it throws BeanCurrentlyInCreationException because it was already called for this bean.

Of cause it is correct situation if i have circular dependencies but there are no circular dependencies in my config.

There are two stack traces below. See comments in both stack traces.

"localhost-startStop-1@305" daemon prio=5 tid=0x10 nid=NA runnable
  java.lang.Thread.State: RUNNABLE

// #beforeSingletonCreation() method put  "deviceServiceHessianProxyFactoryBean" name in singletonsCurrentlyInCreation list

	  at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.beforeSingletonCreation(DefaultSingletonBeanRegistry.java:349)

// #getSingletonFactoryBeanForTypeCheck method calls  #beforeSingletonCreation() method

	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.getSingletonFactoryBeanForTypeCheck(AbstractAutowireCapableBeanFactory.java:856)



	  - locked <0x449> (a java.util.concurrent.ConcurrentHashMap)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.getTypeForFactoryBean(AbstractAutowireCapableBeanFactory.java:790)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch(AbstractBeanFactory.java:542)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.doGetBeanNamesForType(DefaultListableBeanFactory.java:436)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType(DefaultListableBeanFactory.java:404)
	  at org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors(BeanFactoryUtils.java:187)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1112)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1051)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:949)
	  at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:813)
	  at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:741)
	  at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:464)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1111)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1006)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:504)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476)
	  at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:303)
	  at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:299)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:199)
	  at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:150)
	  at org.springframework.context.support.AbstractApplicationContext.invokeBeanFactoryPostProcessors(AbstractApplicationContext.java:606)
	  at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:462)
	  - locked <0x7a2> (a java.lang.Object)
	  at org.springframework.web.context.ContextLoader.configureAndRefreshWebApplicationContext(ContextLoader.java:403)
	  at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:306)
	  at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:106)
	  at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4992)
	  at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5492)
	  - locked <0x434> (a org.apache.catalina.core.StandardContext)
	  at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150)
	  at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:901)
	  at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:877)
	  at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:649)
	  at org.apache.catalina.startup.HostConfig.deployWAR(HostConfig.java:1081)
	  at org.apache.catalina.startup.HostConfig$DeployWar.run(HostConfig.java:1877)
	  at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
	  at java.util.concurrent.FutureTask.run(FutureTask.java:266)
	  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	  at java.lang.Thread.run(Thread.java:745)

"localhost-startStop-1@3" daemon prio=5 tid=0xf nid=NA runnable
  java.lang.Thread.State: RUNNABLE

// here Spring calls #beforeSingletonCreation() for same bean second time but "deviceServiceHessianProxyFactoryBean" bean is already there

	  at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.beforeSingletonCreation(DefaultSingletonBeanRegistry.java:346)

	  at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:223)
	  - locked <0x2ae> (a java.util.concurrent.ConcurrentHashMap)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:299)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.getTypeForFactoryBean(AbstractBeanFactory.java:1421)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.getTypeForFactoryBean(AbstractAutowireCapableBeanFactory.java:802)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch(AbstractBeanFactory.java:542)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.doGetBeanNamesForType(DefaultListableBeanFactory.java:436)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType(DefaultListableBeanFactory.java:404)
	  at org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors(BeanFactoryUtils.java:187)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1112)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1051)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:949)
	  at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:813)
	  at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:741)
	  at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:464)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1111)


// Spring tries to create "deviceServiceHessianProxyFactoryBean" bean and during creation it tries to call #beforeSingletonCreation() one more time 

	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1006)


	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.getSingletonFactoryBeanForTypeCheck(AbstractAutowireCapableBeanFactory.java:860)


	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.getTypeForFactoryBean(AbstractAutowireCapableBeanFactory.java:790)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.isTypeMatch(AbstractBeanFactory.java:542)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.doGetBeanNamesForType(DefaultListableBeanFactory.java:436)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanNamesForType(DefaultListableBeanFactory.java:404)
	  at org.springframework.beans.factory.BeanFactoryUtils.beanNamesForTypeIncludingAncestors(BeanFactoryUtils.java:187)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1112)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1051)
	  at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:949)
	  at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:813)
	  at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:741)
	  at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:464)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1111)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1006)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:504)
	  at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476)
	  at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:303)
	  at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:299)
	  at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:199)
	  at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:150)
	  at org.springframework.context.support.AbstractApplicationContext.invokeBeanFactoryPostProcessors(AbstractApplicationContext.java:606)
	  at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:462)
	  - locked <0x7bc> (a java.lang.Object)
	  at org.springframework.web.context.ContextLoader.configureAndRefreshWebApplicationContext(ContextLoader.java:403)
	  at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:306)
	  at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:106)
	  at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4992)
	  at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5492)
	  - locked <0x278> (a org.apache.catalina.core.StandardContext)
	  at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150)
	  at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:901)
	  at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:877)
	  at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:649)
	  at org.apache.catalina.startup.HostConfig.deployWAR(HostConfig.java:1081)
	  at org.apache.catalina.startup.HostConfig$DeployWar.run(HostConfig.java:1877)
	  at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
	  at java.util.concurrent.FutureTask.run(FutureTask.java:266)
	  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
	  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
	  at java.lang.Thread.run(Thread.java:745)

Affects: 4.1.4

Issue Links:

  • #18406 Lot of undesired WARN logs after migration from Spring 3 to Spring 4

Referenced from: commits 65ba72f, 56f8d17

@spring-issuemaster

This comment has been minimized.

Copy link
Collaborator Author

commented Apr 16, 2015

Juergen Hoeller commented

This is in fact working as designed: When trying to resolve the argument for your factory method, Spring's type matching algorithm is also checking the FactoryBean that you're currently creating there - and fails since it is currently in creation - a kind of circular reference with the currently created FactoryBean when trying to check its type. The FactoryBean check then backs out and considers this self-reference a non-match.

That said, the primary problem seems to be that we're logging a warning in case of such FactoryBean type resolution failure. I'll lower this to debug for the currently-in-creation case, just logging a warning for a 'real' resolution problem (typically an invalid FactoryBean definition).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.