現在の位置: ホーム> 最新記事一覧> curl_multi_closeがリクエストの中間プロセスを妨げないようにする方法

curl_multi_closeがリクエストの中間プロセスを妨げないようにする方法

gitbox 2025-05-29

PHPでCurl拡張機能を使用する場合、 Curl_multi_*関数は通常、複数の同時リクエストを処理するために使用されます。これらの機能は、特に複数のHTTP要求が同時に送信される場合、プログラムのパフォーマンスを大幅に改善できます。ただし、 curl_multi_close関数を使用する場合、一部の開発者は要求処理の干渉の問題に遭遇する可能性があり、要求が正しく完了したり、エラーを返したりしません。

この記事では、要求処理の干渉を回避し、いくつかの実用的なコードの例とソリューションを共有する方法について説明します。

1。curl_multi_ *関数の概要

PHPは、 CURL_MULTI_*関数を提供して、複数の同時CURL要求を実行します。主な機能は次のとおりです。

サンプルコード

<?php

$multiHandle = curl_multi_init();

$urls = [
    'https://gitbox.net/api/endpoint1',
    'https://gitbox.net/api/endpoint2',
    'https://gitbox.net/api/endpoint3'
];

$handles = [];

// 複数の要求ハンドルを初期化します
foreach ($urls as $url) {
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_multi_add_handle($multiHandle, $ch);
    $handles[] = $ch;
}

// リクエストを実行します
$running = null;
do {
    curl_multi_exec($multiHandle, $running);
} while ($running);

// 応答データを取得します
foreach ($handles as $ch) {
    $response = curl_multi_getcontent($ch);
    echo $response . "\n";
    curl_multi_remove_handle($multiHandle, $ch);
}

// ハンドルを閉じます
curl_multi_close($multiHandle);

?>

2。Curl_multi_closeの問題

curl_multi_close関数は便利なクリーニング機能ですが、特にリクエストが完了しないときにcurl_multi_closeが呼び出された場合、要求処理の最後の段階で干渉することがあります。この干渉により、一部の要求が正しく完了できない場合や、受信した応答が不完全である可能性があります。

干渉の一般的な原因

  1. 同時リクエストの完了時間は一貫していません。リクエストの異なる応答時間が異なるため、 Curl_multi_closeが呼び出された場合、一部の要求が完了していないため、リクエストは事前に閉じられます。

  2. リソースリリースの問題:場合によっては、リソースが完全にリリースされる前にcurl_multi_closeを呼び出すと、他の要求に影響を与えるか、接続が切断される可能性があります。

3.干渉を避ける方法は?

curl_multi_close関数の要求処理における干渉を回避するために、次の戦略を採用できます。

3.1すべてのリクエストが完了していることを確認してください

curl_multi_closeを呼び出す前に、すべてのリクエストが完了していることを確認してください。 curl_multi_execによって返される実行ステータスをチェックすることにより、すべてのリクエストが完了したかどうかを確認できます。 curl_multi_closeは、すべての要求が処理された場合にのみ呼び出す必要があります。

改善されたコードの例:

 <?php

$multiHandle = curl_multi_init();

$urls = [
    'https://gitbox.net/api/endpoint1',
    'https://gitbox.net/api/endpoint2',
    'https://gitbox.net/api/endpoint3'
];

$handles = [];

// 複数の要求ハンドルを初期化します
foreach ($urls as $url) {
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_multi_add_handle($multiHandle, $ch);
    $handles[] = $ch;
}

// リクエストを実行します
$running = null;
do {
    $mrc = curl_multi_exec($multiHandle, $running);
    if ($mrc > 0) {
        echo "CURL exec error: " . curl_multi_strerror($mrc);
    }
} while ($running);

// 応答データを取得します
foreach ($handles as $ch) {
    $response = curl_multi_getcontent($ch);
    echo $response . "\n";
    curl_multi_remove_handle($multiHandle, $ch);
}

// ハンドルを閉じます
curl_multi_close($multiHandle);

?>

3.2 curl_multi_selectを使用してパフォーマンスを向上させます

場合によっては、 curl_multi_select()を使用して、リクエスト処理のパフォーマンスを最適化できます。 Curl_multi_execを絶えずポーリングする代わりに、Curl要求が完了するのを待っている間にプロセスをブロックできます。これにより、CPUの使用が削減され、リクエストのスムーズな処理が保証されます。

コード例:

 <?php

$multiHandle = curl_multi_init();

$urls = [
    'https://gitbox.net/api/endpoint1',
    'https://gitbox.net/api/endpoint2',
    'https://gitbox.net/api/endpoint3'
];

$handles = [];

// 複数の要求ハンドルを初期化します
foreach ($urls as $url) {
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_multi_add_handle($multiHandle, $ch);
    $handles[] = $ch;
}

// リクエストを実行します并使用 curl_multi_select パフォーマンスを向上させます
$running = null;
do {
    $mrc = curl_multi_exec($multiHandle, $running);
    if ($mrc > 0) {
        echo "CURL exec error: " . curl_multi_strerror($mrc);
    }
    curl_multi_select($multiHandle);
} while ($running);

// 応答データを取得します
foreach ($handles as $ch) {
    $response = curl_multi_getcontent($ch);
    echo $response . "\n";
    curl_multi_remove_handle($multiHandle, $ch);
}

// ハンドルを閉じます
curl_multi_close($multiHandle);

?>

4。概要

要求処理の干渉を回避するには、すべての要求が完了し、応答が正しく返されたことを確認する必要があります。リクエストの実行ステータスを監視し、 curl_multi_selectを使用してパフォーマンスを最適化し、干渉の可能性を回避するためにリクエストが完了した後にcurl_multi_closeが呼び出されることを確認できます。

これらの方法により、PHPでの同時要求の安定性とパフォーマンスを効果的に改善し、要求処理プロセスがスムーズであり、不必要な干渉がないことを保証します。