micronaut-projects / micronaut-core

Micronaut Application Framework
http://micronaut.io
Apache License 2.0
6.05k stars 1.06k forks source link

@Refreshable annotation on a @Factory class with @EachBean breaks #3120

Open sjrd218 opened 4 years ago

sjrd218 commented 4 years ago

Adding @Refreshable to the Factory class that uses @EachBean to create beans driven from @EachProperty configuration causes the app to break.

Steps to Reproduce

  1. Create a config class to be used with @EachProperty
  2. Create a Factory bean
  3. Create a factory method in the factory bean that uses@EachBean to return a bean for each of the config classes that were created in step 1.
  4. Make a class that uses the factory bean
  5. bootstrap the app and confirm the beans are created and work
  6. Add the @Refreshable annotation to the Factory class
  7. bootstrap and try to create a bean with the factory and see the Stacktrace

Stacktrace

 Error starting Micronaut server: Error instantiating bean of type [each.bean.test.$MyBeanFactoryDefinition$Intercepted]: No bean of type [each.bean.test.MyBeanFactory] exists for the given qualifier: @Named('one'). Make sure the bean is not disabled by bean requirements (enable trace logging for 'io.micronaut.context.condition' to check) and if the bean is enabled then ensure the class is declared a bean and annotation processing is enabled (for Java and Kotlin the 'micronaut-inject-java' dependency should be configured as an annotation processor).
io.micronaut.context.exceptions.BeanInstantiationException: Error instantiating bean of type [each.bean.test.$MyBeanFactoryDefinition$Intercepted]: No bean of type [each.bean.test.MyBeanFactory] exists for the given qualifier: @Named('one'). Make sure the bean is not disabled by bean requirements (enable trace logging for 'io.micronaut.context.condition' to check) and if the bean is enabled then ensure the class is declared a bean and annotation processing is enabled (for Java and Kotlin the 'micronaut-inject-java' dependency should be configured as an annotation processor).
        at io.micronaut.context.DefaultBeanContext.doCreateBean(DefaultBeanContext.java:1721)
        at io.micronaut.context.DefaultBeanContext.lambda$getScopedBeanForDefinition$56(DefaultBeanContext.java:2111)
        at java.util.concurrent.ConcurrentHashMap.computeIfAbsent(ConcurrentHashMap.java:1660)
        at io.micronaut.context.DefaultBeanContext.getScopedBeanForDefinition(DefaultBeanContext.java:2104)
        at io.micronaut.context.DefaultBeanContext.getBeanForDefinition(DefaultBeanContext.java:2086)
        at io.micronaut.context.DefaultBeanContext.getBeanInternal(DefaultBeanContext.java:2058)
        at io.micronaut.context.DefaultBeanContext.getBean(DefaultBeanContext.java:1080)
        at each.bean.test.$MyBeanFactory$CreateMyBean0Definition.build(Unknown Source)
        at io.micronaut.context.BeanDefinitionDelegate.build(BeanDefinitionDelegate.java:125)
        at io.micronaut.context.DefaultBeanContext.doCreateBean(DefaultBeanContext.java:1693)
        at io.micronaut.context.DefaultBeanContext$6.get(DefaultBeanContext.java:2153)
        at io.micronaut.inject.ParametrizedProvider.get(ParametrizedProvider.java:44)
        at io.micronaut.runtime.context.scope.refresh.RefreshScope.lambda$get$0(RefreshScope.java:91)
        at java.util.concurrent.ConcurrentHashMap.computeIfAbsent(ConcurrentHashMap.java:1660)
        at io.micronaut.runtime.context.scope.refresh.RefreshScope.get(RefreshScope.java:90)
        at io.micronaut.context.DefaultBeanContext.getScopedBeanForDefinition(DefaultBeanContext.java:2146)
        at io.micronaut.context.DefaultBeanContext.getBeanForDefinition(DefaultBeanContext.java:2086)
        at io.micronaut.context.DefaultBeanContext.getProxyTargetBean(DefaultBeanContext.java:949)
        at each.bean.test.$MyBeanFactory$CreateMyBean0Definition$Intercepted.$resolveTarget(Unknown Source)
        at each.bean.test.$MyBeanFactory$CreateMyBean0Definition$Intercepted.interceptedTarget(Unknown Source)
        at each.bean.test.$MyBeanFactory$CreateMyBean0Definition$Intercepted.myMessage(Unknown Source)
        at each.bean.test.MyBean$myMessage.call(Unknown Source)
        at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:47)
        at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:115)
        at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:119)
        at each.bean.test.MyBeanPrinter$_onApplicationEvent_closure2.doCall(MyBeanPrinter.groovy:39)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.lang.reflect.Method.invoke(Method.java:498)
        at org.codehaus.groovy.reflection.CachedMethod.invoke(CachedMethod.java:101)
        at groovy.lang.MetaMethod.doMethodInvoke(MetaMethod.java:323)
        at org.codehaus.groovy.runtime.metaclass.ClosureMetaClass.invokeMethod(ClosureMetaClass.java:263)
        at groovy.lang.MetaClassImpl.invokeMethod(MetaClassImpl.java:1041)
        at groovy.lang.Closure.call(Closure.java:405)
        at groovy.lang.Closure.call(Closure.java:421)
        at org.codehaus.groovy.runtime.DefaultGroovyMethods.each(DefaultGroovyMethods.java:2330)
        at org.codehaus.groovy.runtime.DefaultGroovyMethods.each(DefaultGroovyMethods.java:2315)
        at org.codehaus.groovy.runtime.DefaultGroovyMethods.each(DefaultGroovyMethods.java:2344)
        at org.codehaus.groovy.runtime.dgm$184.invoke(Unknown Source)
        at org.codehaus.groovy.runtime.callsite.PojoMetaMethodSite$PojoMetaMethodSiteNoUnwrapNoCoerce.invoke(PojoMetaMethodSite.java:244)
        at org.codehaus.groovy.runtime.callsite.PojoMetaMethodSite.call(PojoMetaMethodSite.java:53)
        at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:47)
        at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:115)
        at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:127)
        at each.bean.test.MyBeanPrinter.onApplicationEvent(MyBeanPrinter.groovy:38)
        at each.bean.test.MyBeanPrinter.onApplicationEvent(MyBeanPrinter.groovy)
        at io.micronaut.context.DefaultBeanContext.publishEvent(DefaultBeanContext.java:1145)
        at io.micronaut.http.server.netty.NettyHttpServer.fireStartupEvents(NettyHttpServer.java:507)
        at io.micronaut.http.server.netty.NettyHttpServer.start(NettyHttpServer.java:378)
        at io.micronaut.http.server.netty.NettyHttpServer.start(NettyHttpServer.java:96)
        at io.micronaut.runtime.Micronaut.lambda$start$2(Micronaut.java:70)
        at java.util.Optional.ifPresent(Optional.java:159)
        at io.micronaut.runtime.Micronaut.start(Micronaut.java:68)
        at io.micronaut.runtime.Micronaut.run(Micronaut.java:294)
        at io.micronaut.runtime.Micronaut.run(Micronaut.java:280)
        at each.bean.test.Application.main(Application.groovy:10)
