【问题标题】:Rewrite rule htaccess disturbing other rewrite rules重写规则 htaccess 干扰其他重写规则
【发布时间】:2015-01-27 16:08:49
【问题描述】:

我的网站上有一个页面动态生成,根据cityf 参数列出所有网点,下面是重写规则,将其转换为对 SEO 友好的 URL,它运行良好。

RewriteRule ^([^/.]+)/?$ /cityres?cityf=$1 [L]

我的网站上有一个博客页面,.htaccess 如下所示用于转换 SEO 友好 URL (http://example.com/title-of-blog)

RewriteRule ^([^/.]+)/?$ /blogdetail?prmn=$1 [L]

现在我面临的问题是,当有人访问 blog 页面时,链接 http://example.com/title-of-blog 而不是在页面上显示博客详细信息,而是显示我的错误消息 No outlets near title-of-blog。

我遇到了 Apache 无法识别何时重写 cityres 页面以及何时重写 blogdetail 页面的问题。

有人建议Make sure that each rule has a common prefix (e.g. /blog/page1 and /news/page2).,但我没听懂。

这里有什么建议吗?


编辑:
整个htaccess如下
Options +FollowSymLinks
RewriteEngine On

RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index\.php
RewriteRule ^index\.php$ / [L,R=301]

RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index
RewriteRule ^index\.php$ / [L,R=301]

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

# remove .php from URL
RewriteCond %{REQUEST_FILENAME}.php -f
RewriteCond %{REQUEST_URI} !/$
RewriteRule (.*) $1\.php [L] 

# remove .html
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^([^/.]+)\.html$ /$1 [L,R=301] 

ErrorDocument 404 /error-page
ErrorDocument 403 /error-page 

RewriteRule ^food-([^-]*)-([^-]*)\.html$ /pdetail?res_id=$1&location=$2 [L]
RewriteRule ^foodies-([^-]*)-([^-]*)$ /pdetail_new?res_id=$1&location=$2 [L]
RewriteRule ^([^/.]+)/([^/.]+)/([^/.]+)/?$ /pdetail_ne?location=$1&res_id=$2&name=$3 [L]

RewriteRule ^blog/([^/.]+)/?$ /blogdetail_fm?prmn=$1 [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond $1 !cityres
RewriteRule ^([^/.]+)/?$ /cityres?cityf=$1 [L]

【问题讨论】:

    标签: .htaccess mod-rewrite url-rewriting


    【解决方案1】:

    您的两个规则都匹配完全相同的模式。因此,第一条规则将始终匹配,而第二条规则不执行任何操作。

    看第一条规则:

    RewriteRule ^([^/.]+)/?$ /blogdetail?prmn=$1 [L]
    

    这匹配 http://example.com/title-of-blog 以及 http://example.com/city-name

    当您查看它时,您可以知道哪些需要由 blogdetail 处理,哪些需要由 cityres 处理,但正则表达式 ([^/.]+) 认为它们完全相同,并且两者都匹配。您的正则表达式不知道区别,所以无论第一条规则是什么,两个 URL 都会被它匹配。

    就像你说的,有人建议使用前缀。这样,正则表达式 知道 是哪个:

    RewriteRule ^city/([^/.]+)/?$ /cityres?cityf=$1 [L]
    RewriteRule ^blog/([^/.]+)/?$ /blogdetail?prmn=$1 [L]
    

    您的网址将如下所示:

    http://example.com/city/city-name
    http://example.com/blog/title-of-blog
    

    如果你实在不放心不加前缀,你可以去掉第二个前缀:

    RewriteRule ^city/([^/.]+)/?$ /cityres?cityf=$1 [L]
    RewriteRule ^([^/.]+)/?$ /blogdetail?prmn=$1 [L]
    

    这样你就有了:

    http://example.com/city/city-name
    http://example.com/title-of-blog
    

    编辑:

    您的 500 服务器错误是由规则循环引起的。您需要添加一个条件,以便它们不会保持匹配:

    RewriteRule ^blog/([^/.]+)/?$ /blogdetail?prmn=$1 [L]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond $1 !cityres
    RewriteRule ^([^/.]+)/?$ /cityres?cityf=$1 [L]
    

    【讨论】:

    • 很好的详细答案 +1 并恭喜获得 100K :)
    • @JonLin .. 我试过 RewriteRule ^blog/([^/.]+)/?$ /blogdetail_fm.php?prmn=$1 [L] RewriteRule ^([^/.]+)/?$ /cityres?cityf=$1 [L] 但现在你在博客页面上收到 500 错误:(
    • 现在我的 Htaccess 看起来像 RewriteRule ^([^/.]+)/?$ /cityres?cityf=$1 [L] RewriteCond %{REQUEST_FILENAME} !-f RewriteRule ^blog/([^/.]+)/?$ /blogdetail_fm?prmn=$1 [L] 但仍然没有运气。
    • @JonLin .. 我添加了有问题的完整 htaccess,因为我仍然面临 500
    • @Gags 当我设置 cityres.php 和 blogdetail_fm.php 文件时,这些规则对我来说很好用。你的错误日志是怎么说的?
    猜你喜欢
    • 1970-01-01
    • 2011-11-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多