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 の 2 つのオブジェクトを作成し、Thread 0 が車両を取得して長時間スリープするシナリオを作成します。一方、スレッド 1 は Vehicle の取得と更新を試みます。スレッド 0 がコミットする前でも、正常にコミットされます。

REPEATABLE_READ 分離レベルにより、T1 はコミットを待機するべきではありません。そうでない場合は、REPEATABLE_READ 分離レベルではなく、READ_COMMITED 分離レベルです。

4

1 に答える 1

2

あなたの期待は間違っています。繰り返し読み取り可能とは、別のトランザクションが同じ行を読み取るときにトランザクションがブロックされる必要があるという意味ではありません。つまり、同じトランザクションで同じ行を2回読み取ると、最初の読み取りと2回目の読み取りの間に別のトランザクションがこの行に変更をコミットした場合でも、同じデータが返されるはずです。

2回目の読み取りでは、データベースにまったくアクセスせずに、第1レベルのキャッシュからデータが返されるため、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 に答える