Announcement Announcement Module
Collapse
No announcement yet.
Generic Bean Factory and @Configurable Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Generic Bean Factory and @Configurable

    Hi
    I am currently testing the use of the @Configurable annotation, to provide Domain Object dependency injection.

    Since the 2.0.3 enhancements within Spring aspects, this now works a treat, re-injecting the dependencies upon de-serialization. (See http://opensource.atlassian.com/proj...rowse/SPR-2896)

    However, I am wondering whether there is any way to inject a bean, dependent upon generics.

    For example, I have a Domain class as follows:
    Code:
    @Configurable(autowire=Autowire.BY_TYPE)
    public class DomainClass {
        private IDependency<DomainClass> dependency;
    
        public void setDependency(final IDependency<DomainClass> dependency) {
            this.dependency = dependency;
        }
        
    }
    I do not wish to have bean definitions for each instance, rather I would prefer to just define the dependent beans, and autowire according to the generic type that the dependency is defined to act against.

    I relealise that the methodology behing the implementation of generics may inhibit this, but reference to "GenericBeanFactoryAccessor" within the Spring API, has given me some hope.

    Is it possible to inject by type, according to the class that a generic dependency acts against?

    Regards (and thanks to Ramnivas for the recent enhancement)

  • #2
    You are welcome!

    Due to the reason you suspect (Java's implementation of generics, which uses erasure as the underlying technique), it won't be possible to detect the full type alongwith generic type parameters of a bean at runtime and thus with current Spring implementation, type-based autowiring that utilizes generic info won't be possible.

    GenericBeanFactoryAccessor merely does casting using generics so the caller doesn't have to.

    With that said, Spring might be able to retain more meta-information about bean's generic type parameters. In that case, autowiring by type may be possible with generics. This is a core Spring issue and you may want to raise a JIRA issue in that area. When the core starts to perform such autowiring, @Configurable beans will automatically leverage such behavior.

    -Ramnivas
    Last edited by ramnivas; Mar 11th, 2007, 11:37 AM.

    Comment


    • #3
      Thanks for the succinct reply. I am currently able to work round the issue, but will consider it further and then raise a JIRA accordingly.

      A further potential issue:

      When using the @Configurable annotation, I am using CTW within my build to weave in the spring-aspects.jar with my domain classes. These woven classes are then used on the server, where I am using <aop:spring-configured/> within my app context. I am also using @Transactional support.

      When the application loads, I am receiving many of the following warnings.

      Are these benign, and if so, what do they mean.
      Code:
      WARN [org.springframework.beans.factory.aspectj.AnnotationBeanConfigurerAspect] - <BeanFactory has not been set on [org.springframework.beans.factory.aspectj.AnnotationBeanConfigurerAspect]: Make sure this configurer runs in a Spring container. For example, add it to a Spring application context as an XML bean definition.>
      Regards
      Marc

      Comment


      • #4
        Hmmm... That warning indicates that somehow the AnnotationBeanConfigurerAspect bean isn't configured before a @Configurable bean is created (normally, <aop:spring-configured/> is all you need). It seems that in your application certain @Configurable objects are getting created prior to loading the application context. It may also be possible one of the bean is creating @Configurable objects (i.e. application context is still being loaded).

        Can you investigate more? I am especially interested in the use case that is making this happen (since recreating the problem is actually quite easy -- just create a @configurable object prior to loading the application context).

        -Ramnivas

        Comment


        • #5
          In fact until erasure is replaced with reification (if it ever happens ) in any java implementation of Collections, it is indeed not possible to retrieve the Generic's defined type.

          A possible (and tested) way of doing this is to use an Annotation in order to provide the needed metadata.

          For example:

          Code:
          @Configurable(autowire=Autowire.BY_TYPE)
          public class DomainClass {
          
              @CollectionRuntimeInfo(type = DomainClass.class)
              private IDependency<DomainClass> dependency;
          
              public void setDependency(final IDependency<DomainClass> dependency) {
                  this.dependency = dependency;
              }
              
          }
          I know this seems quite redundant, but it makes the type accessible at runtime. It would BTW be really interesting if the compiler added this metadata automatically in order to cover this problem with generics.

          Cheers.

          P.A.

          Comment

          Working...
          X