我有两个域johny.com
和alice.com
一个管理它们的 Web 服务器 (apache)。Web 文件位于和中,/var/www/johny.com
并/var/www/alice.com
配置为两个具有适当ServerName
和的虚拟主机DocumentRoot
。现在 Alice 想要保护她在 Web 上的一个文件不被任何人看到。她引入了一个.htaccess
包含以下内容的文件
<Files "private.txt">
Require all denied
</Files>
并为其虚拟主机的 apache 配置添加了以下内容
<Directory /var/www/alice.com>
Options Indexes FollowSymLinks
AllowOverride All
</Directory>
没有人可以访问alice.com/private.txt
。到目前为止一切顺利。
现在 John 决定通过修改他的 vhost apache 配置来为 Alice 的网站提供一个别名
Alias "/alice" "/var/www/alice.com"
任何人都可以看到 Alice 在 上的网页john.com/alice
。但任何人也可以看到 Alice 的私人文件的内容。
alice.com/private.txt
给出 403 Forbidden。
john.com/alice/private.txt
显示文件的内容。
这里发生了什么?AllowOverride
没有通过指令传播Alias
?我们该如何解决这个问题?Apache 版本是Apache/2.4.38 (Debian)
。此外,将乱码放入.htaccess
文件只会在 上产生 500 内部服务器错误alice.com
,而不会在 上产生john.com/alice
,因此似乎 根本.htaccess
不被视为别名。
答案1
问题AllowOverride All
在于目录缺少指令/var/www/alice.com
。
具体来说,问题在于:(重点是我的)
并将以下内容添加到 apache 配置中她的虚拟主机
由于您在 Alice 的虚拟主机块内定义了这些目录权限,因此它们不适用,john.com/alice
因为该目录不是通过与 Alice 对应的块的上下文访问的<VirtualHost>
。就服务器而言,别名合法地访问文件系统中的某个目录。碰巧的是,它是与另一个虚拟主机的根目录相同的目录。
来自文档:
节内的节在虚拟主机定义之外的相应节之后应用。这允许虚拟主机覆盖主服务器配置。
然而,就您的具体情况而言,重要的是要注意,这只有在实际调用VirtualHost
与所讨论部分相对应的上下文时才会真正发生,而这里并非如此。
有几种方法可以解决这个问题。最简单的方法是简单地AllowOverride All
在服务器上下文(即,不在VirtualHost
、.htaccess
或者甚至另一个Directory
块内。)
<Directory "/var/www/alice.com">
Options Indexes FollowSymLinks
Require all granted
AllowOverride All
</Directory>
请再次注意,因为您正在声明AllowOverride All
,所以现在您将能够在.htaccess
该目录中的文件中修改这些设置,而不管VirtualHost
从哪个上下文访问该目录。
如果您想要更花哨一点,并且您执意/var/www/alice.com
要从访问john.com
但在alice.com
的虚拟主机上下文中,那么您可以随时将uri配置john.com/alice
为。ProxyPass
http://alice.com
<VirtualHost "*:80">
...
<Location "/alice">
ProxyPreserveHost Off
ProxyPass http://alice.com/
</Location>
</VirtualHost>
您需要启用上述mod_proxy
功能mod_proxy_http
,但它将满足您对这个特定用例的要求,尽管我会谨慎地依赖该Location
指令,原因如下文档很好地详细阐述了。