swoole中需按单进程、自定义进程、进程池、task模块四类场景区分管理:单进程须手动调用$proc->exit()和swoole_process::wait();自定义进程必须通过addprocess()注入server生命周期;进程池用于常驻多进程调度,不兼容server addprocess();taskworker适用于i/o密集型任务,由底层自动回收。

在Swoole中正确管理进程,避免僵尸进程堆积、子进程意外退出无人接管、主服务停止时子进程残留等问题,必须区分单进程、自定义进程、进程池和Task模块四类使用场景,不能混用生命周期控制方式。
单个Swoole\Process的创建与回收
直接实例化Swoole\Process时,子进程与父进程完全解耦,必须手动回收,否则立即变成僵尸进程。
第一步:用匿名函数定义子进程逻辑,注意【不能在回调内直接exit()或die()】,必须调用$worker->exit()。
第二步:调用$process->start()获取PID,此时子进程已启动,但父进程若不等待或监听,会立刻退出并遗弃子进程。
第三步:在父进程中调用swoole_process::wait()阻塞等待——这只能回收一个子进程;若需非阻塞回收,必须配合pcntl_signal(SIGCHLD, ...) + swoole_process::wait(false)组合使用。
这一步操作起来很简单,直接把文件拖进去就行。但漏掉signal注册或wait调用,5秒后就能在ps aux | grep defunct里看到僵尸进程。
将自定义进程接入Swoole Server生命周期
当Swoole\Http\Server或Swoole\WebSocket\Server已存在时,所有后台任务进程必须通过addProcess()注入,否则server->shutdown()时子进程不会被终止。
方法一:传入Swoole\Process对象实例
$http = new Swoole\Http\Server("0.0.0.0", 9501);
$taskProc = new Swoole\Process(function($proc) { while(true) { // 消费消息 sleep(3); } });
$http->addProcess($taskProc); // 关键:必须走这一步
方法二:使用闭包快捷注册(Swoole ≥ 4.8.0)
$http->addProcess(new Swoole\Process(function($proc) {
while(true) {
$proc->write("tick\n");
sleep(1);
}
}));
【addProcess()必须在$http->start()之前调用】,否则进程不会被纳入管理,SIGTERM信号也无法触达。
Swoole 6.1.1 是一个专为 PHP 设计的高性能事件驱动并发网络引擎。作为稳定版,它修复了编译时对 zlib 依赖的缺失及 curl 模块的内存安全风险。该版本支持协程、多线程与多进程架构,内置 TCP/HTTP/WebSocket 服务器,能够显著提升 PHP 在微服务、实时通信等场景下的执行效率与并发能力。
用进程池管理器统一调度多工作进程
适用于需要固定数量常驻子进程、支持自动拉起、信号重启、任务投递的场景,比如日志归档、定时清理、消息广播。
① 创建PoolsManager实例,指定worker数
② 调用addProcess()注册每个子进程类,传入完整命名空间路径
③ 在子进程类的run()方法中写死循环逻辑,不要sleep(0)或空耗CPU
④ 启动后发送kill -USR2 $MASTER_PID可触发全部worker逐个重启
注意:进程池不兼容Swoole Server的addProcess(),二者不可嵌套使用。若已在HTTP Server中运行,应改用TaskWorker机制替代。
用TaskWorker实现I/O密集型任务异步卸载
当任务本身不耗CPU但需等待数据库、Redis、HTTP响应时,优先选TaskWorker而非Process,因协程+Task更轻量且自动回收。
设置task_worker_num参数启用Task机制
在onReceive或onMessage中调用$server->task($data)投递
在onTask回调中执行实际逻辑,完成后调用$server->finish($result)
无需关心PID、管道、信号、wait——这些全部由Swoole底层封装处理。










