Forum Moderators: phranque
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /(index.php)\?a=4\ HTTP/
RewriteRule ^(index.php)$ profile.mysite.com? [R=301,L]
RewriteRule ^(index.php)$ profile.mysite.com? [R=301,L]
mysite.com/index.php?a=4 >>>> I would like to display as > profile.mysite.com
mysite.com/index.php?a=4&b=1 >>>> I would like to display as > profile.mysite.com/active
mysite.com/index.php?a=4&b=2 >>>> I would like to display as > profile.mysite.com/expired
mysite.com/index.php?a=4&b=8 >>>> I would like to display as > profile.mysite.com/messages
This pattern of a=(A Number)&b=(A Number) goes on and on throughout the website so my question here is there a simple way to rewrite these urls or do i need to rewrite each one of them one-by-one?
The requested URL /(index.php)
Options +FollowSymlinks
RewriteEngine On
RewriteBase /
RewriteCond %{ENV:REDIRECT_STATUS} 200
RewriteRule .* - [L]
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*)$ http://%1/$1 [R=301,NC,L]
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index\.php\ HTTP/
RewriteRule ^index\.php$ http://%{HTTP_HOST}/ [R=301,NS,L]
RewriteRule ^/?(profile)/$ /index.php?a=4 [L]
#Rewrite
RewriteCond %{HTTP_HOST} ^profile\.mysite\.com
RewriteRule ^$ http://profile.mysite\.com/index\.php\?a=4 [L]
# Redirect
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index\.php\?a=4\ HTTP/
RewriteRule ^(index\.php)$ http://profile.mysite.com? [R=301,L] [edited by: phranque at 10:50 am (utc) on Feb 21, 2016]
[edit reason] added code tags for readability [/edit]
The first and third items aren't strictly necessary, though they will do no harm.Options +FollowSymlinks
RewriteEngine On
RewriteBase /
whitespace? You out there? I'm not sure you can do this in mod_rewrite; doesn't {ENV:blahblah} mean an environmental variable that you yourself have set?RewriteCond %{ENV:REDIRECT_STATUS} 200
RewriteRule .* - [L]
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*)$ http://%1/$1 [R=301,NC,L]
RewriteCond %{HTTP_HOST} !^(example\.com)?$
RewriteRule (.*) http://example.com/$1 [R=301,L]
and it will be your last external redirect among your RewriteRules. (The "index" redirect, which we're about to get to, will generally be the second-to-last.) Again, HTTP_HOST doesn't belong here. Use the actual domain name.RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index\.php\ HTTP/
RewriteRule ^index\.php$ http://%{HTTP_HOST}/ [R=301,NS,L]
You don't need to capture "profile" since you're not reusing it. And in htaccess-- or, for that matter, any directory section-- you don't use the leading / so just omit it.RewriteRule ^/?(profile)/$ /index.php?a=4 [L]
Oh, wait, so you do have more than one hostname on the same htaccess. Subdomains count as different hosts.#Rewrite
RewriteCond %{HTTP_HOST} ^profile\.mysite\.com
RewriteRule ^$ http://profile.mysite\.com/index\.php\?a=4 [L]
This rule is in the wrong place. All external redirects need to go before all internal rewrites. Besides, didn't you say this earlier?# Redirect
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index\.php\?a=4\ HTTP/
RewriteRule ^(index\.php)$ http://profile.mysite.com? [R=301,L]
I currently have wildcard domains activeDid you mean subdomains? How many of them are there? "wildcard" is an option your host gives you, but it doesn't always mean that you really have potential infinite subdomains like
RewriteCond %{HTTP_HOST} ^(www\.)?example\.com
Note that this is the only situation where "www." in a condition is optional, because your domain-name-canonicalization comes later.
RewriteCond %{ENV:REDIRECT_STATUS} 200
RewriteRule .* - [L]
whitespace? You out there?
mysite.com/index.php?a=4&b=8 >>>> I would like to display as > profile.mysite.com/messages
This pattern of a=(A Number)&b=(A Number) goes on and on throughout the website so my question here is there a simple way to rewrite these urls or do i need to rewrite each one of them one-by-one?
You said earlier, didn't you, that this specific htaccess is only seen by one domain?
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*)$ http://%1/$1 [R=301,NC,L]
The [NC] flag ....... In the Condition it's outright wrong, since part of your domain-name-canonalization is about getting everyone to use exactly the same form of the name.
The element (.*) in the condition really, really makes no sense, because you're not going to get requests for "www./directory" like that.
It's checking for equality (www, wWw or WWW, etc), not inequality (which would indeed be wrong to use the NC flag).Oops, you're right, my brain went on autopilot and I was thinking of domain-name canonicalization. This one's a positive match, not the negative I was thinking.
The element (.*) in the condition
Let's hear more about (1) the subdomains that actually exist
RewriteCond %{HTTP_HOST} ^www\.(.*) [NC]
RewriteRule ^(.*)$ http://%1/$1 [R=301,NC,L] RewriteCond %{HTTP_HOST} !^(example\.com)?$
RewriteRule (.*) http://example.com/$1 [R=301,L] RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /index\.php\ HTTP/
RewriteRule ^index\.php$ http://%{HTTP_HOST}/ [R=301,NS,L] [edited by: ItsDavid at 3:46 am (utc) on Feb 26, 2016]
I don't have an exact count but i know it is a couple of hundred
if someone has their region set to ny.example.com and wants to navigate to their profile page URL which is example.com/index.php?a=4 they are now taken to the main domain URL (Profile URL). How the sub-domains are being generated within the PHP i couldn't explain.:: glancing upward in hopes that whitespace, who speaks php, has answered this already ::
[] example.com
[]sub1
[]sub2
[]sub3
all on the same level, or are the subdomain directories inside the directory for example.com ... or do the subdomain directories not exist at all? (That is, there are no physical files for ca.example.com, mt.example.com, ny.example.com and so on; it's all handled in index.php.) If the subdomains exist only as URLs, not as physical directories, that may actually make things a lot easier. All i am trying to do is make it so that instead of the user seeing example.com/index.php?a=4 in the address bar it will actually look like they are at profile.example.com when they are on their account profile homepage however, the actual content is coming from example.com/index.php?a=4 without them seeing that in the address bar.It begins to be less muddy. What you're doing is the redirect-to-rewrite two-step, where you're changing old ugly URLs to new pretty URLs, while continuing to serve content from the old ugly location. Have I got that right? Things like /index.php?a=1&b=2 used to exist as publicly visible URLs, and now you want to get rid of them?
Another thing is that if i should miss changing all URL's in the source from example.com/index.php?a=4 to profile.example.com and they click a link or a search engine finds the default link of
example.com/index.php?a=4 it will automatically redirect the user to the new profile.example.com
RewriteCond %{THE_REQUEST} \?
RewriteCond %{QUERY_STRING} some-exact-stuff-here
RewriteRule index\.php http://www.example.com/profile/some-other-stuff-here [R=301,L]
That's the external redirect; it comes first. The line about THE_REQUEST means "The user explicitly asked for an URL with a query string". RewriteRule ^profile/some-stuff-here /example.com/index.php?buncha-stuff-here [L]
and that's where I need to know if it's profile.example.com, or ny.example.com/profile, or ... uh ... whatever the heck it is. In the user’s address bar, are the profiles supposed to look like this
Where are the directories for your subdomains? When you FTP into your site (or whatever you do to get at the files) does it look like this
It begins to be less muddy. What you're doing is the redirect-to-rewrite two-step, where you're changing old ugly URLs to new pretty URLs, while continuing to serve content from the old ugly location. Have I got that right? Things like /index.php?a=1&b=2 used to exist as publicly visible URLs, and now you want to get rid of them?
RewriteCond %{THE_REQUEST} \?
RewriteCond %{QUERY_STRING} \ba=4\b
RewriteRule ^(index\.php)?$ http://profile.example.com/ [R=301,L]
meaning "If they ask for something with suchandsuch query string, redirect to the without-query URL". It's a little tricky because there are really two potential changes: the hostname, and the query string. After giving it some thought I decided you don't need to mention %{HTTP_HOST} at all, because no matter what you request, the point is there's not supposed to be a visible query string. I said "\ba=4\b" on the off chance that you've got an "a=40" or possibly "a=467835" leading to some other page, and similarly "idea=4" or "panorama=4" and so on. (The fancy form uses (^|&)a=4($|&)instead of \b for the query-string anchors, but in most situations you don't need to get that precise.) RewriteCond %{HTTP_HOST} profile\.example\.com
RewriteRule ^$ /index\.php?a=4 [L]
I may have left something out, but that's the idea. If you have a cluster of similar rewrites, all the rules will go in the same place. On paper you're serving content from "profile.example.com" rather than "example.com" but your php will figure out that part. http://%1/$1
http://subdomain.example.com/
have to be enclosed in [ code ] tags. Otherwise you get
RewriteCond %{THE_REQUEST} \?
RewriteCond %{QUERY_STRING} \ba=4\b
RewriteRule ^(index\.php)?$ http://profile.example.com/ [R=301,L]
RewriteCond %{HTTP_HOST} profile\.example\.com
RewriteRule ^$ /index\.php?a=4 [L]
http://profile.mysite.com/?a=4 RewriteCond %{THE_REQUEST} \?
RewriteCond %{QUERY_STRING} \ba=4\b
RewriteRule ^(index\.php)?$ http://profile.example.com/? [R=301,L]
In Apache 2.4 there is also the flag [QSD] for "query string discard", but this is 2.2, right? In any case, may as well stick with one byte (the question mark) instead of four (comma plus three letters).
http://mysite.com/index.php?a=4
http://mysite.com
RewriteCond %{THE_REQUEST} \?
RewriteCond %{QUERY_STRING} \ba=4\b
RewriteRule ^(index\.php)?$ http://profile.mysite.com/? [R=301,L]
RewriteCond %{HTTP_HOST} profile\.mysite\.com
RewriteRule ^$ /index\.php?a=4 [L]
I don't know what version of Apache my host is running on my server.
It just reloads the home page
#request# GET http://mysite.com/index.php?a=4
GET /index.php?a=4
#request# GET http://profile.mysite.com/
#redirect# GET /
#request# GET http://mysite.com/index.php
#redirect# GET /index.php
#request# GET http://mysite.com/
#redirect# GET /
http://mysite.com/index.php?a=4
GET /index.php?a=4 HTTP/1.1
Host: mysite.com
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:44.0) Gecko/20100101 Firefox/44.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Referer: http://mysite.com/
Cookie: XXXXXX
Connection: keep-alive
HTTP/1.1 301 Moved Permanently
Date: Wed, 02 Mar 2016 00:24:50 GMT
Server: Apache
Location: http://my.mysite.com/
Vary: Accept-Encoding
Content-Encoding: gzip
Content-Length: 191
Connection: close
Content-Type: text/html; charset=iso-8859-1
----------------------------------------------------------
http://my.mysite.com/
GET / HTTP/1.1
Host: profile.mysite.com
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:44.0) Gecko/20100101 Firefox/44.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Referer: http://mysite.com/
Cookie: XXXXXXX
Connection: keep-alive
HTTP/1.1 302 Moved Temporarily
Date: Wed, 02 Mar 2016 00:24:50 GMT
Server: Apache
X-Powered-By: PHP/5.4.45
Cache-Control: no-cache, must-revalidate
Expires: Sat, 26 Jul 1997 05:00:00 GMT
Location: http://mysite.com/index.php
Vary: User-Agent,Accept-Encoding
Content-Encoding: gzip
Content-Length: 20
Connection: close
Content-Type: text/html
----------------------------------------------------------
http://mysite.com/index.php
GET /index.php HTTP/1.1
Host: mysite.com
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:44.0) Gecko/20100101 Firefox/44.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Referer: http://mysite.com/
Cookie: XXXXXXX
Connection: keep-alive
HTTP/1.1 301 Moved Permanently
Date: Wed, 02 Mar 2016 00:24:50 GMT
Server: Apache
Location: http://mysite.com/
Vary: Accept-Encoding
Content-Encoding: gzip
Content-Length: 189
Connection: close
Content-Type: text/html; charset=iso-8859-1
----------------------------------------------------------
http://mysite.com/
GET / HTTP/1.1
Host: mysite.com
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:44.0) Gecko/20100101 Firefox/44.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Referer: http://mysite.com/
Cookie: XXXXXXX
Connection: keep-alive
HTTP/1.1 200 OK
Date: Wed, 02 Mar 2016 00:24:50 GMT
Server: Apache
X-Powered-By: PHP/5.4.45
Cache-Control: no-cache, must-revalidate
Expires: Sat, 26 Jul 1997 05:00:00 GMT
Set-Cookie: region=0; expires=Wed, 20-Jul-2016 00:24:50 GMT; path=/; domain=.mysite.com
Accept-Ranges: none
Vary: Accept-Encoding,User-Agent
Content-Encoding: gzip
Content-Length: 8944
Connection: close
Content-Type: text/html
----------------------------------------------------------
http://example.com/index.php?a=4So far so good: The intended redirect took place. (I'm assuming your fingers typed "my" when they meant to type "profile", since otherwise the rest makes no sense.) The browser will now make a fresh request:
GET /index.php?a=4 HTTP/1.1
Host: example.com
HTTP/1.1 301 Moved Permanently
Location: http://my.example.com/
GET / HTTP/1.1wtf? This should absolutely NOT be happening. I smell an internal rewrite that is somehow getting sent out again as an external redirect, causing the browser to make a request that it should never have made.
Host: profile.example.com
HTTP/1.1 302 Moved Temporarily
Location: http://example.com/index.php
GET /index.php HTTP/1.1This last bit is OK: an explicit request for /index.php has been redirected to / alone. That leaves us only with
Host: example.com
HTTP/1.1 301 Moved Permanently
Location: http://example.com/
GET / HTTP/1.1
Host: example.com
HTTP/1.1 200 OK