This patch tweaks Drupal's standard .htaccess file, specifically the part that handles URL rewriting to add or remove the "www." prefix from domain names.* The two main advantages to the way this is handled with this patch are as follows.

Firstly, either rewrite can be done merely by uncommenting the relevant lines in .htaccess; changing the "example.com" domain name to the site's actual domain name is no longer necessary. The RewriteRule uses a captured element from the RewriteCond's regex to remove the "www.", or uses the %{HTTP_HOST} variable when adding it.

Secondly, since the above means the current site's web address is programmatically determined, URL rewriting for multi-site and multisite installations (I'll use both spellings to facilitate searching) will work out-of-the-box. Having to duplicate a RewriteCond/RewriteRule pair for each domain name a Drupal installation is serving is no longer necessary.

* The correct answer is to remove it, by the way. </holywar>

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

Damien Tournoud’s picture

Looks great at first sight. Needs some testing.

no2e’s picture

That would have saved me hours of searching for a solution - please integrate this into the default .htaccess.

The patch works for all my multi-sites that are subdomains.

However, it probably does not work for multi-sites in subdirectories - which is the case for the current .htaccess of Drupal 6, too (as mentioned here). Maybe we could add an example for a working redirection snippet for subdirectory sites, like:


   # If your site (and/or one of your multi-sites) lies in the domain/subdomain root:
   # To redirect all users to access the site WITHOUT the 'www.' prefix,
   # (http://www.example.com/... will be redirected to http://example.com/...)
   # uncomment the following:
   # RewriteCond %{HTTP_HOST} ^www\.(.+)$ [NC]
   # RewriteRule ^(.*)$ http://%1/$1 [L,R=301

   # If your site (and/or one of your multi-sites) lies in a subdirectory:
   # To redirect all users to access the site WITHOUT the 'www.' prefix,
   # (http://www.example.com/... will be redirected to http://example.com/...)
   # uncomment and adapt the following:
   # RewriteCond %{HTTP_HOST} ^www.example.com$ [NC]
   # RewriteRule ^(.)$ http://example.com/subdirectory/drupal/$1 [L,R=301]

(don't know if it is a good solution, just as an example)

So "normal" users, which have their Drupal installed in domain or subdomain root, would only have to uncomment the two lines. Users, which have their Drupal installed in a subdirectory, would have to uncomment & adapt the example (and this example exactly works for them, which does the current one of Drupal 6 not)

wrwrwr’s picture

Good idea, I've definitely adapted that lines too many times :)

The attached one uses %{REQUEST_URI} instead of the matched group and should work with subdirectories too.

(The problem is due to the removal of the local directory with RewriteRules in per-directory configuration -- it is removed before matching and added after substitutions, unless ... the substitution part starts with http://.)

Garrett Albright’s picture

Testing of wrwrwr's version on a D6 multi-site installation (no subdirectories) was successful for me. It should be slightly faster too since it uses less regular expression voodoo. But I'm afraid I don't see how it will treat subdirectories any differently. Not having any Drupal sites which are in subdirectories, I can't test that.

Status: Needs review » Needs work

The last submitted patch failed testing.

Garrett Albright’s picture

FileSize
1.16 KB

Give this a try, testbot.

lilou’s picture

Status: Needs work » Needs review
wrwrwr’s picture

I don't understand why have you reintroduced those regular expressions -- ^(.*)$ seems unnecessary here, because the match is not used anyway.

Garrett Albright’s picture

FileSize
1.15 KB

You're right, of course. I applied your failed patch (though it looks like it's passing now… ?) by hand and didn't pay precise enough attention.

Status: Needs review » Needs work

The last submitted patch failed testing.

Garrett Albright’s picture

It looks like the patch failed due to "User language settings." Unfortunately, I'm not familiar enough with using Drupal in a non-monolingual environment to guess at how to fix that. Anyone more familiar with multilingual Drupal have any ideas on how to fix that?

alexanderpas’s picture

Issue tags: +multi-site
Garrett Albright’s picture

Status: Needs work » Needs review

Marking "needs review" and retesting as per webchick's instructions in #Drupal. Between her, emmajane and I, we couldn't get the same test to fail on our testing servers. Perhaps the error has been fixed since January, or perhaps… IT'S ONLY BROKEN ON THE TESTING BOT (Dun dun DUNNNNN!)

Garrett Albright’s picture

Okay, so the re-test passed and it needs review. I guess it's redundant for me to post one, but long story short (the long story is here), check out http://www.sbdctap.org/ , http://www.californiasbdc.org/ , or http://www.acsbdc.org/ - only the www won't be there by the time you get there. There's gonna be over a dozen subsites for this client once they all go live - you think I wanted to be copying/pasting/modifying stuff in that .htaccess file all day? :)

alexanderpas’s picture

Status: Needs review » Reviewed & tested by the community

consider it reviewed ;)

