PHP 断点续传实例详解


Posted in PHP onNovember 11, 2017

在做一个案例,要给客户端做断点续传的服务,

断点续传主要是HTTP协议中的Content-Range报头。其理解如下:

Content-Range:响应资源的范围。可以在多次请求中标记请求的资源范围,在连接断开重新连接时,客户端只请求该资源未被下载的部分,而不是重新请求整个资源,实现了断点续传。迅雷就是基于这个原理,使用多线程分段读取网络上的资源,最后合并。关于PHP使用多线程实现断点续传稍后讨论。本文只实现简单的断点续传。

$file = $_GET['video'];
$size = filesize($file);
$size2 = $size-1;
$range = 0;
if(isset($_SERVER['HTTP_RANGE'])) { //http_range表示请求一个实体/文件的一个部分,用这个实现多线程下载和断点续传!
 header('HTTP /1.1 206 Partial Content');
 $range = str_replace('=','-',$_SERVER['HTTP_RANGE']);
 $range = explode('-',$range);
 $range = trim($range[1]);
 header('Content-Length:'.$size);
 header('Content-Range: bytes '.$range.'-'.$size2.'/'.$size);
} else {
 header('Content-Length:'.$size);
 header('Content-Range: bytes 0-'.$size2.'/'.$size);
}
header("Content-type: video/mp4");
header('Accenpt-Ranges: bytes');
header('application/octet-stream');
header("Cache-control: public");
header("Pragma: public");
// 解决在IE中下载时中文乱码问题
$ua = $_SERVER['HTTP_USER_AGENT'];
if(preg_match('/MSIE/',$ua)) { //表示正在使用 Internet Explorer。
 $ie_filename = str_replace('+','%20',urlencode($file));
 header('Content-Dispositon:attachment; filename='.$ie_filename);
} else {
 header('Content-Dispositon:attachment; filename='.$file);
}
$fp = fopen($file,'rb+');
fseek($fp,$range);    //fseek:在打开的文件中定位,该函数把文件指针从当前位置向前或向后移动到新的位置,新位置从文件头开始以字节数度量。成功则返回 0;否则返回 -1。注意,移动到 EOF 之后的位置不会产生错误。
while(!feof($fp)) {    //feof:检测是否已到达文件末尾 (eof)
 set_time_limit(0);    //控制运行时间
 print(fread($fp,1024));   //读取文件(可安全用于二进制文件,第二个参数:规定要读取的最大字节数)
 ob_flush();      //刷新PHP自身的缓冲区
 flush();      //刷新缓冲区的内容(严格来讲, 这个只有在PHP做为apache的Module(handler或者filter)安装的时候, 才有实际作用. 它是刷新WebServer(可以认为特指apache)的缓冲区.)
}
fclose($fp);

php中set_time_limit()函数运用

当你的页面有大量数据时,建议使用set_time_limit()来控制运行时间,默认是30s,所以需要你将执行时间加长点。

如 set_time_limit(800) ,其中将秒数设为0 ,表示持续运行到程序结束。如果要停止运行只能重启php-fpm(文章后面附有重启命令)

如:set_time_limit(0)表示持续运行到程序结束,但这个函数有些在window环境下有些人设置不成功,Linux下也可能会出现问题的,做好在逻辑代码加上try catch避免异常。

注意:这个函数的运行需要你关闭安全模式,在php.ini中将safe_mode = Off 安全模式设置为Off,否则将会出现下面错误:
Warning: set_time_limit() [function.set-time-limit]: Cannot set time limit in safe mode in

ps:在php.ini可以通过定义max_execution_time来设置PHP页面的最大执行时间。

在phpinfo()输出内容可以看到php相关配置。

Loaded Configuration File /etc/php.ini
set_time_limit(800);

这个函数指定了当前所在php脚本的最大执行时间为800秒,实际上

最大执行时间=php.ini里的max_execution_time数值 - 当前脚本已经执行的时间 + 设定值

假如php.ini里的max_execution_time=30,当前脚本已经执行5秒,则:

最大执行时间=30-5+800=825秒。

查看php运行目录命令:

which php
/usr/bin/php

查看php-fpm进程数:

ps aux | grep -c php-fpm

查看运行内存

/usr/bin/php -i|grep mem

重启php-fpm

/etc/init.d/php-fpm restart

总结

