transactionの途中でトランザクションが切れてしまった時にそのトランザクションを殺す方法

起こったこと

transactionモードで作業途中、セッションが切れた。 そのとき特定tableにinsertをしたがcommitしていない状態だった。

後ほど再度そのtableをselectしたが、当然commitしていないのでデータがなかった。 しかしinsertしようとすると、

ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

というエラーが表示され失敗した。

 

原因

transactionがロックを取得したまま放置状態になっていたために発生した。

 

対処

基本方針は show processlist;show innodb status; の結果を見比べてそれっぽいthread見つけて kill [thread id] する。

show processlist; してみると、今回はこのへんのデータが怪しかった。

| Id      | User        | Host               | db            | Command     | Time  | State  | Info
| 3503944 | game        | 10.33.84.237:36220 | game_item     | Sleep       |  3912 |        | NULL

show innodb status; してみると、以下が今回のやつに対応しているっぽいことがわかる。(show processlistとshow innodb status の結果を何度か見比べているとわかるはず)

---TRANSACTION 70B8606F4, ACTIVE 4251 sec, process no 2451, OS thread id 1501722944
2 lock struct(s), heap size 376, 1 row lock(s), undo log entries 2
MySQL thread id 3503944, query id 53043667 10.33.84.237 game
Trx read view will not see trx with id >= 70B8621E3, sees < 70B8617B7

よって、この thread id 3503944

kill 3503944

で完了。

 

めも

timeoutの時間のチェック

mysql> show global variables like 'innodb_lock_wait_timeout';
+--------------------------+-------+
| Variable_name            | Value |
+--------------------------+-------+
| innodb_lock_wait_timeout | 5     |
+--------------------------+-------+
1 row in set (0.01 sec)

 

Ref

http://d.hatena.ne.jp/hhelibex/20110329/1301421815