小男孩‘自慰网亚洲一区二区,亚洲一级在线播放毛片,亚洲中文字幕av每天更新,黄aⅴ永久免费无码,91成人午夜在线精品,色网站免费在线观看,亚洲欧洲wwwww在线观看

分享

【Swoole系列6.3】Hyperf 運(yùn)行各種網(wǎng)絡(luò)服務(wù)

 硬核項(xiàng)目經(jīng)理 2022-09-26 發(fā)布于湖南

Hyperf 運(yùn)行各種網(wǎng)絡(luò)服務(wù)

簡(jiǎn)單地運(yùn)行起普通的 HTTP 服務(wù)之后,今天我們?cè)賮?lái)學(xué)習(xí)一下如何使用 Hyperf 運(yùn)行 TCP/UDP 以及 WebSocket 服務(wù)。

之前我們通過(guò)普通的 Swoole 都已經(jīng)搭建起過(guò)這些服務(wù),其實(shí)和 HTTP 服務(wù)都差不多,只是修改一些參數(shù)或者監(jiān)聽的事件而已。在框架中,實(shí)現(xiàn)這些服務(wù)也是類似的,而且會(huì)更加簡(jiǎn)單,只需要進(jìn)行一些簡(jiǎn)單的配置并給上監(jiān)聽事件的對(duì)象方法即可。畢竟原理都是相通的。

TCP/UDP

在上一篇文章的學(xué)習(xí)中,我們其實(shí)就接觸過(guò)一個(gè)配置文件,那就是 config/autoload/server.php 這個(gè)配置文件。當(dāng)時(shí)我們是為了配置模板 View 對(duì)它下面兩個(gè)參數(shù)的內(nèi)容進(jìn)行了配置,不知道大家有沒有看這個(gè)文件的另一個(gè)參數(shù)數(shù)組 servers。

'servers' => [
    [
        'name' => 'http',
        'type' => Server::SERVER_HTTP,
        'host' => '0.0.0.0',
        'port' => 9501,
        'sock_type' => SWOOLE_SOCK_TCP,
        'callbacks' => [
            Event::ON_REQUEST => [Hyperf\HttpServer\Server::class, 'onRequest'],
        ],
    ],
],

看出來(lái)什么端倪了嗎?這就是一個(gè)服務(wù)配置呀。既然是這樣的話,那么我們能不能通過(guò)它來(lái)配置其它的服務(wù)類型呢?當(dāng)然是沒問(wèn)題的。

[
    'name' => 'tcp',
    'type' => Server::SERVER_BASE,
    'host' => '0.0.0.0',
    'port' => 9502,
    'sock_type' => SWOOLE_SOCK_TCP,
    'callbacks' => [
        Event::ON_RECEIVE => [\App\Controller\TcpServer::class, 'onReceive'],
        Event::ON_CLOSE => [\App\Controller\TcpServer::class, 'onClose'],
    ],
],
[
    'name' => 'udp',
    'type' => Server::SERVER_BASE,
    'host' => '0.0.0.0',
    'port' => 9503,
    'sock_type' => SWOOLE_SOCK_UDP,
    'callbacks' => [
        Event::ON_PACKET => [\App\Controller\UdpServer::class, 'onPacket'],
    ],
],

我們添加了兩個(gè)配置,分別就是 TCP 和 UDP 服務(wù)的配置,它們使用的 type 類型都是 Server::SERVER_BASE ,但 sock_type 則分別使用的是 SWOOLE_SOCK_TCP 和 SWOOLE_SOCK_UDP 。然后分別監(jiān)聽 9502 和 9503 兩個(gè)端口,并且去指定不同的事件回調(diào)方法。注意,這里的 callbacks 中的事件回調(diào)類和方法不是框架默認(rèn)的,是我們自定義的。

// app/Controller/TcpServer.php
namespace App\Controller;

use Swoole\Coroutine\Server\Connection;
use Swoole\Server as SwooleServer;

class TcpServer implements \Hyperf\Contract\OnReceiveInterface
{

    /**
     * @inheritDoc
     */

    public function onReceive($server, int $fd, int $reactorId, string $data)void
    
{
        $server->send($fd, 'recv:' . $data);
    }

    public function onClose($server, int $fd, int $reactorId){
        echo '連接關(guān)閉:' . $fd . ',' . $reactorId;
    }
}

// app/Controller/UdpServer.php
namespace App\Controller;

use Swoole\WebSocket\Server;

class UdpServer implements \Hyperf\Contract\OnPacketInterface
{

    /**
     * @inheritDoc
     */

    public function onPacket($server, $data, $clientInfo)void
    
{
        var_dump($clientInfo);
        $server->sendto($clientInfo['address'], $clientInfo['port'], 'Server:' . $data);
    }
}

