在PHP中,cURL 是一个强大且常用的网络请求工具,而 curl_multi_* 系列函数允许我们。这在进行高性能接口聚合、异步请求等场景中非常有用。
然而,许多开发者在使用 curl_multi_* 时,常常忽略了资源的释放环节,尤其是 curl_multi_close() 的使用。本文将以标准流程为主线,带你一步步理解从 curl_multi_init 到 curl_multi_close 的完整使用方式,并辅以代码示例说明。
PHP 提供的 curl_multi_* 系列函数是用于管理多个并发 curl 句柄的工具。这与传统的单个 curl 请求不同,它允许你同时发起多个 HTTP 请求,提升响应效率。
使用这些函数可以大致分为以下几个步骤:
初始化 multi 句柄:curl_multi_init()
添加多个 curl 请求(easy handle):curl_multi_add_handle()
获取响应内容:curl_multi_getcontent()
移除并关闭 easy handle:curl_multi_remove_handle() 和 curl_close()
关闭 multi handle:curl_multi_close()
下面是一个标准的多请求流程,假设我们需要并发请求三个不同的 URL:
<?php
// 要请求的 URL 列表
$urls = [
"https://gitbox.net/api/service1",
"https://gitbox.net/api/service2",
"https://gitbox.net/api/service3"
];
// 初始化 multi handle
$multiHandle = curl_multi_init();
$curlHandles = [];
// 1. 为每个 URL 创建一个 curl easy handle 并添加到 multi handle 中
foreach ($urls as $i => $url) {
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_multi_add_handle($multiHandle, $ch);
$curlHandles[$i] = $ch;
}
// 2. 执行 multi 请求
$active = null;
do {
$mrc = curl_multi_exec($multiHandle, $active);
// 等待网络 I/O 准备好,避免 CPU 占用过高
if ($mrc == CURLM_OK) {
curl_multi_select($multiHandle);
}
} while ($active > 0 && $mrc == CURLM_OK);
// 3. 获取内容并清理句柄
$responses = [];
foreach ($curlHandles as $i => $ch) {
// 获取响应内容
$responses[$i] = curl_multi_getcontent($ch);
// 移除并关闭单个 handle
curl_multi_remove_handle($multiHandle, $ch);
curl_close($ch);
}
// 4. 最后关闭 multi handle,释放资源
curl_multi_close($multiHandle);
// 输出结果
foreach ($responses as $index => $body) {
echo "Response from URL #{$index}: \n";
echo $body . "\n\n";
}
虽然 curl_multi_close() 并不会立即销毁 easy handle(你需要先移除再关闭它们),但它负责释放 multi handle 本身占用的底层资源。如果你忘记调用它,在长时间运行的脚本(如常驻进程)中可能导致内存泄漏或者文件描述符耗尽的问题。
总结:任何使用了 curl_multi_init() 的脚本,必须以 curl_multi_close() 结尾!
请求阻塞卡住?
检查是否正确使用了 curl_multi_select()。
确保没有漏掉 curl_setopt(..., CURLOPT_RETURNTRANSFER, true)。
内存泄露或连接异常?
是否在每个请求后调用了 curl_multi_remove_handle() 和 curl_close()?
是否最终调用了 curl_multi_close()?
在并发处理网络请求时,curl_multi_* 提供了非常高效的手段。掌握从 curl_multi_init() 到 curl_multi_close() 的完整流程,能有效提高代码性能和资源管理能力。
记住这三个“必须”:
每个请求都必须添加到 multi 句柄中;
每个请求都必须在完成后被移除和关闭;
最终必须调用 curl_multi_close() 来释放 multi 资源。
通过规范的流程和资源管理,你的 PHP 并发请求将更加健壮和高效。