PHP使用header方式实现文件下载

摘要:
php文件的下载可以通过使用HTTP请求头和php IO来实现。很久以前,编写了这样的函数,但后来代码消失了。今天,我将把它录下来。首先,我将查看一个正常的http请求http/1.1200OKServer:TennineContent类型:application/octet streamContent长度:5050697连接:keep live日期:2017年10月12日星期四

php文件下载可以使用http的请求头加上php的IO可以实现,很久之前写过这么一个功能,后来代码没了,今天记录一下

1、先看一下一个正常的http请求

HTTP/1.1 200 OK
Server: Tengine
Content-Type: application/octet-stream
Content-Length: 5050697
Connection: keep-alive
Date: Thu, 12 Oct 2017 11:24:46 GMT
Accept-Ranges: bytes
Content-Disposition: attachment; filename=down/20170928/zjbb_2.9.5.apk
Expires: Thu, 12 Oct 2017 11:25:46 GMT
Cache-Control: max-age=60
Via: cache25.l2eu6-1[0,200-0,H], cache16.l2eu6-1[16,0], cache8.cn891[0,200-0,H], cache8.cn891[1,0]
Age: 1733678
X-Cache: HIT TCP_MEM_HIT dirn:6:277104755 mlen:-1
X-Swift-SaveTime: Sat, 14 Oct 2017 00:50:47 GMT
X-Swift-CacheTime: 93312000
Timing-Allow-Origin: *
EagleId: b73d0e1c15095411645886178e

2、一些常见的header功能

header('HTTP/1.1 200 OK'); // ok 正常访问
header('HTTP/1.1 404 Not Found'); //通知浏览器 页面不存在
header('HTTP/1.1 301 Moved Permanently'); //设置地址被永久的重定向 301
header('Location: http://www.test.con/'); //跳转到一个新的地址
header('Refresh: 10; url=http://www.test.con/'); //延迟转向 也就是隔几秒跳转
header('X-Powered-By: PHP/7.0.0'); //修改 X-Powered-By信息
header('Content-language: en'); //文档语言
header('Content-Length: 1234'); //设置内容长度
header('Last-Modified: '.gmdate('D, d M Y H:i:s', $time).' GMT'); //告诉浏览器最后一次修改时间
header('HTTP/1.1 304 Not Modified'); //告诉浏览器文档内容没有发生改变
 
###内容类型###
header('Content-Type: text/html; charset=utf-8'); //网页编码
header('Content-Type: text/plain'); //纯文本格式
header('Content-Type: image/jpeg'); //JPG、JPEG 
header('Content-Type: application/zip'); // ZIP文件
header('Content-Type: application/pdf'); // PDF文件
header('Content-Type: audio/mpeg'); // 音频文件 
header('Content-type: text/css'); //css文件
header('Content-type: text/javascript'); //js文件
header('Content-type: application/json'); //json
header('Content-type: application/pdf'); //pdf
header('Content-type: text/xml'); //xml
header('Content-Type: application/x-shockw**e-flash'); //Flash动画
 
######
 
###声明一个下载的文件###
header('Content-Type: application/octet-stream');
header('Content-Disposition: attachment; filename="ITblog.zip"');
header('Content-Transfer-Encoding: binary');
readfile('test.zip');
######
 
###对当前文档禁用缓存###
header('Cache-Control: no-cache, no-store, max-age=0, must-revalidate');
header('Expires: Mon, 26 Jul 1997 05:00:00 GMT');
######
 
###显示一个需要验证的登陆对话框### 
header('HTTP/1.1 401 Unauthorized'); 
header('WWW-Authenticate: Basic realm="Top Secret"'); 
######
 
 
###声明一个需要下载的xls文件###
header('Content-Disposition: attachment; filename=abc.xlsx');
header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet');
header('Content-Length: '.filesize('./test.xls')); 
header('Content-Transfer-Encoding: binary'); 
header('Cache-Control: must-revalidate'); 
header('Pragma: public'); 
readfile('./test.xls'); 

3、看下下载所要用的的请求头

 header("Content-type:application/octet-stream");
 header("Accept-Ranges:bytes");
 header("Accept-Length:".$file_Size);
 header("Content-Disposition: attachment; filename=".$filename);
  • content-type:文件类型

  • Accept-Ranges:表示接收数据的类型或者范围,图片属于二进制的东西所以需要使用字节的方式传输

  • Accept-Length:表示接收的文件大小,php文件下载需要告诉浏览器下载的文件有多大

  • Content-Disposition:附件只需要把文件名给过去就可以,这个名称就是下载时显示的文件名称

