Announcement Announcement Module
Collapse
No announcement yet.
Help with DomainClassConverter configuration Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Help with DomainClassConverter configuration

    Hi. Hoping someone can help me with this error. The documentation says I can set up a Domain Converter using the following XML, but it causes an error because the outer bean is in construction when the inner bean is created:

    <mvc:annotation-driven conversion-service="conversionService" />

    <bean id="conversionService" class="org.springframework.context.support.Convers ionServiceFactoryBean">
    <property name="converters">
    <list>
    <bean class="org.springframework.data.repository.support .DomainClassConverter">
    <constructor-arg ref="conversionService" />
    </bean>
    </list>
    </property>
    </bean>

    The error is:

    org.springframework.beans.factory.BeanCreationExce ption: Error creating bean with name 'conversionService' defined in class path resource [META-INF/spring/rest-servlet.xml]: Cannot create inner bean 'org.springframework.data.repository.support.Domai nClassConverter#535af9ae' of type [org.springframework.data.repository.support.Domain ClassConverter] while setting bean property 'converters' with key [0]; nested exception is org.springframework.beans.factory.BeanCreationExce ption: Error creating bean with name 'org.springframework.data.repository.support.Domai nClassConverter#535af9ae' defined in class path resource [META-INF/spring/rest-servlet.xml]: Cannot resolve reference to bean 'conversionService' while setting constructor argument; nested exception is org.springframework.beans.factory.BeanCurrentlyInC reationException: Error creating bean with name 'conversionService': FactoryBean which is currently in creation returned null from getObject

  • #2
    Yes, it appears the documented way of doing this is not possible because of the circular reference. This abomination is a workaround:
    Code:
      <bean id="conversionService" class="org.springframework.core.convert.support.DefaultConversionService"/>
    
      <bean class="org.springframework.beans.factory.config.MethodInvokingFactoryBean">
        <property name="targetClass" value="org.springframework.core.convert.support.ConversionServiceFactory"/>
        <property name="targetMethod" value="registerConverters"/>
        <property name="arguments">
          <util:list>
            <set>
              <bean class="org.springframework.data.repository.support.DomainClassConverter">
                <constructor-arg ref="conversionService"/>
              </bean>
            </set>
            <ref bean="conversionService"/>
          </util:list>
        </property>
      </bean>
    The reason this works is the registration of converters is delayed until after the conversion service has been instantiated, breaking the circular instantiation dependency.

    Comment


    • #3
      JIRA ticket created.

      Comment


      • #4
        Thanks for the reply. That allowed the beans to be created, but the conversion is not working. I get the following error:

        org.springframework.beans.ConversionNotSupportedEx ception: Failed to convert value of type 'java.lang.String' to required type 'com.myco.platform.api.domain.User'; nested exception is java.lang.IllegalStateException: Cannot convert value of type [java.lang.String] to required type [com.myco.platform.api.domain.User]: no matching editors or conversion strategy found

        I was able to write my own conversion factory using generics for my domain objects since they all extend from the same base class. And that worked:

        <!-- Custom Domain Conversion Service -->
        <bean id="conversionService" class="org.springframework.context.support.Convers ionServiceFactoryBean">
        <property name="converters">
        <list>
        <bean class="com.myco.platform.api.web.converters.Domain ConverterFactory"/>
        </list>
        </property>
        </bean>

        But I'd like to use the default domain converter if possible. Any ideas? Thanks.

        M

        Comment


        • #5
          Ya, sorry for not taking it all the way to make sure my suggestion works. It looks like a bug in how the Spring Data repositories are registered in the DomainClassConverter, though I don't rule out some incorrect configuration on our part. Please go to the JIRA ticket I submitted and vote for it.

          Comment


          • #6
            Cool. Will do. Thanks for your help!

            M

            Comment


            • #7
              We're suffering from a bug [0] in Spring framework here which will be fixed for 3.1.1. Commented on the ticket.

              [0] https://jira.springsource.org/browse/SPR-8954

              Comment


              • #8
                Hi. Is there any progress on this bug? It seems that it must be fixed in version 1.3 of spring-data-commons-core, but latest release version of spring-data-mongodb uses 1.2.1. So I tried to use this workaround and had no success (DomainClassConverter fails to find repository beans). May be it is another way to use DomainClassConverter in ConversionService?

                Comment


                • #9
                  We're much further down the road already. For XML based configuration (and @EnableRepositories introduced in the latest milestones) this is generally fixed. JavaConfig declared repositories through @Bean methods are still not found because of a subsequent bug [0].

                  However there's still a thing to notice. When working with a web application make sure you have the repositories declared in the ApplicationContext registered through the ContextLoaderListener, the DomainClassConverter registered in the ApplicationContext of the DispatcherServlet. This is the only way to make sure the repositories get created entirely before being accessed the first time.

                  [0] https://jira.springsource.org/browse/SPR-9143

                  Comment


                  • #10
                    Thank you! For now I just created FormattingConversionServiceFactoryBean subclass and override afterPropertiesSet method in which I create and register custom implementation of DomainClassConverter (almost the same but instead of implementing ApplicationContextAware, root application context injected directly). Hope for soon 3.2 release to get rid of this)

                    Comment

                    Working...
                    X