以上所述是小编给大家介绍的PHP 断点续传实例详解,希望对大家有所帮助,如果大家有任何疑问欢迎给我留言,小编会及时回复大家的!

PHP 相关文章推荐
java EJB 加密与解密原理的一个例子
Jan 11 PHP
在Ubuntu 14.04上部署 PHP 环境及 WordPress
Sep 02 PHP
PHP连接操作access数据库实例
Mar 30 PHP
ThinkPHP 整合Bootstrap Ajax分页样式
Dec 23 PHP
thinkphp Apache配置重启Apache1 restart 出错解决办法
Feb 15 PHP
thinkPHP5 ACL用户权限模块用法详解
May 10 PHP
浅谈关于PHP解决图片无损压缩的问题
Sep 01 PHP
ThinkPHP 在阿里云上的nginx.config配置实例详解
Oct 11 PHP
PHP实现的最大正向匹配算法示例
Dec 19 PHP
laravel 实现设置时区的简单方法
Oct 10 PHP
PHP pthreads v3下的Volatile简介与使用方法示例
Feb 21 PHP
MacOS下PHP7.1升级到PHP7.4.15的方法
Feb 22 PHP
PHP+AJAX 投票器功能
Nov 11 #PHP
PHP实现双链表删除与插入节点的方法示例
Nov 11 #PHP
PHP实现基于栈的后缀表达式求值功能
Nov 10 #PHP
PHP实现基于图的深度优先遍历输出1,2,3...n的全排列功能
Nov 10 #PHP
PHP根据树的前序遍历和中序遍历构造树并输出后序遍历的方法
Nov 10 #PHP
PHP用函数嵌入网站访问量计数器
Oct 27 #PHP
PHP实现网站访问量计数器
Oct 27 #PHP
You might like
对text数据类型不支持代码页转换 从: 1252 到: 936
2011/04/23 PHP
php读取本地文件常用函数(fopen与file_get_contents)
2013/09/09 PHP
json跟xml的对比分析
2008/06/10 Javascript
JS 页面自动加载函数(兼容多浏览器)
2009/05/18 Javascript
javascript 24小时弹出一次的代码(利用cookies)
2009/09/03 Javascript
在html页面上拖放移动标签
2010/01/08 Javascript
jQuery使用数组编写图片无缝向左滚动
2012/12/11 Javascript
javascript中的绑定与解绑函数应用示例
2013/06/24 Javascript
jQuery手动点击实现图片轮播特效
2020/04/20 Javascript
JavaScript实现拖拽元素对齐到网格(每次移动固定距离)
2016/11/30 Javascript
JavaScript学习笔记之惰性函数示例详解
2017/08/27 Javascript
js 显示日期时间的实例(时间过一秒加1)
2017/10/25 Javascript
jfinal与bootstrap的登出实战详解
2017/11/27 Javascript
Vue下的国际化处理方法
2017/12/18 Javascript
Vue源码解析之数组变异的实现
2018/12/04 Javascript
python计算文本文件行数的方法
2015/07/06 Python
基于Python Shell获取hostname和fqdn释疑
2016/01/25 Python
python append、extend与insert的区别
2016/10/13 Python
python 连接各类主流数据库的实例代码
2018/01/30 Python
Python定义一个函数的方法
2020/06/15 Python
Django Form设置文本框为readonly操作
2020/07/03 Python
python 偷懒技巧——使用 keyboard 录制键盘事件
2020/09/21 Python
利用python绘制中国地图(含省界、河流等)
2020/09/21 Python
Python通过fnmatch模块实现文件名匹配
2020/09/30 Python
英国电动工具购买网站:Anglia Tool Centre
2017/04/25 全球购物
苹果Mac升级:MacSales.com
2017/11/20 全球购物
JACK & JONES瑞典官方网站:杰克琼斯欧式风格男装
2017/12/23 全球购物
纽约州一群才华横溢的金匠制作而成:Hearth Jewelry
2019/03/22 全球购物
yy司仪主持词
2014/03/22 职场文书
产品质量保证书
2014/04/29 职场文书
一次性工伤赔偿协议书范本
2014/11/25 职场文书
物业工程部经理岗位职责
2015/04/09 职场文书
2015年调度员工作总结
2015/04/30 职场文书
捐书仪式主持词
2015/07/04 职场文书
python 用递归实现通用爬虫解析器
2021/04/16 Python
css height属性中的calc方法详解
2021/06/03 HTML / CSS