今回は、Silverの「開発/SQL - トランザクション概念」からの出題です。
ダーティーリードが発生しなければ、同一トランザクション内で同じSELECT文を2回続けて実行した時の結果は必ず同じになる。
PostgreSQLでダーティーリードを許容するには、
SET TRANSACTION ISOLATION LEVEL DIRTY READ;
を実行すれば良い。
PostgreSQLのデフォルトの設定ではダーティーリードは発生しない。
PostgreSQLでは、ダーティーリードを許容する設定にしても、ダーティーリードは発生しない。
※この例題は実際のOSS-DB技術者認定試験とは異なります。
例題公開日:2014年2月24日
例えば、銀行口座間で資金の移動をするとき、一方の口座の残高を減らす処理と、他方の口座の残高を増やす処理の2つが発生します。コンピュータのプログラムはこれらを順次実行するので2つの処理の間にはどうしても時間差がありますが、一方の処理だけがされている状態のデータが他のユーザに見えることは望ましくありません。トランザクションの機能を使えば、このような一連の処理がすべて完了するまで、更新中の(コミット(COMMIT)されていない)データが他のユーザには見えない(更新前のデータが見える)ようにすることができます。
ただし、データベースの実装によっては、トランザクション機能を使っている場合でも、更新中のデータが見える場合があり、これをダーティーリードと呼びます。
標準SQLでは、Read uncommitted, Read committed, Repeatable read, Serializableの4つのトランザクション分離レベルが定義されており、Read uncommittedはダーティーリードを許容します。
PostgreSQLでは、トランザクションの先頭、つまりBEGINあるいはSTART TRANSACTIONの直後に、
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;
を実行することで、ダーティーリードを許容する設定にすることができます。ただし、PostgreSQLの実装では、この設定をしても、Read committedのモードで動作するため、ダーティーリードは発生しません。
コミットされていないデータを読むことはありませんが、トランザクションの実行途中で、他のトランザクションがデータ更新をコミットした場合は、その影響を受けることがあります。同じSELECT文を2回続けて実行した場合でも、その間に対象のデータが更新されれば、SELECTの結果が変わります。トランザクション分離レベルをSerializableに設定すればこのようなことは起きませんが、デフォルトではRead committedになっています。
間違っているものを選ぶ問題なので、正解はBとCです。
今回の解説について、理解できないポイントがあればどんどん質問をお寄せ下さい。
採用になった方にはLPI-Japanオリジナルの記念品を贈呈します。
※試験問題に関わるお問い合わせにつきましては、LPI-Japan事務局ではお応えできませんのでご了解ください。
© EDUCO All Rights Reserved.