Tag Archives: @Transactional

org.hibernate.HibernateException: No Session found for current thread

I was integrating the Spring and Hibernate on a web application. While do so, I end up with the hibernate exception as follows,

org.hibernate.HibernateException: No Session found for current thread

Solution

First we need to understand that the getCurrentSession() only makes sense inside a scope of transaction. We need to declare an appropriate transaction manager, demarcate boundaries of transaction and perform data access inside it. For example, as follows:

<tx:annotation-driven transaction-manager="hibernateTransactionManager"></tx:annotation-driven>

<bean class="org.springframework.orm.hibernate4.HibernateTransactionManager" id="hibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory"></property>
</bean>

<bean class="org.springframework.orm.hibernate4.LocalSessionFactoryBean" id="sessionFactory">
<property name="dataSource" ref="dataSource"></property>
<property name="annotatedClasses">
<list>
<value>com.saravanansivaji.model.Employee</value>
</list>
</property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">${hibernate.dialect}</prop>
<prop key="hibernate.show_sql">${hibernate.show_sql}</prop>
<prop key="hibernate.hbm2ddl.auto">${hibernate.hbm2ddl.auto} </prop>
</props>
</property>
</bean>

<bean class="org.springframework.jdbc.datasource.DriverManagerDataSource" id="dataSource">
<property name="driverClassName" value="${database.driver}"></property>
<property name="url" value="${database.url}"></property>
<property name="username" value="${database.user}"></property>
<property name="password" value="${database.password}"></property>
</bean>

At the service and DAO classes, the getSession() method only makes sense inside a scope of transaction, If you are trying to get sessionFactory.getCurrentSession() without defining your class in transactional scope then you will get above exception because getCurrentSession() can be use only in transactional scope. Please make your class transaction using @Transactional annnotation


@Service("employeeService")
@Transactional(propagation = Propagation.SUPPORTS, readOnly = true)
public class EmployeeServiceImpl implements EmployeeService {
@Autowired
private EmployeeDao employeeDao;

@Override
@Transactional(readOnly = false)
public List listEmployees() {
return employeeDao.listEmployees();
}
}

And from my DAO class EmployeeDao.java

public List listEmployees() {
try {
return (List) sessionFactory.getCurrentSession().createCriteria(Employee.class).list();
}catch(Exception e) {
System.out.println(e);
return null;
}
}

only looks for @Transactional on beans in the same application context it is defined in. This means that, if you put in a WebApplicationContext for a DispatcherServlet, it only checks for @Transactional beans in your controllers, and not your services.

Advertisements