Home  >  Article  >  Backend Development  >  PHP file download class that supports breakpoint resumption (source code attached)

PHP file download class that supports breakpoint resumption (source code attached)

WBOY
WBOYOriginal
2016-07-25 08:55:241064browse
  1. /**PHP download class, supports breakpoint resume
  2. * Date: 2013-06-30
  3. * Author: fdipzone
  4. * Ver: 1.0
  5. * edit: ww.jbxue.com
  6. * Func:
  7. * download: Download file
  8. * setSpeed : Set the download speed
  9. * getRange: Get the Range in the header
  10. */
  11. class FileDownload{ // class start
  12. private $_speed = 512; // 下载速度
  13. /**Download
  14. * @param String $file The path of the file to be downloaded
  15. * @param String $name The file name, if it is empty, it will be the same as the downloaded file name
  16. * @param boolean $reload Whether to enable breakpoint resumption
  17. */
  18. public function download($file, $name='', $reload=false){
  19. if(file_exists($file)){
  20. if($name==''){
  21. $name = basename($file);
  22. }
  23. $fp = fopen($file, 'rb');
  24. $file_size = filesize($file);
  25. $ranges = $this->getRange($file_size);
  26. header('cache-control:public');
  27. header('content-type:application/octet-stream');
  28. header('content-disposition:attachment; filename='.$name);
  29. if($reload && $ranges!=null){ // 使用续传
  30. header('HTTP/1.1 206 Partial Content');
  31. header('Accept-Ranges:bytes');
  32. // 剩余长度
  33. header(sprintf('content-length:%u',$ranges['end']-$ranges['start']));
  34. // range信息
  35. header(sprintf('content-range:bytes %s-%s/%s', $ranges['start'], $ranges['end'], $file_size));
  36. // fp指针跳到断点位置
  37. fseek($fp, sprintf('%u', $ranges['start']));
  38. }else{
  39. header('HTTP/1.1 200 OK');
  40. header('content-length:'.$file_size);
  41. }
  42. while(!feof($fp)){
  43. echo fread($fp, round($this->_speed*1024,0));
  44. ob_flush();
  45. //sleep(1); // 用于测试,减慢下载速度
  46. }
  47. ($fp!=null) && fclose($fp);
  48. }else{
  49. return '';
  50. }
  51. }
  52. /**Set download speed
  53. * @param int $speed
  54. */
  55. public function setSpeed($speed){
  56. if(is_numeric($speed) && $speed>16 && $speed<4096){
  57. $this->_speed = $speed;
  58. }
  59. }
  60. /**Get header range information
  61. * @param int $file_size file size
  62. * @return Array
  63. */
  64. private function getRange($file_size){
  65. if(isset($_SERVER['HTTP_RANGE']) && !empty($_SERVER['HTTP_RANGE'])){
  66. $range = $_SERVER['HTTP_RANGE'];
  67. $range = preg_replace('/[s|,].*/', '', $range);
  68. $range = explode('-', substr($range, 6));
  69. if(count($range)<2){
  70. $range[1] = $file_size;
  71. }
  72. $range = array_combine(array('start','end'), $range);
  73. if(empty($range['start'])){
  74. $range['start'] = 0;
  75. }
  76. if(empty($range['end'])){
  77. $range['end'] = $file_size;
  78. }
  79. return $range;
  80. }
  81. return null;
  82. }
  83. } // class end
  84. ?>
复制代码

2,演示示例 demo.php

  1. require('FileDownload.class.php');
  2. $file = 'book.zip';
  3. $name = time().'.zip';
  4. $obj = new FileDownload();
  5. $flag = $obj->download($file, $name);
  6. //$flag = $obj->download($file, $name, true); // 断点续传
  7. if(!$flag){
  8. echo 'file not exists';
  9. }
  10. ?>
复制代码

断点续传测试方法: 使用linux wget命令去测试下载, wget -c -O file http://xxx

1,先关闭断点续传

  1. $flag = $obj->download($file, $name);
复制代码

Use wget command to test breakpoint resumption:

  1. root@jbxue:~/Downloads$ wget -O test.rar http://demo.fdipzone.com/demo.php
  2. --2013-06-30 16:52:44-- http: //demo.fdipzone.com/demo.php
  3. Resolving host demo.fdipzone.com... 127.0.0.1
  4. Connecting demo.fdipzone.com|127.0.0.1|:80... Connected.
  5. HTTP request sent, waiting for response... 200 OK
  6. Length: 10445120 (10.0M) [application/octet-stream]
  7. Saving to: “test.rar”
  8. 30% [======== =====================> ] 3,146,580 513K/s Estimated time 14s
  9. ^C
  10. root@jbxue:~/Downloads$ wget -c -O test. rar http://demo.fdipzone.com/demo.php
  11. --2013-06-30 16:52:57-- http://demo.fdipzone.com/demo.php
  12. Resolving host demo.fdipzone. com... 127.0.0.1
  13. Connecting demo.fdipzone.com|127.0.0.1|:80... Connected.
  14. HTTP request sent, waiting for response... 200 OK
  15. Length: 10445120 (10.0M) [application/octet-stream]
  16. Saving to: “test.rar”
  17. 30% [======== =====================> ] 3,146,580 515K/s Estimated time 14s
  18. ^C
Copy the code

You can see it with wget -c The download cannot be resumed from a interrupted point.

2. Enable breakpoint resumption

  1. $flag = $obj->download($file, $name, true);
Copy the code

Use the wget command to test the resume function.

  1. root@jbxue:~/Downloads$ wget -O test.rar http://demo.fdipzone.com/demo.php
  2. --2013-06-30 16:53:19-- http: //demo.fdipzone.com/demo.php
  3. Resolving host demo.fdipzone.com... 127.0.0.1
  4. Connecting demo.fdipzone.com|127.0.0.1|:80... Connected.
  5. HTTP request sent, waiting for response... 200 OK
  6. Length: 10445120 (10.0M) [application/octet-stream]
  7. Saving to: “test.rar”
  8. 20% [====== ============> ] 2,097,720 516K/s Estimated time 16s
  9. ^C
  10. root@jbxue:~/Downloads$ wget -c -O test.rar http://demo.fdipzone. com/demo.php
  11. --2013-06-30 16:53:31-- http://demo.fdipzone.com/demo.php
  12. Resolving host demo.fdipzone.com... 127.0.0.1
  13. Resolving Connect demo.fdipzone.com|127.0.0.1|:80... Connected.
  14. HTTP request sent, waiting for response... 206 Partial Content
  15. Length: 10445121 (10.0M), 7822971 (7.5M) Bytes remaining [application/octet-stream]
  16. Saving to: “test.rar”
  17. 100%[++++++++++++++++++++++++====================== =========>] 10,445,121 543K/s took 14s
  18. 2013-06-30 16:53:45 (543 KB/s) - Saved "test.rar" [10445121/10445121] )
Copy the code

You can see that the download will start from the breakpoint position (%20).

Attached, the source code download address of the PHP file download class (supports breakpoint resume download)



Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn