使用PHP保护文档

1 php authorization

我有一个简单的登录/访问控制系统来保护一些受限制的页面,但在这些页面中有一些需要安全的链接,即Word文档.因此,如果我将这些资源保留在webroot中,则可以通过URL访问它们.保护受限页面内这些资源的最佳方法是什么.我知道我可以用密码保护文件夹,但用户将被挑战两次,一次用于受限页面,然后用于资源链接.有什么建议?

irc*_*ell 12

根据您的使用情况,您可以在此处选择一些选项.

  1. 使用PHP来提供文件.基本上,要么拦截所有通过PHP读取文件的尝试(使用mod_rewrite规则),要么直接链接到PHP并将文件放在文档根目录下.然后使用类似的东西fpassthru将文件发送到浏览器.请注意,您必须正确设置内容类型标头.另请注意,由于服务器需要在PHP中读取整个文件并将其发送,因此会占用大量服务器资源,因此它很容易,但不是很轻.

    $f = fopen('file.doc', 'r');
    if (!$f) {
        //Tell User Can't Open File!
    }
    header('Content-Type: ...');
    header('Content-Length: '.filesize('file.doc'));
    fpassthru($f);
    die();
    
    Run Code Online (Sandbox Code Playgroud)

    这样做的主要好处是它简单易用(适用于所有服务器).但是,您正在交换宝贵的服务器资源(因为虽然PHP正在为文件服务,但它无法为另一个页面提供服务)以获得该优势...

  2. 使用Web服务器使用X-SendFile(Lighttpd),X-SendFile(Apache2/2.2)或X-Accel-Redirect(NginX)等方式发送文件.因此,您将所有请求重定向到PHP(手动或重写).在PHP中,您将进行身份验证.您将发送Content-Type标头,然后发送标题,如X-SendFile: /foo/file.doc.服务器将实际发送的文件,所以你不必(这是远远比PHP本身发送更有效率).

    header('Content-Type: ...');
    header('X-SendFile: /foo/file.doc');
    die();
    
    Run Code Online (Sandbox Code Playgroud)

    这里的主要好处是您不需要从PHP提供文件.您仍然可以执行所需的所有身份验证和日志记录,但在开始传输文件后立即释放PHP.

  3. 使用类似mod_secdownload(lighttpd)或mod_auth_token(Apache)的东西.基本上,当您生成文件的链接时,您在PHP中创建一个令牌.此令牌是密码的MD5与当前时间戳的组合.这里的好处是URL仅对您在配置中指定的时间有效(默认为60秒).这意味着你提供的链接只会激活60秒,然后任何进一步尝试查看内容都会产生一个400系列错误(我不是正面的,这是我的头脑).

    $filename = '/file.doc';
    $secret = 'your-configured-secret-string';
    $time = dechex(time());
    $token = md5($secret . $filename . $time);
    $url = "/downloads/$token/$time$filename";
    echo "<a href="$url">Click Here To Download</a>";
    
    Run Code Online (Sandbox Code Playgroud)

    这样做的主要好处是与实现相关的开销很小.但是你必须习惯让URL在一段时间内有效(默认为60秒)......

  4. 将其推到CDN上进行处理.这类似于选项#3(上面的那个),但是使用CDN来处理文件服务而不是本地服务器.某些CDN(如EdgeCast)提供了类似的功能,您可以在其中设置在一段时间后过期的令牌.如果您拥有大量流量并且可以证明CDN的费用是合理的,那么这种情况将很好地工作.(注意:与链接的CDN没有联系,只有链接,因为我知道它们提供了功能).

至于我个人如何做,我已经做了以上所有.你的用例非常重要.如果您正在构建将要安装在共享主机或您无法控制的多个不同服务器上的系统,请坚持使用第一个选项.如果您具有完全控制权并需要保存服务器资源,请执行其他两个中的一个.

注意:除了这三个之外还有其他选项.这些只是最容易实现的,大多数其他选项都足够相似,以适应这个类别......