【问题标题】:.htaccess - translation to layman terms needed.htaccess - 需要翻译成外行术语
【发布时间】:2013-12-16 10:44:24
【问题描述】:

我的 .htaccess 使用 Zend 框架运行,我们的一位开发人员之前添加了以下代码:

RewriteCond %{THE_REQUEST} ^.*/index.php
RewriteRule ^(.*)/index.php$ http://www.mydomain.com/$1 [R=301,L]

有人可以帮我翻译成英文吗?我相信它是在说,如果有人试图访问 index.php,那么做一个 301 重定向到主域(即不显示世界“index.php”存在)。当 RewriteRule 具有相同的规则时,我不知道为什么 RewriteCond 存在,也许这是一个错误。无论如何,我不知道它是否有效,因为还有其他规则,并且我的网站实际上可以访问 index.php 文件(无重定向),因此也许可以完全删除上述内容。寻找正确的翻译来理解。

非常感谢!

【问题讨论】:

  • @rishjid 以下任何一个答案对您有帮助吗?您能否将其中一个标记为已接受?
  • @Jon 嗨乔恩,是的,这两个答案确实对我有帮助 - 我想将它们标记为已接受,但我还没有正式尝试过这个(因为我们之前有几个新任务要清除回到这个)。我想同时尝试这两种方法,并将对我最有帮助的答案标记为已接受,我将在完成此修复后立即执行。

标签: regex apache .htaccess mod-rewrite


【解决方案1】:

其实这里RewriteCondRewriteRule 都是必需的。但首先,这条规则不会像现在这样起作用。

正确的工作代码是这样的:

RewriteCond %{THE_REQUEST} /index\.php [NC]
RewriteRule ^(.*?)index\.php$ /$1 [L,R=301,NC,NE]

主要区别是/ 在您的RewriteRule 中的存在会导致http://domain.com/index.php 失败

说明:

  • THE_REQUEST 变量表示 Apache 从您的浏览器收到的原始请求
  • 您需要将 URI 与 THE_REQUEST 匹配,以确保 /index.php 存在于原始 URI 中,而不是对 /index.php 进行某些内部重写的结果
  • 如果您删除 RewriteCond,它可能仍然有效,但您必须确保没有任何规则将您的 URI 重写为任何地方的 /index.php

【讨论】:

  • 非常感谢您!是的,我的应用程序确实写入了 index.php - 它是一个 Zend Framework 应用程序,几乎所有请求都转发到 index.php。这里的目的是必须相应地处理对应用程序的 index.php 文件的直接请求。问题 - 您能否检查下面的回复并确认我是否可以继续使用您的代码,因为您的解释表明我应该使用 RewriteCond,因为我的应用程序使用 index.php 进行路由?另外,您包括(。*?) - 我假设“?”将捕获domain.com/index.php 在 index.php 之前什么都没有的地方?
  • 绝对正确的 (.*?) 在正则表达式中被称为非贪婪量词,如果 URL 是 http://domain.com/index.php,它将匹配 /dir1/,如果 URL 是 http://domain.com/dir1/index.php 是肯定继续使用此规则,但请确保这是您在.htaccess 中的第一条规则,否则这些路由规则会获取所有 URL。 (我已经检查了乔恩的答案,正如我所说,只要没有类似/index.php 的路由规则,它就可以工作)
  • 非常感谢!完美运行!
【解决方案2】:

RewriteCond test string 包含服务器变量%{THE_REQUEST},其形式为:

GET /index.php HTTP/1.1
or
POST /login.php HTTP/1.1


条件模式^.*/index.php 包含一个正则表达式,它匹配任何带有/index.php 的东西...

^ 标记字符串的开始,.* 匹配零个或多个 any 字符实例,/index.php 是不言自明的。

因此,任何包含 /index.php 的 URL 都会被匹配。如果 条件模式$ 符号(字符串结束符号)结尾,则它不会匹配 %{THE_REQUEST} 的任何实例,因为 %{THE_REQUEST} 的所有实例都包含 HTTP URL 后面的请求类型。


RewriteRule 然后用于按照您的描述进行 301 重定向,但重要的是,RewriteRule directive 将其 模式 与当前 URL 匹配(而不是与整个请求字符串匹配,如RewriteCond 在此示例中执行)。

RewriteRule 模式 ^(.*)/index.php 捕获(用方括号表示)/index.php 前面的所有内容,然后创建一个 301 重定向以删除 /index.php


@anubhava 指出,如果您访问 website.com/index.php,那么 RewriteRule 将不起作用,因为它匹配的 URL 不包括前导 /


这两行可以改写为:

RewriteRule ^(.*)index.php$ http://www.mydomain.com/$1 [R=301,L,NC]

那么,如果你访问http://website.com/index.php,那么模式(.*)部分将匹配一个空字符串。

或者如果您访问http://website.com/sub/folder/index.php,那么模式(.*)部分将匹配sub/folder/,然后@987654347在替换字符串中引用它@。


请记住,每个重定向都是通过告诉浏览器请求一个新 URL 来工作的,并且每个请求都由 htaccess 重新处理,所以如果有其他规则允许查看index.php,那么这可以解释为什么你可以看到一些包含 index.php 的 URL。

【讨论】:

  • 非常感谢!这两个答案都确实有助于理解和解决问题。我已经使用了上面的第一个答案,但两者都工作得很好。谢谢!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-03-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多