首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 數據庫知識 >  >> MySQL 資料庫 >> MySQL 綜合教學

MySQL 事務完整指南:ACID 特性、隔離級別與鎖機制

     編輯:MySQL 綜合教學

前言

事務是關聯式資料庫的核心功能,確保資料操作的可靠性。MySQL 透過 InnoDB 儲存引擎完整支援 ACID 特性,但 MyISAM 僅能靠「偽事務」模擬。本文系統整理 MySQL 事務的建立、存活週期、隔離級別、自動提交控制、效能調優與偽事務實作,幫助開發者建立正確的事務觀念。

一、ACID 四大特性

特性說明InnoDB 實作機制
原子性事務內所有操作要么全成功,要么全失敗Undo Log 記錄舊值,回滾時還原
一致性事務前後資料庫保持一致狀態(完整性約束)外鍵、唯一索引、檢查約束等
隔離性並發事務互不干擾MVCC + 鎖機制,四種隔離級別
持久性提交後的資料永久保存,不會因故障遺失Redo Log (WAL) + Doublewrite Buffer

二、啟用事務支援

只有 InnoDB 或 BDB 表類型支援事務。建表或修改表類型:

-- 建立 InnoDB 表
CREATE TABLE t_order (
    id INT PRIMARY KEY AUTO_INCREMENT,
    amount DECIMAL(10,2)
) ENGINE=InnoDB;

-- 修改既有表為 InnoDB(操作前請備份!)
ALTER TABLE t_order ENGINE=InnoDB;

三、事務的建立與存活週期

1. 基本流程

START TRANSACTION;  -- 或 BEGIN;

-- 業務 SQL 操作
SELECT * FROM t_account WHERE id=1 FOR UPDATE;
UPDATE t_account SET balance = balance - 100 WHERE id=1;
UPDATE t_account SET balance = balance + 100 WHERE id=2;

-- 檢查無誤後提交
COMMIT;

-- 若發生錯誤,回滾
ROLLBACK;

2. 關鍵特性

  • 不支援巢狀事務:若在未結束的事務中再發起 START TRANSACTION,前一個事務會隱性提交。
  • 隱性提交指令:DDL (CREATE, ALTER, DROP)、TRUNCATE、LOCK TABLES、SET AUTOCOMMIT=1 等皆會觸發隱性提交。
  • 未提交即中斷連線:預設會自動回滾,不保留任何操作。

四、自動提交控制

-- 關閉自動提交(session 級別)
SET AUTOCOMMIT = 0;

-- 查看目前狀態
SELECT @@autocommit;  -- 0=關閉, 1=開啟

-- 此模式下必須顯式 COMMIT/ROLLBACK
-- 若直接斷開連線,等同 ROLLBACK

生產環境建議在連線池層面預設關閉自動提交,由應用程式精確控制事務邊界。

五、事務隔離級別

MySQL 預設為 REPEATABLE READ。四大級別由低到高:

隔離級別髒讀不可重複讀幻讀鎖/ MVCC 行為
READ UNCOMMITTED可能可能可能無鎖,直接讀最新資料
READ COMMITTED不會可能可能每次 SELECT 產生新 Read View,僅鎖修改行
REPEATABLE READ (預設)不會不會不會 (靠 Next-Key Lock)事務啟動時建立 Read View,範圍鎖防幻讀
SERIALIZABLE不會不會不會所有 SELECT 自動加共享鎖,並發度最低

查看與修改隔離級別

-- 查看目前 session 隔離級別
SELECT @@transaction_isolation;

-- 修改全域隔離級別(需 SUPER 權限,重啟生效或下一個新連線生效)
SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;

-- 修改當前 session 隔離級別(立即生效)
SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED;

六、事務與效能優化

  1. 縮小事務範圍:只包含必要的寫操作,避免在事務中做複雜查詢、網路呼叫、檔案 I/O。
  2. 選擇適當隔離級別:高並發讀多寫少可考慮 READ COMMITTED 減少鎖競爭;嚴格一致性需求用 REPEATABLE READ。
  3. 避免死鎖:固定存取表順序、按主鍵排序更新、適當加索引減少掃描鎖行數。
  4. 合理設定 innodb_lock_wait_timeout:預設 50 秒,高並發可適度降低。

七、MyISAM 偽事務:表鎖定模擬

MyISAM 不支援行鎖與事務,只能用表鎖模擬:

-- 加鎖
LOCK TABLES t_order WRITE, t_account READ;

-- 業務操作
UPDATE t_order SET status=1 WHERE id=100;
UPDATE t_account SET balance=balance-100 WHERE id=1;

-- 解鎖
UNLOCK TABLES;

缺點:粒度粗、並發極低、無法回滾、易死鎖。僅適用於低並發、唯讀為主的舊系統維護。

總結

MySQL 事務建立在 InnoDB 的 MVCC 與 Redo/Undo Log 之上,提供強大的 ACID 保證。掌握隔離級別、鎖行為、自動提交控制,是寫出高併發、高可靠系統的關鍵。實務上應:「短事務、低隔離、對稱存取、監控死鎖」,並善用 SHOW ENGINE INNODB STATUS 觀察鎖等待與死鎖資訊。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved