【发布时间】:2012-08-10 16:59:00
【问题描述】:
我正在动态创建用户应该下载的 zip 文件,下载完成后我想删除该文件。我认为所有 JS 方式都不安全。因此,php 它是一种服务器端语言并不是什么秘密,这让我认为在某种程度上,该客户端和我的服务器之间的字节必须不再传输,因此我可以说现在下载已完成。有没有类似的方法来完成我上面描述的事情?
【问题讨论】:
我正在动态创建用户应该下载的 zip 文件,下载完成后我想删除该文件。我认为所有 JS 方式都不安全。因此,php 它是一种服务器端语言并不是什么秘密,这让我认为在某种程度上,该客户端和我的服务器之间的字节必须不再传输,因此我可以说现在下载已完成。有没有类似的方法来完成我上面描述的事情?
【问题讨论】:
据我所知,无法知道用户何时完成下载。
我会将文件存储在单独的队列中,并在经过一定时间后将其删除(介于 1h 和 1d 之间)
【讨论】:
如果您在 PHP 中处理下载,您可以使用 ignore_user_abort() 在连接中断的情况下保持脚本运行,并在发送数据块时检查 connection_aborted()。如果在设置所有块之前发生中止,则下载失败。由于 Web 服务器缓冲了 PHP 输出,因此无法保证传输确实已经结束。
另一种可能的方法是设置一个管道 Apache 日志,它将事件通知发送到 PHP 脚本。即使下载不是由 PHP 本身处理的,它也可以工作。我相信 Apache 不会将请求标记为使用 HTTP 200 完成,除非服务器收到 TCP/IP 确认最后一个数据包已安全到达。
【讨论】:
为什么不让php来处理下载?
//you may need setting php runtime limit to zero.
header('Content-Description: File Transfer');
header('Content-Type: application/octet-stream');
$filename = "myfile.zip";
$file = file_get_contents($filename);
echo $file;
//download complete
unlink($filename); //delete file
注意: 在我的测试中,我没有删除,而是将输出给 syslog 作为“下载完成” 然后观察 syslog 并运行脚本,
它说下载完成,因为下载似乎 ~1900KB/2000KB 这可能是 chrome 问题,但您可以使用 sleep(3);并等待 3 秒再删除文件以确保没有问题。
编辑: 即使下载因任何原因失败,此脚本也会删除文件。您可能需要为每次下载尝试创建文件。 我会选择:
1- 创建文件 2-用户下载/失败 3-删除文件 4-如果用户想再次下载:转到1
【讨论】: