title: How to redirect and remove the .html extension from a URL?
body: <p>I am tearing my hair out on this one while configuring some rewrite rules on nginx. I am running nginx 1.2.1 on a Debian Wheezy machine.</p>
  
  <p>Considering the following tree:</p>
  
  <pre><code>/
  ├── index.html
  ├── folder/
  │   └── index.html
  └── file.html
  </code></pre>
  
  <p>I would like those files to be served by nginx so that there would be no need to specify any <code>.html</code> in the URL, and that any call to a <code>folder/index.html</code> is rewritten in <code>folder/</code>, any call to <code>file.html</code> is rewritten in <code>index</code>.</p>
  
  <p>Here is the formal version of this description. Request examples are on the left and the corresponding response I am trying to get are on the right (HTTP code 301 + redirected location or HTTP code 200 + file to be displayed):</p>
  
  <pre><code>1. http://example.com/                  -&gt; 200 (/index.html)
  2. http://example.com/index.html        -&gt; 301 http://example.com/
  3. http://example.com/index             -&gt; 301 http://example.com/
  
  4. http://example.com/file              -&gt; 200 (/file.html)
  5. http://example.com/file.html         -&gt; 301 http://example.com/file
  
  6. http://example.com/folder/           -&gt; 200 (/folder/index.html)
  7. http://example.com/folder            -&gt; 301 http://example.com/folder/
  8. http://example.com/folder/index.html -&gt; 301 http://example.com/folder/
  9. http://example.com/folder/index      -&gt; 301 http://example.com/folder/
  
  10. http://example.com/foobar           -&gt; 404
  </code></pre>
  
  <p>So far, my closest attempt is the following configuration of <code>/etc/nginx/sites-enabled/example.com</code>:</p>
  
  <pre><code>server {
      server_name example.com;
      root /var/www/example.com/public_html;
  
      rewrite ^(.*/)index(\.html)*$ $1 permanent;        # Applies to 2, 3, 8, 9
      rewrite ^(/.+)\.html$ $1 permanent;                # Applies to 5
  
      try_files $uri $uri.html "${uri}index.html" =404;  # Handles 1, 4, 6, 10
  }
  </code></pre>
  
  <p>As you can see, case <code>7</code> is missing. For now, I got:</p>
  
  <pre><code>7'. http://example.com/folder           -&gt; 404
  </code></pre>
  
  <p>I also managed to have:</p>
  
  <pre><code>7''. http://example.com/folder          -&gt; 200 (/folder/index.html)
  </code></pre>
  
  <p>But it is definitely something I don't want SEO wise (among others), as 2 different URLs (with and without trailing slash) returns the same content.</p>
  
  <p>Every configuration did not pass all of my test cases.</p>
  
  <p>Note that when I simply disable the 2 <code>rewrite</code>s and the <code>try_files</code>, <code>7</code> applies as expected (as well as <code>1</code>, <code>6</code>, <code>10</code> but not the other ones), the redirection is valid by default. I don't understand how and where this redirection rule, so here are my formal questions: how can I make this redirection re-appear and, by extension, how can I have my 10 test cases properly working?</p>
  
  <p>Thanks <em>a lot</em>, and I really mean it :)</p>
  
  <p>PS: I try my best, but of course if there is anything unclear, do not hesitate to ask for clarification!</p>