我负责用PHP编写的API的后端部分,主要由Flash客户端使用。现在发生的事情是:Flash客户端进行调用,后端加载必要的数据,执行任何必要的处理和后期处理,记录和缓存,然后将结果返回给客户端。
我希望发生的是尽快将数据返回给客户端,关闭连接,然后执行客户端不必关心的所有内容。这可能会使API看起来更具响应性。遵循这里的建议:
http://php.net/manual/en/features.connection-handling.php
实际上有效,除了我必须关闭gzip编码以使其工作,这不是很实用。我们在apache中使用mod_deflate,因此使用它的解决方案将是理想的,但如果有必要,我还会考虑使用不同的方法来gzip我们的内容。
似乎就像应该有办法让Apache知道“我已经发送了你要发送的所有数据”,但我似乎无法找到类似的东西
对于那些想知道的人,是的,我可以尽早清除结果,但Flash客户端将不会处理它们,直到连接关闭。
答案 0 :(得分:3)
您可以尝试将其分成两页。
在第一页中,进行必要的处理,然后通过curl加载第二页,并使用die()。
这将导致第一页完成并关闭,与第二页处理无关。
即:
第1页:
<?php
// Do stuff
// Post or get second page...
// Send Data to client
die();
?>
第2页:
<?php
// Do other stuff....
?>
答案 1 :(得分:0)
在通过register_shutdown_function();
答案 2 :(得分:0)
@ Theo.T因为评论系统从我的代码中删除了废话,我在这里发布:
没有运气。以下打印出额外的废话,并在使用mod_deflate时花费完整的执行时间来关闭连接:
function sleepLongTime() {
print "you can't see this";
sleep(30);
}
ob_end_clean();
register_shutdown_function('sleepLongTime');
header("Connection: close\r\n");
ignore_user_abort(true);
ob_start();
echo ('Text user will see');
ob_end_flush();
flush();
ob_end_clean();
die();
答案 3 :(得分:0)
set_time_limit(0);
header("Connection: close");
header("Content-Length: " .(strlen($stream)+256));
ignore_user_abort(true);
echo $stream;
echo(str_repeat(' ',256));
@ob_flush();
@flush();
@ob_end_flush();
your_long_long_long_long_function_here();
一旦收到$stream
的全部内容,这将告诉用户关闭连接。但要注意不要在header
部分之前回复任何事情:p
如果要发送二进制数据(swf),则可能需要删除“+256”和echo(str_repeat(' ',256));
,但在这种情况下,如果发送的数据少于256个字节,代码“可能”会失败。
答案 4 :(得分:-1)
今天我也遇到了这个案例,经过一些测试后,我发现这种方式有效:
两个步骤:
确保php脚本输出不是gzip编码,解决方案可以参考这个link:
<IfModule mod_env.c>
SetEnvIfNoCase Request_URI "\.php$" no-gzip dont-vary
</IfModule>
将以上内容添加到prj网站下的.htaccess
文件中,然后避免apache自动gzip。
正如有些人在features.connection-handling.php
所说,
set_time_limit(0);
ignore_user_abort(true);
// buffer all upcoming output - make sure we care about compression:
if(!ob_start("ob_gzhandler"))
ob_start();
echo $stringToOutput;
// get the size of the output
$size = ob_get_length();
// send headers to tell the browser to close the connection
header("Content-Length: $size");
header('Connection: close');
// flush all output
ob_end_flush();
ob_flush();
flush();
// close current session
if (session_id()) session_write_close(); //close connection
// here, do what you want.