AnnotationMethodHandlerExceptionResolver message converters - java

I want to configure AnnotationMethodHandlerExceptionResolver by adding jackson message converter. The problem is that I have already configured message converters in <mvc:message-converters> by creating a bean, and I can't reference it in AnnotationMethodHandlerExceptionResolver neither use ref in <mvc:message-conferters>
<mvc:annotation-driven>
<mvc:message-converters register-defaults="false">
<bean id="mappingJackson2" class="pl.styall.scylla.json.config.CustomMappingJackson2">
<property name="objectMapper" ref="jacksonObjectMapper" />
</bean>
</mvc:message-converters>
</mvc:annotation-driven>
<bean id="outboundExceptionAdapter"
class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerExceptionResolver">
<property name="messageConverters">
<list>
<ref bean="mappingJackson2" />
</list>
</property>
</bean>
I could define two beans one for <mvc:message-converters> and AnnotationMethodHandlerExceptionResolver, but it is probably not the best idea. Is there other way to do this?

This is not supported yet, but it is on the 3.2 backlog. So it might be supported in 3.2.
See Add support for <ref> in addition to <bean> for <mvc:message-converters> for the Spring feature request.

Related

How to convert an xml config bean to java annotation bean ( spring boot )

I am new to java AOP. I am supposed to convert the following xml config to java annotation config in my spring boot application. May I know how exactly to convert this xml config to java annotation config:
I think none of the examples that I saw in stackoverflow match the pattern I am trying to convert.
<bean id="xyzRestTemplate"
class="org.springframework.web.client.RestTemplate">
<constructor-arg ref="xyzClientHttpRequestFactory" />
<property name="messageConverters">
<list>
<bean class="org.springframework.http.converter.xml.MarshallingHttpMessageConverter">
<property name="marshaller" ref="jaxbDataMarshaller" />
<property name="unmarshaller" ref="jaxbDataMarshaller" />
</bean>
</list>
</property>
<property name="interceptors">
<list>
<bean class="com.example.XYZHeaderRequestInterceptor" />
</list>
</property>
</bean>
<bean id="jaxbDataMarshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller">
<property name="contextPaths">
<list>
<value>com.a.b.c.d.v2</value>
</list>
</property> </bean>
When people talk about converting from XML they don't mean necessarily doing the same thing exactly. What makes Spring Boot attractive isn't just that a configuration is a java class.
You should convert this to use RestTemplate https://docs.spring.io/spring-boot/docs/current/reference/html/boot-features-resttemplate.html
Then you just build the RestTemplate using the builder to have the JaxB marshaller and the interceptor you want.
Rest Template - XML Indentation
A nice testcase that passes with XML and passes with #Configuration classes will prove you got it right.

Dozer mapper singleton instance with Spring IOC

Inside a web application, I'm using dozer mapper (5.3.2) to perform some object to object mappings.
DozerBeanMapper is instantiated using spring bean definition. Mapping file is provided as property in the spring context xml.
<bean id="idmToBoMPersonMapper" class="org.dozer.DozerBeanMapper" lazy-init="false" scope="singleton" >
<property name="mappingFiles" value="config/IiIdmToBoMPersonMapping.xml"/>
</bean>
Mapping is working, but according to logs, instance of DozerBeanMapper is created every time the code uses the mapper.
INFO DozerBeanMapper:166 - Initializing a new instance of dozer bean mapper.
This is concerns me, I'd expect the mapper to be created once and only once.
I have tried to explicitly use scope="singleton" in the spring bean configuration, but that is not helping either.
Any suggestions for me to try?
I would be better to use the Spring integration with Dozer instead, namely the DozerBeanMapperFactoryBean, see here the documentation for further details:
<bean class="org.dozer.spring.DozerBeanMapperFactoryBean">
<property name="mappingFiles"
value="classpath*:/*mapping.xml"/>
<property name="customConverters">
<list>
<bean class=
"org.dozer.converters.CustomConverter"/>
</list>
</property>
<property name="eventListeners">
<list>
<bean class="org.dozer.listeners.EventListener"/>
</list>
</property>
<property name="factories">
<map>
<entry key="id" value-ref="bean-factory-ref"/>
</map>
</property>
</bean>

How to stop DefaultListableBeanFactory from implicitly creating LocalValidatorFactoryBean instance

I am using Spring 3.1 and have the following spring config where I explicitly create LocalValidatorFactoryBean using my own ValidationMessageSource. I have Hibernate Validator 4.1 in my class path.
<bean id="messageSource"
class="org.springframework.context.support.ResourceBundleMessageSource">
<property name="basenames">
<list>
<value>ValidatorMsgID</value>
</list>
</property>
</bean>
<bean id="validator"
class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
<property name="validationMessageSource" ref="messageSource"/>
</bean>
<bean class="org.springframework.validation.beanvalidation.MethodValidationPostProcessor"/>
However I noticed that the LocalValidatorFactoryBean is being created twice by hitting a debug in classes afterPropertiesSet method. The first time is for the explicite bean that I defined in the spring config, however following that the same class is instantiated implicitly again by DefaultListableBeanFactory class - obviously this time with no validationMessageSource. Therefore it seems that when Spring does make use of the LocalValidatorFactoryBean its using the one with the default Hibernates messagesource rather than the one I have specified.
Ok, looking into this a bit further its seems that this is caused by mvc:annotation-driven I have in the spring config.
Any pointers would still help
Ok, I got it sorted eventually by adding the validator attribute to "mvc:annotation-driven". This is how my final spring config looks
<bean id="messageSource"
class="org.springframework.context.support.ResourceBundleMessageSource">
<property name="basenames">
<list>
<value>com.mycompany.msgs.ValidatorMsgID</value>
</list>
</property>
</bean>
<bean id="validator"
class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
<property name="messageInterpolator">
<bean class="org.hibernate.validator.messageinterpolation.ResourceBundleMessageInterpolator">
<constructor-arg index="0">
<bean class="org.springframework.validation.beanvalidation.MessageSourceResourceBundleLocator">
<constructor-arg index="0" ref="messageSource"/>
</bean>
</constructor-arg>
</bean>
</property>
</bean>
<bean class="org.springframework.validation.beanvalidation.MethodValidationPostProcessor">
<property name="validator" ref="validator"/>
</bean>
<mvc:annotation-driven validator="validator"/>

