发布时间:2020-04-09 14:21:09来源:阅读:
操作事务是个很普遍的过程,凡时对数据库的修改有相互依赖都应该使用事务解决。操作事务时要注意以下几点:
1、尽量使用Exception捕获MYSQL的异常
所以第一步:要设置PDO的异常模式为PDO::ERRMODE_EXCEPTION,PDO::ATTR_ERRMODE,有以下三个值:
PDO::ERRMODE_SILENT: 默认模式,不主动报错,需要主动以 $pdo->errorInfo()的形式获取错误信息。 PDO::ERRMODE_WARNING: 引发 E_WARNING 错误,主动报错 PDO::ERRMODE_EXCEPTION: 主动抛出 exceptions 异常,需要以try{}cath(){}输出错误信息。我们在连接MYSQL时使用以下:
$pdo=new pdo("mysql:host=localhost;dbname=dbname","user","****", array(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION));
将上面这句代码写在try catch中,捕获异常,注意PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION必须写在new pdo中。不然mysql连接错误的信息是捕获不到的。catch中的类限制为PDOException,如果有命名空间注意在前面加上顶级命名空间,不然也捕获不了异常的。
2、MYSQL的事务开始前先关闭AUTOCOMMIT
$pdo->setAttribute(PDO::ATTR_AUTOCOMMIT, 0);
$rs = $pdo->beginTransaction();
注意beginTransaction是有返回值的,在调用事务beginTransaction时最好判断其返回值,如果本身返回为false,则后面就不用再回滚。
3、操作事务及回滚
切记在所有的return之前或者其它结束事务之前都记得调用rollBack方法,rollBack方法中也是有返回值的,最好判断返回值,并重试2次回滚,以防止一次回滚发生异常,导致事务锁住。
4、执行开启自动提交
$pdo->setAttribute(PDO::ATTR_AUTOCOMMIT, 1);
此步非常关键,不管是执行commit还是执行rollBack都务必执行此步,自动提交的意义是你执行的每一句SQL是否直接执行MYSQL.默认的MYSQL就是自动提交的,即你执行一条SQL语句,它就更改到数据库,如果MYSQL不是自动提交,则你执行的MYSQL语句就全部卡在那里等待执行。
事务出现异常时最常出现的现象就是前端浏览器涉及到被锁表或行的请求都处在等待中,最后可能报错mysql innodb Lock wait timeout exceeded; try restarting transaction问题,此时:
第一:可通过SHOW ENGINE INNODB STATUSG;查询报错信息,这个信息量太大了,不好排查。
第二:使用select * from information_schema.innodb_trx G; 查询运行的任务列表。
mysql> select * from information_schema.innodb_trx G;
*************************** 1. row ***************************
trx_id: 1429E713A
trx_state: RUNNING
trx_started: 2018-04-02 16:25:31
trx_requested_lock_id: NULL
trx_wait_started: NULL
trx_weight: 0
trx_mysql_thread_id: 23698460
trx_query: NULL
trx_operation_state: NULL
trx_tables_in_use: 0
trx_tables_locked: 0
trx_lock_structs: 0
trx_lock_memory_bytes: 376
trx_rows_locked: 0
trx_rows_modified: 0
trx_concurrency_tickets: 0
trx_isolation_level: REPEATABLE READ
trx_unique_checks: 1
trx_foreign_key_checks: 1
trx_last_foreign_key_error: NULL
trx_adaptive_hash_latched: 0
trx_adaptive_hash_timeout: 10000
mysql> select trx_id,trx_started,trx_state,trx_mysql_thread_id,trx_rows_locked from information_schema.innodb_trx;
+-----------+---------------------+-----------+---------------------+-----------------+
| trx_id | trx_started | trx_state | trx_mysql_thread_id | trx_rows_locked |
+-----------+---------------------+-----------+---------------------+-----------------+
| 1429E713A | 2018-04-02 16:25:31 | RUNNING | 23698460 | 0 |
| 1429E7138 | 2018-04-02 16:25:31 | RUNNING | 23698458 | 0 |
| 1429E7136 | 2018-04-02 16:25:31 | RUNNING | 23697458 | 0 |
| 1429E6734 | 2018-04-02 16:14:39 | RUNNING | 23698477 | 1 |
+-----------+---------------------+-----------+---------------------+-----------------+
4 rows in set (0.00 sec)
#可以通过trx_mysql_thread_id值查询processlist查看导致异常的mysql连接
select * from information_schema.processlist where db='dbname' and id =23698477;
第三,可以排查mysql的bin日志:MYSQL日志文件: show variables like general_log_file;
mysql> show variables like 'general_log_file';
+------------------+-------------------------------+
| Variable_name | Value |
+------------------+-------------------------------+
| general_log_file | /opt/data/mysql/localhost.log |
+------------------+-------------------------------+
1 row in set (0.00 sec)
找到日志文件,直接查看binlog文件可能有乱码。
/opt/modules/mysql/bin/mysqlbinlog --base64-output=DECODE-ROWS mysql-bin.000098
但上面的这个命令只能将已有的日志文件解码展示,不区分里面的数据库,如果日志文件很大,就歇菜了。下面的命令可以指定数据库开始时间:
/opt/modules/mysql/bin/mysqlbinlog --start-datetime='2018-04-02 10:25:00' -d baotoutiao mysql-bin.000098
但上面的命令都不够好,下面这个最佳。可以实现模拟tail -f的功能。并且可指定数据库,非常好用。
export D=$(date +"%Y-%m-%d %H:%M:%S" --date="1 minutes ago"); watch "/opt/modules/mysql/bin/mysqlbinlog --start-datetime="$D" -d dbname --base64-output=decode-rows -v mysql-bin.000098|tail -n 50"
上一篇:如何设置无线网卡共享上网
windows server 2016(服务器操作系统)中文版
5.18G
centos(linux操作系统) 6.4 最新版
3.85GB
优麒麟(国产操作系统) 20.04.1 官方版
2703.36MB
ceb文件阅读器(阅览软件)V4.5.3 中文版
42.6M
fireworks(网页作图软件) v8.0.0.77 中文版
88.4M
gghost一键恢复(系统备份还原工具)v10.03.09 中文版
14.5M
h264播放器(视频播放软件)v6.2.0 中文版
11.2M
hwinfo32(系统信息检测工具) v7.05.4490 中文版
10.1M
picture manager(图像处理软件)2010 中文版
19.46 MB
unlocker(密码解锁工具) v3.0.3.4 中文版
32.1M
vc2005(动态链接库)V0.3.2 中文版
6.63MB
HeidiSQL(mysql服务器数据管理工具) v11.0.0.6055 免费版
10.1M
Task List Guru下载
30.34MB
activesync下载
22.72MB
cdr x6下载
251.8M
cs1.6下载
141MB
ftp上传工具下载
22.3M
ghost11下载
15.8M
winkawaks模拟器下载
2M
印象笔记下载
122.6M
2020-03-19
31-046287 联想应用用户手册(YT)V3.1(R)
2019手游市场报告!
如何知道游戏是否兼容Windows 8系统
Mysql 学习之EXPLAIN作用
通过python和websocket构建实时通信系统[扩展saltstack监控]
nginx apache webbench压力测试比较
联想天逸100/天逸200笔记本内置摄像头使用问题
Windows 8.1升级完之后重启出现logilDA.dll报错
如何设置电池充电阈值