Dries’s picture

Status: Reviewed & tested by the community » Fixed

Committed to CVS HEAD. Thanks!

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.

nball’s picture

I am happy to see those much more skilled than I are tuning up the htaccess file! This is great stuff, however it doesn't seem to accommodate subdomains. I am working on this now, and will post something if it actually behaves.

scor’s picture

Version: 7.x-dev » 6.x-dev
Status: Closed (fixed) » Patch (to be ported)

looks like this could be useful in Drupal 6 too. I'm actually using it on some sites.

jdwfly’s picture

I agree and I am using it on my sites. Could this be brought into Drupal 6?

scor’s picture

Status: Patch (to be ported) » Needs review
FileSize
1.51 KB

reroll for D6.

jdwfly’s picture

Status: Needs review » Needs work

This doesn't work for multi-site installs using subdomains. I need to have the www at the beginning of my domain for reasons beyond the scope of this issue. When I use this patch it breaks all subdomains by adding www. at the beginning of the subdomain.

Example server setup
www.example.com
sub1.example.com rewrites to www.sub1.example.com
sub2.example.com rewrites to www.sub2.example.com

jdwfly’s picture

Just looked at the .htaccess file for Drupal 7. Since it has this code I am assuming that the same problem will happen with Drupal 7. I'll leave this issue as is so it could be worked on for Drupal 6 and I filed a bug as #738616: htaccess changes break subdomains for www. sites.

wrwrwr’s picture

Concerning mod_rewrite, I suppose that it can be hard to distinguish "sub1.example.com" from, for example, "name.provider.com", to which one may want to have the prefix added. Maybe there should be a third option for this case with an appropriate comment? (Nothing better than the old code comes to my mind here.)

Garrett Albright’s picture

jdwfly, frankly, I would say your case is edgy enough that we shouldn't sweat about it too much. You will have to fiddle with domain names in .htaccess to get the behavior you want. This is still better than the current situation, in which everyone has to to fiddle with domain names.

+1 for adding a comment warning people about this happening, though.

scor’s picture

Version: 6.x-dev » 7.x-dev
Status: Needs work » Needs review
FileSize
570 bytes

I just confirmed this does not work for subdomains on D7 as well. I think we should only support the redirect from www.example.com to example.com and leave out the case where www appear in front of a subdomain, that's a rather rare case. Let's get this fixed for Drupal 7 first, then move back to Drupal 6.

This patch only redirects to www.example.com if the initial domain name contains exactly 2 labels separated by a dot (e.g. example.com)

scor’s picture

Title: Better, multi-site friendly "www." addition/removal in .htaccess » htaccess www. redirect breaks subdomains
Category: feature » bug

that becomes a bug, with a better title

jdwfly’s picture

@Garrett Albright
I don't think you understand what I was saying. I don't want that to happen and neither does anyone else that uses subdomains. I want a subdomain to go through untouched.

sub1.example.com should stay as sub1.example.com

Currently it will add the www. at the beginning and therefore break any subdomains.

