多多色-多人伦交性欧美在线观看-多人伦精品一区二区三区视频-多色视频-免费黄色视屏网站-免费黄色在线

國內(nèi)最全I(xiàn)T社區(qū)平臺 聯(lián)系我們 | 收藏本站
阿里云優(yōu)惠2
您當(dāng)前位置:首頁 > 互聯(lián)網(wǎng) > swoole入門教程03-Timer定時器、心跳檢測及Task進(jìn)階實例:mysql連接池

swoole入門教程03-Timer定時器、心跳檢測及Task進(jìn)階實例:mysql連接池

來源:程序員人生   發(fā)布時間:2014-11-07 09:00:39 閱讀次數(shù):10582次

環(huán)境說明: 系統(tǒng):Ubuntu14.04 (安裝教程包括CentOS6.5)
PHP版本:PHP⑸.5.10
swoole版本:1.7.7-stable

Github地址:https://github.com/LinkedDestiny/swoole-doc


1.Timer定時器

在實際利用中,常常會遇到需要每隔1段時間重復(fù)做1件事,比如心跳檢測、定閱消息、http://www.vxbq.cn/db/備份等工作。通常,我們會借助PHP的time()和相干函數(shù)自己實現(xiàn)1個定時器,或使用crontab工具來實現(xiàn)。但是,自定義的定時器容易出錯,而使用crontab則需要編寫額外的腳本文件,不管是遷移還是調(diào)試都比較麻煩。
因此,Swoole提供了1個內(nèi)置的Timer定時器功能,通過函數(shù)addtimer便可在Swoole中添加1個定時器,該定時器會在建立以后,依照預(yù)先設(shè)定好的時間間隔,每到對應(yīng)的時間就會調(diào)用1次回調(diào)函數(shù)onTimer通知Server。
簡單示例以下:

