Swoole服务需通过信号机制实现优雅关闭与热重启。发送SIGTERM使主进程停止新连接、等待旧连接完成、关闭监听并调用onShutdown;发送USR1可逐个重启worker,保持连接不中断;验证需检查主进程退出、端口释放及新实例状态正常。

在Swoole中实现服务的优雅关闭与重启,是保障线上接口零中断、连接不丢包、定时任务不跳过的核心运维动作。直接 kill -9 会导致正在处理的HTTP请求被强行切断、WebSocket客户端异常断连、协程上下文丢失、未flush的日志丢失,必须通过信号机制触发内置生命周期管理。
确认服务运行模式与进程结构
执行 ps aux | grep swoole 查看主进程PID及子进程树,确认是否启用 daemonize => true;若为守护进程,需通过 master_pid 文件或 swoole_process::pid() 获取主进程ID,【不可直接 kill -15 所有匹配进程,否则可能误杀日志轮转子进程】。
检查 swoole_server->stats() 或 swoole_server->getSocket() 输出,确认当前无 worker_num 为0或 reload 状态卡死的情况——这类状态会阻塞后续所有信号响应。
发送优雅关闭信号(SIGTERM)
向主进程PID发送 SIGTERM:kill -TERM {master_pid}。
此时 Swoole 会自动:停止接受新连接 → 等待所有已建立连接完成读写 → 关闭监听socket → 释放协程栈 → 调用 onShutdown 回调 → 终止所有worker和task进程。这一步耗时取决于最长存活连接的生命周期,【若设置了 max_request 或 reload_async,需确保其值大于当前最大并发连接数,否则可能提前触发强制回收】。
热重启服务(不中断连接)
方法一:使用 reload 命令(推荐)
执行 kill -USR1 {master_pid},Swoole 主进程收到 USR1 后逐个重启 worker 进程,每个 worker 在处理完当前请求后退出并由 master 拉起新实例,客户端连接不受影响。
方法二:通过 Manager 进程控制
在代码中调用 $server->reload(),适用于需要动态判断条件后再触发重启的场景,例如配置变更检测后自动 reload;注意该方法仅在 manager 进程中有效,worker 进程内调用无效。
Swoole 6.1.1 是一个专为 PHP 设计的高性能事件驱动并发网络引擎。作为稳定版,它修复了编译时对 zlib 依赖的缺失及 curl 模块的内存安全风险。该版本支持协程、多线程与多进程架构,内置 TCP/HTTP/WebSocket 服务器,能够显著提升 PHP 在微服务、实时通信等场景下的执行效率与并发能力。
方法三:配合 inotifywait 实现配置热加载
监听 config/ 目录变化,当检测到 PHP 配置文件修改,执行 kill -USR1 $(cat /tmp/swoole.pid);需提前在启动脚本中写入 file_put_contents('/tmp/swoole.pid', getmypid())。
验证关闭与重启结果
第一步:检查主进程是否退出
执行 kill -0 {master_pid} 2>/dev/null || echo "已退出",返回非零码表示主进程终止成功。
第二步:确认端口释放
执行 lsof -i :{port} | grep LISTEN,无输出即表示监听端口已释放。
第三步:启动新实例并校验状态
执行启动命令(如 php server.php start),随后立即访问 http://127.0.0.1:{port}/health 或调用 $server->stats(),确认 start_time 为新时间戳、connection_num 从0开始增长,且 worker_status 全部为 idle。

















