コミットされていないトランザクションを逆順に元に戻す必要があるのはなぜですか?


19

いくつかのトランザクションが勝つ(クラッシュの前にコミットされる)、いくつかのトランザクションが失われる(まだコミットされていない)データベースログがあります。授業で、敗者の行動は元に戻す必要があることを学びました。

これを逆方向に行う理由はありますか?誰でも前方への取り消しが間違った結果をもたらすログの簡単な例を与えることができますか?


この質問は、より具体的な別のウェブサイトで尋ねるべきではありませんか?
nbro

回答:


35

元のトランザクション:

  1. レコード挿入します。r
  2. rのフィールドを更新します。fr

順方向の取り消し:

  1. レコード削除します。r
  2. の更新を元に戻します -ちょっと待ってください、rはもう存在しません!これによりエラーが発生します。rr

システムがどの状態のものをロールバックする必要があるかを把握でき、他の処理を行う前に必要な変更をすべて適用できる場合、物事を逆順に物理的に個別に元に戻す必要がありますか?
-supercat

11
変更を逆の順序で元に戻すと、簡単になります。なぜあなたは自分でそれを難し​​くしようとするのですか?
gnasher729

1
いいえ、システムはすべてを行うわけではありませんが、逆の順序でそれを把握します。

3
多くの現実世界のデータベースシステムでは、テーブルの重要な制約のために、逆の順序で実行することさえできません。
SeanR

11

DylanSpの答えに追加すると、存在しないレコードのフィールドを更新しようとしても失敗しますが、結果は期待される結果になります。レコードrは存在しません。

ただし、レコードの削除が実際に失敗する状況を考慮してください。

  1. 注文を挿入O
  2. オーダーラインLを挿入します。

非現実的ではなく、すべてのOrderLine Orderに関連付けられている必要があると仮定しましょう。

注文の削除から始まるトランザクションのロールバックは、ビジネスルールに違反するため失敗します。

だから後

  1. 注文Oを削除します(FAIL)
  2. Ordeline Lを削除します(成功)

既存の注文(注文ラインなし)になる可能性があります。

もちろん、この場合、カスケード削除を使用できますが、それは手順2が失敗することを意味します(影響なし)。さらに悪いことに、注文にカスケード削除を実装するのは望ましくない動作かもしれません。


さて、これは理にかなっています。あなたの助けのための
THX

「通常の」状況でトランザクションの前または後に制約に違反していないと仮定するのは適切ですか?通常、データベースを使用しているのが1人だけであれば、トランザクションは失敗しませんでした。これが当てはまる場合、元に戻すプロセス中に制約違反を導入しないことが重要なのはなぜですか?元に戻す操作の開始時に制約をオフにし、操作が完了すると有効にすることができるようです。
ノクティススカイタワー16

2
@NoctisSkytower通常のI / O操作中に制約を無効にすると、制約が役に立たなくなります。それらには理由があります。私の例は、通常の状況では制約をどのように満たすことができるかを示していますが、ロールバックでは違反します。ロールバック中に制約をオフにすると、問題が不必要に複雑になり、間違った問題が修正されます。問題は制約ではなく、問題は誤ってロールバックしようとすることによる違反です。
-oerkelens

はい、それは理にかなっていますが、なぜロールバック中に制約をチェックするのですか?ロールバックが問題なく完了することが保証されるように設計されていると仮定すると、ロールバックの完了時に違反しないことがわかっているのに、なぜ時間チェック制約を無駄に無駄にするのですか?ところで、ロールバックが失敗した場合、DBはロールフォワードができないように見えるので、それは保証すべきです。
ノクティススカイタワー16

1
@NoctisSkytower DBが一時的な状態であっても、制約に違反する状態になることは不可能です。ロールバック全体がアトミックである場合、順序がないため、どの順序が発生しても問題ありません。これは、「一度にすべて発生する」単一の命令です。何らかの順序で別々にロールバックされる2つ以上のトランザクションがある場合、その順序は、中央でデータを読み取るすべてのオブザーバーがすべての制約が保持される状況のみを見ることができるような順序であることが必須です。
ペテルス

6

類推してみましょう:あなたは夕食に出かけていると言います。

  1. 靴下を履きます。
  2. 靴を履きます。
  3. 立ち上がる。
  4. ドアまで歩いてください。

その後、電話がかかります。ディナープランはキャンセルされました。

  1. 靴下を脱いでください。
  2. 靴を脱ぐ。
  3. 座って下さい。
  4. ドアから離れます。

