首页 > 代码库 > Hibernate持久化对象的状态

Hibernate持久化对象的状态

1. 站在持久化的角度 , Hibernate 把对象分为 4 种状态 : 持久化状态, 临时状态, 游离状态(脱管状态) , 删除状态.Session 的特定方法能使对象从一个状态转换到另一个状态 .

2. 临时状态(Transient :
    1. 在使用代理主键的情况下 , OID 通常为 null
    2. 不处于 Session 的缓存中
    3. 在数据库中没有对应的记录

3. 持久化状态(也叫”托管” ) Persist

    1. OID 不为 null
    2. 位于 Session 缓存中
    3. 若在数据库中已经有和其对应的记录 , 持久化对象和数据库中的相关记录对应
    4. Session  flush 缓存时 , 会根据持久化对象的属性变化 , 来同步更新数据库
    5. 在同一个 Session 实例的缓存中 , 数据库表中的每条记录只对应唯一的持久化对象( Session 缓存对象的 OID 不能重复)

    @Test
    public void testOID(){
        News news2 = (News ) session.get (News.class , 1);
        System.out.println (news2 );
    
        News news = new News ();
        news.setAuthor ("Oracle2" );
        news.setContent ("Oracle DB" );
        news.setDate (new Date ());
        news.setTitle ("DB" );
        news.setId (1 );
    
         //抛出异常: org.hibernate.NonUniqueObjectException
        session.update (news );
    }

4. 游离状态(也叫”脱管” ) Detached ):
    1. OID 不为 null
    2. 不再处于 Session 缓存中
    3. 一般情况需下 , 游离对象是由持久化对象转变过来的 , 因此在数据库中可能还存在与它对应的记录

5. 删除状态(Removed)
    1. 在数据库中没有和其 OID 对应的记录
    2. 不再处于 Session 缓存中
    3. 一般情况下 , 应用程序不该再使用被删除的对象

6. 状态的转换图

7. get & load 的区别:
    共同点:
    getload 从数据表中加载一个对象 , 加载后即为持久化状态的对象
    不同点:
    get: 立即查询数据表. 若没有对应的记录 , 返回 null 
    load: 延迟查询数据表 . 直到第一次使用该对象时 , 再进行查询,
    先返回的是一个代理对象 . 若没有对应的记录 ,并且使用了该对象 , 则会抛出org.hibernate.ObjectNotFoundException 异常


8. update 方法:

    @Test
    public void testUpdate(){
        News news = (News ) session.get (News.class , 1);
        System.out.println (news );
    
        transaction.commit ();
        session.clear ();
    
        session = sessionFactory.openSession ();
        transaction = session.beginTransaction ();
    
         //此时对象为游离状态
        news.setAuthor ("Oracle" );
    
         //update 可以使游离对象变为持久化对象 .
         //通常需要发送一条 UPDATE 语句
         //若对象即为持久化对象 , 则不需要调用 update() 方法
        session.update (news );
    }

注意:
1 . 使用场景: B\S 项目中从页面传过来一个对象,需要对其进行更新时,即调用 update()方法
2 . 若数据表中没有对象对应的记录,还要执行 update() 方法,则会抛出异常: org.hibernate.StaleObjectStateException

9. saveOrUpdate (): 保存或更新

11. delete ():删除一个对象对应的记录。
    1. 若只想删除指定的对象,设置 ID 即可。
    2. 若数据表中没有对应的记录,则抛出异常: java.lang.IllegalArgumentException

12. Hibernate 调用原生的 JDBC API

    session.doWork(new Work() {
        @Override
        public void execute(Connection connection ) throws SQLException {
             //使用 JDBC 原生的 API
         }
    });


Hibernate持久化对象的状态