`
wgllz
  • 浏览: 109811 次
  • 性别: Icon_minigender_1
  • 来自: 西安
社区版块
存档分类
最新评论

让PHP更快的提供文件下载

    博客分类:
  • PHP
 
阅读更多

一般来说, 我们可以通过直接让URL指向一个位于Document Root下面的文件, 来引导用户下载文件.

但是, 这样做, 就没办法做一些统计, 权限检查, 等等的工作. 于是, 很多时候, 我们采用让PHP来做转发, 为用户提供文件下载.<?php

  1.     $file = "/tmp/dummy.tar.gz";
  2.     header("Content-type: application/octet-stream");
  3.     header('Content-Disposition: attachment; filename="' . basename($file) . '"');
  4.     header("Content-Length: ". filesize($file));
  5.     readfile($file);

但是这个有一个问题, 就是如果文件是中文名的话, 有的用户可能下载后的文件名是乱码.

于是, 我们做一下修改(参考: :

  1. <?php
  2.     $file = "/tmp/中文名.tar.gz";
  3.  
  4.     $filename = basename($file);
  5.  
  6.     header("Content-type: application/octet-stream");
  7.  
  8.     //处理中文文件名
  9.     $ua = $_SERVER["HTTP_USER_AGENT"];
  10.     $encoded_filename = urlencode($filename);
  11.     $encoded_filename = str_replace("+", "%20", $encoded_filename);
  12.     if (preg_match("/MSIE/", $ua)) {
  13.      header('Content-Disposition: attachment; filename="' . $encoded_filename . '"');
  14.     } else if (preg_match("/Firefox/", $ua)) {
  15.      header("Content-Disposition: attachment; filename*=\"utf8''" . $filename . '"');
  16.     } else {
  17.      header('Content-Disposition: attachment; filename="' . $filename . '"');
  18.     }
  19.  
  20.     header('Content-Disposition: attachment; filename="' . $filename . '"');
  21.     header("Content-Length: ". filesize($file));
  22.     readfile($file);
  23. 恩, 现在看起来好多了, 不过还有一个问题, 那就是readfile, 虽然PHP的readfile尝试实现的尽量高效, 不占用PHP本身的内存, 但是实际上它还是需要采用MMAP(如果支持), 或者是一个固定的buffer去循环读取文件, 直接输出.

    输出的时候, 如果是Apache + PHP mod, 那么还需要发送到Apache的输出缓冲区. 最后才发送给用户. 而对于Nginx + fpm如果他们分开部署的话, 那还会带来额外的网络IO.

    那么, 能不能不经过PHP这层, 直接让Webserver直接把文件发送给用户呢?

    今天, 我看到了一个有意思的文章: How I PHP: X-SendFile.

    我们可以使用Apache的module mod_xsendfile, 让Apache直接发送这个文件给用户:

    1. <?php
    2.     $file = "/tmp/中文名.tar.gz";
    3.  
    4.     $filename = basename($file);
    5.  
    6.     header("Content-type: application/octet-stream");
    7.  
    8.     //处理中文文件名
    9.     $ua = $_SERVER["HTTP_USER_AGENT"];
    10.     $encoded_filename = urlencode($filename);
    11.     $encoded_filename = str_replace("+", "%20", $encoded_filename);
    12.     if (preg_match("/MSIE/", $ua)) {
    13.      header('Content-Disposition: attachment; filename="' . $encoded_filename . '"');
    14.     } else if (preg_match("/Firefox/", $ua)) {
    15.      header("Content-Disposition: attachment; filename*=\"utf8''" . $filename . '"');
    16.     } else {
    17.      header('Content-Disposition: attachment; filename="' . $filename . '"');
    18.     }
    19.  
    20.     header('Content-Disposition: attachment; filename="' . basename($file) . '"');
    21.  
    22.     //让Xsendfile发送文件
    23.     header("X-Sendfile: $file");

    X-Sendfile头将被Apache处理, 并且把响应的文件直接发送给Client.

    Lighttpd和Nginx也有类似的模块, 大家有兴趣的可以去找找看 :)

分享到:
评论

相关推荐

    让PHP更快的提供文件下载的代码

    于是, 很多时候, 我们采用让PHP来做转发, 为用户提供文件下载. 复制代码 代码如下: &lt;?php $file = “/tmp/dummy.tar.gz”; header(“Content-type: application/octet-stream”); header(‘Content-Disposition:...

    开源免费PHP 5.2.3下载

    PHP,是英文超文本预处理语言Hypertext Preprocessor的缩写。PHP 是一种 HTML 内嵌式的语言,是一种在服务器端执行的嵌入HTML文档的脚本...PHP还可以执行编译后代码,编译可以达到加密和优化代码运行,使代码运行更快。

    快速下载站管理系统 v1.20 PHP版.rar

    一个专门为软件下载站而设计的CMS系统,是用php mysql开发的,程序简单实用,如果您想做一个软件或源码下载站,快速CMS会是您不错的选择  快速下载站管理系统具有如下特点;  1 div css的设计让程序更简捷,有利于搜索...

    PHP教程之用PHP实现上传的ZIP文件的解压

    前不久在浏览网页时,无意中发现了www.chinaren.com的主页大巴能够把上传的ZIP文件自动的解压,感到非常的有意思,更让我感兴趣的是它的功能是用PHP来,考虑到我也会一些PHP,所以,就决定试试。 经过我一番的查找...

    FFS快速文件分享系统 BLSQL版 v4.2.rar

    CSS技术提供更快的访问速度和赏心悦目的用户界面。 更加完善的文件管理功能,还能为您的文件实现加密! 站内文件搜索让你可以轻松分享到他人上传的文件! 面向站长: 傻瓜化的安装方式,只需上传即可使用。 详细的...

    FFS快速文件分享系统 MYSQL版 v4.4.rar

    FFS-M快速文件分享系统,基于MYSQL驱动,所以运行此程序前,请检查您的PHP是否支持MYSQL。 FFS-M V4.4正式版功能 伪静态功能(无需服务器相关组件支持) 老版本浏览器自动提示升级浏览器 智能下载核心(实现下载...

    前端Javascript+Html5+后端PHP分块上传文件

    目前有测试过上传1.5G左右的没有问题(未测试更大的文件),理论上更大的文件也是可以的,(更大的)原理是一样的 必须配置上传允许数据流大于2M 在php.ini里面或者nginx里面配置 1.实现断点续传,已上传过的块,...

    在PHP中使用X-SendFile头让文件下载更快

    主要介绍了在PHP中让文件下载更快的一个方法,那就是使用X-SendFile头实现,主流量的服务器都支持这个头文件,的朋友可以参考下

    PHP和MySQL.Web开发(第5版)PDF书-英文+源代码

    PHP(外文名:PHP: Hypertext Preprocessor,中文名:“超文本预处理器”)是一种通用开源脚本语言。语法吸收了C语言、Java和Perl的特点...PHP还可以执行编译后代码,编译可以达到加密和优化代码运行,使代码运行更快。

    php大文件上传示例代码-mysql-utf8

    HttpUploader4更加注重对硬盘的保护,在HttpUploader4中不再直接对文件进行I/O操作,而是在内存中对文件进行操作,所以不仅极大的减少了对硬盘的读写次数,同时速度却变的更快了。 借助于HttpUploader4企业能够帮助...

    PHP ADODB 操作文档

    ADODB 是一个强大的 PHP 类库,提供了完整的方法和属性,可以用来控制数据库系统,更棒的是你只要记得它的功能即可,因为不同的数据库系统,只要修改一个...如果在编写程序时,对SQL 命令能做妥善规划,那就更快了。

    FFS快速文件分享系统 4.4 MySQL.rar

    2、 CSS技术提供更快的访问速度和赏心悦目的用户界面。 3、更加完善的文件管理功能,还能为您的文件实现加密! 4、站内文件搜索让你可以轻松分享到他人上传的文件! 5、无限制存储空间和数量,存多少都可以,完全...

    FFS快速文件分享系统 v4.0.rar

    CSS技术提供更快的访问速度和赏心悦目的用户界面。 更加完善的文件管理功能,还能为您的文件实现加密! 站内文件搜索让你可以轻松分享到他人上传的文件! 面向站长: 傻瓜化的安装方式,只需上传即可使用。 详细的...

    拓网PHP网络硬盘系统 1.0.rar

    如果您是第一次使用TopWang PHP Disk,在确认您同意拓网的版权声明后请详细阅读以下说明文档,以便能更快和更好的使用TopWang PHP Disk 1、请到本站官方(http://www.TopWang.com)下载最新版本. 2、将下载回的...

    PHP和MySQLweb开发第五版源代码

    PHP(外文名:PHP: Hypertext Preprocessor,中文名:“超文本预处理器”)是一种通用开源脚本语言。语法吸收了C语言、Java和Perl的特点...PHP还可以执行编译后代码,编译可以达到加密和优化代码运行,使代码运行更快。

    八年PHP文件管理器 v2.6.7

    八年PHP文件管理器功能...支持 远程下载文件 支持进度条  支持 解析 迅雷 网际快车 旋风 地址下载 更新了 发送邮件选择附件 的界面 现在能看到选择了那些附件 更新了批量删除文件的时候 先提示删除那些文件 然后再

    快速下载站管理系统 v1.20.rar

    一个专门为软件下载站而设计的CMS系统,是用php mysql开发的,程序简单实用,如果您想做一个软件或源码下载站,快速CMS会是您不错的选择   快速下载站管理系统具有如下特点;  1 div css的设计让程序更简捷,有利于...

    FFS-M快速文件分享系统MYSQL版 v4.1.rar

    FFS-M V4.0正式版功能 伪静态功能(无需服务器相关组件支持) 老版本浏览器自动提示升级浏览器 智能下载核心(实现下载限速,下载广告,下载分块,负载均衡) 独创标签解析引擎,HTML与PHP完美分离,界面美化更自由...

Global site tag (gtag.js) - Google Analytics