sub1.example.com rewrites to www.sub1.example.com

AFAIK the code for removing the www. from a domain works flawlessly (www.example.com rewrites to example.com). Even multisite subdomains worked great. I was using it for some time on a site, but then I had to switch back to adding the www. due to reasons beyond the scope of this issue. When I switched to the other rewrite code all of the subdomains for the site became 404 errors because it was adding the www.

Also I understand that the old code did involve some tweaking. I don't know about anyone else, but it took me less than 30 seconds to make the changes. Not a huge hassle, but if you had many hundreds of sites I could see that it would be a burden. I am not asking we put the old code back in, but I am saying that the new code doesn't work for a normal multisite with subdomains and the main domain adds the www.

@scor
The only problem I see with the patch is the case of country specific sites like: google.co.uk; avon.uk.com; sssc.uk.com; Of course there are many more, those are just from a quick search to find some examples. You said that it looks for exactly two labels separated by a dot, but these domains have three labels and two dots. I haven't tested it, but I am thinking there could be a problem there.

Garrett Albright’s picture

jdwfly: No, I understand what you're saying perfectly, and my comment still stands. Unfortunately, what you're asking for is pretty much impossible to code for in a reusable way without telling people to hack their .htaccess files the same way they have done in the past. That is, it's easy to say "if the requested URL doesn't begin with 'www.', then add it," or "if the requested URL begins with 'www.', then remove it," but impossible say "if the requested URL doesn't begin with 'www.' and is also not a valid subdomain, then add it" without actually listing the subdomains to be considered valid.

jdwfly’s picture

Then they have to change their htaccess files if it is impossible. Sending Drupal 7 like this makes it unusable for sites that want to keep the www. with multisites and subdomains.

You can't just say, "Well, jdwfly warned everyone about this. They should have read the documentation, etc."

Is it really that hard to copy and paste in a text file? If it can't be done programmatically then it can't be done and users should be content to modify a text file to have that sort of setup that you have.

I understand you want to make this process easier, but you should not introduce a bug with a fix and call it better than what it was. I'd like to make it easier too, but not at the expense of creating a bug.

Bottom line is this, why keep this in the htaccess file that creates a bug such as this?

Garrett Albright’s picture

Sending Drupal 7 like this makes it unusable for sites that want to keep the www. with multisites and subdomains.

"www." addition (or removal) will not be enabled by default, just as it isn't now. People will still have to uncomment the relevant lines in .htaccess in order to "break" their sites like this, at which point they will then see the (currently non-existent) warning that this breakage will occur.

Besides, I would argue that the number of people wanting to do what you're talking about - add "www." to some domain names, but not others - is really really tiny (likewise for removing "www." from some domains but not others). I know it's often easy to get into a trap of thinking that everyone wants Drupal to work the same way you want it to work, but we've got to look at the big picture here.

Bottom line is this, why keep this in the htaccess file that creates a bug such as this?

Because it's not a bug; its a difference in functionality not enabled by default, but which will potentially affect a large number of people positively and a very tiny number of people with a situation like yours "negatively" just insofar as the solution for them will be pretty much the same as it is now (they won't be able to use this new, easier solution).

Garrett Albright’s picture

Title: htaccess www. redirect breaks subdomains » Better, multi-site friendly "www." addition/removal in .htaccess
FileSize
1.59 KB

Here's a patch to make it clear that this approach will always be applied to all domains, and clarifies a few other things as well. EDIT: Actually, use the next one.

Garrett Albright’s picture

Scratch the previous patch; this one has more clarification.

EDIT: To address scor's patch, because I never did; that change is going to break domain names which feature three "parts" but which aren't necessarily subdomains, and thus many sites using national TLDs. For example, someone with that patch who tries to enable "www." addition on http://example.co.uk/ or http://example.or.jp/ is going to get frustrated quickly, wondering why it's not working. I think this case is far, far more common than a case like jdwfly's.

scor’s picture

