データ操作演習
概要
- 日程: Day 2 / セッション 2
- 時間: 9:30-10:15
- 形式: 実習
- ゴール: 新規部署の追加、特定社員の給与更新、テスト用レコードの削除を順番に実行し、それぞれ実行前後でSELECTにより差分を確認できる
- 学習形式: ハンズオン実習(AIペアプログラミング)
導入(5分)
前セッションで「WHEREを忘れたら100円さん」という話をしました。今回はいよいよ自分の手でINSERT/UPDATE/DELETEを動かします。でも安心してください。今日はまず**「全部なかったことにできる魔法」**を先に覚えます。それが BEGIN と ROLLBACK です。
これを覚えるとどうなるか。たとえるなら、ゲームでセーブしてからボス戦に挑むようなものです。負けても(壊しても)ロードできる。だから今日は思い切って色々試してください。
本編(10分)
1. 安全装置:BEGIN と ROLLBACK
PostgreSQL では、データを変える操作を「トランザクション」というまとまりで扱えます。
コード例・実例
BEGIN; -- ここからお試しモード開始
UPDATE employees SET salary = 1 WHERE employee_id = 1;
SELECT * FROM employees WHERE employee_id = 1; -- 結果を確認
ROLLBACK; -- 「やっぱりナシ」で元に戻す
BEGIN; を打った直後から、COMMIT; か ROLLBACK; を打つまでの変更は仮のものになります。
COMMIT;→ 「これで確定」、変更が本当に保存されるROLLBACK;→ 「やっぱりやめた」、全部なかったことに
ここがポイント
- 自分の作業以外から見ても、
COMMIT前の変更は見えない - DELETE で消した行も
ROLLBACKで復活する - とりあえず迷ったら
BEGINで始める ことを習慣化する
コラム
新人エンジニアあるある第1位は「BEGIN を打ったまま昼ごはんに行ってロックがかかる」です。トランザクションは開いたまま放置すると、他の人が同じ行を触れなくなる場合があります。試したら必ず COMMIT か ROLLBACK で締める——財布を出したら必ず閉じる、と覚えましょう。
2. 演習で使うシナリオ
今日の演習は、架空の「総務部 新設プロジェクト」をイメージして進めます。
- 新しい部署「総務部」を
departmentsに追加する - 山田太郎さん(employee_id = 1)の給与を昇給させる
- 試しに追加したテスト社員を削除する
各操作の前後で必ず SELECT を打って差分を確認してください。
💬 AIに聞いてみよう
- 「BEGINとROLLBACKの動きを、図書館の本貸出にたとえて説明して」
- 「COMMITした後の変更を戻したい。何かできる方法はある?」
- 「SAVEPOINTって何? ROLLBACKと何が違う?」
実習・演習(30分)
課題
すべての変更は BEGIN; から始め、結果を確認したら ROLLBACK; で元に戻してください。最後にもう一度同じことを COMMIT; で確定する練習もします。
課題1: 新規部署の追加(INSERT)
SELECT * FROM departments;で現在の部署一覧を確認(5件あるはず)BEGIN;でトランザクション開始departmentsに「総務部 / 東京」を1件 INSERT- もう一度
SELECT * FROM departments;で6件になっていることを確認 ROLLBACK;で取り消し、再度SELECTして5件に戻ったことを確認
課題2: 給与の更新(UPDATE)
- まず対象を確認:
SELECT employee_id, first_name, last_name, salary FROM employees WHERE employee_id = 1; BEGIN;でトランザクション開始- 山田太郎さんの給与を 500000 に UPDATE
- 再度 SELECTで500000になっていることを確認
- わざと事故を体験する(任意・要注意):別のクエリで
UPDATE employees SET salary = 100;(WHEREなし!)を実行 SELECT first_name, salary FROM employees;で全員が100円になっているのを確認して震えるROLLBACK;で全員無事に元に戻ることを確認
課題3: テストレコードの削除(DELETE)
BEGIN;でトランザクション開始- テスト社員を追加:
INSERT INTO employees (first_name, last_name, hire_date, salary) VALUES ('テスト', 'テスト', '2099-01-01', 0); SELECT * FROM employees WHERE last_name = 'テスト';で追加されたことを確認、employee_idをメモ- その
employee_idを WHERE 条件にして DELETE - もう一度SELECTして消えたことを確認
ROLLBACK;で取り消し、SELECT * FROM employees WHERE last_name = 'テスト';の結果が0件のままになることを確認(追加自体がなかったことになる)
課題4(チャレンジ): 本当に確定させる
課題1〜3のどれか1つを選び、ROLLBACK の代わりに COMMIT で確定させてみてください。確定した後にもう一度 SELECT して、変更が「本当に残っている」ことを実感しましょう。確定後は、同じ手順で元に戻すクエリ(追加したものを DELETE、変えた値を UPDATE で戻す)も自分で書いてみてください。
成果物
以下を1つのテキストファイルにまとめてください。
- 課題1〜3で実行したSQL文と、それぞれの前後の
SELECT結果(コピペでOK) - 課題2の「全社員100円事件」を体験した感想(1〜2行)
- 課題4で確定→元に戻す、まで完遂したか
ヒント
- 1つのトランザクション内で複数の操作をしてもOK。最後の
ROLLBACKで全部戻る SELECT version();で現在のPostgreSQLバージョンを確認可能- うまくいかないときは、まず「今 BEGIN の中にいるか」をAIに聞いて整理してもらう
まとめ(5分)
今日の体験で、INSERT/UPDATE/DELETEは「確認 → 実行 → 確認」の3ステップで進めるものだと体で覚えてもらえたはずです。そして、BEGIN/ROLLBACK がいかに頼もしい味方かも分かったと思います。
実務では、本番DBでも必ずこの流れで操作します。「セーブしてからボス戦」の感覚を忘れずに。
次のセッションからは、複数のテーブルを「つなぐ」JOINに入ります。テーブル単体では答えられなかった問い(例:社員と部署名を一緒に表示)が、JOINで一気に解けるようになります。
🔄 振り返りチェック
BEGIN;とROLLBACK;を使うと何が嬉しいですか?- UPDATE/DELETE の前後で SELECT を実行する理由を説明できますか?
- 「全社員100円事件」を防ぐにはどうしますか?
補足資料
- 参考リンク: PostgreSQL公式: トランザクション
- 発展課題: customers テーブルに「自分自身を顧客として」INSERT し、UPDATE で住所を変更し、最後に DELETE して元に戻す——ここまでを1トランザクションで実行する
学習ガイド
想定される質問と回答例
| 質問 | ヒント |
|---|---|
| BEGIN を打ったかどうかを確認するには? | psqlのプロンプトが sandbox=# から sandbox=*# に変わっていればトランザクション中。* がサイン |
| 間違えて COMMIT してしまった。戻したい | 同じ行を逆操作するUPDATE/INSERT/DELETEで戻すしかない。だから本番では特に COMMIT 前の確認が大事 |
| ROLLBACK したら自動採番(SERIAL)も戻る? | データは戻るがシーケンス(採番カウンタ)は戻らない。なので一度試したIDは欠番になる。設計の意図通り |
| BEGIN 中に SELECT したら、他の人の変更は見える? | デフォルト(READ COMMITTED)では、他人の COMMIT 済み変更は見える。詳しくは「分離レベル」で学ぶ |
つまずきやすいポイント
| つまずきポイント | ヒント |
|---|---|
| BEGIN を忘れて UPDATE → 後悔 | 「危ない操作の前は反射的に BEGIN;」を体に染み込ませる。とりあえず BEGIN しても害はない |
| トランザクションを開けっ放しで放置 | 他の作業がブロックされる原因に。試したら必ず COMMIT; か ROLLBACK; で締める |
| エラー後に何を打っても "current transaction is aborted" と出る | トランザクション中にエラーになると、PostgreSQLは以降のSQLを全部無視する。ROLLBACK; を打ってリセットすれば解消 |
| SELECT結果と「実行したつもりの操作」を見比べない | INSERT/UPDATE/DELETEを実行したら、必ず直後にSELECTで「想定通りになったか」を見るクセを |