そこで何かがうまくいかない。つまずいて怪我をする可能性があります。または、後のアクションが最初に元に戻されるまで、一部のアクションは元に戻せないことがわかります。

最後に行った操作を取り消すと、次の最後のステップが発生したときの場所に戻ります。次に、そのステップを元に戻し、何もなくなるまで戻ります。一方、後のステップに続く状態では、最初のステップを逆にすることはできません。

数学的に言えば、アクションは通勤しない可能性があるため、最初に実行するステップまたは2番目に実行するステップが重要な場合は、ステップを元に戻す順序が重要になります。


3

トランザクションは互いの上に構築され、トランザクションの結果はコミットされる前の状況に大きく依存するため、これは正しいことです。

金融取引を見てみましょう:

(最初に、取引aが私に100米ドルを支払う前に)

  1. a 私に100米ドルの借金があります(現在は負債総額200)
  2. a彼が私に負っているものの10%の割引を受けます。(現在、負債総額180)

2つのトランザクションをキャンセルするとします。

最初のものを最初にキャンセルすると、次のようになります:

  1. より低い負債100(現在80の負債がある)
  2. 10%の割引をキャンセルします(負債は80 / 0.9 = 88になりました)

これは間違っています。100の借金に戻る必要があります。逆の順序で取引をキャンセルするのは正しいでしょう。

  1. 割引をキャンセル-今の負債は200です
  2. 借金100件-借金は100件

2

1列のみのテーブルTがあると仮定します。

「取り消しログ」は、コミットされていないトランザクションを含むデータベースファイルであり、「やり直しログ」は、データファイルにまだ適用されていないコミットされていないトランザクションとコミットされたトランザクションの両方を含むデータベースファイルであると仮定します。

At 8:00 A.M., Transaction 100 inserts rows with values 101, 102 and 103 into table T. At 8:10 A.M., Transaction 100 is committed and the commit for transaction 100 completes. At 8:15 A.M., Transaction 200 updates row 101 to 201, 102 to 202 and 103 to 203. At 8:20 A.M., Transaction 200 has not been committed and remains in the undo log of the database. At 8:25 A.M., Transaction 300 increments each row by 50, changing row 201 to 251, 202 to 252, and 203 to 253. At 8:30 A.M., Transaction 300 has not been committed and remains in the undo log of the database. At 8:35 A.M., The instance providing access to the database crashes.

At 8:40 A.M., The instance is restarted, and the database files are opened as the instance is started:

              The committed values in T are still 101, 102 and 103.

              Since 201, 202, and 203, and 251, 252 and 253
              are not committed, if they are written into the "redo
              log" of the database, there is a need to "roll back"
              the transactions AFTER the "redo log" is applied.

              Since 201, 202, and 203, and 251, 252 and 253
              are not committed, they are in the "undo log"
              of the database.

              The undo log of the database is used BOTH to (1) roll
              back a transaction that is deliberately rolled 
              back in the memory structure of the database instance, 
              and also (2) during the instance recovery at 8:40 A.M.

At 8:41 A.M., The redo log has been applied, and the T table contains values 251, 252 and 253 in the instance memory.

              The undo log has not yet been applied.

At 8:42 A.M., The undo log is applied in the reverse order: Uncommitted transaction 300 is undone, and Uncommitted transaction 200 is undone.

コミットされたトランザクションとコミットされていないトランザクションの両方がREDOログファイルに書き込まれるのはなぜですか? これは、ポイントインタイムリカバリを提供するためです。

これは、「redoログ」ファイルの内容がトランザクション一貫性がないことを意味します。 このため、コミットされたトランザクションをデータファイルに適用するためにREDOログが使用される場合は常に、コミットされていないトランザクションをロールバックするために「取り消しログ」も使用する必要があります。

「取り消しログ」内のトランザクションが逆の順序でロールバックされるのはなぜですか?トランザクション300は、各行の各列の既存の値に50を追加しました。したがって、トランザクション200が最初にロールバックされると、値は251、252、253から201、202、203に変更されます。トランザクション300が最後にロールバックされた場合、値は151、152、153になり、一致しません元のコミット値。

参考文献:

https://asktom.oracle.com/pls/asktom/f?p=100:11:0:::::P11_QUESTION_ID:1670195800346464273


0

それは本質的に真実ではありません。ロールバックは、最終状態が初期状態と同じになるように、元に戻すログにキャッシュされたブロックを再適用するだけです。ログは順方向に書き込まれたため、ロールバックも順方向に適用されました。ログファイルが確定済みとしてマークされるまでロールバックが再試行するため、順序はまったく関係ありませんでした。

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