为了发挥出PolarDB MySQL的最佳性能,PolarDB提供线程池(Thread Pool)功能,将线程和会话分离,在拥有大量会话的同时,只需要少量线程完成活跃会话的任务即可。

优势

MySQL默认的线程使用模式是会话独占模式,每个会话都会创建一个独占的线程。当有大量的会话存在时,会导致大量的资源竞争,大量的系统线程调度和缓存失效也会导致性能急剧下降。

PolarDB的线程池实现了不同类型SQL操作的优先级及并发控制机制,将连接数始终控制在最佳连接数附近,使PolarDB数据库在高连接大并发情况下始终保持高性能。线程池的优势如下:

  • 当大量线程并发工作时,线程池会自动调节并发的线程数量在合理的范围内,从而避免线程调度工作过多和大量缓存失效。
  • 大量的事务并发执行时,线程池会将语句和事务分为不同的优先级,分别控制语句和事务的并发数量,从而减少资源竞争。
  • 线程池给予管理类的SQL语句更高的优先级,保证这些语句优先执行。这样在系统负载很高时,新建连接、管理、监控等操作也能够稳定执行。
  • 线程池给予复杂查询SQL语句相对较低的优先级,并且有最大并发数的限制。这样可以避免过多的复杂SQL语句将系统资源耗尽,导致整个数据库服务不可用。

使用Thread Pool

Thread Pool设计了以下七个参数,您可以在控制台进行修改。具体请参见设置集群参数

参数名称 说明
loose_thread_pool_enabled 是否开启线程池功能。取值:
  • ON
  • OFF

默认值:OFF。

说明 开启或关闭线程池功能无需重启实例。
loose_thread_pool_high_prio_mode 线程池高优先级队列模式。取值:
  • transactions:已开启事务的SQL将被加入高优先级队列,并被赋予thread_pool_high_prio_tickets这个门票,接下来执行的SQL都将被放入高优先级队列,直到门票被耗尽。
  • statements:所有SQL都会加入高优先级队列。
  • none:所有SQL都不加入高优先级队列。

默认值:transactions。

说明PolarDB MySQL 5.6和5.7支持该参数。
loose_thread_pool_high_prio_tickets 高优先级队列的单次门票数。

取值:0~4294967295。

默认值:4294967295。

说明PolarDB MySQL 5.6和5.7支持该参数。
loose_thread_pool_idle_timeout 释放线程池空闲线程的时间阈值,超过此时间,没有服务任何请求的空闲线程将被释放。

取值:0~31536000。

单位:秒,默认值:60。

说明PolarDB MySQL 5.6和5.7支持该参数。
loose_thread_pool_max_threads 线程池中允许的最大工作线程数。

取值:1~100000。

默认值:100000。

说明PolarDB MySQL 5.6和5.7支持该参数。
loose_thread_pool_oversubscribe 每个组中允许的活跃线程的数量。

活跃线程是指正在执行SQL语句的线程,但是不包括以下两种情形:

  • SQL语句在等待磁盘I/O。
  • SQL语句在等待事务提交。

取值:1~1000。

默认值:10。

loose_thread_pool_stall_limit 判断线程池进入拥塞状态的时间阈值。

当线程池进入拥塞状态时,系统会创建新的线程来服务SQL。

取值:1~18446744073709551615。

单位:毫秒。默认值:30。

说明PolarDB MySQL 5.6和5.7支持该参数。

查询Thread Pool状态

您可以通过如下命令查询Thread Pool状态:

select * from information_schema.THREAD_POOL_STATUS;

返回示例如下所示。

mysql>select * from information_schema.THREAD_POOL_STATUS;
+--------------+------------------------+-------------------------------+--------------------------------+-----------------------------+----------------------------+---------------------------+----------------------------+
| ID           | THREAD_COUNT           | ACTIVE_THREAD_COUNT           | WAITING_THREAD_COUNT           | DUMP_THREAD_COUNT           | CONNECTION_COUNT           | LOW_QUEUE_COUNT           | HIGH_QUEUE_COUNT           |
+--------------+------------------------+-------------------------------+--------------------------------+-----------------------------+----------------------------+---------------------------+----------------------------+
|            0 |                      2 |                             1 |                              0 |                           0 |                          1 |                         0 |                          0 |
|            1 |                      2 |                             0 |                              0 |                           0 |                          0 |                         0 |                          0 |
|            2 |                      2 |                             0 |                              0 |                           0 |                          1 |                         0 |                          0 |
|            3 |                      2 |                             0 |                              0 |                           0 |                          1 |                         0 |                          0 |
|            4 |                      2 |                             0 |                              0 |                           0 |                          1 |                         0 |                          0 |
+--------------+------------------------+-------------------------------+--------------------------------+-----------------------------+----------------------------+---------------------------+----------------------------+
返回行数:[5],耗时:7 ms.

参数说明如下。

参数 说明
ID 线程池ID。
THREAD_COUNT 线程池中的线程数。
ACTIVE_THREAD_COUNT 线程池中的活跃线程数。
WAITING_THREAD_COUNT 线程池中正在等待磁盘I/O、事务提交的线程数。
DUMP_THREAD_COUNT 线程池中DUMP类长连接数量。
CONNECTION_COUNT 线程池中已建立的用户连接数。
LOW_QUEUE_COUNT 线程池中低优先级队列中等待的请求数。
HIGH_QUEUE_COUNT 线程池中高优先级队列中等待的请求数。

Sysbench测试

如下是开启线程池和不开启线程池的性能对比。从测试结果可以看出线程池在高并发的情况下有着明显的性能优势。

图 1. OLTP无索引更新测试
OLTP无索引更新
图 2. OLTP只写测试
OLTP只写
图 3. OLTP只读测试
OLTP只读
图 4. OLTP读写测试
OLTP读写测试