PHP用proc_open新建子进程使用管道通信非阻塞执行PHP脚本

PHP用proc_open新建子进程使用管道通信非阻塞执行PHP脚本.
脚本结束时register_shutdown_function回调函数访问管道获取子进程输出的数据.

1例子1(popen): 2<?php 3function foo() { 4 echo date('Y-m-d H:i:s')."\n"; 5 echo shell_exec('php -r \'sleep(1); echo date("Y-m-d H:i:s")." by shell_exec:blocking\n";\''); //阻塞 6 $pipe1 = popen('php -r \'sleep(2); echo date("Y-m-d H:i:s")." by popen1:non-blocking\n";\'', 'r'); //非阻塞(管道) 7 $pipe2 = popen('php -r \'sleep(1); echo date("Y-m-d H:i:s")." by popen2:non-blocking\n";\'', 'r'); //非阻塞(管道) 8 echo date('Y-m-d H:i:s')."\n"; 9 register_shutdown_function(function() use ($pipe1, $pipe2) { //事件驱动(脚本结束事件),异步回调 10 echo stream_get_contents($pipe1); //输出子进程返回的数据 11 echo stream_get_contents($pipe2); //输出子进程返回的数据 12 pclose($pipe1); 13 pclose($pipe2); 14 }); 15} 16foo(); 17//输出 182016-09-11 20:25:30 192016-09-11 20:25:31 by shell_exec:blocking 202016-09-11 20:25:31 212016-09-11 20:25:33 by popen1:non-blocking 222016-09-11 20:25:32 by popen2:non-blocking 23 24例子2(proc_open): 25<?php 26function foo() { 27 $proc = proc_open( 28 //task.php 内容为 $arr = unserialize(stream_get_contents(STDIN)); $arr['time'] = date('Y-m-d H:i:s', $arr['time']); echo serialize($arr); 29 '/png/php/5.4.45/bin/php /home/eechen/task.php', 30 array( 31 0 => array('pipe','r'), //stdin (用fwrite写入数据给管道) 32 1 => array('pipe','w'), //stdout(用stream_get_contents获取管道输出) 33 2 => array('pipe','w'), //stderr(用stream_get_contents获取管道输出) 34 //2 => array('file','/tmp/err.txt','a') //stderr(写入到文件) 35 ), 36 $pipes, //管道(stdin/stdout/stderr) 37 '/tmp', //当前PHP进程的工作目录 38 array('foo' => 'bar') //php.ini 配置 variables_order = "EGPCS" 其中E表示$_ENV,否则$_ENV输出为空 39 ); 40 //var_dump($pipes); //resource of type (stream) 41 if(is_resource($proc)) { 42 //stdin 43 $stdin = serialize(array('time' => time())); 44 fwrite($pipes[0], $stdin); //把参数传给脚本task.php 45 fclose($pipes[0]); //fclose关闭管道后proc_close才能退出子进程,否则会发生死锁 46 register_shutdown_function(function() use($pipes, $proc) { //事件驱动(脚本结束事件),异步回调 47 //stdout 48 $stdout = stream_get_contents($pipes[1]); 49 fclose($pipes[1]); 50 //stderr 51 $stderr = stream_get_contents($pipes[2]); 52 fclose($pipes[2]); 53 //exit code (返回进程的终止状态码,如果发生错则返回-1) 54 $status = proc_close($proc); 55 $data = array( 56 'stdout' => $stdout, 57 'stderr' => $stderr, 58 'status' => $status, 59 ); 60 var_export($data); //echo json_encode($data); 61 }); 62 } 63} 64foo(); 65//输出: 66array ( 67 'stdout' => 'a:1:{s:4:"time";s:19:"2016-09-11 21:26:29";}', 68 'stderr' => '', 69 'status' => 0, 70)
点赞
收藏

评论区

加载中...

相关推荐

MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1

文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s

Oracle 分组与拼接字符串同时使用

SELECTT.,ROWNUMIDFROM(SELECTT.EMPLID,T.NAME,T.BU,T.REALDEPART,T.FORMATDATE,SUM(T.S0)S0,MAX(UPDATETIME)CREATETIME,LISTAGG(TOCHAR(

MySQL部分从库上面因为大量的临时表tmp_table造成慢查询

背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_

皕杰报表之UUID

​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为

手写Java HashMap源码

HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22

2020年前端实用代码段,为你的工作保驾护航

有空的时候,自己总结了几个代码段,在开发中也经常使用,谢谢。1、使用解构获取json数据let jsonData  id: 1,status: "OK",data: 'a', 'b';let  id, status, data: number   jsonData;console.log(id, status, number )

PHP用proc_open新建子进程使用管道通信非阻塞执行PHP脚本 - HelloWorld