我有一个虚拟主机,它的一些访问限制配置如下:
<Location "/">
AuthType Basic
AuthName "Restricted Content"
AuthUserFile /var/www/domain/htdocs/.htpasswd
Require valid-user
</Location>
除此之外,我还有以下conf
文件:
Alias /.well-known/acme-challenge/ "/var/www/letsencrypt/"
<Location /.well-known/acme-challenge/>
# Security Options
Options None
AllowOverride None
ForceType text/plain
RedirectMatch 404 "^(?!/\.well-known/acme-challenge/[\w-]{43}$)"
# Do not redirect to https or perform other rewrites
RewriteEngine off
</Location>
我需要/.well-known/acme-challenge/
无需授权即可访问。
我已经尝试Require all granted
向我的conf
文件中添加不同的变体,但无济于事。
如何才能使/.well-known/acme-challenge/
所有虚拟主机无需身份验证即可访问?(我不想修改任何虚拟主机,这个虚拟主机只是一个例子)。
答案1
无法<Location />
在服务器上下文中覆盖虚拟主机上下文中的语句。从阿帕奇文档:
节内的节
<VirtualHost>
在虚拟主机定义之外的相应节之后应用。这允许虚拟主机覆盖主服务器配置。
合并的顺序是(最后合并的组获胜):
<Directory>
(正则表达式除外)和 .htaccess 同时完成(如果允许,则使用 .htaccess 覆盖<Directory>
)<DirectoryMatch>
(和<Directory "~">
)<Files>
并<FilesMatch>
同时完成<Location>
并<LocationMatch>
同时完成<If>
除此之外<Directory>
,每个组都按照它们在配置文件中出现的顺序进行处理。
<VirtualHost>
不允许进入,<If>
所以<Location>
最后合并。
但
如果您仅在 https vhost 中为网站提供服务(由于身份验证,这是合理的),您可以执行以下操作(不会影响您的 https vhost):
Apache v2.2
<VirtualHost *:80>
ServerName example.com
Include letsencrypt-well-known.conf
RedirectMatch permanent ^(?!/\.well-known/acme-challenge/)(.*) "https://example.com$1"
</VirtualHost>
<VirtualHost *:443>
ServerName example.com
DocumentRoot /var/www/html
<Location "/">
AuthType Basic
AuthName "Restricted Content"
AuthUserFile /var/www/domain/htdocs/.htpasswd
Require valid-user
</Location>
...
</VirtualHost>
letsencrypt-well-known.conf
:
<IfModule mod_proxy.c>
ProxyPass /.well-known !
</IfModule>
Alias /.well-known/ /var/www/html/.well-known/
<Location /.well-known/acme-challenge>
Options None
Require all granted
</Location>
Apache v2.4
<Macro RedirectTo $protocol $domain>
<If "'${well_known_enabled}' == 'On' && %{REQUEST_URI} =~ m#^/\.well-known(/|$)#">
# Do nothing
</If>
<ElseIf "tolower(req('Host')) != '$domain' || tolower(%{REQUEST_SCHEME}) != '$protocol'">
Redirect permanent / $protocol://$domain/
</ElseIf>
</Macro>
<VirtualHost *:80>
ServerName example.com
Include letsencrypt-well-known.conf
RedirectTo https example.com
</VirtualHost>
<VirtualHost *:443>
ServerName example.com
DocumentRoot /var/www/html
<Location "/">
AuthType Basic
AuthName "Restricted Content"
AuthUserFile /var/www/domain/htdocs/.htpasswd
Require valid-user
</Location>
...
</VirtualHost>
letsencrypt-well-known.conf
:
<IfModule mod_proxy.c>
ProxyPass /.well-known !
</IfModule>
Define well_known_enabled On
Define well_known_root "/var/www/html"
Alias /.well-known/ "${well_known_root}/.well-known/
<Directory "${well_known_root}/.well-known">
Options None
AllowOverride None
Require all granted
</Directory>
<Location /.well-known/acme-challenge>
Options None
Require all granted
</Location>
答案2
在 Apache 2.4 中,您可以Require expr
向第一个位置块添加一个语句并评估请求 URI,如下所示:
Require expr %{REQUEST_URI} =~ m#^/.well-known/acme-challenge/.*#
或类似的东西(语法实际上没有测试过)。奇怪的m#
语法是正则表达式可以/
在字符串中使用的另一种形式。