Swoole 关于 HTTP SERVER 的事件顺序
来源:互联网 发布:苹果手机越狱软件 编辑:程序博客网 时间:2024/05/21 02:22
最近想把 swoole 整合到框架里面, 做了些测试, 这次测试 HTTP Server 使用到的主要事件触发顺序
测试使用的版本 Swoole 2.0.7 , PHP 7.1.2
下面是完整的测试代码:
/** * Author: ZHOUZ * Blog: http://blog.csdn.net/zhouzme * Time: 2017-04-05 15:22 */function server(){ $server = new Swoole\Http\Server("0.0.0.0", 9501); $server->set(array( 'worker_num' => 2, 'daemonize' => false, )); // worker 中的 ManagerStart | WorkerStart 事件是并发执行的, 不一定按顺序来 // ManagerStart 可能在 WorkerStart 之后执行 // 服务器启动时执行一次 $server->on('Start', function (\Swoole\Http\Server $server) { echo PHP_EOL . PHP_EOL . 'Start: http://blog.csdn.net/zhouzme' . PHP_EOL . PHP_EOL; }); // 服务器启动时执行一次 $server->on('ManagerStart', function (\Swoole\Http\Server $server) { echo 'ManagerStart: ' . PHP_EOL . PHP_EOL; }); // 每个 Worker 进程启动或重启时都会执行 $server->on('WorkerStart', function (\Swoole\Http\Server $server, int $workerId) { echo 'WorkerStart: ' . PHP_EOL . PHP_EOL; echo ' Worker ID: ' . $workerId . PHP_EOL . PHP_EOL; }); // 每次连接时(相当于每个浏览器第一次打开页面时)执行一次, reload 时连接不会断开, 也就不会再次触发该事件 $server->on('Connect', function (\Swoole\Http\Server $server, int $fd, int $reactorId) { echo 'Connect: ' . PHP_EOL . PHP_EOL; echo ' Worker ID: '. $server->worker_id . PHP_EOL . PHP_EOL; echo ' fd: ' . $fd . ' , reactorId: ' . $reactorId . PHP_EOL . PHP_EOL; }); // 浏览器连接服务器后, 页面上的每个请求均会执行一次, // 每次打开链接页面默认都是接收两个请求, 一个是正常的数据请求, 一个 favicon.ico 的请求 $server->on('Request', function (\Swoole\Http\Request $request, \Swoole\Http\Response $response) use ($server) { echo 'Request: ' . PHP_EOL . PHP_EOL; echo ' Worker ID: '. $server->worker_id . PHP_EOL . PHP_EOL; echo ' URL: ' . ($request->server['request_uri'] ?? '') . PHP_EOL . PHP_EOL; // 通过链接参数热重载 worker 进程观察触发事件 $act = $request->get['act'] ?? ''; if ($act == 'reload') { echo ' ... Swoole Reloading ! ... ' . PHP_EOL . PHP_EOL; // 触发 reload 之后, 貌似后面的代码也还是会执行的 $server->reload(); echo ' ... Under Reload ! ... ' . PHP_EOL . PHP_EOL; // 看看 reload 时是否会执行后续的代码 } elseif ($act == 'exit') { // 直接立即终止当前 worker 进程, 和 reload 的效果比较相似, 新的 worker 进程的 ID 和原来的一样 // 所以程序内部应该尽量避免使用 exit 而应该抛出异常在外部 catch echo ' ... Swoole Exit ! ... ' . PHP_EOL . PHP_EOL; exit; } elseif ($act == 'shutdown') { // 直接立即终止当前 worker 进程, 和 reload 的效果比较相似, 新的 worker 进程的 ID 和原来的一样 // 所以程序内部应该尽量避免使用 exit 而应该抛出异常在外部 catch echo ' ... Swoole Shutdown ! ... ' . PHP_EOL . PHP_EOL; $server->shutdown(); echo ' ... After Swoole Shutdown ! ... ' . PHP_EOL . PHP_EOL; } $response->header("X-Server", "Swoole"); $msg = 'hello swoole !'; $response->end($msg); }); // 每个浏览器连接关闭时执行一次, reload 时连接不会断开, 也就不会触发该事件 $server->on('Close', function (\Swoole\Http\Server $server, int $fd, int $reactorId) { echo 'Close: ' . PHP_EOL . PHP_EOL; echo ' fd: '. $fd .' , reactorId: ' . $reactorId . PHP_EOL . PHP_EOL; }); // 每个 Worker 进程退出或重启时执行一次 $server->on('WorkerStop', function (\Swoole\Http\Server $server, int $workerId) { echo 'WorkerStop' . PHP_EOL . PHP_EOL; echo ' Worker ID:' . $workerId . PHP_EOL . PHP_EOL; }); // 服务器关闭时执行一次 $server->on('Shutdown', function (\Swoole\Http\Server $server) { echo 'Shutdown: ' . PHP_EOL . PHP_EOL; }); // 当 worker_num 为 1 时, 服务器启动会生成 3 个进程 // 一个 master 主进程, 一个 manager 管理进程, 一个 worker 进程 $server->start();}server();
总结下事件顺序:
server -> Start
server -> ManagerStart ; WorkerStart ; 并发处理进入 worker 进程事件循环
等待客户端连接…worker -> Connect
worker -> Request
worker -> Close 连接超时则关闭连接, 重启时不会触发exit|die 或 reload 重启 worker 进程
server -> WorkerStop
server -> WorkerStartworker -> Connect 若当前已连接则不会再触发该事件
worker -> Request
worker -> Close 连接超时则关闭连接, 否则不触发关闭服务器
server -> WorkerStop
server -> Shutdown
测试列子的输出结果:
启动 -> 请求连接 -> 重启 -> exit -> shutdown
[root@localhost swoole]# php http.php
Start: http://blog.csdn.net/zhouzme
WorkerStart:
Worker ID: 0
ManagerStart:
WorkerStart:
Worker ID: 1
Connect:
Worker ID: 0fd: 1 , reactorId: 0
Request:
Worker ID: 0URL: /
Request:
Worker ID: 0URL: /favicon.ico
Connect:
Worker ID: 1fd: 2 , reactorId: 1
Request:
Worker ID: 1URL: /
Request:
Worker ID: 1URL: /favicon.ico
Close:
fd: 1 , reactorId: 0
Connect:
Worker ID: 0fd: 3 , reactorId: 0
Request:
Worker ID: 0URL: /favicon.ico
Request:
Worker ID: 0URL: /... Swoole Reloading ! ... ... Under Reload ! ...
[2017-04-05 20:13:43 $4708.0] NOTICE Server is reloading now.
WorkerStop
Worker ID:0
WorkerStop
Worker ID:1
WorkerStart:
Worker ID: 0
WorkerStart:
Worker ID: 1
Request:
Worker ID: 0URL: /favicon.ico
Request:
Worker ID: 0URL: /... Swoole Exit ! ...
[2017-04-05 20:14:00 *4715.0] ERROR zm_deactivate_swoole (ERROR 9003): worker process is terminated by exit()/die().
WorkerStart:
Worker ID: 0
Request:
Worker ID: 0URL: /favicon.ico
Request:
Worker ID: 0URL: /... Swoole Shutdown ! ... ... After Swoole Shutdown ! ...
[2017-04-05 20:14:05 #4707.0] NOTICE Server is shutdown now.
WorkerStop
Worker ID:1
WorkerStop
Worker ID:0
[2017-04-05 20:14:05 #4707.0] ERROR swReactorThread_free(:1445): pthread_cancel(140148593481472) failed. Error: Resource temporarily unavailable[11].
Shutdown:
worker 进程启动后, 浏览器 Connect
触发一次后不再触发, 后续刷新只会触发 Request
事件, 直到超时触发 Close
事件
程序中有 exit
| die
时, worker 进程会退出重新启动并使用相同的workerId
上面两图注意查看 WorkerStart
和 ManagerStart
两个事件是并发的, 顺序并不固定
- Swoole 关于 HTTP SERVER 的事件顺序
- 【swoole】关于信号量的总结
- Swoole 关于变量作用域的问题
- 当SWOOLE遇上SERVER
- ASF 基于Swoole开发的PHP App Server框架
- 【Swoole】关于共享内存
- swoole关于task事项
- 关于HttpModule事件顺序和执行顺序
- 关于asp.net中页面事件加载的先后顺序
- 关于asp.net中页面事件加载的先后顺序
- 关于asp.net中页面事件加载的先后顺序
- 关于asp.net中页面事件加载的先后顺序
- 关于asp.net中页面事件加载的先后顺序
- 关于asp.net中页面事件加载的先后顺序
- Android 关于 OnScrollListener 事件顺序次数的简要分析
- Android 关于 OnScrollListener 事件顺序次数的简要分析
- Android 关于 OnScrollListener 事件顺序次数的简要分析
- Android 关于 OnScrollListener 事件顺序次数的简要分析
- centos7中配置elasticsearch集群和离线安装x-pack
- 与MVC框架解耦的OGNL:前世今生及其基本用法
- LeetCode -- Add Two Numbers
- 2017.4.5所学
- B. Number Busters----数学推演
- Swoole 关于 HTTP SERVER 的事件顺序
- [树形DP] BZOJ 4013 [HNOI2015]实验比较
- RabbitMQ+PHP 消息队列环境配置
- 题目1156:谁是你的潜在朋友 九度OJ
- 冒泡排序,快速排序,归并排序
- Ubuntu 14.04 php7.0 php7.0-fpm nginx 环境搭建备注
- ftp下载命令行工具wget
- Spring集成Quartz有2种方法:
- How to Type