[php-src] Issue #13164: flush() doesn't actually flush
| From: | kkmuffme | Date: | Tue, 16 Jan 2024 13:36:31 +0000 |
| Subject: | [php-src] Issue #13164: flush() doesn't actually flush | ||
| Groups: | php.bugs | ||
| Request: | Send a blank email to php-bugs+get-246269@lists.php.net to get a copy of this message | ||
Issue: https://github.com/php/php-src/issues/13164
Author: kkmuffme
### Description
Followup to https://github.com/php/php-src/issues/12385 -
since this added a "feature/fix?" that didn't actually fix the issue*
(*the original issue seems to work correctly in PHP-FPM 7.4/8/8.1/8.2 too for me without the fix -
@nielsdos were you actually able to reproduce the reported issue?)
It just looked like it did fix the issue, because var_dump was used to output text. When there are
only headers (which was the original intention - since we want to send the headers asap and not wait
for the rest of the body), it doesn't work:
```php
<?php
// header( 'X-Abc: Hello'); - actually setting a header makes no difference
$first = headers_sent();
while (ob_get_level() !== 0) {
ob_end_flush();
}
$second = headers_sent();
flush();
$third = headers_sent();
var_dump($first);
$fourth = headers_sent();
var_dump($second);
var_dump($third);
var_dump($fourth);
```
You get 3x
false and the headers are only actually sent after the first
var_dump call (therefore $fourth is true)
Bug:
Currently flush() (and/or ob_implicit_flush being enabled) will only
trigger if there is any non-empty output.
(e.g. adding echo ''; before the flush() won't do anything, however
echo 'a'; will make it flush).
I assume this is also the reason that ob_gzhandler (and/or zlib.output_compression)
starts to output the initial gzip bytes immediately on first callback, as this non-empty return
value will force flush the headers (and therefore break all responses with no body, e.g. HTTP
304,... won't work when using zlib.output_compression) so that later code cannot modify the
Content-Encoding,... headers.
### PHP Version
8.3.1
### Operating System
All