世界を動かす技術を、日本語で。

データベーストランザクションとは何ですか?

2026年2月22日原文(planetscale.com)

概要

  • SQLデータベースの根幹となる トランザクション の基本動作と重要性を解説
  • MySQLPostgres におけるトランザクション管理の違いと仕組み
  • 一貫性のある読み取り(Consistent Reads)や アイソレーションレベル の比較
  • 同時書き込み時の 競合処理 やロック機構の概要
  • データベース設計・運用で知っておくべき代表的なポイントを網羅

トランザクションの基本

  • トランザクション とは、複数のデータベース操作を 原子的な単位 でまとめて実行する処理単位
  • 典型的なトランザクションは、 読み取り・作成・更新・削除 など複数のクエリ実行を含む
  • MySQLやPostgresでは、begin;で開始しcommit;で確定、途中でrollback;による 取り消し も可能
  • トランザクション中の変更は コミット前は他セッションから不可視、コミットで一斉反映
  • 障害発生時 や意図的な中断時は、データベースが ロールバック復旧機構 (例:PostgresのWAL)で一貫性維持

トランザクションの同時実行とデータの可視性

  • 複数セッションが同じデータを扱う場合、 コミット前の変更は他セッションから見えない
  • ロールバック時は、 全ての変更がなかったこと になるため、他セッションへ影響を与えない
  • Consistent Reads (一貫性のある読み取り)で、各トランザクションは 独立したデータのスナップショット を参照

Postgresのマルチバージョン制御(MVCC)

  • Postgresは 行の複数バージョン を管理し、各バージョンにxmin(作成トランザクションID)とxmax(削除トランザクションID)を付与
  • 新しいトランザクションが行を更新すると、 新バージョンが生成 され、古いバージョンも一定期間保持
  • コミット前の変更は他トランザクションから不可視、コミット後にのみ新バージョンが参照可能
  • VACUUM FULL コマンドで、不要な古いバージョンを削除しテーブルを圧縮

MySQLのUndo Log方式

  • MySQLは 行データを即時上書き しつつ、 Undo Log で直近の変更履歴を保持
  • 各行にxid(最新更新トランザクションID)やptr(Undo Log参照)などのメタデータを付与
  • 他トランザクションからはUndo Logを参照して 必要な過去バージョンを動的復元
  • Postgresのような VACUUM操作は不要 だが、Undo Logの管理が重要

アイソレーションレベル

  • データベースは 4段階のアイソレーションレベル をサポート
    • Serializable :最も厳格。全トランザクションが直列実行されたかのように振る舞う
    • Repeatable Read :同一トランザクション内で同じSELECTは常に同じ結果
    • Read Committed :コミット済みの変更のみ参照可能。 非再現読取ファントムリード が発生
    • Read Uncommitted :未コミットの変更も参照可能。 ダーティリード が発生しやすい
  • アイソレーションレベルが高いほど 一貫性は高いがパフォーマンス低下 の可能性

ファントムリード・非再現読取・ダーティリード

  • ファントムリード :同一SELECTで結果が変化する現象。Repeatable Read以下で発生
  • 非再現読取 :同じ行を複数回SELECTし、他のコミット済み変更で値が変わる現象。Read Committed以下で発生
  • ダーティリード :未コミットの他トランザクション変更を読めてしまう現象。Read Uncommittedで発生

同時書き込み時の競合制御

  • MySQL行レベルロック で競合処理

    • 共有ロック(Sロック) :複数トランザクションが同時に取得可能(主に読取時)
    • 排他ロック(Xロック) :1つのトランザクションのみ取得可能(更新時)
  • Postgres や他DBも、アイソレーションレベルや内部実装により異なるロック戦略を採用

まとめ

  • トランザクション管理は データ整合性とパフォーマンスの両立 に不可欠
  • MySQLPostgres は異なる実装で同様の目的を達成
  • 適切な アイソレーションレベル 選択と ロック制御 理解が、堅牢なアプリケーション設計の鍵

Hackerたちの意見

planetscaleのブログを読むのは本当に楽しい!このビジュアライゼーションを作るのにどんなツールを使ってるのか気になるな。

ここで作者です。ありがとう!このビジュアルはjsとgsapで作ってるよ。(https://gsap.com)

この文章はちょっと物足りないな。他の記事と同じように、SQL標準で説明されている現象を通じて隔離レベルを紹介してるけど、もっと直感的なアプローチがあると思う。厳密な直列性の概念からこの問題空間を定義する方が、スムーズだと思うんだ。これはスレッドセーフの概念の一般化でもあるし、ソフトウェアエンジニアなら誰でも直感的に理解できるはず。直列性が欠けると、実行依存の挙動が起きて、診断が難しいバグが発生することが多い。だから、すべてのシステムは直列性を目指すべきで、データベースはそれを実現するためのツールになり得る。さまざまな非直列化レベルのデータベーストランザクションの隔離は、直列性の保証を緩和したもので、データベースがその保証を強制しなくなるから、ユーザーが他の手段でそれを確保する必要がある。隔離現象は、非直列性のさまざまなコーナーケースを視覚化するのに役立つツールだけど、必ずしもそれに結びついているわけではない。すべてのSQL現象を観察しながら直列性を達成することも可能だよ。例えば、慎重に書かれたコントローラーを持つKubernetesクラスターは直列性を持つことができる。

じゃあ、もっと良い説明を勧めてくれる?

https://aphyr.com/posts/327-jepsen-mariadb-galera-cluster もっと記号や引用があれば、もっと良くなるよ。

ここで作者です。いいフィードバックありがとう!トランザクション、隔離レベル、MVCCの組み合わせは、一度に全部カバーするのが本当に大変なんだ。特に、複数のDB間での比較を試みたから、技術的な深さと経験の少ない人へのアクセスのしやすさのバランスを常に考えてる。長々とした読み物にならないようにしないとね。

ほとんどのRDBMSは、必要なら直列化可能な隔離を提供してるよ。でも、実際にはあまり必要ないことが多い。直列化可能な隔離を不必要に使うと、トランザクション間の調整が増えて、同時実行性やスループットが減少するのがデメリットだね。

(厳密な) シリアライズ可能性の概念 [("S")] は、実際にはスレッドセーフの概念の一般化なんだよね。「厳密な」(L + S) が括弧に入ってる理由がよくわからないけど、リニアライズ可能性("L")がSMPシステムでの安全性に最も似てるってこと?

最近のデータベースツールは、トランザクションやACID特性よりも、更新の即時共有を優先してることが多いね。例えば、Airtableでは、フィールドを更新すると、同じテーブルを開いている同僚の画面にもすぐにその更新が表示される。でも、そのデメリットはAirtableがトランザクションを行わないこと。トランザクションを行わないことのデメリットは、データの不整合が起こる可能性があることだね。詳しくはこちらで: https://visualdb.com/blog/concurrencycontrol/

競合に対して一発かましながら、さりげなく製品の宣伝してるね。

これ、実はバックエンドエンジニアの面接で好きな質問の一つだったんだよね。みんなトランザクションは使ったことあるけど、経験によって理解度が違うんだよね。もちろん、隔離レベルを暗記してるとは期待しないけど、いくつかの種類があってそれぞれの動きが違うって知ってるだけでも、結構いい感じだし、物事の裏側に興味があるってことが伝わるよ。

名目上同じ隔離レベルでも、異なるデータベースシステムでは動作が異なることがあるから、一般的にはケースバイケースで詳細を調査する必要があるよ。

Hacker Newsで議論の続きを見る