Caused by: io.micronaut.context.exceptions.NoSuchBeanException: No bean of type [each.bean.test.MyBeanFactory] exists for the given qualifier: @Named('one'). Make sure the bean is not disabled by bean requirements (enable trace logging for 'io.micronaut.context.condition' to check) and if the bean is enabled then ensure the class is declared a bean and annotation processing is enabled (for Java and Kotlin the 'micronaut-inject-java' dependency should be configured as an annotation processor).
        at io.micronaut.context.BeanDefinitionRegistry.lambda$getProxyTargetBeanDefinition$1(BeanDefinitionRegistry.java:275)
        at java.util.Optional.orElseThrow(Optional.java:290)
        at io.micronaut.context.BeanDefinitionRegistry.getProxyTargetBeanDefinition(BeanDefinitionRegistry.java:275)
        at io.micronaut.context.DefaultBeanContext.findProxyTargetMethod(DefaultBeanContext.java:972)
        at io.micronaut.context.ExecutionHandleLocator.getProxyTargetMethod(ExecutionHandleLocator.java:184)
        at each.bean.test.$MyBeanFactoryDefinition$Intercepted.<init>(Unknown Source)
        at each.bean.test.$$MyBeanFactoryDefinition$InterceptedDefinition.build(Unknown Source)
        at io.micronaut.context.DefaultBeanContext.doCreateBean(DefaultBeanContext.java:1693)
        ... 56 common frames omitted

Expected Behaviour

Factory method should return the configured bean. Factory should participate in RefreshEvents triggered in the application.

Actual Behaviour

Stacktrace is thrown saying the bean cannot be found.

Environment Information

Example Application

https://github.com/sjrd218/MicronautEachBeanDemo

Sleepy-GH commented 1 year ago

Blowing the dust and cobwebs off of this one.. I seem to be running into the same issue. Did you find a workaround?

easowj0 commented 1 month ago

I'm also running in to the same issue, currently using Micronaut v. 3.9.4. Does this get resolved in later versions? If not, are there plans to fix this issue soon?