天天看點

Workerman 聊天系統

文檔、檔案下載下傳位址

聊天庫: Workerman 

文檔: http://doc2.workerman.net/

手冊: http://www.workerman.net/gatewaydoc/

下載下傳Demo: http://doc2.workerman.net/

 CatewayWorker 服務端安裝 Liunx: http://www.workerman.net/download/GatewayWorker.zip

 CatewayWorker 服務端安裝 Window: http://www.workerman.net/download/GatewayWorker-for-win.zip

GatewayWorker架構與MVC結合總體原則:

現有mvc架構項目與GatewayWorker獨立部署互不幹擾

所有的業務邏輯都由網站頁面post/get到mvc架構中完成

GatewayWorker不接受用戶端發來的資料,即GatewayWorker不處理任何業務邏輯,GatewayWorker僅僅當做一個單向的推送通道

僅當mvc架構需要向浏覽器主動推送資料時才在mvc架構中調用Gateway的API GatewayClient完成推送。

用戶端安裝

composer 安裝 GatewayClinet  用戶端

composer require workerman/gatewayclient

//使用時引入vendor/autoload.php 類似如下:
use GatewayClient\Gateway;
require_once '真實路徑/vendor/autoload.php';      

 或是下載下傳源檔案到任意目錄,手動引入 

GatewayClient/Gateway.php

, 類似如下:

use GatewayClient\Gateway;
require_once '真實路徑/GatewayClient/Gateway.php';      

服務端安裝

CatewayWorker 服務端安裝,可以直接下載下傳源檔案

composer require workerman/gateway-worker-for-win //安裝Windows版本的gateway
composer require workerman/gateway-worker //安裝Linux版本的gateway      

服務端項目目錄結構,GatewayWorker單獨部署的

├── Applications // 這裡是所有開發者應用項目
│   └── YourApp  // 其中一個項目目錄,目錄名可以自定義
│       ├── Events.php // 開發者隻需要關注這個檔案
│       ├── start_gateway.php // gateway程序啟動腳本,包括端口号等設定
│       ├── start_businessworker.php // businessWorker程序啟動腳本
│       └── start_register.php // 注冊服務啟動腳本
│
├── start.php // 全局啟動腳本,此腳本會依次加載Applications/項目/start_*.php啟動腳本
│
└── vendor    // GatewayWorker架構和Workerman架構源碼目錄,此目錄開發者不用關心      

服務端檔案操作

建立 start.bat,一般放根目錄,Window 啟動檔案,輕按兩下

php worker\win\start_register.php worker\win\start_gateway.php worker\win\start_businessworker.php
pause      

建立 start.php,一般放根目錄,Liunx 啟動檔案,指令行  php start.php start

/**
 * run with command
 * php start.php start 官網檔案
 */

ini_set('display_errors', 'on');
use Workerman\Worker;

if(strpos(strtolower(PHP_OS), 'win') === 0)
{
    exit("start.php not support windows, please use start_for_win.bat\n");
}

// 檢查擴充
if(!extension_loaded('pcntl'))
{
    exit("Please install pcntl extension. See http://doc3.workerman.net/appendices/install-extension.html\n");
}

if(!extension_loaded('posix'))
{
    exit("Please install posix extension. See http://doc3.workerman.net/appendices/install-extension.html\n");
}

// 标記是全局啟動
define('GLOBAL_START', 1);

require_once __DIR__ . '/worker/vendor/autoload.php';

// 加載所有Applications/*/start.php,以便啟動所有服務, 此處我放根目錄/worker/win/ 下,其他要啟動的檔案是start.bat檔案中指定的檔案
foreach(glob(__DIR__.'/worker/win/start*.php') as $start_file)
{
    require_once $start_file;
}
// 運作所有服務
Worker::runAll();      

兩種啟動方式 :start_gateway.php start_businessworker.php start_register.php分别是程序啟動腳本,三個腳本統一由根目錄的start.php/ start.bat啟動。

檔案說明

start_register.php 為注冊服務啟動腳本,用于協調GatewayWorker叢集内部Gateway與Worker的通信,參見Register類使用一節。

注意:用戶端不要連接配接Register服務端口,用戶端應該連接配接Gateway端口

use \Workerman\Worker;
use \GatewayWorker\Register;

// 自動加載類,根據需求自定義
require_once __DIR__ . '/../../vendor/autoload.php';

// register 必須是text協定
$register = new Register('text://127.0.0.1:1234');

// 如果不是在根目錄啟動,則運作runAll方法
if(!defined('GLOBAL_START'))
{
    Worker::runAll();
}      

start_gateway.php   為gateway程序啟動腳本,主要定義了用戶端連接配接的端口号、協定等資訊,具體參見 Gateway類的使用一節。

use \Workerman\Worker;
use \Workerman\WebServer;
use \GatewayWorker\Gateway;
use \GatewayWorker\BusinessWorker;
use \Workerman\Autoloader;

// 自動加載類
require_once __DIR__ . '/../vendor/autoload.php';
/**
 * 與GatewayWorker建立websocket連接配接,域名和端口改為你實際的域名端口,
 * 其中端口為Gateway端口,即start_gateway.php指定的端口。
 * start_gateway.php 中需要指定websocket協定,像這樣
 * $gateway = new Gateway(websocket://0.0.0.0:7272);
 * js部分:
 * ws = new WebSocket("ws://your_domain.com:7272");
 */
// gateway 程序,這裡使用Text協定,可以用telnet測試

