【PHP8.x】connection_aborted関数の使い方

作成日: 更新日:

connection_aborted関数は、PHPスクリプトがクライアントとの間で確立しているネットワーク接続が、予期せず中断されたかどうかをチェックする関数です。Webアプリケーションを構築する際、サーバーがクライアントからのリクエストを処理している途中で、クライアント側、例えばユーザーのWebブラウザがページを閉じたり、別のページに移動したりすることで、接続が切断されることがあります。この関数は、そうした接続の中断をサーバー側で検知するために利用されます。

この関数を呼び出すと、接続が既に切断されている場合には整数値の1(真)を返し、接続がまだ確立されているか、あるいは中断されていない場合には0(偽)を返します。例えば、非常に時間のかかるデータ処理やファイルアップロードのようなタスクをPHPスクリプトが実行している最中に、ユーザーが待てずにブラウザを閉じてしまった場合、サーバー側ではその処理を無駄に継続してしまう可能性があります。connection_aborted関数を定期的にチェックすることで、スクリプトはクライアントが既に接続を中断していることを検知し、不要な処理を途中で中止することができます。

これにより、サーバーのリソースが無駄に消費されるのを防ぎ、システムの効率性を高めることが可能です。システムエンジニアを目指す方にとって、Webアプリケーションの信頼性やパフォーマンスを向上させる上で、このような接続状態の管理は重要な知識の一つとなります。

基本的な使い方

構文(syntax)

$isAborted = connection_aborted();

引数(parameters)

引数なし

引数はありません

戻り値(return)

int

connection_aborted関数は、クライアントが接続を中断したかどうかを示す整数値を返します。0以外の場合は接続が中断されています。

サンプルコード

connection_aborted()で接続切断を検出する

<?php

/**
 * connection_aborted() 関数の動作をデモンストレーションします。
 *
 * このスクリプトは、クライアントがWeb接続を中断したかどうかを検出する方法を示します。
 * 出力バッファリングを適切に管理することで、接続状態を正確に把握します。
 *
 * 動作確認手順:
 * 1. このPHPスクリプトをWebサーバーに配置し、ブラウザでアクセスします。
 * 2. ページ表示中に("Processing..."の表示後)、ブラウザのタブを閉じます。
 * 3. PHPが接続切断を検出すると、スクリプトはメッセージを出力して終了します。
 */
function demonstrateConnectionAborted(): void
{
    // 既存の出力バッファをすべてクリアし、以後の出力を直ちにクライアントに送信するように設定します。
    // これにより、connection_aborted() が接続状態を正確に検出できるようになります。
    while (ob_get_level() > 0) {
        ob_end_clean();
    }
    // 暗黙的なフラッシュを有効にすることで、echo や print の後に出力が自動的にクライアントに送信されます。
    ob_implicit_flush(true);

    echo "Script started. Waiting for up to 10 seconds to detect connection abort.\n";
    // 初期のメッセージをクライアントに送信します。
    flush(); 

    $maxIterations = 10;
    for ($i = 1; $i <= $maxIterations; $i++) {
        echo "Processing... ($i/" . $maxIterations . ")\n";
        // 各ステップで出力をフラッシュし、クライアントとの通信を維持します。
        // これにより、クライアントが接続を切断した際にPHPがそれを検出しやすくなります。
        flush();

        // connection_aborted() は、クライアントが接続を切断した場合に 1 を返します。
        // 出力バッファリングが適切に管理されている場合にのみ、正確に検出できます。
        if (connection_aborted()) {
            echo "Client aborted the connection! Terminating process.\n";
            break; // 接続が切断されたため、ループを終了します。
        }

        sleep(1); // 1秒間処理を一時停止します。
    }

    if (!connection_aborted()) {
        echo "All processing completed. Client did not abort the connection.\n";
    }

    echo "Script finished.\n";
}

// 関数を実行します。
demonstrateConnectionAborted();

connection_aborted()関数は、PHP 8においてWebサーバーとクライアント間の接続が、クライアント側から中断されたかどうかを検出するために使用されます。この関数は引数を取りません。クライアントが接続を中断した場合は整数値の 1 を返し、接続が維持されている場合は 0 を返します。

この関数を正確に機能させるためには、出力バッファリングの適切な管理が不可欠です。具体的には、ob_implicit_flush(true) を呼び出して出力の自動フラッシュを有効にするか、flush() 関数を定期的に呼び出して、PHPが出力バッファの内容をクライアントに送信し続ける必要があります。そうしないと、PHPは接続が切断されたことを正確に検出できません。

提供されたサンプルコードでは、まず出力バッファをクリアし、ob_implicit_flush(true)flush() を利用しています。数秒ごとにメッセージをクライアントに送信しながら connection_aborted() を繰り返しチェックしており、ユーザーがブラウザのタブを閉じるなどの操作で接続を切断すると、PHPスクリプトがそれを検出し、処理を中断して終了する動作を示しています。これにより、不要なサーバーリソースの消費を防ぐことができます。

connection_aborted()関数は、Web接続がクライアントによって切断されたかを確認しますが、正確な検出には出力バッファリングの適切な管理が不可欠です。サンプルコードのようにob_implicit_flush(true)で自動フラッシュを有効にし、flush()を適宜呼び出して出力をクライアントへ送信することが特に重要です。これにより、PHPが接続状態を正しく認識できるようになります。また、既存の出力バッファをwhile (ob_get_level() > 0) { ob_end_clean(); }でクリアすることも忘れないでください。これらの設定がないと、関数は常に「未切断」と判断し、期待通りに動作しません。コマンドライン環境(CLI)では接続切断の概念がないため機能せず、WebサーバーやPHP-FPMの設定によっても挙動が変わる可能性がありますので、必ずWeb環境で動作確認してください。

【PHP8.x】connection_aborted関数の使い方 | いっしー@Webエンジニア