只要是跟我們之前一起學(xué)習(xí)過(guò)普通 Swoole 搭建這些服務(wù)的同學(xué),對(duì)這一塊應(yīng)該不會(huì)很難理解。當(dāng)時(shí)我們是直接將事件監(jiān)聽及操作寫在回調(diào)函數(shù)中,而在這里,在框架中,則是通過(guò) callbacks 這個(gè)回調(diào)數(shù)組的方式配置到配置文件中,然后當(dāng)服務(wù)監(jiān)聽這些程序的時(shí)候,再將對(duì)應(yīng)的監(jiān)聽類的方法傳遞給事件監(jiān)聽函數(shù)。

好了,現(xiàn)在運(yùn)行起服務(wù)之后,你會(huì)發(fā)現(xiàn) Hyperf 框架可以同時(shí)監(jiān)聽多個(gè)端口,之前我們的 HTTP 端口是可以正常訪問(wèn)的,同時(shí),這些新定義的 TCP/UDP 服務(wù)也是沒問(wèn)題的。命令行中,我們也可以看到下面這樣的信息表示監(jiān)聽端口開啟。

剩下的,不管你是用 telnet/nc 命令,還是用之前我們寫過(guò)的客戶端程序,都可以進(jìn)行測(cè)試?yán)病?/p>

WebSocet

使用 Hyperf 的 WebSocket 客戶端是需要額外的組件的,我們可以通過(guò) Composer 來(lái)進(jìn)行安裝。

composer require hyperf/websocket-server

安裝完成后,就可以去配置服務(wù)了,依然還是在 config/autoload/server.php 中。

[
    'name' => 'ws',
    'type' => Server::SERVER_WEBSOCKET,
    'host' => '0.0.0.0',
    'port' => 9504,
    'sock_type' => SWOOLE_SOCK_TCP,
    'callbacks' => [
        Event::ON_HAND_SHAKE => [Hyperf\WebSocketServer\Server::class, 'onHandShake'],
        Event::ON_MESSAGE => [Hyperf\WebSocketServer\Server::class, 'onMessage'],
        Event::ON_CLOSE => [Hyperf\WebSocketServer\Server::class, 'onClose'],
    ],
],

然后,我們就可以創(chuàng)建相關(guān)的控制器,注意,WebSocket 使用的事件監(jiān)聽程序是組件自帶的,但是真實(shí)到達(dá)的控制器,還是需要我們實(shí)現(xiàn)的,這個(gè)服務(wù)其實(shí)和 HTTP 是很類似的。

namespace App\Controller;

use Swoole\Http\Request;
use Swoole\Http\Response;
use Swoole\WebSocket\Frame;
use Swoole\WebSocket\Server;

class WebSocketController implements \Hyperf\Contract\OnMessageInterface, \Hyperf\Contract\OnCloseInterface, \Hyperf\Contract\OnOpenInterface
{

    public function onMessage($server, Frame $frame)void
    
{
        $server->push($frame->fd, 'Recv: ' . $frame->data);
    }

    public function onClose($server, int $fd, int $reactorId)void
    
{
        var_dump('closed');
    }

    public function onOpen($server, Request $request)void
    
{
        $server->push($request->fd, 'Opened');
    }
}

控制器中實(shí)現(xiàn)對(duì)應(yīng)的接口及方法,然后我們就去定義路由。

Router::addServer('ws'function () {
    Router::get('/''App\Controller\WebSocketController');
});

這個(gè)路由的方法是 addServer() ,可以看做是增加一個(gè) ws 協(xié)議的服務(wù)路由組。然后指定的是我們之前定義好的那個(gè)控制器。

最后,沒別的多說(shuō)的了吧,重新啟動(dòng)服務(wù),你會(huì)看到現(xiàn)在我們的服務(wù)程序已經(jīng)監(jiān)聽了 4 個(gè)端口了,并且也可以直接使用之前我們?cè)?span> 【Swoole系列2.4】WebSocket服務(wù)https://mp.weixin.qq.com/s/-w-48E3xXEpC3fezpqd4-Q 中的那個(gè)靜態(tài)頁(yè)來(lái)測(cè)試我們的 WebSocket 服務(wù)了。

總結(jié)

是不是總體感覺來(lái)看是要比純手寫 Swoole 的這些服務(wù)更方便一些呀。畢竟框架走了一層封裝之后還是讓我們能更容易去使用這些服務(wù)了。如果你在日常工作中有這方面的需求,那還是需要更深入地去官方文檔中進(jìn)行更加詳細(xì)的學(xué)習(xí)。

測(cè)試代碼:

https://github.com/zhangyue0503/swoole/tree/main/6.%E6%A1%86%E6%9E%B6/hyperf-skeleton

參考文檔:

https:///2.2/#/zh-cn/tcp-server

https:///2.2/#/zh-cn/websocket-server

    轉(zhuǎn)藏 分享 獻(xiàn)花(0

    0條評(píng)論

    發(fā)表

    請(qǐng)遵守用戶 評(píng)論公約

    類似文章 更多