diff --git a/README.md b/README.md index b4b9132..e8bb257 100644 --- a/README.md +++ b/README.md @@ -21,133 +21,156 @@ ## 简介 - 一个event-loop实验品; - - 是一个类似ReactPHP、AMPHP的事件循环组件; - - 该项目主要研究ext-parallel和PHP-fiber在event-loop中如何有效结合, - 研究PHP在不利用ext-event、ext-ev、ext-uv等拓展的前提下是否可以实现 - 更高的处理能力。 - - An event loop experiment; - - It is an event loop component similar to ReactPHP and AMPHP; - - This project mainly studies how ext-parallel and PHP-fiber can - be effectively combined in event-loop, and studies whether PHP - can achieve higher processing power without using extensions - like ext-event, ext-ev, ext-uv, etc. + 一个事件循环库,目的是为了构建高性能网络应用。 ## 使用 -### 1. 安装 +注:本文档为 2.x 版本,旧版请点击 **[1.x 版本](https://github.com/workbunny/event-loop/tree/1.x)** 跳转 + +### 安装 ``` composer require workbunny/event-loop ``` -### 2. 创建loop +### 创建loop ```php use WorkBunny\EventLoop\Loop; use WorkBunny\EventLoop\Drivers\NativeLoop; use WorkBunny\EventLoop\Drivers\EventLoop; use WorkBunny\EventLoop\Drivers\EvLoop; -use WorkBunny\EventLoop\Drivers\OpenSwooleLoop; +use WorkBunny\EventLoop\Drivers\SwowLoop; -# 创建PHP原生loop +// 创建PHP原生loop $loop = Loop::create(NativeLoop::class); - -# 创建ext-event loop +// 创建ext-event loop $loop = Loop::create(EventLoop::class); - -# 创建ext-ev loop +// 创建ext-ev loop $loop = Loop::create(EvLoop::class); - -# 创建ext-openswoole loop -$loop = Loop::create(OpenSwooleLoop::class); +// 创建swow loop +$loop = Loop::create(SwowLoop::class); ``` -### 3. 创建定时器 +### 注册loop -- 无延迟触发器 +- 创建 YourLoopClass 实现 LoopInterface +- 调用 Loop::register() 注册 YourLoopClass - 通过loop立即执行一次回调函数; ```php -# 立即执行 -$id = $loop->addTimer(0.0, 0.0, function (){ - # 业务 -}); +use WorkBunny\EventLoop\Loop; +// 注册 +loop::register(YourLoopClass::class); +// 创建 +$yourLoop = Loop::create(YourLoopClass::class); ``` -- 延迟触发器 +### 创建定时器 - 延迟 delay 参数的数值后,执行注册的回调函数,仅执行一次; +- Future 触发器 ```php -# 延迟1秒后执行一次 -$id = $loop->addTimer(1.0, 0.0, function (){ - # 业务 -}); +/** + * @Future [delay=0.0, repeat=false] + * 在下一个周期执行,执行一次即自动销毁 + */ +$loop->addTimer(0.0, false, function (){ echo 'timer'; }); // loop->run()后立即输出字符串 ``` -- 无延迟定时器 +- ReFuture 重复触发器 +```php +/** + * @ReFuture [delay=0.0, repeat=0.0] + * 在每一个周期执行,不会自动销毁 + */ +$id = $loop->addTimer(0.0, 0.0, function () use(&$loop, &$id) { + // 此方法可以实现自我销毁 + $loop->delTimer($id); +}); +``` - 通过loop立即执行一次回调函数后,根据 repeat 参数的数值间隔执行,直到主动移除该定时器; +- DelayReFuture 延迟的重复触发器 ```php -# 立即执行一次以后间隔0.1s执行 -$id = $loop->addTimer(0.0, 0.1, function (){ - # 业务 +/** + * @DelayReFuture [delay>0.0, repeat=0.0] + * 延迟delay秒后每一个周期执行,不会自动销毁 + */ +$id = $loop->addTimer(1.0, 0.0, function () use(&$loop, &$id) { + // 此方法可以实现自我销毁 + $loop->delTimer($id); }); ``` -- 延迟定时器 +- Delayer 延迟器 +```php +/** + * @Delayer [delay>0.0, repeat=false] + * 延迟delay秒后执行,执行一次即自动销毁 + */ +$loop->addTimer(2.0, false, function (){ echo 'timer'; }); // loop->run() 2秒后输出字符串 +``` - 延迟 delay 参数的数值后,执行一次注册的回调函数,之后根据 repeat 参数的数值间隔执行,直到主动移除该定时器; +- Timer 定时器 ```php -# 延迟0.1s后间隔0.1s执行 -$id = $loop->addTimer(0.1, 0.1, function (){ - # 业务 +/** + * @Timer [delay=0.0, repeat>0.0] + * 在下一个周期开始每间隔repeat秒执行,不会自动销毁 + */ +$id = $loop->addTimer(0.1, 0.1, function () use(&$loop, &$id) { + // 此方法可以实现自我销毁 + $loop->delTimer($id); }); +``` -# 延迟0.5s后间隔0.1s执行 -$id = $loop->addTimer(0.5, 0.1, function (){ - # 业务 +- DelayTimer 延迟的定时器 +```php +/** + * @DelayTimer [delay>0.0, repeat>0.0] + * 延迟delay秒后每间隔repeat秒执行,不会自动销毁 + */ +$id = $loop->addTimer(0.2, 0.1, function () use(&$loop, &$id) { + // 此方法可以实现自我销毁 + $loop->delTimer($id); }); ``` -### 4. 创建流事件 +### 流事件 这里的流是指 **[PHP Streams](https://www.php.net/manual/zh/book.stream.php)** - 读取流 ```php -$loop->addReadStream(resource, function (){ - # 业务 +// 创建 +$loop->addReadStream(resource, function (resource $stream) { }); +// 注意:EvLoop在这里较为特殊,回调函数的入参为EvIo对象 +$loop->addReadStream(resource, function (\EvIo $evio) { + $evio->stream // resource 资源类型 }); +// 移除 $loop->delReadStream(resource); ``` - 写入流 ```php -$loop->addWriteStream(resource, function (){ - # 业务 +// 创建 +$loop->addWriteStream(resource, function (resource $stream) { }); +// 注意:EvLoop在这里较为特殊,回调函数的入参为EvIo对象 +$loop->addWriteStream(resource, function (\EvIo $evio) { + $evio->stream // resource 资源类型 }); +// 移除 $loop->delWriteStream(resource); ``` -### 5. 创建信号事件 +### 信号事件 用于接收系统的信号,比如kill等 ```php -$loop->addSignal(\SIGUSR1, function (){ - # 业务 -}); - -$loop->delSignal(\SIGUSR1, function (){ - # 业务 -}); +// 注册 +$loop->addSignal(\SIGUSR1, function (){}); +// 移除 +$loop->delSignal(\SIGUSR1, function (){}); ``` -### 6. 启动/停止 +### 启动/停止 - 启动 @@ -170,27 +193,4 @@ $loop->destroy(); var_dump('123'); ``` -## 说明 -### 1. 测试用例中各个loop比较特殊的地方会在对应测试用例中说明 -- EvLoop 的Stream总是后于Timer **详见EvLoopTest.php** -- EventLoop 的延迟定时器区别于其他Loop的定时器,需要多一个loop周期 **详见EventLoopTest.php** -- OpenSwoole 的读/写流不能通过 **testReadStreamHandlerTriggeredMultiTimes** 测试 **详见OpenSwooleLoopTest.php** - -### 2. 相同定时器/触发器的优先级遵循先注册先触发 - -### 3. OpenSwoole在同一周期内是有优先级的 - -> 1. 通过 Process::signal 设置的信号处理回调函数 -> -> 2. 通过 Timer::tick 和 Timer::after 设置的定时器回调函数 -> -> 3. 通过 Event::defer 设置的延迟执行函数 -> -> 4. 通过 Event::cycle 设置的周期回调函数 - - -### 4. OpenSwoole的无延迟触发器/无延迟定时器利用了 Event::defer,需要注意优先级 - -### 5. OpenSwoole的 Event::defer 可以重复注册多个回调 - --- diff --git a/Dockerfile b/env/Dockerfile similarity index 100% rename from Dockerfile rename to env/Dockerfile diff --git a/docker-compose.yaml b/env/docker-compose.yaml similarity index 93% rename from docker-compose.yaml rename to env/docker-compose.yaml index c099ba5..6d5e94d 100644 --- a/docker-compose.yaml +++ b/env/docker-compose.yaml @@ -4,7 +4,7 @@ services: restart: always container_name: workbunny-php build: - context: ./ + context: .. image: workbunny-php volumes: - ./../:/var/www diff --git a/event.ini b/event.ini deleted file mode 100644 index 3189ce6..0000000 --- a/event.ini +++ /dev/null @@ -1 +0,0 @@ -extension=event.so \ No newline at end of file