自定义进程
支持开发者创建一些特殊的工作进程,用于监控、上报或者其他特殊的任务,参考addProcess。
创建Proccess类,实现CustomProcessInterface接口。
namespace App\Processes;
use App\Tasks\TestTask;
use Hhxsv5\LaravelS\Swoole\Process\CustomProcessInterface;
use Hhxsv5\LaravelS\Swoole\Task\Task;
use Swoole\Coroutine;
use Swoole\Http\Server;
use Swoole\Process;
class TestProcess implements CustomProcessInterface
{
/**
* @var bool 退出标记,用于Reload更新
*/
private static $quit = false;
public static function callback(Server $swoole, Process $process)
{
// 进程运行的代码,不能退出,一旦退出Manager进程会自动再次创建该进程。
while (!self::$quit) {
\Log::info('Test process: running');
// sleep(1); // Swoole < 2.1
Coroutine::sleep(1); // Swoole>=2.1 已自动为callback()方法创建了协程并启用了协程Runtime。
// 自定义进程中也可以投递Task,但不支持Task的finish()回调。
// 注意:修改config/laravels.php,配置task_ipc_mode为1或2,参考 https://wiki.swoole.com/#/server/setting?id=task_ipc_mode
$ret = Task::deliver(new TestTask('task data'));
var_dump($ret);
// 上层会捕获callback中抛出的异常,并记录到Swoole日志,然后此进程会退出,3秒后Manager进程会重新创建进程,所以需要开发者自行try/catch捕获异常,避免频繁创建进程。
// throw new \Exception('an exception');
}
}
// 要求:LaravelS >= v3.4.0 并且 callback() 必须是异步非阻塞程序。
public static function onReload(Server $swoole, Process $process)
{
// Stop the process...
// Then end process
\Log::info('Test process: reloading');
self::$quit = true;
// $process->exit(0); // 强制退出进程
}
// 要求:LaravelS >= v3.7.4 并且 callback() 必须是异步非阻塞程序。
public static function onStop(Server $swoole, Process $process)
{
// Stop the process...
// Then end process
\Log::info('Test process: stopping');
self::$quit = true;
// $process->exit(0); // 强制退出进程
}
}
注册TestProcess。
// 修改文件 config/laravels.php
// ...
'processes' => [
'test' => [ // Key为进程名
'class' => \App\Processes\TestProcess::class,
'redirect' => false, // 是否重定向输入输出
'pipe' => 0, // 管道类型:0不创建管道,1创建SOCK_STREAM类型管道,2创建SOCK_DGRAM类型管道
'enable' => true, // 是否启用,默认true
//'queue' => [ // 启用消息队列作为进程间通信,配置空数组表示使用默认参数
// 'msg_key' => 0, // 消息队列的KEY,默认会使用ftok(__FILE__, 1)
// 'mode' => 2, // 通信模式,默认为2,表示争抢模式
// 'capacity' => 8192, // 单个消息长度,长度受限于操作系统内核参数的限制,默认为8192,最大不超过65536
//],
//'restart_interval' => 5, // 进程异常退出后需等待多少秒再重启,默认5秒
],
],
注意:callback()方法不能退出,如果退出,Manager进程将会重新创建进程。
示例:向自定义进程中写数据。
// config/laravels.php
'processes' => [
'test' => [
'class' => \App\Processes\TestProcess::class,
'redirect' => false,
'pipe' => 1,
],
],
// app/Processes/TestProcess.php
public static function callback(Server $swoole, Process $process)
{
while ($data = $process->read()) {
\Log::info('TestProcess: read data', [$data]);
$process->write('TestProcess: ' . $data);
}
}
// app/Http/Controllers/TestController.php
public function testProcessWrite()
{
/**@var \Swoole\Process $process */
$process = app('swoole')->customProcesses['test'];
$process->write('TestController: write data' . time());
var_dump($process->read());
}