$this->serv->on('Timer', array($this, 'onTimer')); public function onWorkerStart( $serv , $worker_id) { // 在Worker進(jìn)程開啟時綁定定時器 // 只有當(dāng)worker_id為0時才添加定時器,避免重復(fù)添加 if( $worker_id == 0 ) { $serv->addtimer(500); $serv->addtimer(1000); $serv->addtimer(1500); } } public function onTimer($serv, $interval) { switch( $interval ) { case 500: { // echo "Do Thing A at interval 500 "; break; } case 1000:{ echo "Do Thing B at interval 1000 "; break; } case 1500:{ echo "Do Thing C at interval 1500 "; break; } } }

可以看到,在onWorkerStart回調(diào)函數(shù)中,通過addtimer添加了3個定時器,時間間隔分別為500、1000、1500。而在onTimer回調(diào)中,正好通過間隔的不同來辨別不同的定時器回調(diào),從而履行不同的操作。
需要注意的是,在上述示例中,當(dāng)1000ms的定時器被觸發(fā)時,500ms的定時器一樣會被觸發(fā),但是不能保證會在1000ms定時器前觸發(fā)回是后觸發(fā),因此需要注意,定時器中的操作不能依賴其他定時器的履行結(jié)果。

點此查看完全示例

(PS:在Swoole⑴.7.7版本,新提供了1個after函數(shù), 這個功能的用法會在以后的教程中給出。)

2.心跳檢測

上文提到過,使用Timer定時器功能可以實現(xiàn)發(fā)送心跳包的功能。事實上,Swoole已內(nèi)置了心跳檢測功能,能自動close掉長時間沒有數(shù)據(jù)來往的連接。而開啟心跳檢測功能,只需要設(shè)置heartbeat_check_interval和heartbeat_idle_time便可。以下:

$this->serv->set( array( 'heartbeat_check_interval' => 60, 'heartbeat_idle_time' => 600, ) );

其中heartbeat_idle_time的默許值是heartbeat_check_interval的兩倍。 在設(shè)置這兩個選項后,swoole會在內(nèi)部啟動1個線程,每隔heartbeat_check_interval秒后遍歷1次全部連接,檢查最近1次發(fā)送數(shù)據(jù)的時間和當(dāng)前時間的差,如果這個差值大于heartbeat_idle_time,則會強(qiáng)迫關(guān)閉這個連接,并通過回調(diào)onClose通知Server進(jìn)程。 點此查看完全示例 小技能: 結(jié)合之前的Timer功能,如果我們想保持連接,就設(shè)置1個略小于如果這個差值大于heartbeat_idle_time的定時器,在定時器內(nèi)向所有連接發(fā)送1個心跳包。如果收到心跳回應(yīng),則判斷連接正常,如果沒有收到,則關(guān)閉這個連接或再次嘗試發(fā)送。

3.Task進(jìn)階:MySQL連接池

上1章中我簡單講授了如何開啟和使用Task功能。這1節(jié),我將提供1個Task的高級用法。

在PHP中,訪問MySQLhttp://www.vxbq.cn/db/常常是性能提升的瓶頸。而MySQL連接池我想大家都不陌生,這是1個很好的提升http://www.vxbq.cn/db/訪問性能的方式。傳統(tǒng)的MySQL連接池,是預(yù)先申請1定數(shù)量的連接,每個新的要求都會占用其中1個連接,要求結(jié)束后再將連接放回池中,如果所有連接都被占用,新來的連接則會進(jìn)入等待狀態(tài)。
知道了MySQL連接池的實現(xiàn)原理,那我們來看如何使用Swoole實現(xiàn)1個連接池。
首先,Swoole允許開啟1定量的Task Worker進(jìn)程,我們可讓每一個進(jìn)程都具有1個MySQL連接,并保持這個連接,這樣,我們就創(chuàng)建了1個連接池。
其次,設(shè)置swoole的dispatch_mode為搶占模式(主進(jìn)程會根據(jù)Worker的忙閑狀態(tài)選擇投遞,只會投遞給處于閑置狀態(tài)的Worker)。這樣,每一個task都會被投遞給閑置的Task Worker。這樣,我們保證了每一個新的task都會被閑置的Task Worker處理,如果全部Task Worker都被占用,則會進(jìn)入等待隊列。

下面直接上關(guān)鍵代碼:

public function onWorkerStart( $serv , $worker_id) { echo "onWorkerStart "; // 判定是不是為Task Worker進(jìn)程 if( $worker_id >= $serv->setting['worker_num'] ) { $this->pdo = new PDO( "mysql:host=localhost;port=3306;dbname=Test", "root", "123456", array( PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES 'UTF8';", PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, PDO::ATTR_PERSISTENT => true ) ); } }

首先,在每一個Task Worker進(jìn)程中,創(chuàng)建1個MySQL連接。這里我選用了PDO擴(kuò)大。

public function onReceive( swoole_server $serv, $fd, $from_id, $data ) { $sql = array( 'sql'=>'select * from Test where pid > ?', 'param' => array( 0 ), 'fd' => $fd ); $serv->task( json_encode($sql) ); }

其次,在需要的時候,通過task函數(shù)投遞1個任務(wù)(也就是發(fā)起1次SQL要求)

public function onTask($serv,$task_id,$from_id, $data) { $sql = json_decode( $data , true ); $statement = $this->pdo->prepare($sql['sql']); $statement->execute($sql['param']); $result = $statement->fetchAll(PDO::FETCH_ASSOC); $serv->send( $sql['fd'],json_encode($result)); return true; }

最后,在onTask回調(diào)中,根據(jù)要求過來的SQL語句和相應(yīng)的參數(shù),發(fā)起1次MySQL要求,并將獲得到的結(jié)果通過send發(fā)送給客戶端(或通過return返回給Worker進(jìn)程)。而且,這樣的1次MySQL要求還不會阻塞Worker進(jìn)程,Worker進(jìn)程可以繼續(xù)處理其他的邏輯。

可以看到,簡單10幾行代碼,就實現(xiàn)了1個高效的異步MySQL連接池。
通過測試,單個客戶端1共發(fā)起1W次select要求,共耗時9s;
1W次insert要求,共耗時21s。
(客戶端會在每次收到前1個要求的結(jié)果后才會發(fā)起下1次要求,而不是并發(fā))。

點此查看完全服務(wù)端代碼
點此查看完全客戶端代碼

下章預(yù)告:Swoole多端口監(jiān)聽、熱重啟和Timer進(jìn)階:簡單crontab

生活不易,碼農(nóng)辛苦
如果您覺得本網(wǎng)站對您的學(xué)習(xí)有所幫助,可以手機(jī)掃描二維碼進(jìn)行捐贈
程序員人生
------分隔線----------------------------
分享到:
------分隔線----------------------------
關(guān)閉
程序員人生
主站蜘蛛池模板: 国产精品一区二区三区免费视频 | 国产精品久久亚洲不卡4k岛国 | 亚洲欧洲国产成人综合一本 | jizz在线免费 | 欧美成人性色区 | 激情综合婷婷丁香六月花 | 成人18网址在线观看 | 亚洲国产天堂久久九九九 | 国产成人一区二区三区小说 | 欧美乱乱 | 日本乱性 | 九九爱精品视频 | 日韩欧美中文字幕出 | 国产不卡一区二区三区免费视 | 色综合欧美 | 福利片国产 | 欧美videos另类极品 | 日韩高清无砖砖区2022 | h在线观看免费 | 日本一区二区三区四区不卡 | 亚洲国产一区二区三区最新 | 日本欧美在线 | 一二三四观看在线视频中文 | 男人边吃奶边做性视频 | 18网站在线观看 | 亚洲第一网址 | 国产午夜亚洲精品久久www | 亚洲涩福利高清在线 | 久久久久18 | 国产永久高清免费动作片www | 欧美一区二区三区高清不卡tv | 国产69成人免费视频观看 | 久久久精品久久 | 波多野结衣在线网站 | 欧美式free群乱 | 日本一区二区三区不卡在线视频 | 欧美猛交xxxx免费看 | 国产精视频 | 欧美大片aaaa一级毛片 | 欧美日韩aa一级视频 | 亚洲日本在线观看视频 |