The problem is following code snippet doesn't delete the record in DB.
import org.hibernate.Session;
import org.hibernate.SessionFactory;
...
...
void deleteForm() {
Session session = sessionFactory.openSession();
FormDO formDO = new FormDO();
formDO.setId(formId);
session.delete(formDO); // No delete SQL query is getting fired.
However, if I call session.flush() after delete, it works perfectly. Please note, I am NOT using any Transaction.
In JavaDoc of Session class the description of delete method is:
Remove a persistent instance from the datastore. The argument may be an instance associated with the receiving Session or a transient instance with an identifier associated with existing persistent state.
And I have seen many code snippets online which shows that it is not necessary to call flush() after delete(). Similar question was raised in other forum here but it remained unanswered.
Also, session.save works fine without session.flush.
I am using Hibernate 4.2.16 + Spring 4.0.9 + JPA 1.0 annotations. Following are the source files for further reference,
FormDO.java
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity
@Table(name="form")
public class FormDO {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
@Column(name="id")
Integer id;
@Column(name="name")
String name;
...
...
Spring Configuration File
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
destroy-method="close">
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url" value="jdbc:mysql://localhost:3306/tempdb" />
<property name="username" value="root" />
<property name="password" value="****" />
</bean>
<!-- Hibernate 4 SessionFactory Bean definition -->
<bean id="hibernate4AnnotatedSessionFactory"
class="org.springframework.orm.hibernate4.LocalSessionFactoryBean" >
<property name="dataSource" ref="dataSource" />
<property name="annotatedClasses">
<list>
<value>com.test.FormDO</value>
</list>
</property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop>
<prop key="hibernate.current_session_context_class">thread</prop>
<prop key="hibernate.show_sql">true</prop>
</props>
</property>
</bean>
FormDAO.java
@Named
public class FormDAO {
@Inject
private SessionFactory sessionFactory;
public boolean deleteForm(Integer formId) {
Session session = sessionFactory.openSession();
FormDO formDO = new FormDO();
formDO.setId(formId);
session.delete(formDO);
session.flush(); // If this line is commented, record DOES NOT get deleted
return true;
}
public boolean saveForm(FormDO formDO) {
Session session = sessionFactory.openSession();
session.save(formDO); // Save doesn't require session.flush
return true;
}
...
...
UPDATE:
My dilemma was largely due to the inconsistency.. session.save was inserting the record immediately but session.delete doesn't reflect unless flush() was called explicitly. But when I refer the Flushing the Session link posted by Afsun, my doubts were cleared by reading following line,
An exception is that objects using native ID generation are inserted when they are saved.
I really appreciate the answers posted by everyone as almost all of them were pointing to the right direction but Afsun clears my doubt totally. Thanks!