mysql> show variables like "%timeout%";
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 28800 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 3600 |
| wait_timeout | 28800 |
+-----------------------------+----------+
12 rows in set (0.01 sec)
interactive_timeout和wait_timeout参数区别和设置策略
请问mysql的interactive_timeout和wait_timeout这两个参数,如何根据业务的特点来确定?
interactive_timeout是MySQL在等待一个活动连接关闭连接前等待的秒数。
wait_timeout是MySQL在等待一个非活动连接关闭连接前等待的秒数。
活动的连接和非活动的连接的定义如下:活动的连接是指使用mysql_real_connect连接时指定了CLIENT_INTERACTIVE的连接。
MySQL 5.1.41之前wait_timeout只适用于TCP/IP连接,不适用于Unix sock,name pipe,share memory的连接。
实际上,一个MySQL thread连接以后,首先会判断它是一个活动连接还是非活动连接(见上面的定义)。活动连接的话会设置为global interactive_timeout,非活动连接会设置为global wait_timeout。超时就会退出。
根据业务来的话,如果你用的是连接池,并且没有F5(F5可能会设置一个超时,把连接时间过长的session kill掉),那么你的两个timeout时间尽量设置长一些,避免应用连接池不断的重新连接数据库。如果你是短连接,那么你就需要把数据库的连接设置得短一些,否则数据库的最大连接数是有限的,你的很多连接一直不释放掉的话,数据库的资源就被拜拜浪费了。
MySQL的timeout那点事
11月 24th, 2011 | Posted by P.Linux | Filed under 数据库 发表评论 | Trackback
本文内容遵从CC版权协议, 可以随意转载, 但必须以超链接形式标明文章原始出处和作者信息及版权声明
网址: http://www.penglixun.com/tech/database/mysql_timeout.html
因为最近遇到一些超时的问题,正好就把所有的timeout参数都理一遍,首先数据库里查一下看有哪些超时:
root@localhost : test 12:55:50> show global variables like "%timeout%";
+----------------------------+--------+
| Variable_name | Value |
+----------------------------+--------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_lock_wait_timeout | 120 |
| innodb_rollback_on_timeout | ON |
| interactive_timeout | 172800 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| slave_net_timeout | 3600 |
| table_lock_wait_timeout | 50 | # 这个参数已经没用了
| wait_timeout | 172800 |
+----------------------------+--------+
我们一个个来看
目录 (Contents) [隐藏 (Hide)]
1 connect_timeout
2 delayed_insert_timeout
3 innodb_lock_wait_timeout
4 innodb_rollback_on_timeout
5 interactive_timeout/wait_timeout
6 net_read_timeout / net_write_timeout
7 slave_net_timeout
connect_timeout
手册描述:
The number of seconds that the mysqld server waits for a connect packet before responding with Bad handshake. The default value is 10 seconds as of MySQL 5.1.23 and 5 seconds before that.
Increasing the connect_timeout value might help if clients frequently encounter errors of the form Lost connection to MySQL server at ‘XXX’, system error: errno.
解释:在获取链接时,等待握手的超时时间,只在登录时有效,登录成功这个参数就不管事了。主要是为了防止网络不佳时应用重连导致连接数涨太快,一般默认即可。
delayed_insert_timeout
手册描述:
How many seconds an INSERT DELAYED handler thread should wait for INSERT statements before terminating.
解释:这是为MyISAM INSERT DELAY设计的超时参数,在INSERT DELAY中止前等待INSERT语句的时间。
innodb_lock_wait_timeout
手册描述:
The timeout in seconds an InnoDB transaction may wait for a row lock before giving up. The default value is 50 seconds. A transaction that tries to access a row that is locked by another InnoDB transaction will hang for at most this many seconds before issuing the following error:
ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction
When a lock wait timeout occurs, the current statement is not executed. The current transaction is not rolled back. (To have the entire transaction roll back, start the server with the –innodb_rollback_on_timeout option, available as of MySQL 5.1.15. See also Section 13.6.12, “InnoDB Error Handling”.)
innodb_lock_wait_timeout applies to InnoDB row locks only. A MySQL table lock does not happen inside InnoDB and this timeout does not apply to waits for table locks.
InnoDB does detect transaction deadlocks in its own lock table immediately and rolls back one transaction. The lock wait timeout value does not apply to such a wait.
For the built-in InnoDB, this variable can be set only at server startup. For InnoDB Plugin, it can be set at startup or changed at runtime, and has both global and session values.
解释:描述很长,简而言之,就是事务遇到锁等待时的Query超时时间。跟死锁不一样,InnoDB一旦检测到死锁立刻就会回滚代价小的那个事务,锁等待是没有死锁的情况下一个事务持有另一个事务需要的锁资源,被回滚的肯定是请求锁的那个Query。
innodb_rollback_on_timeout OFF
手册描述:
In MySQL 5.1, InnoDB rolls back only the last statement on a transaction timeout by default. If –innodb_rollback_on_timeout is specified, a transaction timeout causes InnoDB to abort and roll back the entire transaction (the same behavior as in MySQL 4.1). This variable was added in MySQL 5.1.15.
解释:这个参数关闭或不存在的话遇到超时只回滚事务最后一个Query,打开的话事务遇到超时就回滚整个事务。
interactive_timeout/wait_timeout
手册描述:
The number of seconds the server waits for activity on an interactive connection before closing it. An interactive client is defined as a client that uses the CLIENT_INTERACTIVE option to mysql_real_connect(). See also
解释:一个持续SLEEP状态的线程多久被关闭。线程每次被使用都会被唤醒为acrivity状态,执行完Query后成为interactive状态,重新开始计时。wait_timeout不同在于只作用于TCP/IP和Socket链接的线程,意义是一样的。
net_read_timeout / net_write_timeout
手册描述:
The number of seconds to wait for more data from a connection before aborting the read. Before MySQL 5.1.41, this timeout applies only to TCP/IP connections, not to connections made through Unix socket files, named pipes, or shared memory. When the server is reading from the client, net_read_timeout is the timeout value controlling when to abort. When the server is writing to the client, net_write_timeout is the timeout value controlling when to abort. See also slave_net_timeout.
On Linux, the NO_ALARM build flag affects timeout behavior as indicated in the description of the net_retry_count system variable.
解释:这个参数只对TCP/IP链接有效,分别是数据库等待接收客户端发送网络包和发送网络包给客户端的超时时间,这是在Activity状态下的线程才有效的参数
slave_net_timeout
手册描述:
The number of seconds to wait for more data from the master before the slave considers the connection broken, aborts the read, and tries to reconnect. The first retry occurs immediately after the timeout. The interval between retries is controlled by the MASTER_CONNECT_RETRY option for the CHANGE MASTER TO statement or –master-connect-retry option, and the number of reconnection attempts is limited by the –master-retry-count option. The default is 3600 seconds (one hour).
解释:这是Slave判断主机是否挂掉的超时设置,在设定时间内依然没有获取到Master的回应就人为Master挂掉了
MySQL中的配置参数interactive_timeout和wait_timeout(可能导致过多sleep进程的两个参数)
1)interactive_timeout:
参数含义:服务器关闭交互式连接前等待活动的秒数。交互式客户端定义为在mysql_real_connect()中使用CLIENT_INTERACTIVE选项的客户端。
参数默认值:28800秒(8小时)
(2)wait_timeout:
参数含义:服务器关闭非交互连接之前等待活动的秒数。
在线程启动时,根据全局wait_timeout值或全局interactive_timeout值初始化会话wait_timeout值,取决于客户端类型(由mysql_real_connect()的连接选项CLIENT_INTERACTIVE定义)。
参数默认值:28800秒(8小时)
MySQL服务器所支持的最大连接数是有上限的,因为每个连接的建立都会消耗内存,因此我们希望客户端在连接到MySQL Server处理完相应的操作后,应该断开连接并释放占用的内存。如果你的MySQL Server有大量的闲置连接,他们不仅会白白消耗内存,而且如果连接一直在累加而不断开,最终肯定会达到MySQL Server的连接上限数,这会报'too many connections'的错误。对于wait_timeout的值设定,应该根据系统的运行情况来判断。在系统运行一段时间后,可以通过show processlist命令查看当前系统的连接状态,如果发现有大量的sleep状态的连接进程,则说明该参数设置的过大,可以进行适当的调整小些。
问题:
如果在配置文件my.cnf中只设置参数wait_timeout=100,则重启服务器后进入,执行:
Mysql> show variables like '%timeout%';
会发现参数设置并未生效,仍然为28800(即默认的8个小时)。
查询资料后,要同时设置interactive_timeout和wait_timeout才会生效。
【mysqld】
wait_timeout=100
interactive_timeout=100
重启MySQL Server进入后,查看设置已经生效。
问题1:这里为什么要同时设置interactive_timeout,wait_timeout的设置才会生效?
问题2:interactive的值如果设置的和wait_timeout不同,为什么Interactive_timeout会覆盖wait_timeout?
问题3:在进行MySQL优化时,因为interactive_timeout决定的是交互连接的时间长短,而wait_timeout决定的是非交互连接的时间长短。如果在进行连接配置时mysql_real_connect()最后一个参数client_flag不设置为CLIENT_INTERACTIVE,是不是interactive_timeout的值不会覆盖wait_timeout?
问题4:为了减少长连接的数量,在设置优化时是不是可以将interactive_timeout的值设置的大些,而wait_timeout的值设置的小些?但是问题2的描述好像又不允许这样。。。
(1)interactive_timeout:
参数含义:服务器关闭交互式连接前等待活动的秒数。交互式客户端定义为在mysql_real_connect()中使用CLIENT_INTERACTIVE选项的客户端。
参数默认值:28800秒(8小时)
(2)wait_timeout:
参数含义:服务器关闭非交互连接之前等待活动的秒数。
在线程启动时,根据全局wait_timeout值或全局interactive_timeout值初始化会话wait_timeout值,取决于客户端类型(由mysql_real_connect()的连接选项CLIENT_INTERACTIVE定义)。
参数默认值:28800秒(8小时)
问题1:这里为什么要同时设置interactive_timeout,wait_timeout的设置才会生效?
答: 不设置interactive_timeout,wait_timeout也会生效。
问题2:interactive的值如果设置的和wait_timeout不同,为什么Interactive_timeout会覆盖wait_timeout?
答:在交互模式下(CLIENT_INTERACTIVE),interactive_timeout才生效,非交互模式下,不生效。
问题3:在进行MySQL优化时,因为interactive_timeout决定的是交互连接的时间长短,而wait_timeout决定的是非交互连接的时间长短。如果在进行连接配置时mysql_real_connect()最后一个参数client_flag不设置为CLIENT_INTERACTIVE,是不是interactive_timeout的值不会覆盖wait_timeout?
答:可以做实验试试。
问题4:为了减少长连接的数量,在设置优化时是不是可以将interactive_timeout的值设置的大些,而wait_timeout的值设置的小些?但是问题2的描述好像又不允许这样。。。
答:如2所述,在交互模式下,interactive_timeout取代wait_timeout。这样,如果有的客户端是交互模式方式连接mysql server。那么客户端的timeout受制于interactive_timeout。如果有的客户 端是非交互模式,长连接mysql server。那么客户端的timeout受制于wait_timeout。(是否是交互模式的连接,由客户端决定)
my.cnf
[mysqld]
wait_timeout=100
but
mysql> show variables like '%timeout%';
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 28800 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 3600 |
| wait_timeout | 28800 |
+-----------------------------+----------+
12 rows in set (0.20 sec)
Q:通过 Socket 连接 timeout 会从哪个 global timeout 继承
A:由下例可见,通过 socket 登录, timeout 继承于 global.interactive_timeout;
mysql> set global interactive_timeout = 11111;
Query OK, 0 rows affected (0.19 sec)
mysql> set global wait_timeout = 22222;
Query OK, 0 rows affected (0.01 sec)
mysql> show global variables like '%timeout%';
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 11111 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 3600 |
| wait_timeout | 22222 |
+-----------------------------+----------+
12 rows in set (0.01 sec)
mysql> exit
Bye
[root@localhost ~]# mysql -uroot -p
Enter password:
mysql> show global variables like '%timeout%';
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 11111 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 3600 |
| wait_timeout | 22222 |
+-----------------------------+----------+
12 rows in set (0.00 sec)
mysql> show session variables like '%timeout%';
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 11111 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 3600 |
| wait_timeout | 11111 |
+-----------------------------+----------+
12 rows in set (0.01 sec)
Q:通过 TCP/IP client 连接, timeout 会从哪个 global timeout 继承
A:由下例可见,通过 TCP/IP client 连接后的 wait_timeout 仍然继承于 global.interactive_timeout
[root@localhost ~]# mysql -uroot -p -h127.0.0.1 --port 3306
Enter password:
mysql> show session variables like '%timeout%';
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 11111 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 3600 |
| wait_timeout | 11111 |
+-----------------------------+----------+
12 rows in set (0.00 sec)
2.2 起效关系
Q: timeout 值,对于正在运行用的语句是否起效?
A:由下例可见 SQL 正在执行状态的等待时间不计入 timeout 时间
mysql> set session wait_timeout=10;
Query OK, 0 rows affected (0.00 sec)
mysql> set session interactive_timeout=10;
Query OK, 0 rows affected (0.00 sec)
mysql> select 1,sleep(20) from dual;
+---+-----------+
| 1 | sleep(20) |
+---+-----------+
| 1 | 0 |
+---+-----------+
1 row in set (17.47 sec)
Q: wait_timeout 和 interacitve_timeout 如何相互作用。
A:只有 session.wait_timeout 会起效
会话1
mysql> set session interactive_timeout=10;
Query OK, 0 rows affected (0.00 sec)
mysql> set session wait_timeout=20;
Query OK, 0 rows affected (0.00 sec)
mysql> show processlist;
+----+------+-----------------+------+---------+------+-------+------------------+
| Id | User | Host | db | Command | Time | State | Info |
+----+------+-----------------+------+---------+------+-------+------------------+
| 5 | root | localhost | NULL | Query | 0 | init | show processlist |
| 9 | root | localhost:34775 | NULL | Sleep | 17 | | NULL |
+----+------+-----------------+------+---------+------+-------+------------------+
2 rows in set (0.00 sec)
mysql> show processlist;
+----+------+-----------------+------+---------+------+-------+------------------+
| Id | User | Host | db | Command | Time | State | Info |
+----+------+-----------------+------+---------+------+-------+------------------+
| 5 | root | localhost | NULL | Query | 0 | init | show processlist |
| 9 | root | localhost:34775 | NULL | Sleep | 18 | | NULL |
+----+------+-----------------+------+---------+------+-------+------------------+
2 rows in set (0.00 sec)
mysql> show processlist;
+----+------+-----------------+------+---------+------+-------+------------------+
| Id | User | Host | db | Command | Time | State | Info |
+----+------+-----------------+------+---------+------+-------+------------------+
| 5 | root | localhost | NULL | Query | 0 | init | show processlist |
| 9 | root | localhost:34775 | NULL | Sleep | 19 | | NULL |
+----+------+-----------------+------+---------+------+-------+------------------+
2 rows in set (0.00 sec)
mysql> show processlist;
+----+------+-----------------+------+---------+------+-------+------------------+
| Id | User | Host | db | Command | Time | State | Info |
+----+------+-----------------+------+---------+------+-------+------------------+
| 5 | root | localhost | NULL | Query | 0 | init | show processlist |
| 9 | root | localhost:34775 | NULL | Sleep | 19 | | NULL |
+----+------+-----------------+------+---------+------+-------+------------------+
2 rows in set (0.00 sec)
mysql>
mysql> show processlist;
+----+------+-----------+------+---------+------+-------+------------------+
| Id | User | Host | db | Command | Time | State | Info |
+----+------+-----------+------+---------+------+-------+------------------+
| 5 | root | localhost | NULL | Query | 0 | init | show processlist |
+----+------+-----------+------+---------+------+-------+------------------+
1 row in set (0.00 sec)
mysql>
Q: global timeout 和 session timeout 哪个起作用。
A:只有 session timeout 会起作用。
1. mysql> set session interactive_timeout = 10;
2. Query OK, 0 rows affected (0.00 sec)
3. mysql> set session wait_timeout = 10;
4. Query OK, 0 rows affected (0.00 sec)
5. mysql> show session variables like '%timeout%';
6. +----------------------------+----------+
7. | Variable_name | Value |
8. +----------------------------+----------+
9. | interactive_timeout | 10 |
10. | wait_timeout | 10 |
11. +----------------------------+----------+
12. 10 rows in set (0.00 sec)
13. mysql> show global variables like '%timeout%';
14. +----------------------------+----------+
15. | Variable_name | Value |
16. +----------------------------+----------+
17. | interactive_timeout | 20 |
18. | wait_timeout | 20 |
19. +----------------------------+----------+
由以上的阶段测试可以获得以下结论。
1. 超时时间只对非活动状态的 connection 进行计算。
2. 超时时间指通过 session wait_timeout 起效。
3. 交互式连接的 wait_timeout 继承于 global.interactive_timeout
非交互式连接的 wait_timeout 继承于 global.wait_timeout
4. 继承关系和超时对 TCP/IP 和 Socket 连接均有效果