4

単純な php ループの進行状況インジケーターを作成しようとしています。

ここには進行状況とphpループに関するajax / phpの質問がたくさんありますが、それらの多くを読んだ後でも、ロジックを実装できません(正確に理解することもできません)..

それらのほとんどは、-upload-プログレス バーについて話しているか、特定のケースに限定されすぎているかのどちらかです (それか、検索する適切なキーワードの選択方法がわからない)

私の最終的な目標は、プログレス バーを作成することですが、手始めに、少しエコー ループを試してみました。

私は次のことを試しました:

HTML フォーム :

<p class="submit">
    <input type="submit" class="button-primary" id="o99_sudi_do_now" value="<?php _e('DO IT NOW !', 'o99_sudi_domain'); ?>" />
    <img src="<?php echo admin_url('/images/wpspin_light.gif'); ?>" class="waiting" id="o99_sudi_loading" style="display:none;"/>
</p>

            <div id="o99_sudi_results"></div>

jQuery

jQuery(document).ready(function($){
  jQuery('#o99_sudi_do_now_form').click(function(e){
    e.preventDefault();
    jQuery.post(ajaxurl,{action:'o99_random_loop'}, function(data){
      jQuery('#o99_sudi_results').empty().append( data );
    });
  });
});

PHP

function o99_random_loop_cb(){
 for ($i = 0; $i < 10; $i++) {
        //ob_end_clean(); // [TESING]
        echo '-- step' .$i . ' of 10</br>';
        //flush();// [TESING]
        //usleep(100000000000*0.1); // total time 10 sec.// [TESING]
        //ob_flush();// [TESING]
        usleep(20000);
    }
  die();

そしてそれはすべてワードプレスの管理エリアにあるので -

add_action( 'wp_ajax_o99_random_loop', 'o99_random_loop_cb' ); 

結果(または出力)は次のとおりです。

-- Step 0 of 10
-- Step 1 of 10
-- Step 2 of 10
-- Step 3 of 10
-- Step 4 of 10
-- Step 5 of 10
-- Step 6 of 10
-- Step 7 of 10
-- Step 8 of 10
-- Step 9 of 10

これはまあまあですが、問題は、実行が終了したときにのみ出力が到着し、divが更新されることです-そして、それをオンザフライで段階的に更新したい...(私の実際の計画されたループは非常に長く、反復に約 2 ~ 3 秒かかります。)

コードでわかるように、私は試してみましたがflush();ob_flush();私が見た他の提案はありますが、ここでロジックが間違っていると思われます(ワードプレスですか??または間違った場所でフラッシュするためですか?)そして実際には、どのようにずっと私flush(); - 関数が ENDING の場合にのみ結果が到着する..

私の目標は進行状況バーを作成することです-しかし、今のところ、単純なエコー進行状況の助けさえあれば素晴らしいでしょう..

4

1 に答える 1

5

PHP への単一の POST では、目的を達成することはできません。PHP 出力をフラッシュしても、PHP プロセス全体が完了するまで、jQuery 側は結果ハンドラーを処理しません。昔は、ドキュメントが完成する前にコンテンツの表示を開始する一部のブラウザー (Netscape など) でのみ、このような動作を得ることができましたが、AJAX を使用すると、PHP スクリプトが実行されるまで、PHP からの結果のコンテンツは表示されません。終了した。

したがって、すべての出力を一度に取得する理由です。

やりたいことを実現する方法はいくつかあります。1 つの方法は、ループの一部のみが毎回実行されるように、PHP ループを段階に分割することです。次に、いくつかの反復 (または 1 回の反復) を実行し、その結果をブラウザーに返すことができます。ブラウザーは結果を表示し、次の反復 (または一連の反復) のために PHP を再度呼び出します。これにより進行状況のインジケーターが表示されますが、全体的な操作が大幅に遅くなるため、お勧めできません。

並行性の問題のために機能しない SESSION の使用を削除するために編集されました:

もう 1 つのオプションは、PHP でループの進行状況をデータベースに保存し、ブラウザー側でデータベースをチェックして進行状況を判断する別の PHP スクリプトを定期的にポーリングすることです。クイック ループでは、これはそれほど役に立ちませんが、より長い実行ループでは、これは実行可能になる可能性があります。したがって、$.post 呼び出しに加えて、進行状況を確認するために一連の時間指定された $.get 呼び出しを開始します。

編集:説明するためのいくつかのスニペットを次に示します。

// variable to control polling logic
var pollInterval;
// Your current post logic here with the addition of a variable to stop execution of the polling process
jQuery.post(ajaxurl,{action:'o99_random_loop'}, function(data){
    // post is complete so stop execution
    window.clearInterval(pollInterval);
});
// Now start a get process to get the progress every 5 seconds
pollInterval = window.setInterval(function () {
    // I'm assuming pollingurl is the URL to your PHP script that checks the progress
    jQuery.get(pollingurl, function(data){
        jQuery('#o99_sudi_results').empty().append( data );
    });
}, 5000);

今のところ、PHP 側では、進行状況をデータベース テーブルに保存し、その進行状況をテーブルから取得することに慣れていると仮定します。

于 2012-11-14T11:18:09.013 に答える