$context = array(
    // 更多ssl選項請參考手冊 http://php.net/manual/zh/context.ssl.php
    'ssl' => array(
        // 請使用絕對路徑
        'local_cert'                 => __dir__.'/certificate/server.pem', // 也可以是crt檔案
        'local_pk'                   => __dir__.'/certificate/server.key',
        'verify_peer'               => false,
        // 'allow_self_signed' => true, //如果是自簽名證書需要開啟此選項
    )
);
// websocket協定(端口任意,隻要沒有被其它程式占用就行)
$gateway = new Gateway("websocket://0.0.0.0:8899", $context);
// 開啟SSL,websocket+SSL 即wss
$gateway->transport = 'ssl';
// gateway名稱,status友善檢視
$gateway->name = 'YourAppGateway';
// gateway程序數
$gateway->count = 4;
// 本機IP,分布式部署時使用内網IP,GatewayWorker與GatewayClient不在同一台伺服器使用目前伺服器内網IP,如果不在同一個内網改為公網IP
$gateway->lanIp = '127.0.0.1';
// 内部通訊起始端口,假如$gateway->count=4,起始端口為4000
// 則一般會使用4000 4001 4002 4003 4個端口作為内部通訊端口 
$gateway->startPort = 2900;
// 服務注冊位址
$gateway->registerAddress = '127.0.0.1:1238';

// 心跳間隔
//$gateway->pingInterval = 10;
// 心跳資料
//$gateway->pingData = '{"type":"ping"}';

/* 
// 當用戶端連接配接上來時,設定連接配接的onWebSocketConnect,即在websocket握手時的回調
$gateway->onConnect = function($connection)
{
    $connection->onWebSocketConnect = function($connection , $http_header)
    {
        // 可以在這裡判斷連接配接來源是否合法,不合法就關掉連接配接
        // $_SERVER['HTTP_ORIGIN']辨別來自哪個站點的頁面發起的websocket連結
        if($_SERVER['HTTP_ORIGIN'] != 'http://kedou.workerman.net')
        {
            $connection->close();
        }
        // onWebSocketConnect 裡面$_GET $_SERVER是可用的
        // var_dump($_GET, $_SERVER);
    };
}; 
*/

// 如果不是在根目錄啟動,則運作runAll方法
if(!defined('GLOBAL_START'))
{
    Worker::runAll();
}      

start_businessworker.php 為businessWorker程序啟動腳本,也即是調用Events.php的業務處理程序,具體參見 BusinessWorker類的使用一節。

use \Workerman\Worker;
use \Workerman\WebServer;
use \GatewayWorker\Gateway;
use \GatewayWorker\BusinessWorker;
use \Workerman\Autoloader;

// 自動加載類
require_once __DIR__ . '/../../vendor/autoload.php';

// bussinessWorker 程序
$worker = new BusinessWorker();
// worker名稱
$worker->name = 'YourAppBusinessWorker';
// bussinessWorker程序數量
$worker->count = 4;
// 服務注冊位址
$worker->registerAddress = '127.0.0.1:1234';

// 如果不是在根目錄啟動,則運作runAll方法
if(!defined('GLOBAL_START'))
{
    Worker::runAll();
}      

Events.php 所有業務代碼都在這裡

/* 
 * 用于檢測業務代碼死循環或者長時間阻塞等問題
 * 如果發現業務卡死,可以将下面declare打開(去掉//注釋),并執行php start.php reload
 * 然後觀察一段時間workerman.log看是否有process_timeout異常
 */
//declare(ticks=1);

use \GatewayWorker\Lib\Gateway;

/**
 * 主邏輯
 * 主要是處理 onConnect onMessage onClose 三個方法
 * onConnect 和 onClose 如果不需要可以不用實作并删除
 */
class Events
{
    /**
     * 當用戶端連接配接時觸發
     * 如果業務不需此回調可以删除onConnect
     * @param int $client_id 連接配接id
     * @desc $client_id 為系統自動生成
     */
    public static function onConnect($client_id)
    {
        // 向目前client_id發送資料 
        /*Gateway::sendToClient($client_id, "Hello $client_id\r\n");
        // 向所有人發送
        Gateway::sendToAll("$client_id login\r\n");*/
    }
    
   /**
    * 當用戶端發來消息時觸發
    * @desc type:0 打開連結  其他發送消息
    * @param int $client_id 連接配接id
    * @param mixed $message 具體消息
    */
   public static function onMessage($client_id, $message)
   {
        // 向所有人發送 
        Gateway::sendToAll("$client_id said $message\r\n");
   }
   
   /**
    * 當使用者斷開連接配接時觸發
    * @param int $client_id 連接配接id
    */
   public static function onClose($client_id)
   {

   }
}      

啟動與停止

注意:Workerman啟動停止等指令都是在指令行中完成的。

啟動

以debug(調試)方式啟動

php start.php start

以daemon(守護程序)方式啟動

php start.php start -d

停止

php start.php stop

重新開機

php start.php restart

平滑重新開機

php start.php reload

檢視狀态

php start.php status

debug和daemon方式差別

1、以debug方式啟動,代碼中echo、var_dump、print等列印函數會直接輸出在終端。

2、以daemon方式啟動,代碼中echo、var_dump、print等列印會預設重定向到/dev/null檔案,可以通過設定

Worker::$stdoutFile = '/your/path/file';

來設定這個檔案路徑。

3、以debug方式啟動,終端關閉後workerman會随之關閉并退出。

4、以daemon方式啟動,終端關閉後workerman繼續背景正常運作。

繼續閱讀