0

我正在尝试开发一个演示来巩固我对 REPEATABLE_READ 隔离级别的理解。我尝试过使用 hibernate 和 jdbc 的演示。JDBC 按预期工作,但 hibernate 不能。

我的期望是,如果我在一个会话中读取数据库行,并且我尝试从另一个会话写入同一行,它应该阻塞直到第一个会话完成。

休眠:- 当我在线程 0 中“获取”一个对象(行)并休眠时,在线程 1 中我们尝试更新同一个对象(行),线程 1 应该等到线程 0 提交。

class HibernateExample7_IsolationRR_Read_Write_Thread implements Runnable {

    private static final Logger logger = LoggerFactory.getLogger(HibernateExample7_IsolationRR_Read_Write_Thread.class);

    SessionFactory sessionFactory;
    int sleep;
    int newnumberplate;
    public HibernateExample7_IsolationRR_Read_Write_Thread(SessionFactory sessionFactory, int sleep, int newnumberplate) {
        this.sessionFactory = sessionFactory;
        this.sleep = sleep;
        this.newnumberplate = newnumberplate;
    }

    public void run() {
        Session session = sessionFactory.openSession();
        Transaction tx = session.beginTransaction();
        logger.info("TRYING TO GET VEHICLE 1");
        Vehicle vid1 = (Vehicle) session.get(Vehicle.class, Integer.valueOf(1));
        logger.info("GOT VEHICLE 1");
        vid1.setNumberplate(this.newnumberplate);
        logger.info("SET NUMBERPLATE FOR 1");
        try {
            Thread.sleep(sleep);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        tx.commit();
        session.close();
        logger.info("COMMITED");
    }
}

hibernate.connection.url 是jdbc:derby:isolation;create=true和 hibernate.connection.isolation 是2。我制作了两个 HibernateExample7_IsolationRR_Thread 对象,并创建了一个场景,其中线程 0 获取车辆并长时间休眠。同时线程 1 尝试获取和更新 Vehicle。它甚至在线程 0 提交之前成功提交。

由于 REPEATABLE_READ 隔离级别,T1 不应该等待提交。如果不是,那么它是 READ_COMMITED 隔离级别而不是 REPEATABLE_READ 隔离级别。

4

1 回答 1

2

你的期望是错误的。可重复读取并不意味着一个事务应该阻塞,而另一个事务读取同一行。这意味着在同一个事务中读取同一行两次应该返回相同的数据,即使另一个事务在第一次和第二次读取之间对该行提交了更改。

使用 Hibernate 可以免费获得(或多或少)这些,因为第二次读取将从一级缓存返回数据,而根本不需要访问数据库。

请参阅http://en.wikipedia.org/wiki/Isolation_%28database_systems%29#Non-repeatable_reads

此外,您正在使用不支持此隔离级别的数据库进行测试:

http://www.hsqldb.org/doc/2.0/guide/dbproperties-chapt.html#N15385

于 2013-02-23T08:42:20.480 回答