Spring Transaction with JNDI and JPA transaction manager - spring

I have defined DataSource in Context.xml(JNDI) and i would like to use with JPA transaction manager in Spring application Context.xml. I don't want to use JTA Transaction since i am using tomcat server.
Could anyone help me how can i achieve this with an example? I am using #transactional annotations in DAO's and services.
Regards
Vijay

you can Define DataSource: Use JndiObjectFactoryBean class. To define the data source by providing JNDI binding name.
<!– Data Source JNDI –>
<bean id=”dataSource” class=”org.springframework.jndi.JndiObjectFactoryBean”>
<property name=”jndiName”>
<value>jdbc/SampleDS</value>
</property>
</bean>

Here is an example:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:jee="http://www.springframework.org/schema/jee"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/jee
http://www.springframework.org/schema/jee/spring-jee-3.0.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-3.0.xsd">
<!-- Provides access to the JNDI datasource -->
<jee:jndi-lookup id="dataSource" jndi-name="jdbc/jpetstore"/>
<!-- Defines transaction manager -->
<bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>
<!-- Enables transactional behavior -->
<tx:annotation-driven />
<!-- other <bean/> definitions here -->
</beans>
Use <jee:jndi-lookup/> to get access to the JNDI data source. Then, pass the obtained datasource reference to an appropriate PlatformTransactionManager such as DataSourceTransactionManager.
Also, <tx:annotation-driven /> should be provided for the #Transactional annotations to be activated.
To obtain a good understanding of Spring transaction management, I would recommend reading chapter 10 of Spring reference available here.

Related

Spring configuration issues not easy to find solution for

