什么是事务?

要么都成功 要么都失败
————————————————————————
SQL执行 A 给 B 转账 A 1000—>B 200 A 800

SQL执行 B 收到 A 的钱 B 200
———————————————————————-
将一组SQL放在一个批次去执行

INNODB表支持事务
MYISAM 新版本也支持事务

事务原则 ACID原则

  • 原子性:针对同一事物 要么都完成 要么都不完成
  • 一致性:事务前后的数据完整性要保持一致
  • 持久性:事务一旦提交不可逆,被持久化到数据库中
  • 隔离性:多个用户并发访问数据库时,数据库为每一个用户开启的事务,不能被其他事务的操作数据所干扰,事物之间要相互隔离

隔离所导致的问题

  • 脏读:一个事务读取了另一个事务未提交的数据
  • 不可重复读:在一个事务内读取表中的某一行数据,多次读取结果不同
  • 幻读:在一个事务内读取了别的事务插入的数据,导致前后读取不一致

执行事务

  1. --mysql 是默认开启事务自动提交的
  2. SET autocommit=0 /*关闭*/
  3. SET autocommit=1 /*开启(默认)*/
  4. --手动处理事务
  5. SET autocommit=0 /*关闭自动提交*/
  6. --事务开启、
  7. START TRANSACTION /*标志一个事务的开始 从这之后的sql 都在一个事务内*/
  8. --提交,持久化(成功)
  9. COMMIT
  10. --回滚,回到原来的样子(失败)
  11. ROLLBACK
  12. --事务结束
  13. SET autocommit /*开启自动提交*/
  14. --了解
  15. SAVEPOINT 保存点名 --设置一个事务的保存点
  16. ROLLBACK TO SAVEPOINT /*回滚到保存点*/
  17. RELEASE SAVEPOINT 撤销保存点

模拟场景

  1. --创建数据库并设置编码格式
  2. CREATE DATABASE shop CHARSET=utf8 COLLATE utf8_general_ci;
  3. USE shop
  4. CREATE TABLE `account`(
  5. `id` INT(4) NOT NULL AUTO_INCREMENT,
  6. `name` VARCHAR(20) NOT NULL,
  7. `money` DECIMAL(9,2) NOT NULL,
  8. PRIMARY KEY(`id`)
  9. )ENGINE=INNODB DEFAULT CHARSET=utf8;
  10. INSERT INTO `account`(`name`,`money`)
  11. VALUES('A','10000'),
  12. ('B','1000');
  13. --模拟转账
  14. SET autocommit = 0 /*关闭自动提交*/
  15. START TRANSACTION /*开启一个事务(一组事务)*/
  16. UPDATE `account` SET `money`=`money`-500 WHERE `name`='A'; /*A减500*/
  17. UPDATE `account` SET `money`=`money`+500 WHERE `name`='B'; /*B加500*/
  18. COMMIT /*提交事务(成功)*/
  19. ROLLBACK /*回滚(失败)*/
  20. /*恢复默认值*/
  21. SET autocommit=1