Hibernate Session持久化方法实战
Hibernate Session中有一系列的持久化方法比如:save, update, saveOrUpdate, persist, merge, replicate等等,经常有人问起它们之间的细微差别,而Hibernate的官方文档并没有进行详细的说明,因此以几个测试用例验证它们的不同之外。文中所使用的持久化类以及配置请参考之前写的hibernate二级缓存
一、save, update, saveOrUpdate
这三个方法使用最为频繁,区别较直观,简单说一下
save:持久化对象,并根据ID生成策略分配ID
update(detachedInstance):根据detachedInstance的ID更新该对象,如果当前session中存在相同ID的persistent instance会抛异常
saveOrUpdate:根据对象ID的unsaved-value来决定是执行save还是update
代码:略
二、update, merge
merge(detachedInstance):merge方法会将detachedInstance的属性复制到相同ID的持久化对象,并返回该持久化对象。注意这里的detachedInstance本身并不会被持久化,继续保持游离状态,这是merge与update的最大区别
测试用例如下:
@Testpublic void test_update_merge(){Session session = sessionFactory.openSession();Author a1 = new Author();a1.setName("septem");session.save(a1);session.close();session = sessionFactory.openSession();a1.setName("septem_new");//Copy the state of a1 onto the persistent object a2Author a2 = (Author) session.merge(a1);//a1 doesn't become associated with the sessionassertFalse(session.contains(a1));assertEquals(a1.getName(), a2.getName());session.close();}@Testpublic void test_persist_outside_transaction(){Session session = sessionFactory.openSession();Author a1 = new Author();a1.setName("septem");//persist outside transactionsession.persist(a1);//ID is NOT assignedassertNull(a1.getId());assertTrue(session.contains(a1));session.close();//hibernate doesn't execute INSERT statementassertNull(a1.getId());}@Testpublic void test_lock_author_throw_exception(){Session session = sessionFactory.openSession();Author a1 = new Author();a1.setName("septem");session.save(a1);session.close();session = sessionFactory.openSession();try {session.lock(a1, LockMode.NONE);fail("lock doesn't throw exception as expected");} catch (HibernateException e) {// org.hibernate.HibernateException: reassociated object has dirty collection reference}assertTrue(session.contains(a1));session.close();}@Testpublic void test_lock_book(){Session session = sessionFactory.openSession();Book book = new Book();book.setTitle("java");session.save(book);session.close();session = sessionFactory.openSession();session.lock(book, LockMode.NONE);// book is associated with the sessionassertTrue(session.contains(book));session.close();}