Yes, I agree #26 is not a good approach wrt to co.uk and other similar TLDs. It's hard to cover all the uses cases in a bunch of generic .htaccess rules, and for multisite installs, one might need to have different rules for each domain, and end up hardcoding each domain with its redirect (say if some domains are without www and some others redirect to www.), much like the same way it was before the patch of this issue got committed:

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

cross-posting the #544454: Force www prefix in url feature request for global redirect here.

jdwfly’s picture

Status: Needs review » Needs work

From patch:

if you only want it to happen for SOME domain names, this approach will not work for you.

So what will work for them? No mention of what will work. Maybe a documentation page should be created and a link should be put there. I'll even make the page if needed.

@Garrett Albright
You still don't understand, but since you apparently are already set on leaving this I'll try to offer as much help as I can in making sure people know about this problem.

Garrett Albright’s picture

Maybe a documentation page should be created and a link should be put there. I'll even make the page if needed.

Go for it.

mikeytown2’s picture

subscribe

mikeytown2’s picture

Looking into this issue, I do not see a way to handle the subdomain issue in a generalized solution; at least not with apache & htaccess. The best we can do is document and give examples of different solutions to the problem.

The issue is example.co.uk & www.example.co.uk are valid sites so using dots will not work in all cases.

Adding in www. is the issue. Right now this code is generalized, it works for any site and doesn't require one to put in the host name.

  # To redirect all users to access the site WITH the 'www.' prefix,
  # (http://example.com/... will be redirected to http://www.example.com/...)
  # uncomment the following:
  # RewriteCond %{HTTP_HOST} !^www\. [NC]
  # RewriteRule ^ http://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]

One solution is to add in a RewriteCond where one can list all the subdomains in use. Something like this

  # To redirect all users to access the site WITH the 'www.' prefix,
  # (http://example.com/... will be redirected to http://www.example.com/...)
  # uncomment the following:
  # RewriteCond %{HTTP_HOST} !^www\. [NC]
  # RewriteCond %{HTTP_HOST} !^(subdomain-a|subdomain-b|subdomain-c)\. [NC]
  # RewriteRule ^ http://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]

Technically you could place it all on one line, but then that would make the code modification harder, since www is a special case subdomain. Thoughts?

mikeytown2’s picture

I think a better way to do it is by the domain name.

  # To redirect all users to access the site WITH the 'www.' prefix,
  # (http://example.com/... will be redirected to http://www.example.com/...)
  # uncomment the following:
  # RewriteCond %{HTTP_HOST} !^www\. [NC]
  # RewriteCond %{HTTP_HOST} ^(example-a|example-b|example-c)\. [NC]
  # RewriteRule ^ http://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]

So in the example above we have 3 multi-sites; example-a.com, example-b.com and example-c.com. Rules read If host name doesn't start with www AND it dose start with example-a OR example-b OR example-c THEN redirect to www. version of the host.

Olmo INXCO’s picture

How about this?

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

This simply says: domain.com is the main domain name... if you arrived here through any other domain, please redirect.
Thus, it will work with an unlimited number of TLD's (suppose domain.net, domain.org, domain.name all point to the same address...).
(You can also use www.domain.com if you always want to use a www.)

If you want leave a certain (sub)domain as is, you can add this line to the top:

RewriteCond %{HTTP_HOST} !^sub.domain.com [NC]

AFAICT this does not work with multisite installs, I'd be interested to see a solution for that.

cweagans’s picture

Is there anything that still needs to be done on this issue? It doesn't look like there has been much movement on it for a while. If somebody could write an issue summary, that would be awesome.

Garrett Albright’s picture

Status: Needs work » Fixed

I don't think there's anything more to do, no. My patch or a variant thereof made it into D7, and later discussion was around edge cases that may not be generalizable enough to put into .htaccess for all of core. Marking fixed.

Status: Fixed » Closed (fixed)
Issue tags: -multi-site, -Needs issue summary update

Automatically closed -- issue fixed for 2 weeks with no activity.