• 技术文章 >php框架 >Workerman

    浅谈workerman中worker类的用法

    青灯夜游青灯夜游2021-02-22 17:57:36转载969
    本篇文章给大家介绍一下workerman,以及谈谈workerman中worker类的用法。有一定的参考价值,有需要的朋友可以参考一下,希望对大家有所帮助。

    相关推荐:《workerman教程

    什么是workerman?

    Workerman是一款开源高性能异步PHP socket 即时通讯框架。支持高并发,超高稳定性,被广泛的用于手机app、移动通讯,微信小程序,手游服务端、网络游戏、PHP聊天室、硬件通讯、智能家居、车联网、物联网等领域的开发。 支持TCP长连接,支持Websocket、HTTP等协议,支持自定义协议。拥有异步Mysql、异步Redis、异步Http、MQTT物联网客户端、异步消息队列等众多高性能组件。

    官网:https://www.workerman.net/

    workerman的特性

    纯PHP开发
    支持PHP多进程
    支持TCP、UDP
    支持长连接
    支持各种应用层协议
    支持高并发
    支持服务平滑重启
    支持HHVM
    支持以指定用户运行子进程
    自带监控
    支持毫秒级别定时器
    支持异步IO
    支持对象或者资源永久保持
    高性能
    支持分布式部署
    支持心跳检测

    workerman应用场景

    workerman安装

    环境要求:

    workerman从3.5.3版本开始已经能够同时支持linux系统和windows系统。

    需要PHP>=5.3.3,并配置好PHP的环境变量。

    注意 本教程 使用linux 不会讲windows 实际使用 也不推荐用 windows系统

    Linux lnmp一键安装脚本

    1、安装PHP>=5.3.3,并安装了pcntl、posix扩展 --enable-pcntl --enable-posix
    2、建议安装event或者libevent扩展,但不是必须的(注意event扩展需要PHP>=5.4)

    curl -Ss http://www.workerman.net/check.php | php

    git clone https://github.com/walkor/Workerman

    安装libevent

    yum install libevent-devel

    php版本在7以下
    wget http://pecl.php.net/get/libevent-0.1.0.tgz

    注意目前libevent扩展不支持php7,php7用户只能使用Event扩展。

    wget http://pecl.php.net/get/event-2.4.3.tgz

    解压 编译
    /user/local/php/bin/phpize
    ./configure --with-php-config=/usr/local/php/bin/php-config
    make && make install

    配置到 php.ini

    workerman目录结构


    workerman简单开发demo

    实现简单的http服务器

    require_once  'workman/Autoloader.php';
    
    use \Workerman\Worker;
    
    $http_work = new Worker('http://0.0.0.0:1111’);
    
    $http_work->onMessage = function($conn,$data){
    
            $conn->send('hello workman');
    };
    
    Worker::runAll();
    
    浏览器 访问  ip:1111  即可

    实现websocket

    ws.php

    require_once  'workman/Autoloader.php';
    use \Workerman\Worker;
    $http_work = new Worker('websocket://0.0.0.0:2222');
    $http_work->onMessage = function($conn,$data){
            $conn->send('hello workman'.$data);
    };
    Worker::runAll();
    
    
    <!DOCTYPE HTML>
    <html>
    <body>
    
    <script>
            ws = new WebSocket("ws://192.168.113.136:2222");
            ws.onopen = function(){
               ws.send('lampol');
            }
    
            ws.onmessage = function(e){
                    console.log(e.data)
            }
    
    </script>
    </body>
    </html>

    workerman原理

    Worker类

    WorkerMan中有两个重要的类Worker与Connection。
    Worker类用于实现端口的监听,并可以设置客户端连接事件、连接上消息事件、连接断开事件的回调函数,从而实现业务处理。

    $worker = new Worker($listen,$context); //实例化 返回对象

    $listen 的格式为 <协议>://<监听地址>

    <协议> 可以为以下格式:

    tcp: 例如 tcp://0.0.0.0:8686

    udp: 例如 udp://0.0.0.0:8686

    unix: 例如 unix:///tmp/my_file (需要Workerman>=3.2.7)

    http: 例如 http://0.0.0.0:80

    websocket: 例如 websocket://0.0.0.0:8686

    text: 例如 text://0.0.0.0:8686 (text是Workerman内置的文本协议,兼容telnet,详情参见附录Text协议部分)

    $context 用于传递socket的上下文选项

    Worker类属性

    count

    设置当前Worker实例启动多少个进程,不设置时默认为1。

    此属性必须在Worker::runAll();运行前设置才有效。windows系统不支持此特性。

    进程数设置依据:

    1、cpu核数

    2、内存大小

    3、业务偏向IO密集还是CPU密集型

    不清楚自己业务偏向于哪种类型,可设置进程数为CPU核数的2倍左右即可。

    lscpu top  1 查看cpu核数

    id

    当前worker进程的id编号,范围为0到$worker->count-1。进程重启后id编号值是不变的。

    name

    设置当前Worker实例的名称,方便运行status命令时识别进程。不设置时默认为none。

    protocol
    设置当前Worker实例的协议类。

    transport
    设置当前Worker实例所使用的传输层协议,目前只支持3种(tcp、udp、ssl)。不设置默认为tcp。

    daemonize
    此属性为全局静态属性,表示是否以daemon(守护进程)方式运行。如果启动命令使用了 -d参数,则该属性会自动设置为true。也可以代码中手动设置。

    logFile

    用来指定workerman日志文件位置。此文件记录了workerman自身相关的日志,包括启动、停止等。
    Worker::$logFile = '/tmp/workerman.log’;

    stdoutFile

    此属性为全局静态属性,如果以守护进程方式(-d启动)运行,则所有向终端的输出(echo var_dump等)都会被重定向到stdoutFile指定的文件中。
    Worker::$stdoutFile = 'test.log’;

    pidFile
    如果无特殊需要,建议不要设置此属性
    Worker::$pidFile = '/var/run/workerman.pid’;

    user
    设置当前Worker实例以哪个用户运行。此属性只有当前用户为root时才能生效。不设置时默认以当前用户运行。
    建议$user设置权限较低的用户,例如www-data、apache、nobody等。

    connections

    array(id=>connection, id=>connection, ...)
    此属性中存储了当前进程的所有的客户端连接对象,其中id为connection的id编号

    reloadable
    设置当前Worker实例是否可以reload,即收到reload信号后是否退出重启。不设置默认为true,收到reload信号后自动重启进程。

    reusePort

    设置当前worker是否开启监听端口复用(socket的SO_REUSEPORT选项),默认为false,不开启。

    globalEvent
    此属性为全局静态属性,为全局的eventloop实例,可以向其注册文件描述符的读写事件或者信号事件。

    Worker类回调属性


    onWorkerStart

    设置Worker子进程启动时的回调函数,每个子进程启动时都会执行。

    回掉函数参数 $worker Worker 对象

    $worker->onWorkerStart = function($worker){
         //代码
    };
    
    $worker->onWorkerStart = 'test’;
    function test($worker){
            echo 'hhhhh';
    }

    onConnect

    当客户端与Workerman建立连接时(TCP三次握手完成后)触发的回调函数。每个连接只会触发一次onConnect回调。

    回调函数的参数

    $connection

    连接对象,即TcpConnection实例,用于操作客户端连接,如发送数据,关闭连接等

    $worker->onConnect = function($connection){
            echo 'new connect....'.$connection->getRemoteIp();
    };

    onMessage

    当客户端通过连接发来数据时(Workerman收到数据时)触发的回调函数

    回调函数的参数

    $connection
    连接对象,即TcpConnection实例,用于操作客户端连接,如发送数据,关闭连接等

    $data
    客户端连接上发来的数据,如果Worker指定了协议,则$data是对应协议decode(解码)了的数据

    $worker->onMessage = function($connection,$data){
            echo $data;
            $connection->send('hello '.$data.PHP_EOL);
    };

    onClose

    当客户端连接与Workerman断开时触发的回调函数。不管连接是如何断开的,只要断开就会触发onClose。每个连接只会触发一次onClose。由于断网或者断电等极端情况断开的连接 ,也就无法及时触发onClose,这种情况需要通过应用层心跳来解决

    $worker->onClose = function($connection){
            echo 'connection close';
    };

    onError
    当客户端的连接上发生错误时触发。

    目前错误类型有

    1、调用Connection::send由于客户端连接断开导致的失败(紧接着会触发onClose回调) (code:WORKERMAN_SEND_FAIL msg:client closed)

    2、在触发onBufferFull后(发送缓冲区已满),仍然调用Connection::send,并且发送缓冲区仍然是满的状态导致发送失败(不会触发onClose回调)(code:WORKERMAN_SEND_FAIL msg:send buffer full and drop package)

    3、使用AsyncTcpConnection异步连接失败时(紧接着会触发onClose回调) (code:WORKERMAN_CONNECT_FAIL msg:stream_socket_client返回的错误消息)

    onWorkerReload

    此特性不常用到。

    设置Worker收到reload信号后执行的回调。

    可以利用onWorkerReload回调做很多事情,例如在不需要重启进程的情况下重新加载业务配置文件。

    onBufferFull

    每个连接都有一个单独的应用层发送缓冲区,如果客户端接收速度小于服务端发送速度,数据会在应用层缓冲区暂存,如果缓冲区满则会触发onBufferFull回调。

    缓冲区大为TcpConnection::$maxSendBufferSize,默认值为1MB,可以为当前连接动态设置缓冲区大小例

    onBufferDrain

    每个连接都有一个单独的应用层发送缓冲区,缓冲区大小由TcpConnection::$maxSendBufferSize决定,默认值为1MB,可以手动设置更改大小,更改后会对所有连接生效。

    Worker类接口方法

    runAll

    运行所有Worker实例。

    Worker::runAll()执行后将永久阻塞,也就是说位于Worker::runAll()后面的代码将不会被执行。所有Worker实例化应该都在Worker::runAll()前进行。

    stopAll

    停止当前进程(子进程)的所有Worker实例并退出。
    此方法用于安全退出当前子进程,作用相当于调用exit/die退出当前子进程。

    listen

    用于实例化Worker后执行监听。


    Worker类代码流程分析

    public function __construct($socket_name = '', $context_option = array())
    
    public static function runAll()
    {
        static::checkSapiEnv();     //检测命令行模式
        static::init();                      //初始化日志 pid  workid…
        static::lock();                     //启动文件 加锁 独占锁
        static::parseCommand();  //解析命令  start   stop  restart  …
        static::daemonize();          //守护进程运行
        static::initWorkers();          //初始化 所有worker 实例
        static::installSignal();         //安装信号
        static::saveMasterPid();    //保存主进程id
        static::unlock();                  //解锁
        static::displayUI();              //展示UI
        static::forkWorkers();          //fork 进程
        static::resetStd();                //重置输入输出
        static::monitorWorkers();    //主进程监控各个worker的状态
    }

    SAPI(Server Application Programming Interface)服务器应用程序编程接口,即PHP与其他应用交互的接口,PHP脚本要执行有很多方式,通过Web服务器,或者直接在命令行下,也可以嵌入在其他程序中。

    常见的SAPI有:cgi、fast-cgi、cli、apache模块的DLL、isapi

    Linux 常用SIG信号及其键值

    01 SIGHUP 挂起(hangup)
    02 SIGINT 中断,当用户从键盘按^c键或^break键时
    03 SIGQUIT 退出,当用户从键盘按quit键时
    04 SIGILL 非法指令
    05 SIGTRAP 跟踪陷阱(trace trap),启动进程,跟踪代码的执行
    06 SIGIOT IOT指令
    07 SIGEMT EMT指令
    08 SIGFPE 浮点运算溢出
    09 SIGKILL 杀死、终止进程
    10 SIGBUS 总线错误
    11 SIGSEGV 段违例(segmentation violation),进程试图去访问其虚地址空间以外的位置
    12 SIGSYS 系统调用中参数错,如系统调用号非法
    13 SIGPIPE 向某个非读管道中写入数据
    14 SIGALRM 闹钟。当某进程希望在某时间后接收信号时发此信号
    15 SIGTERM 软件终止(software termination)
    16 SIGUSR1 用户自定义信号1
    17 SIGUSR2 用户自定义信号2
    18 SIGCLD 某个子进程死

    更多计算机编程相关知识,请访问:编程视频!!

    以上就是浅谈workerman中worker类的用法的详细内容,更多请关注php中文网其它相关文章!

    声明:本文转载于:csdn,如有侵犯,请联系admin@php.cn删除
    专题推荐:workerman worker类
    上一篇:workerman怎么设置开机重启自启动(linux环境) 下一篇:谈谈利用workerman实现即时聊天功能的方法
    大前端线上培训班

    相关文章推荐

    • Workerman中你不得不知道的属性reusePort• workerman如何搭配tp• workerman需要安装吗• workerman无法使用怎么办• workerman无法正常访问

    全部评论我要评论

  • 取消发布评论发送
  • 1/1

    PHP中文网