普通mysql连接和连接池连接的方式对比
对于一个简单的数据库应用,由于对于数据库的访问不是很频繁。这时可以简单地在需要访问数据库时,就新创建一个连接,用完后就关闭它,这样做也不会带来什么明显的性能上的开销。但是对于一个复杂的数据库应用,情况就完全不同了。频繁的建立、关闭连接,会极大的减低系统的性能,因为对于连接的使用成了系统性能的瓶颈。
连接池的作用就是连接复用
。通过建立一个数据库连接池以及一套连接使用管理策略,使得一个数据库连接可以得到高效、安全的复用,避免了数据库连接频繁建立、关闭的开销。
数据库连接池的基本原理是在内部对象池中维护一定数量的数据库连接。
为什么要使用连接池(为了解决什么问题)
对于共享资源,有一个很著名的设计模式:资源池。该模式正是为了解决资源频繁分配、释放所造成的问题的。把该模式应用到数据库连接管理领域,就是建立一个数据库连接池,提供一套高效的连接分配、使用策略,最终目标是实现连接的高效
、安全
的复用
。连接池会带来以下几个优势:
- 连接复用:可以复用连接池初始化的连接,可以避免频繁的创建和释放连接引起的大量性能开销。
- 更快的系统相应速度:由于初始化连接池时会创建最小连接数个连接在连接池中备用,对于业务请求处理而言,直接利用现有可用连接,避免了数据库连接初始化和释放过程的时间开销,从而缩减了系统整体响应时间
- 避免数据库泄漏:在较为完备的数据库连接池实现中,可根据预先的连接占用超时设定,强制收回被占用连接。从而避免了常规数据库连接操作中可能出现的资源泄漏。一个最小化的数据库连接池实现
先解释几个概念
- mincon 连接池最小连接数也是连接池一直保持的最小连接数,所以如果应用程序对数据库连接的使用量不大,将会有大量的数据库连接闲置,资源被浪费。
- maxcon 连接池最大连接数,mysql连接数超过这个值就会报错too many connections。
- connections mysql的连接数
数据库连接池(Connection pooling)是程序启动时建立(也就是连接池的mincon),并将这些连接组成一个连接池,由程序动态地对池中的连接进行申请,使用,释放。
数据库连接池最小连接数和最大连接数:
数据库连接池在初始化时将创建一定数量的数据库连接放到连接池中, 这些数据库连接的数量是由连接池最小连接数
来设定的.无论这些数据库连接是否被使用,连接池都将一直保证至少
拥有这么多的连接数量。如果数据库连接数没有超过最小连接数,这时进来的连接会复用连接池的连接,而不需要创建新的连接,使用完连接也不会释放,只是把该连接重新放到池中。
连接池的最大数据库连接数量限定了这个连接池能占有的最大连接数,连接池的最大连接数不能超过mysql的最大连接数(连接池是基于mysql)。如果数据连接请求超过此数,后面的数据连接请求将被加入到等待队列中,这会影响之后的数据库操作。
如果最小连接数与最大连接数相差太大,那么,最先的连接请求将会获利,复用连接池中的连接(也就是连接池初始化的最小连接数),之后超过最小连接数量的连接请求等价于建立一个新的数据库连接。不过,这些大于最小连接数的数据库连接在使用完不会马上
被释放,它将被放到连接池中等待重复使用或是空闲超时后被释放
。
常用命令
查看mysql的最大连接数
mysql> show variables like 'max_connections';
+-----------------+-------+
| Variable_name | Value |
+-----------------+-------+
| max_connections | 151 |
+-----------------+-------+
查看当前连接数,Threads数就是连接数
xiaoyudeMBP:bin xiaoyu$ ./mysqladmin -u laravel -p status
Enter password:
Uptime: 233116 Threads: 23 Questions: 4630 Slow queries: 0 Opens: 140 Flush tables: 1 Open tables: 133 Queries per second avg: 0.019
查询服务器响应的最大连接数
mysql> show global status like 'Max_used_connections';
+----------------------+-------+
| Variable_name | Value |
+----------------------+-------+
| Max_used_connections | 216 |
+----------------------+-------+
比如MySQL服务器最大连接数是650,没有达到服务器连接数上限650,应该不会出现too many connections(1040)错误,比较理想的设置是:
Max_used_connections / max_connections * 100% ≈ 85%
最大连接数占上限连接数的85%左右,如果发现比例在10%以下,MySQL服务器连接上限就设置得过高了。
设置mysql最大连接数
mysql> set GLOBAL max_connections=256;
Query OK, 0 rows affected (0.00 sec)
注意:
- 连接池的最大连接数设置成mysql的最大连接数即可
- 最小连接数怎么设置
连接池的配置
- 连接池中到底放多少连接系统才能最稳定,性能最优呢(也就是最小连接数是多少)?参考这篇文章
连接数 = ((核心数 * 2) + 有效磁盘数)
下面的公式是由PostgreSQL提供的,不过我们认为可以广泛地应用于大多数数据库产品。你应该模拟预期的访问量,并从这一公式开始测试你的应用,寻找最合适的连接数值。
核心数不应包含超线程(hyper thread),即使打开了hyperthreading也是。如果活跃数据全部被缓存了,那么有效磁盘数是0,随着缓存命中率的下降,有效磁盘数逐渐趋近于实际的磁盘数。这一公式作用于SSD时的效果如何尚未有分析。
按这个公式,你的4核i7数据库服务器的连接池大小应该为((4 * 2) + 1) = 9。取个整就算是是10吧。是不是觉得太小了?跑个性能测试试一下,我们保证它能轻松搞定3000用户以6000TPS的速率并发执行简单查询的场景。如果连接池大小超过10,你会看到响应时长开始增加,TPS开始下降。响应起来却慢
- 最大连接数设置成多少更合适呢?
设置成mysql的最大连接数即可。那mysql的最大连接数设置成多大合适?上面已经说了,Max_used_connections / max_connections * 100% ≈ 85%
如何确保连接池中的最小连接数呢?
有动态和静态两种策略。动态即每隔一定时间就对连接池进行检测,如果发现空闲连接数量
小于最小连接数
,则补充相应数量的新连接,以保证连接池的正常运转。静态是发现空闲连接不够时再去检查。
常见问题
我们经常会遇见“MySQL: ERROR 1040: Too many connections”的情况,一种是访问量确实很高,MySQL服务器抗不住,这个时候就要考虑增加从服务器分散读写压力,另外一种情况是MySQL配置文件中max_connections值过小。
网友评论