I have found several really awkward problems which took me 3hr+ to resolve. I was wondering if anyone could explain me why this is the case. I believe both of them belong to the very much same context so I have two questions. I hope reader will have patience as for me this is both intimidating and interesting behavior of sf.
I only know the error and resolution, but not satisfied until I understand:
Guidance I follow: Have one configuration file - use package scan inside of your root customConfig only(declared via mapping in web.xml), make sure servlet-context.xml only scans controllers' package. All other context files import via import directive at the very beginning of your customConfig.
1.1 Error if you do it other way: Dependency injection(of various components) will dramatically fail with multiple overlapping config package scanning.
1.2 Error if you do it other way: Transaction during service request of transactionManager in context with entityManagerFactory will fail if servlet-context.xml scans the same package. (i.e. same service package as your customConfig scans)
2: LocaleChangeInterceptor can only be declared in servlet-context - won't work in custom root configuration, reason unknown(doesn't work even if adding package scan for controllers package inside customConfig however now funny bit - SessionLocaleResolver on the other hand will work ok if defined in custom config! )
Q1: So it is me to blame who as human was mistakenly adding overlapping context-component package scan or it would be logical for Spring to resolve these collisions? Or they should be resolved but it doesn't work for me for some reason?
I observed fellow developer and smiled when he told it is best not to touch spring configuration nor try to improve it nor try to update it. I smiled, now I clearly don't(I now find myself intimated by this sf config violence), after all of this do you think it is ok to place everything inside just a single configuration file like servlet-context.xml ?
Q2: What is the magic behind LocaleChangeInterceptor, I've spent around 5 hours fixing it until just moved in "try-and-fail" mood it into servlet-context and it worked.
Second is a pure mystery to solve. Nothing fancy inside customConfig
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:tx="http://www.springframework.org/schema/tx"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.1.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.2.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd">
<!--
<import resource="securityContext.xml"/> -->
<import resource="jpaContext.xml"/>
<context:annotation-config />
<context:component-scan base-package="com.org.app" />
<bean id="messageSource" class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
<property name="basename" value="/WEB-INF/messages" />
<property name="defaultEncoding" value="UTF-8"/>
</bean>
<bean id="localeResolver" class="org.springframework.web.servlet.i18n.SessionLocaleResolver">
<property name="defaultLocale" value="en_GB" />
</bean>
<mvc:interceptors>
<bean
class="org.springframework.web.servlet.i18n.LocaleChangeInterceptor"
p:paramName="lang" />
</mvc:interceptors> ...
After firing ?lang=locale_LOCALE request nothing will happen - no error, no indication , app will load successfully and page will just be reloaded under the same locale.
However placing this interceptor code inside servlet-context.xml below will resolve on locale request successfully.
<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/mvc"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:beans="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
<!-- DispatcherServlet Context: defines this servlet's request-processing
infrastructure -->
<!-- Enables the Spring MVC #Controller programming model -->
<annotation-driven />
<context:component-scan base-package="com.org.app.controller" />
<!-- Handles HTTP GET requests for /resources/** by efficiently serving
up static resources in the ${webappRoot}/resources directory -->
<resources mapping="/resources/**" location="/resources/" />
<!-- Resolves views selected for rendering by #Controllers to .jsp resources
in the /WEB-INF/views directory -->
<beans:bean
class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<beans:property name="prefix" value="/WEB-INF/views/" />
<beans:property name="suffix" value=".jsp" />
</beans:bean>
<interceptors>
<beans:bean
class="org.springframework.web.servlet.i18n.LocaleChangeInterceptor"
p:paramName="lang" />
</interceptors>
</beans:beans>
Your LocalChangeInterceptor and LocaleResolver must be defined in the servlet-context.xml. <context:annotation-driven /> is already implied by the use of <context:component-scan />
In your root context you are also scanning for #Controller you need to exclude them.
<context:component-scan base-package="com.org.app">
<context:exclude-filter type="annotation" value="org.springframework.stereotype.Controller" />
</context:compoment-scan>
Basically all the web related things (and the things which are used by the DispatcherServlet) must be loaded by the DispatcherServlet. Due to its nature it will only look into its own local application context for the beans it needs instead of in its parents.
The reason for this is that you can have multiple DispatcherServlets each with its own configuration, this would break if it would load the configuration from the root application context.

Create DataSource using JBoss 7 JNDI and Spring

I am first time making a webapp for Jboss server.
For JBoss we have the jndi details, but I am wondering how to create the Datasource using it in spring application context.
If anyone has an example to create the connection, please share it.
I will put this sample here.
just to show another way to do it.
<bean id="dataSource" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiName">
<value>java:jboss/datasources/DSName</value>
</property>
</bean>
I found the solution
Add below configuration to applicationContext.xml
xmlns:jee="http://www.springframework.org/schema/jee"
xsi:schemaLocation="http://www.springframework.org/schema/jee
http://www.springframework.org/schema/jee/spring-jee-3.0.xsd"
<jee:jndi-lookup expected-type="javax.sql.DataSource" id="dataSource" jndi-name="java:jboss/SAMPLE_JNDI"/>

Distribute transaction with Spring but without Hibernate

I try to do a global (distribute) transaction in Spring without Java EE (aplication server like JBoss) only with tomcat. There are two databases involved, the first is a PostgreSQL Database, the second is a MS SQLServer Database.
Is there a way to do it without using hibernate?
I tried it with the atomikos API, but I don't know how to do it without a hibernate session. I think it would to great to do it JDBC-based or some other Tool that comes with Spring. But I don't know how to do it.
My Spring configuration looks like that:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:jdbc="http://www.springframework.org/schema/jdbc"
xmlns:util="http://www.springframework.org/schema/util"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/jdbc http://www.springframework.org/schema/jdbc/spring-jdbc-3.1.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.1.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-3.0.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd">
<!-- Get database driver XA properties from file -->
<util:properties id="jdbcConfiguration1" location="classpath:jdbcconfiguration1.properties"/>
<util:properties id="jdbcConfiguration2" location="classpath:jdbcconfiguration2.properties"/>
<bean id="dataSourceA"
class="com.atomikos.jdbc.AtomikosDataSourceBean" init-method="init" destroy-method="close">
<property name="uniqueResourceName"><value>XADBMS01</value></property>
<property name="xaDataSourceClassName"><value>org.postgresql.xa.PGXADataSource</value></property>
<property name="xaProperties" ref="jdbcConfiguration1"/>
<property name="poolSize"><value>1</value></property>
</bean>
<bean id="dataSourceB"
class="com.atomikos.jdbc.AtomikosDataSourceBean" init-method="init" destroy-method="close">
...
<property name="poolSize"><value>1</value></property>
</bean>
<!-- Construct Atomikos UserTransactionManager, needed to configure Spring -->
<bean id="atomikosTransactionManager" class="com.atomikos.icatch.jta.UserTransactionManager"
init-method="init" destroy-method="close">
<!-- when close is called, should we force transactions to terminate or not? -->
<property name="forceShutdown">
<value>true</value>
</property>
</bean>
<!-- Also use Atomikos UserTransactionImp, needed to configure Spring -->
<bean id="atomikosUserTransaction" class="com.atomikos.icatch.jta.UserTransactionImp">
<property name="transactionTimeout"><value>300</value></property>
</bean>
<!-- Configure the Spring framework to use JTA transactions from Atomikos -->
<bean id="transactionManager" class="org.springframework.transaction.jta.JtaTransactionManager">
<property name="transactionManager"><ref bean="atomikosTransactionManager" /></property>
<property name="userTransaction"><ref bean="atomikosUserTransaction" /></property>
</bean>
<tx:annotation-driven transaction-manager="transactionManager" />
......
</beans>
Is it required to use Hibernate? I do not want to use hibernate, because i think it is do complicated for my needs. Is it possible to do that "Spring-based"?
So, you have configured two DataSources and want to know how to use in a way consistent with JtaTransactionManager you declared.
Spring provides two options:
(Recommended) Use JdbcTemplate. Operations on JdbcTemplate automatically participate in the current transaction.
Use DataSourceUitls.getConnection() to obtain a Connection that's aware of the current transaction, and execute arbitrary JDBC operations on it.
In both cases you need to define transaction boundaries in your code using #Transactional or TransactionTemplate, as described in 11. Transaction Management.

Does Spring's validation routine support Hibernate's JSR 303 implementation option for fail fast mode?

8.2. Fail fast mode
I'm looking for where I might configure this option in Spring, but I'm not sure this is a part of JSR 303 so much as it is a Hibernate configuration for their own validator implementation. This is important because if I have multiple constraint violations I only want the first one "thrown".
Assuming you're using Spring's LocalValidatorFactoryBean to set up your validator, you can specify provider-specific configuration properties within the validationPropertyMap attribute.
The property name of Hibernate Validator's fail-fast attribute is "hibernate.validator.fail_fast", so you would set up your validator like this:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:util="http://www.springframework.org/schema/util"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-3.1.xsd">
<bean name="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
<property name="validationPropertyMap">
<util:map>
<entry key="hibernate.validator.fail_fast" value="true"/>
</util:map>
</property>
</bean>
</beans>

Spring MVC 2.5 Using a mix of annotations & XML configuration but xml gets ignored

In my Spring MVC webapplication I want to mix xml based configuration with annotations:
I use annotations like #Controller, #RequestMapping("bla.htm"), #RequestParam etc. to resolve HttpRequests to Controller Methods. Therefore I added
<bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping"/>
<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter"/>
<context:component-scan base-package="somePackage.controller"/>
to my dispatcher-servlet.xml.
But my controllers have attributes. Those attributes could be injected via #AutoWired annotation. But I also have do define Scopes. So i would have two annotations per attribute, which makes the code bad readable. So I want to inject dependencies in my applicationContext.xml file.
Is there a way I can keep the annotation-driven request-mapping but use context.xml files for Dependency Injection? Or is it only possible to use EITHER annotations OR xml configuration?
note: my beans for dependency injection are in a different xml file.
PS:
I should have mentioned, I use Spring 2.5 and can't upgrade it.
No, <mvc:annotation-driven> works fine with XML. But you'll need to get rid of the <context:component-scan>.
Update: with Spring 2.5, this should get you started:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-2.5.xsd">
<context:annotation-config />
<bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping" />
<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" />
<!-- now add some controllers -->
</beans>
Yes this is certainly possible.
To use the controller annotations such as #Controller and #RequestMapping make sure you put
<mvc:annotation-driven/>
in your <servletname>-servlet.xml
Then simple define your controllers using the normal XML bean notation such as:
<bean class="com.company.controllers.AController">
<property name="propertyName" ref="beanId" />
</bean>
These bean refs can come from any other applicationContext.xml defined in your web.xml too.

Resources