How to Fix Trailing Slash Issues in .htaccess 301 Redirects to PHP Files


6 views

When migrating websites or restructuring URLs, Apache's Redirect directive can sometimes behave unexpectedly with trailing slashes. The core issue occurs when:

  • Source URL has a trailing slash
  • Destination is a PHP file
  • The redirect incorrectly appends a slash to the destination

The standard approach:

Redirect 301 /example/ /example.php

Results in the undesired redirect to example.php/. This happens because Apache's Redirect directive treats the trailing slash as part of the path to be preserved.

For precise control over URL redirects, mod_rewrite is more flexible:

RewriteEngine On
RewriteRule ^example/?$ /example.php [L,R=301]

Key advantages:

  • /? makes the trailing slash optional
  • No slash gets appended to the destination
  • Works for both /example and /example/

Here's a robust implementation that handles multiple cases:

<IfModule mod_rewrite.c>
    RewriteEngine On
    
    # Redirect /example/ and /example to /example.php
    RewriteRule ^example/?$ /example.php [L,R=301]
    
    # Alternative version that preserves query strings
    RewriteCond %{REQUEST_URI} ^/example/?$
    RewriteRule .* /example.php [L,R=301,QSA]
</IfModule>

Always verify redirects using:

  1. Browser's network inspector
  2. cURL command: curl -I https://yoursite.com/example/
  3. Online redirect checkers
  • Forgetting to enable RewriteEngine On
  • Not clearing browser cache when testing
  • Mixing Redirect and RewriteRule directives for the same paths
  • Omitting the [L] flag which can cause rule interference

When migrating a website or changing URL structures, we often need to set up 301 redirects in the .htaccess file. A common issue arises when dealing with URLs that may or may not have trailing slashes.

Consider this standard redirect:

Redirect 301 /example /example.php

This works perfectly for requests to /example, but fails when users access /example/ (with trailing slash). The natural solution might seem to be:

Redirect 301 /example/ /example.php

However, this creates a new problem - the redirect adds a trailing slash to the destination, resulting in example.php/, which breaks the URL.

The Redirect directive in Apache's mod_alias has this behavior by design. When the source path ends with a slash, it preserves that slash in the destination URL. This is intentional for directory redirects but problematic for file redirects.

The more robust approach is to use mod_rewrite instead of mod_alias for these redirects. Here's how:

RewriteEngine On
RewriteRule ^example/?$ /example.php [L,R=301]

This solution:

  • Matches both /example and /example/ (the /? makes the slash optional)
  • Redirects to the exact destination URL without adding a trailing slash
  • Uses a 301 (permanent) redirect status

For multiple similar redirects, you can create a more generic rule:

RewriteEngine On
RewriteRule ^([a-z0-9-]+)/?$ /$1.php [L,R=301]

This will redirect any alphanumeric path (with optional trailing slash) to its corresponding .php file.

If you need to preserve query parameters during the redirect:

RewriteEngine On
RewriteRule ^example/?$ /example.php [QSA,L,R=301]

The QSA flag (Query String Append) ensures any original query parameters are passed through to the destination URL.

Always test redirects thoroughly. You can use:

curl -I http://yoursite.com/example
curl -I http://yoursite.com/example/

Check that both return:

HTTP/1.1 301 Moved Permanently
Location: http://yoursite.com/example.php