4


C++ アプリケーション用の非常に原始的な Web フロントエンドがあります。クライアント (Web ブラウザー) は、php サイトに入り、フォームにパラメーターを入力します。(送信後)php がexecを呼び出し、アプリケーションがその作業を行うよりも。アプリケーションは数分以上動作する可能性があり、かなり大量の RAM を必要とします。

クライアントからの切断を検出する可能性はありますか (たとえば、Web ブラウザーのタブを閉じるなど)。クライアントを切断した後、計算の結果を見ることができないため、これを行いたいので、アプリケーションを強制終了してサーバー上のRAMを解放できます。

助けや提案をありがとう。

4

1 に答える 1

2

C++ プログラムが実行中に出力を生成する限り、終了直前にすべての出力を生成するのではpassthru()なく、exec().

これにより、PHP はコンテンツの生成時に出力をクライアントにフラッシュします。これにより、PHP はクライアントの切断を検出できます。PHP は、クライアントが切断されると終了し、子プロセスをすぐに強制終了します (設定されていない限りignore_user_abort())。

例:

<?php

  function exec_unix_bg ($cmd) {
    // Executes $cmd in the background and returns the PID as an integer
    return (int) exec("$cmd > /dev/null 2>&1 & echo $!");
  }
  function pid_exists ($pid) {
    // Checks whether a process with ID $pid is running
    // There is probably a better way to do this
    return (bool) trim(exec("ps | grep \"^$pid \""));
  }

  $cmd = "/path/to/your/cpp arg_1 arg_2 arg_n";

  // Start the C++ program
  $pid = exec_unix_bg($cmd);

  // Ignore user aborts to allow us to dispatch a signal to the child
  ignore_user_abort(1);

  // Loop until the program completes
  while (pid_exists($pid)) {

    // Push some harmless data to the client
    echo " ";
    flush();

    // Check whether the client has disconnected
    if (connection_aborted()) {
      posix_kill($pid, SIGTERM); // Or SIGKILL, or whatever
      exit;
    }

    // Could be done better? Only here to prevent runaway CPU
    sleep(1);

  }

  // The process has finished. Do your thang here.

プログラムの出力を収集するには、出力を ではなくファイルにリダイレクトします/dev/null。PHP のマニュアルでは、拡張機能によって定数が定義されていることが示されているため、これpcntlと同様にインストールする必要があると思われます。posixSIGxxxpcntl

于 2012-07-09T11:52:57.173 に答える