使用RewriteCond中的后引用过滤QUERY_STRING

时间:2015-06-17 13:30:44

标签: php regex apache .htaccess backreference

我有一个PHP脚本用于处理图像,然后在网页上显示它们。必须检查查询字符串以拒绝来自外部域的所有请求。 如果TLD是example.com

http://example.com/process.php?img=somepath/images/imgX.png OK
http://example.com/process.php?img=http://example.com/anotherpath/folder/images/imgX.png OK
http://example.com/process.php?img=http://anotherdomain.com/images/someimg.jpg Rejected!

此重写规则适用于我的测试服务器:

<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond %{REQUEST_METHOD} GET
RewriteCond %{QUERY_STRING} [a-zA-Z0-9_]=http://
RewriteCond expr "! %{QUERY_STRING} -strmatch '*%{HTTP_HOST}*'"
RewriteRule .* - [F]
</IfModule>

但是在生产服务器上这不起作用。经过一些头痛和搜索后,我发现在Apache 2.4之前不支持expr ...
根据我的阅读,我可以使用原子反向引用来检查%{QUERY_STRING}中是否存在%{HTTP_HOST}。我的想法是构建像这样的东西

RewriteCond %{HTTP_HOST}::%{QUERY_STRING} ^(.*?)::/\1/?

这显然不适用于当前状态。任何有关此语法的帮助和进一步说明将不胜感激。

2 个答案:

答案 0 :(得分:1)

如果你想在PHP土地上这样做,那么你可以使用s = 'https://mywebsite.com//hello/world//foo/bar' s.gsub(Regexp.new('(?<!http:)(?<!https:)//'), '/') # => "https://mywebsite.com/hello/world/foo/bar"

Link to PHP documentation.

答案 1 :(得分:1)

您可以在Apache 2.2中使用此规则:

RewriteCond %{QUERY_STRING} [a-zA-Z0-9_]=http://
RewriteCond %{HTTP_HOST}#%{QUERY_STRING} !^([^#]+)#.*?\1
RewriteRule ^ - [F]

\1HTTP_HOST

的反向引用

将RewriteCond修改为

RewriteCond %{HTTP_HOST}#.*#%{QUERY_STRING} !^([^#]+)#.*?\1

这会捕获任何网址结构。 JF