4、php的文件操作出现的比较早,文件名是中文的时候需要注意转码

$filename=iconv("UTF-8","GB2312",$filename);

5、php的文件下载机制是首先nginx把文件信息读入服务器内存,然后使用请求头把文件二进制信息通过浏览器传给客户端

feof用来判断文件是否已经读到了末尾,fread用来把文件读入缓冲区,缓冲区的大小是1024,一边读取一边把数据输出到浏览器。为了下载的安全性每次读数据都进行字节的计数。文件读取完毕后关闭输入流

注意:

a、如果运行的过程中出现问题,可以清空(擦掉)输出缓冲区,使用下面的代码即可

ob_clean();

b、很多人喜欢用readfile,如果是大文件,可能会有问题

完整代码

<?php
    ob_clean();
    $action = $_GET['action'];
    $filename = base64_decode($action);//传的参数encode了
    $filepath = '/data/www/www.test.com/'.$filename;

    if(!file_exists($filepath)){
        exit;
    }

    $fp=fopen($filepath,"r");
    $filesize=filesize($filepath);

    header("Content-type:application/octet-stream");
    header("Accept-Ranges:bytes");
    header("Accept-Length:".$filesize);
    header("Content-Disposition: attachment; filename=".$filename);

    $buffer=1024;
    $buffer_count=0;
    while(!feof($fp)&&$file_Size-$buffer_count>0){
    $data=fread($fp,$buffer);
    $buffer_count+=$buffer;
        echo $data;
    }
    fclose($fp);

?>

 

免责声明:文章转载自《PHP使用header方式实现文件下载》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇C# 使用XML序列化对象(二)plsql 建表空间下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

kong

https://ma.ttias.be/nginx-proxy-upstream-sent-big-header-reading-response-header-upstream/#:~:text=If%20the%20HTTP%20headers%20contain,configurations%20to%20your%20location%20bloc...

10个超级有用、必须收藏的PHP代码样例

作为一个正常的程序员,会好几种语言是十分正常的,相信大部分程序员也都会编写几句PHP程序,如果是WEB程序员,PHP一定是必备的,即使你没用它开发过大型软件项目,也一定多少了解它的语法。 尽管PHP经常被人诟病,被人贬低,被人当玩笑开,事实证明,PHP是全世界网站开发中使用率最高的编程语言。PHP最大的缺点是太简单,语法不严谨,框架体系很弱,但这也是它最大...

使用C++ 实现的 websocket 客户端 (基于easywsclient)

直接上代码 easywsclient.hpp #ifndef EASYWSCLIENT_HPP_20120819_MIOFVASDTNUASZDQPLFD #define EASYWSCLIENT_HPP_20120819_MIOFVASDTNUASZDQPLFD // This code comes from: // https://github.co...

perl5 第九章 关联数组/哈希表

第九章 关联数组/哈希表 by flamephoenix 一、数组变量的限制二、定义三、访问关联数组的元素四、增加元素五、创建关联数组六、从数组变量复制到关联数组七、元素的增删八、列出数组的索引和值九、用关联数组循环十、用关联数组创建数据结构  1、(单)链表  2、结构  3、树一、数组变量的限制    在前面讲的数组变量中,可以通过下标访问其中的元素。...

aksk鉴权

简介 鉴权功能的位置处于基础服务的接入网关中。 1. 认证简介 本鉴权方案是在api层面上进行,通过使用Access Key/Secret Key加密的方法来对验证某个请求的调用者身份。 当接入网关接收到业务调用方的请求时,将使用相同的SK和同样的认证机制生成认证字符串,并与用户请求中包含的认证字符串进行比对。如果认证字符串相同,系统认为用户拥有指定的操作...

Nginx tomcat集群 转发后端口丢失

场景: 阿里云主机 docker 搭建nginx集群,访问项目端口丢失 配置如下: 丢失的可能原因: proxy_set_header Host设置不对,修改如下: proxy_set_header Host $http_host; proxy_set_header Host 可以设置有如下几种: proxy_set_header Host $prox...