php下載遠(yuǎn)程文件類(支持?jǐn)帱c(diǎn)續(xù)傳)
更新時(shí)間:2008年11月14日 12:31:51 作者:
1.功能:支持?jǐn)帱c(diǎn)續(xù)傳的下載,能計(jì)算傳輸率,能控制傳輸率
簡(jiǎn)易使用方法:
$object = new httpdownload();
$object->set_byfile($file)%N#H#%;//服務(wù)器文件名,包括路徑
$object->filename = $filename;//下載另存為的文件名
$object->download();
3.源文件:
<?
class httpdownload {
var $data = null;
var $data_len = 0;
var $data_mod = 0;
var $data_type = 0;
var $data_section = 0; //section download
var $sentSize=0;
var $handler = array('auth' => null);
var $use_resume = true;
var $use_autoexit = false;
var $use_auth = false;
var $filename = null;
var $mime = null;
var $bufsize = 2048;
var $seek_start = 0;
var $seek_end = -1;
var $totalsizeref = 0;
var $bandwidth = 0;
var $speed = 0;
function initialize() {
global $HTTP_SERVER_VARS;
if ($this->use_auth) //use authentication
{
if (!$this->_auth()) //no authentication
{
header('WWW-Authenticate: Basic realm="Please enter your username and password"');
header('HTTP/1.0 401 Unauthorized');
header('status: 401 Unauthorized');
if ($this->use_autoexit) exit();
return false;
}
}
if ($this->mime == null) $this->mime = "application/octet-stream"; //default mime
if (isset($_SERVER['HTTP_RANGE']) || isset($HTTP_SERVER_VARS['HTTP_RANGE']))
{
if (isset($HTTP_SERVER_VARS['HTTP_RANGE'])) $seek_range = substr($HTTP_SERVER_VARS['HTTP_RANGE'] , strlen('bytes='));
else $seek_range = substr($_SERVER['HTTP_RANGE'] , strlen('bytes='));
$range = explode('-',$seek_range);
if ($range[0] > 0)
{
$this->seek_start = intval($range[0]);
}
if ($range[1] > 0) $this->seek_end = intval($range[1]);
else $this->seek_end = -1;
if (!$this->use_resume)
{
$this->seek_start = 0;
//header("HTTP/1.0 404 Bad Request");
//header("Status: 400 Bad Request");
//exit;
//return false;
}
else
{
$this->data_section = 1;
}
}
else
{
$this->seek_start = 0;
$this->seek_end = -1;
}
$this->sentSize=0;
return true;
}
function header($size,$seek_start=null,$seek_end=null) {
header('Content-type: ' . $this->mime);
header('Content-Disposition: attachment; filename="' . $this->filename . '"');
header('Last-Modified: ' . date('D, d M Y H:i:s \G\M\T' , $this->data_mod));
if ($this->data_section && $this->use_resume)
{
header("HTTP/1.0 206 Partial Content");
header("Status: 206 Partial Content");
header('Accept-Ranges: bytes');
header("Content-Range: bytes $seek_start-$seek_end/$size");
header("Content-Length: " . ($seek_end - $seek_start + 1));
}
else
{
header("Content-Length: $size");
}
}
function download_ex($size)
{
if (!$this->initialize()) return false;
ignore_user_abort(true);
//Use seek end here
if ($this->seek_start > ($size - 1)) $this->seek_start = 0;
if ($this->seek_end <= 0) $this->seek_end = $size - 1;
$this->header($size,$seek,$this->seek_end);
$this->data_mod = time();
return true;
}
function download() {
if (!$this->initialize()) return false;
try
{
error_log("begin download\n", 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
$seek = $this->seek_start;
$speed = $this->speed;
$bufsize = $this->bufsize;
$packet = 1;
//do some clean up
@ob_end_clean();
$old_status = ignore_user_abort(true);
@set_time_limit(0);
$this->bandwidth = 0;
$size = $this->data_len;
if ($this->data_type == 0) //download from a file
{
$size = filesize($this->data);
if ($seek > ($size - 1)) $seek = 0;
if ($this->filename == null) $this->filename = basename($this->data);
$res = fopen($this->data,'rb');
if ($seek) fseek($res , $seek);
if ($this->seek_end < $seek) $this->seek_end = $size - 1;
$this->header($size,$seek,$this->seek_end); //always use the last seek
$size = $this->seek_end - $seek + 1;
while (!(connection_aborted() || connection_status() == 1) && $size > 0)
{
if ($size < $bufsize)
{
echo fread($res , $size);
$this->bandwidth += $size;
$this->sentSize+=$size;
}
else
{
echo fread($res , $bufsize);
$this->bandwidth += $bufsize;
$this->sentSize+=$bufsize;
}
$size -= $bufsize;
flush();
if ($speed > 0 && ($this->bandwidth > $speed*$packet*1024))
{
sleep(1);
$packet++;
}
}
fclose($res);
}
elseif ($this->data_type == 1) //download from a string
{
if ($seek > ($size - 1)) $seek = 0;
if ($this->seek_end < $seek) $this->seek_end = $this->data_len - 1;
$this->data = substr($this->data , $seek , $this->seek_end - $seek + 1);
if ($this->filename == null) $this->filename = time();
$size = strlen($this->data);
$this->header($this->data_len,$seek,$this->seek_end);
while (!connection_aborted() && $size > 0) {
if ($size < $bufsize)
{
$this->bandwidth += $size;
$this->sentSize+=$size;
}
else
{
$this->bandwidth += $bufsize;
$this->sentSize+=$bufsize;
}
echo substr($this->data , 0 , $bufsize);
$this->data = substr($this->data , $bufsize);
$size -= $bufsize;
flush();
if ($speed > 0 && ($this->bandwidth > $speed*$packet*1024))
{
sleep(1);
$packet++;
}
}
} else if ($this->data_type == 2) {
//just send a redirect header
header('location: ' . $this->data);
}
if($this->totalsizeref==$this->sentSize )error_log("end download\n", 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
else error_log("download is canceled\n", 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
if ($this->use_autoexit) exit();
//restore old status
ignore_user_abort($old_status);
set_time_limit(ini_get("max_execution_time"));
}
catch(Exception $e)
{
error_log("cancel download\n".$e, 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
}
return true;
}
function set_byfile($dir) {
if (is_readable($dir) && is_file($dir)) {
$this->data_len = 0;
$this->data = $dir;
$this->data_type = 0;
$this->data_mod = filemtime($dir);
$this->totalsizeref = filesize($dir);
return true;
} else return false;
}
function set_bydata($data) {
if ($data == '') return false;
$this->data = $data;
$this->data_len = strlen($data);
$this->data_type = 1;
$this->data_mod = time();
return true;
}
function set_byurl($data) {
$this->data = $data;
$this->data_len = 0;
$this->data_type = 2;
return true;
}
function set_lastmodtime($time) {
$time = intval($time);
if ($time <= 0) $time = time();
$this->data_mod = $time;
}
function _auth() {
if (!isset($_SERVER['PHP_AUTH_USER'])) return false;
if (isset($this->handler['auth']) && function_exists($this->handler['auth']))
{
return $this->handler['auth']('auth' , $_SERVER['PHP_AUTH_USER'],$_SERVER['PHP_AUTH_PW']);
}
else return true; //you must use a handler
}
}
?>
復(fù)制代碼 代碼如下:
$object = new httpdownload();
$object->set_byfile($file)%N#H#%;//服務(wù)器文件名,包括路徑
$object->filename = $filename;//下載另存為的文件名
$object->download();
3.源文件:
復(fù)制代碼 代碼如下:
<?
class httpdownload {
var $data = null;
var $data_len = 0;
var $data_mod = 0;
var $data_type = 0;
var $data_section = 0; //section download
var $sentSize=0;
var $handler = array('auth' => null);
var $use_resume = true;
var $use_autoexit = false;
var $use_auth = false;
var $filename = null;
var $mime = null;
var $bufsize = 2048;
var $seek_start = 0;
var $seek_end = -1;
var $totalsizeref = 0;
var $bandwidth = 0;
var $speed = 0;
function initialize() {
global $HTTP_SERVER_VARS;
if ($this->use_auth) //use authentication
{
if (!$this->_auth()) //no authentication
{
header('WWW-Authenticate: Basic realm="Please enter your username and password"');
header('HTTP/1.0 401 Unauthorized');
header('status: 401 Unauthorized');
if ($this->use_autoexit) exit();
return false;
}
}
if ($this->mime == null) $this->mime = "application/octet-stream"; //default mime
if (isset($_SERVER['HTTP_RANGE']) || isset($HTTP_SERVER_VARS['HTTP_RANGE']))
{
if (isset($HTTP_SERVER_VARS['HTTP_RANGE'])) $seek_range = substr($HTTP_SERVER_VARS['HTTP_RANGE'] , strlen('bytes='));
else $seek_range = substr($_SERVER['HTTP_RANGE'] , strlen('bytes='));
$range = explode('-',$seek_range);
if ($range[0] > 0)
{
$this->seek_start = intval($range[0]);
}
if ($range[1] > 0) $this->seek_end = intval($range[1]);
else $this->seek_end = -1;
if (!$this->use_resume)
{
$this->seek_start = 0;
//header("HTTP/1.0 404 Bad Request");
//header("Status: 400 Bad Request");
//exit;
//return false;
}
else
{
$this->data_section = 1;
}
}
else
{
$this->seek_start = 0;
$this->seek_end = -1;
}
$this->sentSize=0;
return true;
}
function header($size,$seek_start=null,$seek_end=null) {
header('Content-type: ' . $this->mime);
header('Content-Disposition: attachment; filename="' . $this->filename . '"');
header('Last-Modified: ' . date('D, d M Y H:i:s \G\M\T' , $this->data_mod));
if ($this->data_section && $this->use_resume)
{
header("HTTP/1.0 206 Partial Content");
header("Status: 206 Partial Content");
header('Accept-Ranges: bytes');
header("Content-Range: bytes $seek_start-$seek_end/$size");
header("Content-Length: " . ($seek_end - $seek_start + 1));
}
else
{
header("Content-Length: $size");
}
}
function download_ex($size)
{
if (!$this->initialize()) return false;
ignore_user_abort(true);
//Use seek end here
if ($this->seek_start > ($size - 1)) $this->seek_start = 0;
if ($this->seek_end <= 0) $this->seek_end = $size - 1;
$this->header($size,$seek,$this->seek_end);
$this->data_mod = time();
return true;
}
function download() {
if (!$this->initialize()) return false;
try
{
error_log("begin download\n", 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
$seek = $this->seek_start;
$speed = $this->speed;
$bufsize = $this->bufsize;
$packet = 1;
//do some clean up
@ob_end_clean();
$old_status = ignore_user_abort(true);
@set_time_limit(0);
$this->bandwidth = 0;
$size = $this->data_len;
if ($this->data_type == 0) //download from a file
{
$size = filesize($this->data);
if ($seek > ($size - 1)) $seek = 0;
if ($this->filename == null) $this->filename = basename($this->data);
$res = fopen($this->data,'rb');
if ($seek) fseek($res , $seek);
if ($this->seek_end < $seek) $this->seek_end = $size - 1;
$this->header($size,$seek,$this->seek_end); //always use the last seek
$size = $this->seek_end - $seek + 1;
while (!(connection_aborted() || connection_status() == 1) && $size > 0)
{
if ($size < $bufsize)
{
echo fread($res , $size);
$this->bandwidth += $size;
$this->sentSize+=$size;
}
else
{
echo fread($res , $bufsize);
$this->bandwidth += $bufsize;
$this->sentSize+=$bufsize;
}
$size -= $bufsize;
flush();
if ($speed > 0 && ($this->bandwidth > $speed*$packet*1024))
{
sleep(1);
$packet++;
}
}
fclose($res);
}
elseif ($this->data_type == 1) //download from a string
{
if ($seek > ($size - 1)) $seek = 0;
if ($this->seek_end < $seek) $this->seek_end = $this->data_len - 1;
$this->data = substr($this->data , $seek , $this->seek_end - $seek + 1);
if ($this->filename == null) $this->filename = time();
$size = strlen($this->data);
$this->header($this->data_len,$seek,$this->seek_end);
while (!connection_aborted() && $size > 0) {
if ($size < $bufsize)
{
$this->bandwidth += $size;
$this->sentSize+=$size;
}
else
{
$this->bandwidth += $bufsize;
$this->sentSize+=$bufsize;
}
echo substr($this->data , 0 , $bufsize);
$this->data = substr($this->data , $bufsize);
$size -= $bufsize;
flush();
if ($speed > 0 && ($this->bandwidth > $speed*$packet*1024))
{
sleep(1);
$packet++;
}
}
} else if ($this->data_type == 2) {
//just send a redirect header
header('location: ' . $this->data);
}
if($this->totalsizeref==$this->sentSize )error_log("end download\n", 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
else error_log("download is canceled\n", 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
if ($this->use_autoexit) exit();
//restore old status
ignore_user_abort($old_status);
set_time_limit(ini_get("max_execution_time"));
}
catch(Exception $e)
{
error_log("cancel download\n".$e, 3,"/usr/local/www/apache22/LOGS/apache22_php.err");
}
return true;
}
function set_byfile($dir) {
if (is_readable($dir) && is_file($dir)) {
$this->data_len = 0;
$this->data = $dir;
$this->data_type = 0;
$this->data_mod = filemtime($dir);
$this->totalsizeref = filesize($dir);
return true;
} else return false;
}
function set_bydata($data) {
if ($data == '') return false;
$this->data = $data;
$this->data_len = strlen($data);
$this->data_type = 1;
$this->data_mod = time();
return true;
}
function set_byurl($data) {
$this->data = $data;
$this->data_len = 0;
$this->data_type = 2;
return true;
}
function set_lastmodtime($time) {
$time = intval($time);
if ($time <= 0) $time = time();
$this->data_mod = $time;
}
function _auth() {
if (!isset($_SERVER['PHP_AUTH_USER'])) return false;
if (isset($this->handler['auth']) && function_exists($this->handler['auth']))
{
return $this->handler['auth']('auth' , $_SERVER['PHP_AUTH_USER'],$_SERVER['PHP_AUTH_PW']);
}
else return true; //you must use a handler
}
}
?>
相關(guān)文章
PHP下對(duì)數(shù)組進(jìn)行排序的函數(shù)
如果你已經(jīng)使用了一段時(shí)間PHP的話,那么,你應(yīng)該已經(jīng)對(duì)它的數(shù)組比較熟悉了——這種數(shù)據(jù)結(jié)構(gòu)允許你在單個(gè)變量中存儲(chǔ)多個(gè)值,并且可以把它們作為一個(gè)集合進(jìn)行操作。2010-08-08
php json_encode()函數(shù)返回json數(shù)據(jù)實(shí)例代碼
php返回json數(shù)據(jù)用到j(luò)son_encode()函數(shù),此函數(shù)會(huì)生成一個(gè)標(biāo)準(zhǔn)的json格式的數(shù)據(jù),實(shí)例代碼如下2014-10-10
php使用PDO事務(wù)配合表格讀取大量數(shù)據(jù)插入操作實(shí)現(xiàn)方法
這篇文章主要介紹了php使用PDO事務(wù)配合表格讀取大量數(shù)據(jù)插入操作實(shí)現(xiàn)方法,涉及php使用excel_reader操作Excel文件及PDO操作數(shù)據(jù)庫(kù)的相關(guān)技巧,需要的朋友可以參考下2017-02-02
php實(shí)現(xiàn)簡(jiǎn)單的語(yǔ)法高亮函數(shù)實(shí)例分析
這篇文章主要介紹了php實(shí)現(xiàn)簡(jiǎn)單的語(yǔ)法高亮函數(shù),實(shí)例分析了php通過(guò)正則表達(dá)式實(shí)現(xiàn)語(yǔ)法高亮的相關(guān)技巧,需要的朋友可以參考下2015-04-04
PHP7創(chuàng)建銷毀session的實(shí)例方法
在本篇文章里小編給大家整理的是關(guān)于PHP7創(chuàng)建銷毀session的實(shí)例方法,有需要的朋友們可以參考下。2020-02-02
php連接本地mysql連接錯(cuò)誤的問(wèn)題解決方法
這篇文章主要介紹了php連接本地mysql連接錯(cuò)誤的問(wèn)題解決方法,文中通過(guò)代碼示例講解的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下2024-10-10
php實(shí)現(xiàn)隨機(jī)顯示圖片方法匯總
本文分享一個(gè)php實(shí)現(xiàn)的隨機(jī)顯示圖片的函數(shù),可以將指定文件夾中存放的圖片隨機(jī)地顯示出來(lái)。有興趣的朋友研究下吧。2015-05-05