How to force disable JSR-303 support in Spring 3?

I have some legacy Spring MVC code mixed with gwt code in same artifact (built using maven) and I cannot make it run. It wants validation provider at runtime which i do not need (since I'm not using any JSR-303 validation annotations) and do not want in CP (it may conflict with some app containers this artifact will be deployed in)
How to force spring not to do any JSR-303 validations and get rid of runtime dependency on validation provider?
PS artifact has validation-api in CP since GWT is using it somehow
PPS
Seems like removing <mvc:annotation-driven/> from Spring config fixes this.
Binding and classic validations still works (I have <context:annotation-config/> enabled)
As you already discovered, <mvc:annotation-driven/> sets a lot of features including JSR-303. The equivalent is
<bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping">
<property name="order" value="0" />
</bean>
<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter">
<property name="webBindingInitializer">
<bean class="org.springframework.web.bind.support.ConfigurableWebBindingInitializer">
<property name="validator" ref="validator" />
</bean>
</property>
<property name="messageConverters">
<list>
<bean class="org.springframework.http.converter.ByteArrayHttpMessageConverter" />
<bean class="org.springframework.http.converter.StringHttpMessageConverter" />
<bean class="org.springframework.http.converter.FormHttpMessageConverter" />
<bean class="org.springframework.http.converter.xml.SourceHttpMessageConverter" />
</list>
</property>
</bean>
<bean id="validator"
class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" />
<bean id="conversion-service"
class="org.springframework.format.support.FormattingConversionServiceFactoryBean" />
So you may substitute the tag onto this xml configuration and remove parts you don't need.

Spring: Getting FactoryBean object instead of FactoryBean.getObject()

Short question: If I have class that impelemnts FactoryBean interface, how can I get from FactoryBean object itself instead of FactoryBean.getObject()?
Long question: I have to use 3-rd party Spring based library which is hardly use FactoryBean interface. Right now I always must configure 2 beans:
<!-- Case 1-->
<bean id="XYZ" class="FactoryBean1" scope="prototype">
<property name="steps">
<bean class="FactoryBean2">
<property name="itemReader" ref="aName"/>
</bean>
</property>
</bean>
<bean id="aName" class="com.package.ClassName1" scope="prototype">
<property name="objectContext">
<bean class="com.package.ABC"/>
</property>
</bean>
<!-- Case 2-->
<bean id="XYZ2" class="FactoryBean1" scope="prototype">
<property name="steps">
<bean class="FactoryBean2">
<property name="itemReader" ref="aName2"/>
</bean>
</property>
</bean>
<bean id="aName2" class="com.package.ClassName1" scope="prototype">
<property name="objectContext">
<bean class="com.package.QWE"/>
</property>
</bean>
Actyually defintion of a bean with name "XYZ" (compare with "XYZ2") never will be changed, but because of factory nature I must copy the code for each configuration.
Definition of a bean with name "aName" always will be new (i.e. each configuration will have own objectContext value).
I would like to simplify the configuration have a single factory bean (remove "XYZ2" and rid of link to "aName"):
<bean id="XYZ" class="FactoryBean1" scope="prototype">
<property name="steps">
<bean class="FactoryBean2"/>
</property>
</bean>
<bean id="aName" class="com.package.ClassName1" scope="prototype">
<property name="objectContext">
<bean class="com.package.ABC"/>
</property>
</bean>
<bean id="aName2" class="com.package.ClassName1" scope="prototype">
<property name="objectContext">
<bean class="com.package.QWE"/>
</property>
</bean>
Unfortunately, it's not as simple as I expect. I suppose to glue factory (i.e. XYZ bean from the example) with necessary objects (i.e. "aName", "aName2") at runtime.
The approach doesn't work because when I ask Spring for FactoryBean object it returns to me FactoryBean.getObject() which impossible to instanciate at that time because of missing itemReader value.
I hope that SpringSource foresee my case I can somehome "hook" FactoryBean.getObject() call to provide all necessary properties at runtime.
Another complexity that disturb me a bit it's chains of Factories (Factory1 get an object from Factory2 that I have to "hook" at runtime).
Any ideas will be appreciated.
It's the & (ampersand), not the At-symbol, see Spring Framework documentation: Customizing instantiation logic using FactoryBeans
<property name="factoryBean" ref="&theFactoryBean" />
You can get the factory bean itself using the & syntax in the spring config:
<property name="factoryBean" ref="&theFactoryBean" />
as opposed to:
<property name="createdBean" ref="theFactoryBean" />

Categories