实现一个协程版mysql连接池
实现一个协程版的mysql连接池,该连接池支持自动创建最小连接数,自动检测mysql健康;基于swoole的chanel。
最近事情忙,心态也有点不积极。技术倒是没有落下,只是越来越不想写博客了。想到平时自己上网上找资料的痛苦,于是将自己这篇连接池的文章放出来,给需要的程序员一点帮助。
<?php
/**
* 实现一个协程版的mysql 连接池
* Created by PhpStorm.
* User: roverliang
* Date: 2018/12/10
* Time: 23:27
*/
namespace console\libs;
use Swoole\Coroutine\MySQL as coMysql;
use Swoole\Coroutine\Channel;
class CoMysqlPool extends coMysql
{
protected $maxNums; //最大连接数
protected $minNums; //最小连接数
protected $mysqlConfig = array(
'host' => '127.0.0.1',
'port' => 3306,
'user' => 'root',
'password' => '',
'database' => 'hifuli',
'timeout' => -1,
); //mysql配置
protected $chan; //channel
protected $currentConnectedNums; //当前连接数
protected $tag; //标识
/**
* 初始化连接池
* CoMysqlPool constructor.
* @param int $maxNums 最大连接数
* @param int $minNums 最小连接数
* @param array $mysqlConfig mysql配置
*/
public function __construct($maxNums = 20, $minNums = 5, $mysqlConfig = [])
{
$this->maxNums = $maxNums;
$this->minNums = $minNums;
if (!empty($mysqlConfig) && is_array($mysqlConfig)) {
$this->mysqlConfig = $mysqlConfig;
}
$this->chan = new Channel($maxNums);
$this->tag = true;
}
/**
* 从连接池中获取一个mysql连接对象
* Created by 梁子(roverliang) <mr.roverliang@gmail.com>
* 2018/12/10
*/
public function pop()
{
if (!$this->tag) return false;
if ($mysql = $this->getMysqlInstance()) {
echo "创建了一个mysql".PHP_EOL;
return $mysql;
}
$mysql = $this->chan->pop();
if (!$this->checkMysqlHealth($mysql)) {
$mysql = $this->getMysqlInstance();
} else {
echo "复用mysql".PHP_EOL;
}
return $mysql;
}
/**
* 将mysql对象放回连接池
* Created by 梁子(roverliang) <mr.roverliang@gmail.com>
* 2018/12/10
* @param $obj
*/
public function push($mysql)
{
if (!$this->tag) return false;
if (!$this->chan->isFull()) {
echo "将mysql放入连接池".PHP_EOL;
$this->chan->push($mysql);
}
return true;
}
/**
* 获取mysql实例
* Created by 梁子(roverliang) <mr.roverliang@gmail.com>
* 2018/12/10
* @return bool
*/
protected function getMysqlInstance()
{
if (!$this->chan->isFull()) {
$mysqlInstance = new \Swoole\Coroutine\MySQL();
$mysqlInstance->connect($this->mysqlConfig);
return $mysqlInstance;
}
return false;
}
/**
* 检测mysql连接是否健康
* Created by 梁子(roverliang) <mr.roverliang@gmail.com>
* 2018/12/10
*/
protected function checkMysqlHealth($mysql)
{
if (!$mysql->connected) return false;
return true;
}
/**
* 销毁连接池
* Created by 梁子(roverliang) <mr.roverliang@gmail.com>
* 2018/12/11
*/
public function destroyPool()
{
$this->tag = false;
while ($this->chan->length()) {
$mysql = $this->chan->pop();
$mysql->close();
echo "销毁mysql".PHP_EOL;
}
return true;
}
/**
* 监控进程池
* Created by Roverliang.
* Date: 2018/12/12 Time: 17:12
*/
public function monitorPool()
{
declare(ticks=10);
$self = $this;
register_tick_function(function () use ($self) {
if (($self->chan->length() < $self->minNums) && $self->tag) {
$mysql = $self->pop();
if ($self->checkMysqlHealth($mysql)) {
echo "mysql进程监控池自动创建mysql".PHP_EOL;
$self->push($mysql);
}
}
});
}
}
go(function(){
$mysqlPool = new CoMysqlPool(10, 2);
$mysqlPool->monitorPool();
for($i=0; $i<20;$i++) {
$mysqlPool->monitorPool();
$mysql = $mysqlPool->pop();
$mysqlPool->push($mysql);
\Swoole\Coroutine::sleep(1);
}
$mysqlPool->destroyPool();
});
实现一个协程版mysql连接池的更多相关文章
- nodejs + redis/mysql 连接池问题
nodejs + redis/mysql 连接池问题 需不需要连接池 连接池的作用主要是较少每次临时建立连接所带来的开销.初步一看,nodejs运行单线程上,它不能同时使用多个连接,乍一看是不需要连接 ...
- Swoole MySQL 连接池的实现
目录 概述 代码 扩展 小结 概述 这是关于 Swoole 入门学习的第八篇文章:Swoole MySQL 连接池的实现. 第七篇:Swoole RPC 的实现 第六篇:Swoole 整合成一个小框架 ...
- 如何在 Swoole 中优雅的实现 MySQL 连接池
如何在 Swoole 中优雅的实现 MySQL 连接池 一.为什么需要连接池 ? 数据库连接池指的是程序和数据库之间保持一定数量的连接不断开, 并且各个请求的连接可以相互复用, 减少重复连接数据库带来 ...
- 解决Mysql连接池被关闭 ,hibernate尝试连接不能连接的问题。 (默认mysql连接池可以访问的时间为8小时,如果超过8小时没有连接,mysql会自动关闭连接池。系统发布第二天访问链接关闭问题。
解决Mysql连接池被关闭 ,hibernate尝试连接不能连接的问题. (默认MySQL连接池可以访问的时间为8小时,如果超过8小时没有连接,mysql会自动关闭连接池. 所以系统发布第二天访问会 ...
- Java Mysql连接池配置和案例分析--超时异常和处理
前言: 最近在开发服务的时候, 发现服务只要一段时间不用, 下次首次访问总是失败. 该问题影响虽不大, 但终究影响用户体验. 观察日志后发现, mysql连接因长时间空闲而被关闭, 使用时没有死链检测 ...
- MySQL连接池
1. using System; using System.Collections; using MySql.Data.MySqlClient; namespace Helper { /// < ...
- tomcat中使用mysql连接池的配置
1.下载相应的jar包,添加到工程中 需要下载的包主要有commons-pool2-2.2 commons-dbcp2-2.0.1-src commons-dbcp2-2.0.1 commons-c ...
- mysql连接池的使用工具类代码示例
mysql连接池代码工具示例(scala): import java.sql.{Connection,PreparedStatement,ResultSet} import org.apache.co ...
- 用swoole简单实现MySQL连接池
MySQL连接池 在传统的网站开发中,比如LNMP模式,由Nginx的master进程接收请求然后分给多个worker进程,每个worker进程再链接php-fpm的master进程,php-fpm再 ...
随机推荐
- [Golang] 第三方包应该如何安装--在线和离线
一 在线安装 采用go get的方式安装import 的时候找不到对应的包看看pkg里面有没有 二 离线安装 redis客户端采用git clone的方法安装的话可以用以下方法 cd src git ...
- SpringMVC源码阅读:拦截器
1.前言 SpringMVC是目前J2EE平台的主流Web框架,不熟悉的园友可以看SpringMVC源码阅读入门,它交代了SpringMVC的基础知识和源码阅读的技巧 本文将通过源码(基于Spring ...
- PBN飞越转弯Flyover衔接TF、CF航段保护区组图
PBN飞越转弯Flyover衔接TF.CF航段虽不常用,但也很重要,与旁切转弯有一定的相似性. 飞越转弯 flyover-TF/CF 叠加图: 飞越转弯 flyover-TF/CF 分解图:
- stack堆栈容器、queue队列容器和priority_queue优先队列容器(常用的方法对比与总结)
stack堆栈是一个后进先出的线性表,插入和删除元素都在表的一端进行. stack堆栈的使用方法: 采用push()方法将元素入栈: 采用pop()方法将元素出栈: 采用top()方法访问栈顶元素: ...
- 并发编程之 线程协作工具 LockSupport
前言 在前面的文章中,我们介绍了并发工具中的4个,Samephore,CyclicBarrier,CountDownLatch,Exchanger,但是我们漏了一个,非常的好用的工具,楼主在这里必须加 ...
- 在ASP.NET MVC应用程序中随机获取一个字符串
在开发ASP.NET MVC应用程序时,有可能需要一个随机字符串,作为密码或是验证码等. 如果你需要的是SQL版本,可以参考<密码需要带特殊字符(二)>http://www.cnblogs ...
- Oracle中如何写存储过程
>存储过程是什么? 存储过程是一种命名的PL/SQL程序块,输入.输出参数数量[0个或多个],通常没有返回值[也有特殊的情况]. 运行SQL语句时,Oracle是要先编译再执行的:而存储过程是已 ...
- 子序列个数(fzu2129)
子序列个数 Time Limit:2000MS Memory Limit:32768KB 64bit IO Format:%I64d & %I64u Submit Status ...
- Java基础知识你知道多少?
Java虚拟机基础知识你知道多少? Java并发基础知识你知道多少? Java数据结构基础知识你知道多少? java序列化与反序列化 https://github.com/zhantong/inter ...
- JS中那些让人头昏眼花的弯子
看别人在讨论,于是整理了下,大家来看看下面代码中1-11分别输出的答案是什么???(不要试过再说) var obj={ a:1, b:2, add:function(c,d){ console.log ...