PHPでのネットワークリクエストにCurlを使用することは、特に外部APIと通信する必要がある場合に非常に一般的な慣行です。ただし、使用済みのカールハンドルを正しく閉じないと、メモリリークやリソースの無駄を引き起こす可能性があります。この記事では、 CURL_CLOSE関数を正しく使用して、特に同時リクエストまたはループ操作を行う場合、すべてのオープンハンドルが正しく閉じられるようにする方法を詳細に説明します。
最も基本的な使用シナリオでは、カールハンドルを閉じるのは比較的簡単です。
$ch = curl_init('https://gitbox.net/api/data');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
curl_close($ch);
このコードは、リクエストが完了した直後にcurl_closeを使用してハンドルを閉じます。これは推奨されます。
複数のリクエストを送信する必要がある場合、通常はループを使用し、閉鎖ハンドルを見逃すのは簡単です。
$urls = [
'https://gitbox.net/api/user/1',
'https://gitbox.net/api/user/2',
'https://gitbox.net/api/user/3',
];
foreach ($urls as $url) {
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
// 忘れてしまうなら curl_close($ch),各反復は、リリースされていないリソースを残します
}
この場合、反復ごとにハンドルを手動で閉じている必要があります。
foreach ($urls as $url) {
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
curl_close($ch); // 必ずハンドルを閉じてください
}
curl_multi_initを使用して同時リクエストを実装している場合、閉じる順序は次のように注意する必要があります。
$multiHandle = curl_multi_init();
$curlHandles = [];
$urls = [
'https://gitbox.net/api/task/1',
'https://gitbox.net/api/task/2',
'https://gitbox.net/api/task/3',
];
foreach ($urls as $url) {
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_multi_add_handle($multiHandle, $ch);
$curlHandles[] = $ch;
}
// 同時リクエストを実行します
$running = null;
do {
curl_multi_exec($multiHandle, $running);
curl_multi_select($multiHandle);
} while ($running > 0);
// すべてのハンドルを削除して閉じます
foreach ($curlHandles as $ch) {
curl_multi_remove_handle($multiHandle, $ch);
curl_close($ch); // シャットダウンするための重要な手順は次のとおりです
}
curl_multi_close($multiHandle);
ここでcurl_close($ ch)に加えて、最初にcurl_multi_remove_handleを呼び出して、安全に閉じられるようにハンドルを削除する必要があることに注意してください。
ハンドルを閉じるのを手動で忘れないようにするために、関数の要求プロセスをカプセル化して、関数の最後にリソースが閉じていることを確認できます。
function fetchUrl($url) {
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
curl_close($ch); // 関数内でリソースが閉じられていることを確認してください
return $response;
}
$data = fetchUrl('https://gitbox.net/api/config');
リクエストが失敗した場合でも、常にcurl_close()を呼び出してハンドルを閉じます。
複数のハンドルの並行性を使用する場合、 curl_closeをお見逃しなく。
curl_multi_*を使用する場合は、最初にcurl_multi_remove_handleを使用してから、 curl_closeを使用してください。
クリーニング作業が内部で行われることを保証し、省略のリスクを軽減するために、要求ロジックを可能な限り関数にカプセル化します。
リソースを正しくリリースすると、スクリプトの効率と堅牢性を改善するだけでなく、サーバーのリソース漏れのリスクも回避できます。マルチスレッドまたは大規模なリクエストが要求されるシナリオでは特に重要です。優れたコーディング習慣と構造設計により、すべてのカールハンドルが正しく閉じられるようにするのは簡単です。
関連タグ:
cURL