如何为可下载文件创建临时链接

时间:2012-09-25 11:04:55

标签: php cakephp cakephp-1.3

我正在制作一个临时下载链接的项目,以保护文件不受hotlinkers的影响......

我相信这有可能这样做..因为我们都知道许多文件共享网站“不想提及任何”......他们的文件链接已过期。 ..

实施例

如果我从他们的网站下载一个文件,他们会提供直接链接以点击它吗? 但是那个链接会在几小时或几分钟后过期。

我怎么知道链接已过期?如果我在一天后在我的下载管理器上复制相同的链接,则无法下载相同的文件。

我已经在htaccess中实现了这一点。

实施例

RewriteRule .*\.(rar|ZIP)$ http://domain.com [R,NC]

如果他们复制浏览器地址栏中的直接链接,他们将被重定向到 http://domain.com

但是如果他们复制下载管理器上的直接链接,则会下载该文件。

如果他们将链接发布到论坛网站,博客等任何其他网站,该怎么办? 并要求读者将链接复制并粘贴到他们的下载管理器中,以便他们可以直接下载。

这是我想阻止保护我的文件的问题。我在PHP上这样做,但我无法弄明白......

非常感谢您的帮助。

5 个答案:

答案 0 :(得分:23)

链接到/downloads/abb76b3acbd954a05bea357144d614b4之类的内容,其中 abb ... 是一个随机字符串,例如当前时间的盐渍哈希。为某人创建此链接时,将随机字符串存储在数据库表中。该表可能如下所示:

+----+-------------+----------------------------------+---------------------+---------------------+
| id | filename    | token                            | created             | modified            |
+----+-------------+----------------------------------+---------------------+---------------------+
|  1 | image.jpg   | abb76b3acbd954a05bea357144d614b4 | 2012-03-26 19:36:41 | 2012-03-26 19:36:41 |
|  2 | program.exe | 19660d0f5e0ca3d42e1718de5d0a1d7e | 2012-08-29 11:07:58 | 2012-08-29 11:07:58 |
+----+-------------+----------------------------------+---------------------+---------------------+

当您在/downloads/...收到请求时,请查找随机字符串并发回正确的文件。如果created时间戳太旧,请不要这样做。使用cronjob清除旧表行,或者理想情况下,每当有人向/downloads/...发出请求时执行此操作。

答案 1 :(得分:2)

使用像这样的代码

 $path="uploads/";
                  $actualfilename=$path.$filename;
                  $fakefilename="downloadfile.pdf";
                   if($typeofview=="download") {
                          @readfile($actualfilename);
                        header('Content-type: application/pdf');
                        header('Content-Disposition: attachment; filename="' . $fakefilename . '"');
                        header('Content-Transfer-Encoding: binary');
                        header('Content-Length: ' . filesize($actualfilename));
                        header('Accept-Ranges: bytes');
                        exit;

将此添加到.htaccess文件

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule fakefile.php(.*)$ orignalfile.php?$1 [L,QSA]

答案 2 :(得分:0)

我想到的解决方案如下: 如果您有表示文件的表,例如FileModel,您可以保存文件的名称,一些细节,大小,文件系统中文件的路径和唯一,这可能是您选择的某些数据的md5的结果它基于一些文件细节,例如:

$data[FileModel]['unique'] = md5(time() . $data[FileModel]['file']);

每次让某人下载你的文件之前你会检查你的表中是否有这样的独特价值,如果是这样你让别人用你在FileModel中创建的downloadFile方法下载它,但就在此之前你创造了新的唯一以防止更多下载

$data[FileModel]['unique'] = md5(time() . $data[$this -> name]['file']);
$this -> FileModel-> save($data[$this -> name]);
$this -> FileModel -> downloadFile($data[$this -> name]);

如果您的数据库中没有这样的唯一值,那么您只需显示有关用户的超时链接的错误

$this -> setFlashError('link expired');

在这里,我为您提供一个示例动作原型,您可以在控制器中开始:

function download($file_data = ''){
        $data = $this->FileModel->find('first', array('conditions' => array('FileModel.unique' => $file), 'fields' => array('*')));

        if(!is_array($data[FileModel])) $this -> setFlashError('link expired');

        else
        {
            $data[FileModel]['unique'] = md5(time() . $data[$this -> name]['file']);
            $this -> FileModel-> save($data[$this -> name]);
            if(!$this -> FileModel -> downloadFile($data[$this -> name]))
            {
                $this -> setFlashError('error'));
            }
        }
}

此外,您可以创建日期时间字段,例如,您可以将1天添加到当前日期,并检查剩余时间以下载过期。

答案 3 :(得分:0)

我发现的那个:

header('Content-Type: application/force-download');
$filee = "your_file.txt";
$filesLocation = dirname(__file__).'/the_sub_folder_for_the_file/'.$filee;
header('Content-Length:' . filesize($filesLocation));
header("Content-Disposition: inline; filename=\"".$filee."\"");
$filesPointer = fopen($filesLocation,"rb");
fpassthru($filesPointer);

答案 4 :(得分:0)

我知道这个老问题,但我有办法下载文件一次没有使用数据库,快速方式:)

if( isset($_GET['file']) && file_exists($_GET['file']) )
{
    $oldName = $_GET['file'];
    $newName = md5(time()).".txt";

    if( rename($oldName, $newName) ) { // rename file to download just once
        downloadFile( $newName ); // download file function
    } else {
        echo 'this file is not exist';
    }
}