在四处打听和做一些研究时,似乎很多人真的在推动 X-Sendfile 作为从 PHP 脚本向基于浏览器的客户端提供大型可下载文件的首选方法。
我一直在研究的一些方法是:
其中,大多数人告诉我 X-Sendfile 是最好的。
问题是,我正在尝试实现一种下载方法,它不仅能够处理大文件,而且可以在大多数服务器上广泛通用,因为我正在编写的脚本将被许多其他服务器使用,而不仅仅是我自己的。
我的问题是:是什么让 X-Sendfile 变得更好?如果它这么好,为什么我没有听到很多关于它的消息,为什么它没有被更频繁地使用?最后,大多数典型的低预算共享网络主机是否支持 X-Sendfile?
谢谢!
我遇到的情况是,当我必须通过 HTTP 协议从 Web 服务器 Apache 2.4.4 下载大文件(最多 4GB)时。我尝试了几种方法,但最好的解决方案似乎是使用 X-SendFile 模块。
由于我为文件上传提供进度条,因此我需要为文件下载提供相同的功能。这是我的问题:
一般来说,是否有更好的文件下载选项,可以让我监控文件下载进度?它可以是客户端 (JavaScript) 或服务器解决方案 (PHP)。是否有任何特定的网络服务器允许这样做?
目前我使用:
多次感谢。
在 LAMP 堆栈上,我无法让 xSendFile 工作。问题是下载有 0 个字节。
为了确保我安装了 xSendFile,我已将其添加到我的.htaccess文件中:
<IfModule mod_xsendfile.c>
SetEnv MOD_mod_xsendfile 1
</IfModule>
Run Code Online (Sandbox Code Playgroud)
(我无法测试这个,apache_get_modules()因为我将 PHP 作为 fastCGI 运行。)
然后我有以下 PHP 代码:
if (1 != getenv('MOD_mod_xsendfile'))
{
echo 'mod_xsendfile is not installed';
}
else
{
$path = '/home/infar/';
$file = 'hello.txt';
if (file_exists($path.$file) && strlen($path.$file)>1)
{
if (true) // change to false to go around Yii
{
Yii::app()->request->xSendFile($path.$file,array(
'saveName'=> 'hello.txt',
'mimeType'=> 'plain/text',
'terminate'=> true,
));
}
else
{
//set proper Content-Type
header('Content-Type: plain/text');
//force download …Run Code Online (Sandbox Code Playgroud) 我正在编写一个 PHP 应用程序,用户可以在其中下载一些文件。并非所有文件都可以被所有用户下载,一些复杂的权限检查正在幕后进行。
由于此权限检查,我不想公开文件实际所在的 url,因为我想强制用户始终使用验证其凭据的端点。
在我当前的实现中,这都是使用 PHP(fread 等)编写的。为了最大限度地减少内存消耗,它被实现为一个流,这样 PHP 主要充当代理。
但我想只使用 PHP 进行身份验证,然后使用 Apache2 进行实际托管。环顾四周,似乎 X-Sendfile 是一个理想的选择。
使用 X-Sendfile 的唯一问题是它仅适用于本地文件,而我的文件位于远程存储服务器(而不是我的网络服务器)上。
所以基本上我有一个直接链接到我的存储服务器(我想隐藏):
https://storage.example.com/the-pet-goat.pdf
以及用户与之交互的公共链接:
https://www.example.com/randomized-id/download
我希望当用户访问https://www.example.com/randomized-id/download 时检查其凭据,如果成功,他应该(不可见地)重定向到存储服务器上的文件。
有没有办法实现这一点(使用Apache)?我找到了 X-Accel-Redirect,但那是针对 NGinx 的
我在 SO 上发现了一个类似的问题: Alternative to X-sendfile in Apache for sent file given a URL? 但那个是专门针对 S3、Apache(和 Ruby on Rails)的,而这个问题对于 Apache 来说更通用。
我正在开发一个webapp,X-Accel-Redirect标头只能在没有扩展名的文件中正常工作.出于某种原因,如果我在文件名中添加扩展名,则X-Accel-Redirect不起作用.
工作范例:
X-Accel-Redirect: /protected_files/myfile01.z
Run Code Online (Sandbox Code Playgroud)
非工作示例:
X-Accel-Redirect: /protected_files/myfile01.zip
Run Code Online (Sandbox Code Playgroud)
我正在使用nginx 1.7.1.
最初,奇怪的部分是,如果我用mime.types文件中未注册的内容更改扩展部分(在本例中为".zip"),它工作正常(显然我相应地重命名文件),但扩展指向知道mime类型(类似"zip","jpg","html")将生成"404 Not found"错误.
更新: 似乎问题是由于我在conf文件中的这个规则:
location ~ \.(js|css|png|jpg|gif|swf|ico|pdf|mov|fla|zip|rar)$ {
try_files $uri =404;
}
Run Code Online (Sandbox Code Playgroud)
出于某种原因,似乎nginx首先在文件系统中测试文件的存在,然后尝试"内部/别名"路径.
关于如何让nginx将所有来自X-Accel-Redirect的"/ protected_files"直接过滤到"内部"而不是先尝试在其他路径中查找的想法?
提前致谢.
我在前端使用 React-native,在服务器上使用 PHP 后端。我需要能够向我想要从中下载文件的服务器发送密码。我正在连接到一个 PHP 脚本,该脚本使用 X-SendFile 库在密码正确的情况下将文件发回。
目前我正在使用 RNFS.downloadFile() 下载和保存文件,但这似乎只适用于 GET 而不适用于 POST。我希望能够将文件保存到 DocumentDirectoryPath。
我当前的代码如下所示:
await RNFS.downloadFile({
fromUrl: 'http://example.com/myfile.zip',
toFile: RNFS.DocumentDirectoryPath + "/userdata/myfile.zip",
}).promise
Run Code Online (Sandbox Code Playgroud)
我希望能够做这样的事情:
await RNFS.downloadFile({
method: post,
body: {passcode: "abc123", filename: "myfile.zip"},
fromUrl: 'http://example.com/getfile.php',
toFile: RNFS.DocumentDirectoryPath + "/userdata/myfile.zip",
}).promise
Run Code Online (Sandbox Code Playgroud)
如何更改我的代码,以便将密码作为 POST 参数传递?
我在我的服务器上设置了一个带PHP的下载脚本,它在让用户通过Apache(X-Sendfile)下载文件之前检查一些细节.文件位于Document-Root之外.
使用Apache和Module X-Sendfile下载的代码是:
header("X-Sendfile: $fullpath");
header("Content-Type: application/octet-stream");
header("Content-Disposition: attachment; filename=\"$link_file\"");
Run Code Online (Sandbox Code Playgroud)
使用Apache和X-Sendfile时,我的客户端下载速度为500 kB/s.我还用Apache测试了它,没有X-Sendfile和Document Root中的相同文件 - 这里也是一样!
所以我测试下载相同的文件,使用相同的客户端,两侧相同的基础设施和几秒钟后通过PHP与readfile连接相同的互联网连接:
header("Pragma: no-cache");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Content-Type: application/octet-stream");
header("Content-Length: ".(string)(filesize($fullpath)));
header("Content-Disposition: attachment; filename=\"$link_file\"");
readfile($fullpath);
Run Code Online (Sandbox Code Playgroud)
这次下载速度为9.500 kB/s!
我使用两个选项多次重复此测试,每次尝试时结果都相同.除了下载速度之外,唯一的区别是在尝试使用PHP readfile方法时,几秒钟的等待时间(取决于下载的文件的大小).当立即重复PHP readfile方法时,等待时间没有再出现.很可能是因为它在第一次存储在内存中.
我在服务器上使用专业的HP Raid系统,其平均本地速度为800 MB/s,因此不能使用Diskspeed.我也没有在Apache的httpd.conf中找到任何压缩或带宽设置.
你们中的任何人都可以解释为什么下载速度和如何改变它有如此大的差异?
先感谢您.
- 服务器:Windows Server 2008 R2 Apache/2.2.21(Win32)PHP/5.4.20
- 客户端:Windows 7旗舰版x64谷歌浏览器30.0.1599.101局域网> 100 Mbit/s
如何在amazon linux ami上为httpd 2.4安装xsendfile?来自amazon和epel的默认软件包存储库没有httpd 2.4的软件包,仅适用于httpd 2.2.如果可能的话,我宁愿不编译模块.谢谢.
我需要使用PHP和身份验证从我的网络服务器提供非常大的文件 (1Gb+) ,因此只有一些客户有权下载文件。
我不想使用直接链接,并且PHP由于内存和超时限制,不能选择使用脚本来提供文件。
我的网络服务器由/ 6管理Plesk并运行。ApacheCentOS
x-sendfile ×9
php ×7
apache ×3
apache2 ×1
apache2.4 ×1
curl ×1
fopen ×1
http ×1
javascript ×1
linux ×1
mime-types ×1
nginx ×1
performance ×1
plesk ×1
post ×1
react-native ×1
readfile ×1
yii ×1