如何使用PHP会话保护Apache中的目录


8

我有一个使用PHP会话进行身份验证的网站。我想限制访问的目录是一个不使用任何PHP的目录,它只包含静态内容。

我只是不知道如何在没有每个请求都通过PHP脚本的情况下限制访问。有什么方法可以让Apache检查会话凭据并限制访问权限,例如基本身份验证?

Answers:


5

除非您更改设置,否则PHP会话数据将以其自己的serialize()格式的变体形式存储在临时目录中,并且不使用PHP本身也不容易做到这一点。

不幸的是,您似乎希望在动态授权每个请求的同时获得静态服务的文件的速度,这并不是真正的兼容目标。您可能会有一个超轻量级的PHP脚本,然后使用mod_rewrite将对其中的文件的请求重写到该脚本中,从而使事情变得复杂,这可以使事情顺利进行。超级简单的例子:

.htaccess:

 RewriteEngine On
 RewriteMap auth prg:auth.php
 RewriteRule (.*) ${auth:$1}

auth.php:

#!/usr/bin/php
 <?PHP
 set_time_limit(0); # This program needs to run forever. 
 $stdin = fopen("php://stdin","r"); # Keeps reading from standard in
 while (true) {
        $line = trim(fgets($stdin));
        if (isset($_SESSION['USER_LOGGED_IN'])) {
                echo $line\n";
        } else {
                echo "authfailed.html\n";
        }
 }

值得注意的是,该PHP脚本将永远运行,因此,我认为如果更改它,则需要重新启动apache。

这都是未经测试的,但这大致就是我认为您必须进入的方向。

参考文献:


我喜欢这种方法,但是我想知道RewriteMap脚本是否可以访问除stdin之外的任何内容?它具有cookie等的上下文吗?
Cogsy

实际上,是的,您确实有一点。您可以使用mod_rewrite的环境变量语法发送cookie的值(因此,我认为语法将变成$ {auth:$ 1 $ COOKIES}之类的东西,您必须按参数将stdin行分开,通过这种方法,您可以拾取会议内容
Aquarion

如果您通过登录使用恒定的身份验证ID(很多位长度)来设置Cookie,并通过目录访问对其进行检查,该怎么办?不是最好的解决方案,但是它可以在管理页面上使用...(通过文件共享页面,因为用户可以共享cookie而无法使用...)
inf3rno

1

如果您有一个特定的cookie,则可以使用mod_rewrite测试它是否不存在,并给出403禁止。

RewriteCond %{HTTP_COOKIE} !LoggedIn=true
RewriteRule .* - [F,L]

但是,如果有人知道他们需要一个设置为“ LoggedIn = true”的cookie,那么他们可以轻松地绕过您的“保护”。

PHP会话特定于PHP。Apache无法在PHP会话中使用任何信息。您将必须具有一些专门用于进行会话验证的身份验证模块。

我看到的大多数人所做的就是让一个PHP脚本处理静态内容的提供,因为它获取请求,验证会话,读取文件并使用适当的MIME信息发送内容。


或者,您可以通过修改每次登录,注销和GC .htaccess文件...
inf3rno

1

解决该问题的常规方法是将该文件夹上的每个调用重定向到一个php文件,该文件检查用户权限,然后读取文件,并将其发送到输出流或将用户重定向到“无权限”现场。 例如...

保护文件的另一种棘手的方法是从session_id和静态盐(以及可选地从静态文件路径)生成令牌,并通过文件访问对其进行检查。因此,您必须在htaccess文件中重新生成该令牌。我不知道是否只有.htaccess才有可能,否则您必须使用php。我在这里找到了类似的解决方案。我99%的人相信md5不是内置的mod重写功能。


1
我喜欢Blogspot链接中的想法,该想法可用于执行所有实际MD5加密和验证RewriteMapprg://…Shell脚本资源。我需要对其进行测试,并确保它可以在我的设置中正常工作,但是看起来它应该可以与原始Apache + mod_rewrite模块一起使用。
第三方

1

我现在解决这个问题的计划是

  1. 将请求重定向到PHP

    RewriteEngine on
    RewriteRule ([0-9a-z-_]+)$ authenticateUser.php?&file=$1 [L]
    
  2. 使用PHP对用户进行身份验证(所有其他身份验证方法可能太弱或需要始终写入文件中)

    if ( User::hasPermission() && isSane( $filePath ) ) {
        // 
        header( 'X-Sendfile: ' . $filePath );
    }
    
  3. 使用Apache的mod_xsendfiledocsgithub


By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.