IT博客汇
  • 首页
  • 精华
  • 技术
  • 设计
  • 资讯
  • 扯淡
  • 权利声明
  • 登录 注册

    PHP CLI模式下PCNTL扩展实现多进程服务

    mckee发表于 2015-06-15 00:12:47
    love 0

    PHP可通过PCNTL扩展实现进程控制,如进程创建,信号处理,进程中断判断等。但只能在CLI模式下操作。
    PCNTL的信号机制是基于 ticks 机制实现的。因此在使用信号相关函数时需要在前面添加declare(ticks = n) 语法结构。
    pcntl_alarm ( int $seconds )指定秒数后向进程发送一个 SIGALRM 信号
    pcntl_signal ( int $signo , callback $handler [, bool $restart_syscalls ])给指定信号$signo设置回调函数

    declare(ticks = 1);
    
    function signal_handler($signal) {
        print "Caught SIGALRM\n";
        pcntl_alarm(3);
    }
    
    pcntl_signal(SIGALRM, "signal_handler", true);
    pcntl_alarm(3);
    
    for(;;) {
    }

    pcntl_exec ( string $path [, array $args [, array $envs ]] )执行指定命令,执行完即结束,后面将不会执行
    $dir = '/root/';
    $cmd = 'ls';
    $option = '-l';
    $pathtobin = '/bin/ls';
    
    $arg = array($cmd, $option, $dir);
    pcntl_exec($pathtobin, $arg);
    
    echo 'will not exec here';

    pcntl_fork ( void )为当前进程fork子进程
    此时,父进程执行过程中,得到的fork返回值为子进程号(>0),失败时,在 父进程上下文返回-1,不会创建子进程,并且会引发一个PHP错误;
    父进程的阻塞同时会阻塞子进程。但是父进程的结束不影响子进程的运行;
    子进程会从执行pcntl_fork()的那条语句开始执行(包括此函数),但是此时它返回的是零(代表这是一个子进程)。在子进程的代码块中最好有exit语句,即执行完子进程后立即就结束。
    int pcntl_wait ( int &$status [, int $options = 0 ] ) 等待或返回fork的子进程状态
    说明子进程调用结束后,并没有完全销毁,而是变成了僵尸进程,不占内存,仅存在进程列表。此时需要调用父进程调用wait来等待子进程结束。如果父进程在子进程前退出了,那么init进程将会对僵尸进程进行管理,它还是可以被清除的。第二个参数可设置阻塞方式:
    1. WUNTRACED 阻塞方式调用的,函数返回值为子进程的pid,如果没有子进程返回值为-1;
    2. WNOHANG 非阻塞方式调用,函数还可以在有子进程在运行但没有结束的子进程时返回0。
    $pid  =  pcntl_fork ();
    //父进程和子进程都会执行下面代码
    if ( $pid  == -1 ) {
        //错误处理:创建子进程失败时返回-1.
        die( 'could not fork' );
    } else if ( $pid ) {
        //父进程会得到子进程号,所以这里是父进程执行的逻辑
        pcntl_wait ($status, WUNTRACED);  //等待子进程中断,防止子进程成为僵尸进程。
        echo "ok".PHP_EOL;
    } else if ($pid == 0){
        //子进程得到的$pid为0, 所以这里是子进程执行的逻辑。
        echo "子进程运行" . getmypid() .PHP_EOL;
        sleep(5);
        exit;
    }
    
    echo "父进程运行" . getmypid() .PHP_EOL;

    参考资料:
    • PHP手册
    • http://www.hdj.me/php-multithread
    • http://blog.csdn.net/lgg201/article/details/5809994



沪ICP备19023445号-2号
友情链接