反復可能読み取りの不整合


10

http://www.postgresql.org/docs/9.2/static/transaction-iso.html

反復可能読み取りモードは、各トランザクションがデータベースの完全に安定したビューを見ることを厳密に保証します。ただし、このビューは、必ずしも同じレベルの同時トランザクションのいくつかの(一度に1つの)逐次実行と常に整合しているとは限りません。たとえば、このレベルの読み取り専用トランザクションでも、バッチが完了したことを示すように更新された制御レコードが表示されますが、制御レコードの以前のリビジョンを読み取ったため、論理的にバッチの一部である詳細レコードの1つは表示されません。 。この分離レベルで実行されているトランザクションによってビジネスルールを適用しようとすると、競合するトランザクションをブロックする明示的なロックを注意深く使用しないと、正しく機能しない可能性があります。

これは、反復可能読み取りモードでは不可能なファントム読み取りではありませんか?

ドキュメントには、反復可能な読み取りトランザクションのクエリは、トランザクションの開始時のスナップショットが表示されるとありますが、クエリが一貫性のないデータを読み取ることができるのはなぜでしょうか。

回答:


5

これがそのセクションの私の読みです。紛らわしいことは認めます。

2つのテーブルがあるとします。

CREATE TABLE batch (
   id serial not null unique,
   control_code text primary key,
   date_posted date not null default now()
);

CREATE TABLE details (
   batch_id int not null references batch(id),
   description text,
   primary key(batch_id, description)
);

ここで、異なるトランザクションにバッチレコードと詳細レコードを挿入するとします。セッション1はバッチを挿入して詳細の挿入を開始しますが、完了する前にセッション2が開始されます。セッション2は、バッチの見出し情報を確認しますが、詳細のコミットを待たずに、レコードが見つからないことをユーザーに通知します。バッチと詳細が完全に同じトランザクションにある場合、これは決して問題にはなりません。

これは、行が見つからなかったことをユーザーに通知するかどうかを決定する前に、前の挿入が完了してコミットまたはロールバックするのを待つ必要があるシリアライズ可能とは異なります。


3

ある文書 REPEATABLE READトランザクション分離レベルでのトランザクションの特定の組み合わせで発生する可能性があるいくつかの問題を示してPostgreSQLのWikiの中には、どのように彼らは、PostgreSQLバージョン9.1から始まるSERIALIZABLEトランザクション分離レベルで回避されています。

また、REPEATABLE READレベルのREAD-ONLYトランザクションが一貫性のないデータを読み取ることが可能な場合の例含まれています。


@dezso興味があるかもしれません
907th

1

ファントム読み取り(これを繰り返し不可の読み取りと混同しないように注意してください)は、原則として「反復可能読み取り」分離レベルで可能です... ただし、「繰り返し読み取り」を選択した場合のPostgresqlの事実上の動作は標準よりも強力であり(ほとんど「シリアル化可能」な分離)、そのため、実際にはファントムリードはありません。ドキュメント

コミットされていない読み取りレベルを選択すると、実際には読み取りがコミットされ、反復可能な読み取りのPostgreSQL実装ではファントム読み取りができないため、実際の分離レベルは選択したレベルよりも厳しい場合があります。

さて、その警告についてはどうでしょうか。「このビューは、必ずしも同じレベルの同時トランザクションの(一度に1つの)逐次実行と常に一貫しているとは限りません」?(よくわかりません)つまり、「外部から」(トランザクションの開始時に固定)のスナップショットには最終的に他のトランザクションの行を含めることができますが、同じトランザクションの他の行を含めることができないことを意味します。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.