【问题标题】:.htaccess rewriterule /state/city/.htaccess rewriterule /state/city/
【发布时间】:2012-01-23 21:28:15
【问题描述】:

这需要一点解释,所以我希望我不会在这里失去所有人。

我需要得到类似以下的东西:
http://example.com/results.html?state=iowa&city=davenport

变成:
http://example.com/iowa/davenport/

我能够通过使用这两个重写规则来实现这一点:

RewriteRule ^([A-Za-z0-9-]+)/?$ cities.html?state=$1
RewriteRule ^([A-Za-z0-9-]+)/([A-Za-z0-9-]+)/?$ results.html?state=$1&city=$2

问题在于,在后端有“某处的一些代码”由于第二次重写而被破坏。它与根据另一个选择的结果填写选择框有关(不过我认为这并不重要)。我认为问题在于我对 /state/city 的修改过于广泛。

这是我的完整(为了安全而修改).htaccess 文件的副本:

IndexIgnore *
AddHandler application/x-httpd-php5 .html .htm

RewriteRule ^([A-Za-z0-9-]+)/?$ cities.html?state=$1
RewriteRule ^([A-Za-z0-9-]+)/([A-Za-z0-9-]+)/?$ results.html?state=$1&city=$2

<Files .htaccess>
order allow,deny
deny from all
</Files>

RewriteEngine On
RewriteCond %{HTTP_HOST} ^example.com
RewriteRule (.*) http://www.example.com/$1 [R=301,L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . index.php [L]

<IfModule mod_suphp.c>
 suPHP_ConfigPath /home/USER
<Files php.ini>
 order allow,deny
 deny from all
</Files>

它搞砸的代码非常复杂,而且是别人的代码。几个小时后,我无法浏览他们所有的东西,甚至无法接近我可能能够改变的东西以使事情正常进行。

有没有人对我可以做些什么来避免这个问题有任何想法?我真的只有 3 个 .html 文件,我通过这些文件汇集了我的前端代码,所以我尝试了类似

的东西

我的重写规则

与仅使用“文件”而不是 filesMatch 相同。我想出的所有东西都会以某种方式破坏其他东西或整个网站。

【问题讨论】:

  • 是否可以帮助您将[L] 标志(最后一条规则,不要进一步处理)添加到每个:RewriteRule ^([A-Za-z0-9-]+)/?$ cities.html?state=$1 [L]
  • 开启重写日志。您正在重写的请求可能非常明显,您不应该这样做。这些是非常广泛的重写规则。
  • @derobert,我尝试按照您的建议打开日志记录,但它给了我 500 内部服务器错误。
  • @ScottRowley:检查你的错误日志——RewriteLog 不应该给你一个 500 错误。
  • @derobert:我跟踪了我的 error_log 并点击了几次刷新,但没有出现任何新内容。

标签: html .htaccess mod-rewrite


【解决方案1】:

首先:(i) hostgator 不会启用或授予您重写日志的权限; (ii) 您的 suPHP 配置有语法错误,hostgator 几乎肯定会对此进行 spme,并且 .htacess / php.ini 在其自己的 root / vhost 配置中拒绝。但是,我将专注于 mod_rewrite 元素:

RewriteEngine On

RewriteRule ^([A-Za-z0-9-]+)/?$ cities.html?state=$1
RewriteRule ^([A-Za-z0-9-]+)/([A-Za-z0-9-]+)/?$ results.html?state=$1&city=$2

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

RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . index.php [L]

我还假设您在启用了重写引擎的子目录中没有任何 .htaccess 文件,因为这些文件可能会在重写“每个目录”优先规则下抢占它。

Rules (3) 是一个简单的域重定向器。规则 (4) 很严厉:将任何不是现有文件或目录的 URI 重定向到当前目录中的 index.php,但保持查询字符串不变。

规则 (1) 和 (2) 是您的新规则。正如迈克所说,您应该包含[L],但由于文件cities.htmlresults.html 存在,它无论如何都不会匹配。

我很好奇为什么 URI 中的尾随 slach 是可选的。最好决定并解决这个问题。

问题在于 (1) 和 (2) 的匹配标准是两个宽泛的,并且正在挑选用于通用包罗万象 (4) 的 URI。您需要将其锁定以使它们互斥。一个原因是挖掘您的访问日志(可通过 hostgator 获得)以找到应用程序期望的标准 URI 并检查不匹配 (1) 或 (2) - 但是,由于大多数将包含“.”,因此可能不是这样。但是检查一下。

另一个问题是现有脚本是使用绝对引用还是相对引用,例如&lt;img src="images/myimage.png"&gt; 在任何输出 HTML 中。在这里,浏览器请求http://www.example.com/texas/houston,因此将寻找与(1)、(2)或(3)不匹配的http://www.example.com/texas/images/myimage.png,因此被(4)捕获并传递给/index.php。同上 CSS 文件等。因此它们不会 404 和 index.php 会混淆并发送一些默认响应,这将无可救药地混淆浏览器。

但是,再次分析访问日志(在这种情况下或带有推荐人 http://www.example.com/texas/houston 的 USI)将向您显示这种情况是否正在发生。

如果您的应用使用标准子目录,那么您可能可以通过类似于以下内容的规则 (3.1) 来解决此问题

RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond $1/$2                -f
RewriteRule .*?(images|css|styles)/(.+)  $1/$2 [L]

虽然细节将取决于您的应用程序的其余部分。

【讨论】:

    【解决方案2】:

    我能够通过将我的(相关).htaccess 条目更改为以下内容来解决它:

    重写引擎开启
    RewriteRule ^([A-Za-z0-9-]+)/?$ cities.html?state=$1
    RewriteCond %{REQUEST_URI} !^/signup/
    重写规则 ^([A-Za-z0-9-]+)/([A-Za-z0-9-]+)/?$ results.html?state=$1&city=$2
    RewriteCond %{HTTP_HOST} ^example.com
    重写规则 (.*) http://www.example.com/$1 [R=301,L]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    重写规则。 index.php [L]

    补充是:

    RewriteCond %{REQUEST_URI} !^/signup/

    HostGator 能够发现问题是 /signup 在某处的某个日志中的某处,从未找到他们能够查看的日志,但我认为这是我无权访问的内容。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-11-17
      • 1970-01-01
      • 2014-12-18
      • 2023-03-28
      • 2011-04-23
      • 2013-02-03
      相关资源
      最近更新 更多