在处理大量并发HTTP请求时,curl_multi 系列函数是PHP中非常实用的工具。其中,curl_multi_close 是收尾阶段不可或缺的一步,用来正确释放由 curl_multi_init 创建的资源。本文将讲解 curl_multi_close 的正确用法,并提供一个实战示例,帮助你避免常见的资源泄漏问题。
每当使用 curl_multi_init 创建一个多句柄(curl multi handle)时,PHP都会分配一块内存用来管理这个多句柄及其包含的各个请求。即使单个子句柄(curl_init 生成的)已经用 curl_close 关闭,整体的 multi handle 依然会占用系统资源。
如果忘记使用 curl_multi_close,在高并发场景下很容易引起内存泄露,甚至导致程序崩溃。
因此,在完成所有并发请求后,必须调用 curl_multi_close 来彻底释放资源。
一般使用 curl_multi 系列函数的流程如下:
创建 multi handle(curl_multi_init)
创建并配置多个单独的 curl handle(curl_init)
将各个 curl handle 加入 multi handle(curl_multi_add_handle)
执行并监控所有请求(curl_multi_exec 和 curl_multi_select)
移除单个 handle(curl_multi_remove_handle)并关闭(curl_close)
最后关闭 multi handle(curl_multi_close)
下面是一个完整示例,展示了如何同时请求多个URL,并正确清理所有相关资源:
<?php
// 要并发请求的URL列表
$urls = [
"https://gitbox.net/api/endpoint1",
"https://gitbox.net/api/endpoint2",
"https://gitbox.net/api/endpoint3",
];
// 初始化 multi handle
$multiHandle = curl_multi_init();
$curlHandles = [];
// 初始化每个单独的 curl handle 并加入 multi handle
foreach ($urls as $key => $url) {
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_multi_add_handle($multiHandle, $ch);
$curlHandles[$key] = $ch;
}
// 执行请求
$running = null;
do {
$status = curl_multi_exec($multiHandle, $running);
if ($status > CURLM_OK) {
// 错误处理
echo "cURL error: " . curl_multi_strerror($status);
break;
}
// 等待活动连接
curl_multi_select($multiHandle);
} while ($running > 0);
// 收集响应结果
$responses = [];
foreach ($curlHandles as $key => $ch) {
$responses[$key] = curl_multi_getcontent($ch);
// 移除并关闭每个子 handle
curl_multi_remove_handle($multiHandle, $ch);
curl_close($ch);
}
// 最后关闭 multi handle
curl_multi_close($multiHandle);
// 输出响应
foreach ($responses as $index => $response) {
echo "Response from URL {$urls[$index]}:" . PHP_EOL;
echo $response . PHP_EOL . PHP_EOL;
}
?>
一定要先移除单个 curl handle,再关闭它们,最后关闭 multi handle。
不要直接关闭 multi handle 后再操作子 handle,那样会引发不可预期的错误。
在高并发环境下建议加上超时控制(CURLOPT_TIMEOUT),防止长时间阻塞。
curl_multi_close 是保证资源合理释放的最后一步,尤其在多并发场景下,养成良好的关闭习惯非常关键。正确地清理每个子句柄并最终关闭 multi handle,能有效防止资源泄漏,提高PHP应用的稳定性和性能。