一旦调用 echo,PHP 就会刷新输出

发布于 2024-09-14 11:48:24 字数 422 浏览 12 评论 0原文

我认为 flush(); 可以工作,至少从 Google/Stackoverflow 告诉我的来看是这样,但在我的 Windows WAMP(Windows、Apache、MySQL、PHP)系统上它不起作用。

我是否必须设置一些 PHP 设置才能使flush() 工作?

这是我的代码:

<?php
echo "Fun";

flush();

sleep(5);

echo "<br>Mo";
?>

当脚本执行完成时(5秒后),代码只是一起输出。我不希望这样,我希望立即显示“Fun”,然后在5秒后显示“Mo”。

我尝试过其他刷新组合,例如 ob_end_flush(); 或 ob_implicit_flush(true); 但没有任何效果。有什么想法吗?

I thought flush(); would work, at least from what Google/Stackoverflow tell me, but on my Windows WAMP (Windows, Apache, MySQL, PHP) system it doesn't work.

Is there some PHP setting I have to set to make flush() work?

Here's my code:

<?php
echo "Fun";

flush();

sleep(5);

echo "<br>Mo";
?>

The code just outputs all together when the script is done executing (after 5 seconds).. I don't want this, I want 'Fun' to show up right away, and then after 5 seconds 'Mo'.

I've tried other combinations of flush like ob_end_flush(); or ob_implicit_flush(true); but nothing is working. Any ideas?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

梦毁影碎の 2024-09-21 11:48:24

这就是我发现的:

Flush 在 Apache 的 mod_gzip 或 Nginx 的 gzip 下不起作用,因为从逻辑上讲,它正在对内容进行 gzip 压缩,并且要做到这一点,它必须缓冲内容以对其进行 gzip。任何类型的 Web 服务器 gzip 压缩都会影响这一点。简而言之,在服务器端,我们需要禁用 gzip 并减小 fastcgi 缓冲区大小。所以:

  • 在 php.ini 中:

    。输出缓冲 = 关闭

    。 zlib.output_compression = Off

  • 在 nginx.conf 中:

    。 gzip 关闭;

    。 proxy_buffering off;

另外,请准备好以下几行,特别是如果您无法访问 php.ini:

  • @ini_set('zlib.output_compression',0);

  • @ini_set('implicit_flush',1);

  • @ob_end_clean();

  • set_time_limit(0);

最后,如果你有的话,注释下面的代码:

  • ob_start('ob_gzhandler');

  • ob_flush();

PHP测试代码:

ob_implicit_flush(1);

for($i=0; $i<10; $i++){
    echo $i;

    //this is for the buffer achieve the minimum size in order to flush data
    echo str_repeat(' ',1024*64);

    sleep(1);
}

So that's what I found out:

Flush would not work under Apache's mod_gzip or Nginx's gzip because, logically, it is gzipping the content, and to do that it must buffer content to gzip it. Any sort of web server gzipping would affect this. In short, at the server side, we need to disable gzip and decrease the fastcgi buffer size. So:

  • In php.ini:

    . output_buffering = Off

    . zlib.output_compression = Off

  • In nginx.conf:

    . gzip off;

    . proxy_buffering off;

Also have this lines at hand, specially if you don't have acces to php.ini:

  • @ini_set('zlib.output_compression',0);

  • @ini_set('implicit_flush',1);

  • @ob_end_clean();

  • set_time_limit(0);

Last, if you have it, coment the code bellow:

  • ob_start('ob_gzhandler');

  • ob_flush();

PHP test code:

ob_implicit_flush(1);

for($i=0; $i<10; $i++){
    echo $i;

    //this is for the buffer achieve the minimum size in order to flush data
    echo str_repeat(' ',1024*64);

    sleep(1);
}
夜巴黎 2024-09-21 11:48:24

该脚本在 CLI 中运行良好,显示“Fun”,等待 5 秒后显示“
Mo”。

对于浏览器,结果可能会有所不同,因为:

  1. 浏览器不会立即开始渲染。获取 HTML 文档的 3 个字节的数据不足以执行任何操作,因此很可能会等待更多字节。
  2. 库级别上的隐式 IO 缓冲很可能会处于活动状态,直到收到换行符为止。

要解决此问题,请执行以下操作: 1)使用文本/纯内容类型进行测试; 2) 需要换行符,所以做一个 echo "Fun\n";echo "
Mo\n";
当然你不会使用 text/plain对于真实的 HTML 数据。

The script works fine from CLI, displaying "Fun", waiting 5 secs before displaying "<br>Mo".

For a browser the results might be a bit different because:

  1. The browser wont start rendering right away. Getting 3 bytes of data for HTML document isn't enough to do anything, so it'll most likely wait for a few more.
  2. Implicit IO buffering on the lib level will most likely be active until a newline is received.

To work around 1) use text/plain content type for your test; 2) needs newlines, so do an echo "Fun\n"; and echo "<br>Mo\n"; Of course you wont be using text/plain for real HTML data.

比忠 2024-09-21 11:48:24

如果您正在使用 CGI/FastCGI,那就算了!这些不实现冲洗。网络服务器可能有它自己的缓冲区。

您可以使用以下命令禁用 PHP 中的所有输出缓冲:

ob_implicit_flush();

If you're using CGI/FastCGI, forget it! These don't implement flush. The Webserver might have it's own buffer.

You can disable all output buffering in PHP with following command:

ob_implicit_flush();
恬淡成诗 2024-09-21 11:48:24

如果问题仍然存在,尽管您

implicit_flush = yes 

在 php.ini 中明确设置,但您可能还想设置

output_buffering = off

在我的情况下起作用的方法(在拉扯我的头发 4 个多小时后)

If the problem persists, although you explicitly set

implicit_flush = yes 

in your php.ini, you might also want to set

output_buffering = off

which did the trick in my case (after pulling my hair for 4+hrs)

小嗲 2024-09-21 11:48:24

检查 php.ini 中的 output_buffering

Check your php.ini for output_buffering.

平安喜乐 2024-09-21 11:48:24

也许问题是 Apache 这里,它也可能有缓冲区......

Maybe the problem is Apache here, which also may have buffers...

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文