ob_implicit_flush(),flush(),ob_flush() - 不在远程服务器上工作

时间:2015-09-12 12:01:44

标签: php long-polling flush

如果我在XAMPP上从我的本地服务器加载此脚本:

header("Content-Type:text/plain");

set_time_limit(0);

$max = 40;
for ($i = 0; $i < $max; $i++) {
    $response = array(  'server time: ' . date("h:i:s", time()), 'progress' => round($i/$max*100));
    echo json_encode($response);
    ob_flush();
    flush();
    sleep(1);
}
ob_clean();

它按预期工作,每秒页面显示一个新的响应。 但是,当我将其上传到我的远程服务器(运行相同版本的php)时,它会等到整个脚本完成后再显示输出。 在非常长的脚本上,它每30-60秒左右更新一次输出。

正如标题所示,我尝试过使用所有不同的刷新功能,但没有任何效果。 我的本地服务器和远程服务器的php.ini可能有些不同,但我不知道是什么。

请帮忙。

--- --- EDIT

我一直在做更多的测试。我注意到它确实只更新每4096个字节,这恰好是我的远程服务器的'output_buffering'的php ini值。 但是,出于某种原因,如果我将output_buffering更改为“1”或“关闭”,则不会发生任何变化。它仍然只更新每4096个字节。

我正在同一浏览器上的不同服务器上测试2个相同的脚本。

3 个答案:

答案 0 :(得分:7)

我没有考虑nginx,它有自己的输出缓冲区。

我只是添加了标题(&#34; X-Accel-Buffering:no&#34;);&#39;到php脚本的顶部,现在一切正常。

答案 1 :(得分:6)

对我来说,添加header('Content-Encoding: none');就可以了。使用PHP-FPM时需要这样做。

答案 2 :(得分:-1)

在您需要使用ob_start()ob_end_clean()之前。并添加标题Content-LengthTransfer-Encoding: chunked。并检查php.ini

中的“implicit_flush”是否为On

添加填充以进行响应。检查此代码:

<?php

set_time_limit(0);
ob_start();

header('Content-Type: text/plain');

define("PADDING", 16);

//+padding
for($i=0;$i<PADDING;$i++){
    //64 spaces (1 block)
    echo str_repeat(' ', 64);
}

$max = 40;
for ($i = 0; $i < $max; $i++) {
    $response = array(  'server time: ' . date("h:i:s", time()), 'progress' => round($i/$max*100));
    echo json_encode($response);
    ob_flush();
    flush();
    sleep(1);
}
ob_end_clean();

?>