htaccess RewriteRules在子目录上不起作用

时间:2018-10-31 20:07:27

标签: .htaccess

我有一个静态HTML网站,试图通过.htaccess文件向其中添加一些URL重写规则。

站点文件目录如下:

- index.htm

- about-us [subdirectory]
    - index.htm

- careers [subdirectory]
    - index.htm

- contact [subdirectory]
    - index.htm
    - map.htm
    - privacy.htm

- projects [subdirectory]
    - index.htm
    - education.htm
    - healthcare.htm
    - recreation.htm
    - residential.htm
    - hospitality.htm

- services [subdirectory]
    - index.htm

我的目标是从页面URL中删除文件扩展名,添加斜杠并强制301重定向,以便尝试访问原始格式(即https://example.com/projects/education.htm)文件的任何人都将被自动重写到更干净的格式(即https://example.com/projects/education/)。

我已经在网站根目录的.htaccess文件中重写/重定向了index.htm文件。这是我到目前为止的内容:

DirectoryIndex index.php index.html index.htm
RewriteEngine On

RewriteCond %{REQUEST_URI} (.*)/$
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.htm -f

RewriteRule ^(.+)/$ /$1/ [R=301,L]
RewriteRule ^index\.htm$ / [R=301,L]
RewriteRule ^(.*)/index\.htm$ /$1/ [R=301,L]

我已经成功从URL中删除了目录根文件(index.htm),但是对于我来说,我似乎无法以所需的格式重写非根文件(即education.htm)

有人可以告诉我我在做什么错吗?

更新

根据@misorude的评论,我删除了第一个重写规则。我也将301s更改为302s(至少暂时是为了避免规则缓存问题)。我还修改了现有规则,以在正则表达式中使用“ +”字符在规则中强制使用真实的文件或文件夹名称。

最后,我添加了一个新的第三条规则。这是一种尝试查找所有子目录“非索引”页面并删除其文件扩展名的尝试,该扩展名似乎起作用。但是,在那些非索引页面上却出现404错误。

我以前所有可用的index.htm重写规则都可以正常工作,但非索引规则会抛出404错误。这是我的更新htaccess文件:

DirectoryIndex index.php index.html index.htm
RewriteEngine On

RewriteCond %{REQUEST_URI} (.*)/$
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.htm -f

# If we're on the root index page of the site, 
# remove index.htm from URL
RewriteRule ^index\.htm$ / [R=302,L]

# If we're on a subdirectory index page, remove the index.htm from the URL
RewriteRule ^(.+)/index\.htm$ /$1/ [R=302,L]

# If we're on a non-index page of a subdirectory, 
# remove the extension from the   URL
RewriteRule ^(.+)/(.+)\.htm$ /$1/$2/ [R=302,L]

有什么建议吗?

1 个答案:

答案 0 :(得分:2)

通过禁用MultiViews选项并处理每种情况,这是一个完整的解决方案

DirectoryIndex index.php index.html index.htm
Options -MultiViews

RewriteEngine On

# redirect "/index.htm" or "/xxx/index.htm" to "/" or "/xxx/"
RewriteCond %{REQUEST_FILENAME} -f
RewriteCond %{THE_REQUEST} \s/([^/]+/)?index\.htm\s [NC]
RewriteRule ^ /%1 [R=302,L]

# redirect "/xxx/page.htm" to "/xxx/page/"
RewriteCond %{REQUEST_FILENAME} -f
RewriteCond %{THE_REQUEST} \s/([^/]+)/([^/]+)\.htm\s [NC]
RewriteRule ^ /%1/%2/ [R=302,L]

# rewrite back "/xxx/page/" to "/xxx/page.htm"
RewriteCond %{DOCUMENT_ROOT}/$1/$2\.htm -f
RewriteRule ^([^/]+)/([^/]+)/$ /$1/$2.htm [L]