2012-11-05 49 views
3

我有以下文件/文件夹结构的静态网站:当'index.html'被剥离时如何去除'/folder/index.html'的尾部斜线?

  • 的index.html
  • /foobar的/
    • 的index.html
    • bob.html
    • alice.html

我想实现以下功能:

  • 删除全部.html扩展名。 ✔作品
  • 删除index.html(resp。index)。 ✔作品
  • 我希望文件结尾没有斜线。 ✔作品
    • 如果有人添加了尾部斜线,则重定向到URL而没有斜线。 ✘不起作用
  • 我想要的“文件夹”(实际上index.html文件的文件夹内),以结束不斜线。 ✘不起作用
    • 如果有人添加了尾部斜线,则重定向到URL而没有斜线。 ✘不起作用

所以下面的网址应该工作:

  • example.com/(实际上是:/index.html
  • example.com/foobar(实际上是:/foobar/index.html
  • example.com/foobar/bob(实际上:/foobar/bob.html
  • example.com/foobar/alice(实际上:/foobar/alice.html

以下请求应该重定向(301):

  • example.com/foobar/重定向到:example.com/foobar
  • example.com/foobar/bob/重定向到:example.com/foobar/bob
  • example.com/foobar/alice/重定向到: example.com/foobar/alice

我发现这会在文件/foobar.html存在时产生问题:当某人访问/foobar时,目录或文件是否被请求并不清楚。但是,我会确保这一切都不会发生。


目前,我有这个.htaccess:在我.htaccess

# Turn MultiViews off. (MultiViews on causes /abc to go to /abc.ext.) 
Options +FollowSymLinks -MultiViews 

# It stops DirectorySlash from being processed if mod_rewrite isn't. 
<IfModule mod_rewrite.c> 

    # Disable mod_dir adding missing trailing slashes to directory requests. 
    DirectorySlash Off 

    RewriteEngine On 

    # If it's a request to index(.html) 
    RewriteCond %{THE_REQUEST} \ /(.+/)?index(\.html)?(\?.*)?\ [NC] 
    # Remove it. 
    RewriteRule ^(.+/)?index(\.html)?$ /%1 [R=301,L] 

    # Add missing trailing slashes to directories if a matching .html does not exist. 
    # If it's a request to a directory. 
    RewriteCond %{SCRIPT_FILENAME}/ -d 
    # And a HTML file does not (!) exist. 
    RewriteCond %{SCRIPT_FILENAME}.html !-f 
    # And there is not trailing slash redirect to add it. 
    RewriteRule [^/]$ %{REQUEST_URI}/ [R=301,L] 

    # Remove HTML extensions. 
    # If it's a request from a browser, not an internal request by Apache/mod_rewrite. 
    RewriteCond %{ENV:REDIRECT_STATUS} ^$ 
    # And the request has a HTML extension. Redirect to remove it. 
    RewriteRule ^(.+)\.html$ /$1 [R=301,L] 

    # If the request exists with a .html extension. 
    RewriteCond %{SCRIPT_FILENAME}.html -f 
    # And there is no trailing slash, rewrite to add the .html extension. 
    RewriteRule [^/]$ %{REQUEST_URI}.html [QSA,L] 

</IfModule> 

我有什么更改/删除/添加?我不太了解它。我试图删除块注释“添加缺少尾随斜杠到目录如果匹配的.html不存在”,但这没有帮助。

+0

FWIW,我在Code Review上询问了可能的改进:http://codereview.stackexchange.com/q/18440/16414 – unor

回答

4

右键你# Add missing trailing slashes to directories if a matching .html does not exist.规则上面,你可以添加以下规则:重定向时,有一个HTML文件和要求是不是目录,并且有一个结尾的斜线:

# if request has a trailing slash 
RewriteCond %{REQUEST_URI} ^/(.*)/$ 
# but it isn't a directory 
RewriteCond %{DOCUMENT_ROOT}/%1 !-d 
# and if the trailing slash is removed and a .html appended to the end, it IS a file 
RewriteCond %{DOCUMENT_ROOT}/%1.html -f 
# redirect without trailing slash 
RewriteRule^/%1 [L,R=301] 

这不应该与重定向冲突因为它的条件检查完全相反。


编辑:

要处理的index.html的事情,你需要改变这个规则,你有,这是附加尾随斜杠:

# Add missing trailing slashes to directories if a matching .html does not exist. 
# If it's a request to a directory. 
RewriteCond %{SCRIPT_FILENAME}/ -d 
# And a HTML file does not (!) exist. 
RewriteCond %{SCRIPT_FILENAME}.html !-f 
# And there is not trailing slash redirect to add it. 
RewriteRule [^/]$ %{REQUEST_URI}/ [R=301,L] 

要:

# Add missing trailing slashes to directories if a matching .html does not exist. 
# If it's a request to a directory. 
RewriteCond %{REQUEST_FILENAME}/ -d 
# And a HTML file does not (!) exist. 
RewriteCond %{REQUEST_FILENAME}/index.html !-f 
# And there is not trailing slash redirect to add it. 
RewriteRule [^/]$ %{REQUEST_URI}/ [R=301,L]  

这会检查index.html文件是否为缺失从添加尾部斜杠之前的目录。之所以你必须有这是因为information disclosure security issue when missing the trailing slash will actually expose all of your directory contents if you don't have the trailing slash。现在,添加这些规则删除尾随斜线时,有一个index.html

RewriteCond %{REQUEST_FILENAME} -d 
# And a HTML file exists. 
RewriteCond %{REQUEST_FILENAME}/index.html -f 
# And there is a trailing slash redirect to remove it. 
RewriteRule ^(.*?)/$ /$1 [R=301,L]  

现在添加这些规则后立即明确地显示index.html时,有没有尾随斜线(注意规则的标志没有R=301):

RewriteCond %{REQUEST_FILENAME} -d 
# And a HTML file exists. 
RewriteCond %{REQUEST_FILENAME}/index.html -f 
# And there is no trailing slash show the index.html. 
RewriteRule [^/]$ %{REQUEST_URI}/index.html [L]  
+0

谢谢Jon。有用。我在回答中将这一点标记为工作。你也有一个想法如何让其他两点工作? – unor

+0

@unor该规则处理所有3个“不工作”点,这就是为什么有所有额外的条件。适用于我,无论是我还是不明白你想要什么。 –

+0

嗯,如果我访问'example.com/foobar'(没有结尾斜杠),我会被重定向到'example.com/foobar /'(带有斜线)。我想显示文件'/ foobar/index.html',但是使用URL'/ foobar'。 – unor