概述
AsyncIO 基于 PHP Fiber 和 Workerman 实现的高性能异步 IO 扩展包,提供类似 Python asyncio 的 API 和功能。
特性
-
🚀 基于 PHP Fiber - 原生协程支持,性能卓越
-
⚡ 完全事件驱动 - 零轮询,充分利用 Workerman 高性能
-
🎯 并发控制 -
gather, wait_for, 任务管理 -
⏰ 精确定时 -
< 0.1ms延迟,Timer 事件驱动 -
🛡️ 异常处理 - 完整的错误传播和处理
-
📦 简洁API - 类似
Python asyncio的使用体验
安装
composer require pfinalclub/asyncio
要求
-
PHP >= 8.1 (需要 Fiber 支持)
-
Workerman >= 4.1
快速开始
基础示例
<?php
require_once__DIR__ . '/vendor/autoload.php';
usefunctionPfinalClub\Asyncio\{run, sleep};
// 定义一个异步函数
function hello_world(): mixed
{
echo"Hello\n";
sleep(1); // 异步睡眠 1 秒
echo"World\n";
return"Done!";
}
// 运行主函数
$result = run(hello_world(...));
echo"Result: {$result}\n";
并发任务
<?php
usefunctionPfinalClub\Asyncio\{run, create_task, gather, sleep};
function task1(): string
{
echo"Task 1 开始\n";
sleep(2);
echo"Task 1 完成\n";
return"结果 1";
}
function task2(): string
{
echo"Task 2 开始\n";
sleep(1);
echo"Task 2 完成\n";
return"结果 2";
}
function main(): array
{
// 创建任务
$t1 = create_task(task1(...));
$t2 = create_task(task2(...));
// 并发等待所有任务完成
$results = gather($t1, $t2);
return $results; // ['结果 1', '结果 2']
}
run(main(...));
超时控制
<?php
usefunctionPfinalClub\Asyncio\{run, wait_for, sleep};
usePfinalClub\Asyncio\TimeoutException;
function slow_task(): string
{
sleep(5);
return"完成";
}
function main(): void
{
try {
// 最多等待 2 秒
$result = wait_for(slow_task(...), 2.0);
echo"结果: {$result}\n";
} catch (TimeoutException $e) {
echo"任务超时: {$e->getMessage()}\n";
}
}
run(main(...));
任务管理
<?php
usefunctionPfinalClub\Asyncio\{run, create_task, await, sleep};
function background_task(string $name): string
{
for ($i = 1; $i <= 5; $i++) {
echo"{$name}: 步骤 {$i}\n";
sleep(0.5);
}
return"{$name} 完成";
}
function main(): void
{
// 创建多个后台任务
$task1 = create_task(fn() => background_task("任务A"));
$task2 = create_task(fn() => background_task("任务B"));
// 等待一段时间
sleep(2);
// 检查任务状态
echo"任务1 完成: " . ($task1->isDone() ? "是" : "否") . "\n";
echo"任务2 完成: " . ($task2->isDone() ? "是" : "否") . "\n";
// 等待任务完成
$result1 = await($task1);
$result2 = await($task2);
echo"{$result1}, {$result2}\n";
}
run(main(...));
API 参考
核心函数
run(callable $main): mixed
运行主函数直到完成并返回结果。这是程序的主入口点。
$result = run(my_function(...));
create_task(callable $callback, string $name = ''): Task
创建并调度一个任务,立即开始执行。
$task = create_task(my_function(...), 'my-task');
async(callable $callback, string $name = ''): Task
create_task 的别名,更符合异步编程习惯。
$task = async(my_function(...));
sleep(float $seconds): void
异步睡眠指定的秒数。必须在 Fiber 上下文中调用。
sleep(1.5); // 睡眠 1.5 秒
await(Task $task): mixed
等待任务完成并返回结果。
$result = await($task);
gather(Task ...$tasks): array
并发运行多个任务并等待它们全部完成。
$results = gather($task1, $task2, $task3);
wait_for(callable|Task $awaitable, float $timeout): mixed
等待任务完成,如果超时则抛出 TimeoutException。
try {
$result = wait_for(my_task(...), 5.0);
} catch (TimeoutException $e) {
echo "超时!\n";
}
事件循环
get_event_loop(): EventLoop
获取当前事件循环实例。
$loop = get_event_loop();
Task 类
isDone(): bool
检查任务是否已完成。
getResult(): mixed
获取任务结果(如果任务未完成会抛出异常)。
cancel(): bool
取消任务。
addDoneCallback(callable $callback): void
添加任务完成时的回调。
Future 类
Future 表示一个未来的结果,可以手动设置。
$future = create_future();
// 在某处设置结果
$future->setResult("结果");
// 等待结果
$result = await_future($future);
高级用法
HTTP 客户端
use functionPfinalClub\Asyncio\{run, create_task, gather};
usePfinalClub\Asyncio\Http\AsyncHttpClient;
function main(): void
{
$client = new AsyncHttpClient(['timeout' => 10]);
// 单个请求
$response = $client->get('https://api.example.com/users');
echo"Status: {$response->getStatusCode()}\n";
echo"Body: {$response->getBody()}\n";
// 并发请求
$task1 = create_task(fn() => $client->get('https://api.example.com/users/1'));
$task2 = create_task(fn() => $client->get('https://api.example.com/users/2'));
$task3 = create_task(fn() => $client->get('https://api.example.com/users/3'));
$responses = gather($task1, $task2, $task3);
foreach ($responses as $response) {
echo"Status: {$response->getStatusCode()}\n";
}
}
run(main(...));
监控工具
use functionPfinalClub\Asyncio\{run, create_task, gather};
usePfinalClub\Asyncio\Monitor\AsyncioMonitor;
function main(): void
{
$monitor = AsyncioMonitor::getInstance();
// 创建任务
$tasks = [
create_task(fn() => my_task1()),
create_task(fn() => my_task2()),
];
gather(...$tasks);
// 显示监控报告
echo $monitor->report();
// 导出 JSON
echo $monitor->toJson();
}
run(main(...));
调试器
use functionPfinalClub\Asyncio\run;
usePfinalClub\Asyncio\Debug\AsyncioDebugger;
function main(): void
{
$debugger = AsyncioDebugger::getInstance();
$debugger->enable();
// 你的代码...
// 显示调用链
echo $debugger->visualizeCallChain();
// 显示报告
echo $debugger->report();
}
run(main(...));
与 v1.x 的区别
主要变更
| v1.x (Generator) | v2.0 (Fiber) |
|---|---|
function f(): \Generator |
function f(): mixed |
yield sleep(1) |
sleep(1) |
yield $task |
await($task) |
yield gather(...) |
gather(...) |
run(generator()) |
run(callable) |