How to combine .htaccess rules? - apache

I want to combine these two .htaccess rules for a website:
RewriteRule ^newsletter\.html$ https://fleio.com/newsletter [L,R=301]
RewriteRule ^newsletter[/]?$ newsletter.html [L]
If only one is active, it is doing what it has to do. But when I use both of them I get an error
too many redirects.
https://docs.google.com/document/d/1M6rYkEV-tmO7wRSJYjGtGOFow-76ZvbODnnjiqCh1m0/edit?usp=sharing

Your second rule is internally redirecting the request to same location (The first rue) multiple time so you are getting the loop error. You need to use a RewriteCond and match against the_request variable to prevent the rewrite loop.
Try this :
RewriteEngine on
RewriteCond %{THE_REQUEST} /newsletter\.html [NC]
RewriteRule ^ /newsletter/ [L,R]
RewriteRule ^newsletter/?$ /newsletter.html [NC,L]

Related

301 Redirect in htaccess for URLs having Parameter P

I need to set 301 redirect in htaccess for URLs having parameter P. One example URL is
http://www.price4india.co.in/vivo-x20-plus-ud-price-in-india-scanner-feature-real.html?p=1028
to
http://www.price4india.co.in/vivo-x20-plus-ud-price-in-india-scanner-feature-real.html
After redirect everything after .html shall get removed and the value after P=...... can be any numerical value. So far I have tried below query but it is not working. Any suggestion please...
RewriteCond %{QUERY_STRING} ^p(&|$) [NC]
RewriteRule ^ %{REQUEST_URI}? [R=301,L]
With your shown samples, please try following .htaccess rules file. Make sure to keep your .html file and .htaccess files in root path only.
Make sure to clear your browser cache before testing your URLs.
RewriteEngine ON
RewriteCond %{THE_REQUEST} \s/(.*\.html)\?p=\d+\s [NC]
RewriteRule ^ /%1? [R=301,L]
NOTE: In case you have further more rules in your .htaccess rules, which includes internal rewrite of html files then you could keep these rules above those.
RewriteCond %{QUERY_STRING} ^p(&|$) [NC]
RewriteRule ^ %{REQUEST_URI}? [R=301,L]
This is almost correct, except the regex ^p(&|$) is incorrect. This matches p&<anything> or p exactly. Whereas you need to match p=<anything> (eg. ^p=) or p=<number> (eg. ^p=\d+). This is of course assuming the p URL parameter always occurs at the start of the URL-path (as in your example).
For example:
RewriteCond %{QUERY_STRING} ^p= [NC]
RewriteRule ^ %{REQUEST_URI}? [R=301,L]

How do I combine these two .htaccess rules?

I want to combine these two rules, but not sure how
RewriteRule ^([^\.]+)$ $1.html [L]
RewriteRule ^(.*)$ http://www.example.com/$1 [L,R=301]
when I put both, I get the error "too many redirects"
My goal here is to combine them both,
the first rule is to remove file extensions (ex. html)
the second rule is: make every URL go to https://www.example.com, rather than https://example.com
With the additional information you now gave I would suggest this approach:
RewriteEngine on
RewriteCond %{HTTP_HOST} !^www\.example\.com$
RewriteRule ^ https://www.example.com%{REQUEST_URI} [R=301,END]
RewriteRule ^/?(.+)\.html$ /$1 [R=301,END]
RewriteCond %{REQUEST_FILENAME}.html -f
RewriteRule ^ %{REQUEST_URI}.html [END]
In general it is a good diea to start using a R=302 temporary redirection and only change that to a R=301 permanent redirection once everything works as expected. That prevents nasty caching issues ...

How do I Redirect and Show Content with same urls?

I have a maybe simple Problem. I have serveral URLs that needed to be redirected in this way:
if the URL "/abc/" is called, it should show the content located under "xyz.html"
i can do that with
RewriteRule abc$ xyz.html
but "xyz.html" should be 301 redirecting to "/abc" if it is called.
This is my simple problem i am searching for an solution since hours.
it would be easy if its like "test.html" and /test/. i can do it like
RewriteRule ^(.+)\.html$ /$1 [L,R=301]
RewriteCond %{REQUEST_FILENAME}.html -f
RewriteRule !.*\.html$ %{REQUEST_URI}.html [END]
But in my case i have a bunch of URLs with no pattern.
All i tried results to server misconfiguration.
Can you help me with that one sample?
thanks, kanuddel
Could you please try following.
RewriteEngine ON
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{REQUEST_URI} ^/abc/? [NC]
RewriteRule ^(.*) /xyz.html [L]
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{REQUEST_URI} ^/xyz\.html/? [NC]
RewriteRule ^(.*) /abc/? [R=301,L]
Detailed Explanation:
Why there is redirection loop with normal rule writing: Question from OP is interesting and contradictory(kind of), why because lets say we write 1st rule to redirect(in backend) from abc url to xyz.html it will work fine. But then when we write our 2nd rule which is to rewrite url from xyz.html to abc/ which is exactly opposite of first rule. Hence it becomes a loop, ASAP 1st rules gets served it reaches out to 2nd rule and it serves it back to 1st rule thus a REDIRECTION INFINITE LOOP(till 50 cycles or so).
How to prevent redirection loop?
First since both rules are exactly opposite of each other so in a normal rule writing it will become a loop, now how could we prevent it to become a loop? Answer is using: RewriteCond(explained in next step)
I have used an ENVIRONMENT VARIABLE named ENV:REDIRECT_STATUS which will have any redirection status in its value. 2 things we need to understand about this variable.
1- Without any request redirection its default value is NULL.
2- Whenever we do a successful redirection its value becomes 200(NON ZERO), which we can make use of in our conditions part.
Detailed explanation of htaccess Rules:
Now coming to the condition explanation part: In RewriteRuleRewriteRule ^(.*) /xyz.html [L] I have NOT done any rewriting of url on browser why because of the THUMB RULE that we always want to show USER FRIENDLY URLs to users, so environment variable ENV:REDIRECT_STATUS will always be ZERO here.
Coming to 2nd RewriteRule now RewriteRule ^(.*) /abc/? [R=301,L] where user already using a user NON-friendly URL so first thing is I need to rewrite URL in browser to user friendly url hence R=301(redirection with permanent flag is used here). Once Redirection happens through this condition, 1st condition will start failing now why because that checks if REDIRECT_STATUS variable is NULL which is NOT after serving redirection from 2nd condition. Hence this is how it prevents loop by this small trick :)
Thanks for the great Explanation!
I tried it with a second URL, where "/xxx/" should show "zzz.html" But this gave me an Misonfiguration. I tried to shorten it like this:
RewriteEngine ON
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{REQUEST_URI} ^/abc/? [NC]
RewriteRule ^(.*) /xyz.html [L]
RewriteCond %{REQUEST_URI} ^/xxx/? [NC]
RewriteRule ^(.*) /zzz.html [L]
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{REQUEST_URI} ^/xyz\.html/? [NC]
RewriteRule ^(.*) /abc/? [R=301,L]
RewriteCond %{REQUEST_URI} ^/zzz\.html/? [NC]
RewriteRule ^(.*) /xxx/? [R=301,L]

Redirection is not working with mod_rewrite in htaccess

I need to redirect few URIs having query string like:
/pages/foo.bar?pageId=123456 to http://some.site/spam/egg/
/pages/foo.bar?pageId=45678 to http://another.site/spaming/egging/
I have this in my htaccess:
RewriteEngine On
RewriteCond %{REQUEST_URI} ^/pages/foo.bar$
RewriteCond %{QUERY_STRING} ^pageId=123456$
RewriteRule ^.*$ http://some.site/spam/egg/ [R=301,L]
RewriteCond %{REQUEST_URI} ^/pages/foo.bar$
RewriteCond %{QUERY_STRING} ^pageId=45678$
RewriteRule ^.*$ http://another.site/spaming/egging/ [R=301,L]
But its not working, showing 404. What am i doing wrong?
You need to move these 2 rules i.e. before all other rules just below RewriteEngine On line as other rules might be overriding this.
(Based on your comments) Your culprit rule is this rule:
RewriteRule . index.php [L]
Which is actually rewriting every request to index.php and changing value of REQUEST_URI variable to /index.php thus causing this condition to fail:
RewriteCond %{REQUEST_URI} ^/pages/foo.bar$
From your example, you get redirected to
http://some.site/spam/egg/?pageId=123456
http://another.site/spaming/egging/?pageId=45678
You can use your browser developer tools to see the redirection (in the Network tab).
Maybe the query strings in the redirected URL lead to a 404? You can add a ? at the end of your redirection to clear the query string:
RewriteCond %{REQUEST_URI} ^/pages/foo.bar$
RewriteCond %{QUERY_STRING} ^pageId=45678$
RewriteRule ^.*$ http://another.site/spaming/egging/? [R=301,L]

Redirect in combination with a rewrite condition in htaccess

I've got a cms-driven website, with no option to change the code. What I want to accomplish is creating friendly url's, using only apaches mod-rewrite engine.
The problem is I'm creating an infinite loop, because I first redirect the original url (index.php?id=21) to a friendly one (/friendly/) and then rewrite the '/friendly' part back to 'id=21'
I know there should be an extra condition or parameter to avoid looping in this case, but I can´t get one of the possible solutions to work.
Here´s the code:
RewriteCond %{query_string} ^id=21$ [NC]
RewriteRule /* /peuterspeelzaal? [R=301,L]
RewriteRule ^peuterspeelzaal$ index.php?id=21 [L]
You need to look at the request line in THE_REQUEST to see what originally has been requested:
RewriteCond %{THE_REQUEST} ^[A-Z]+\ /[^?\ ]*\?id=21\ [NC]
RewriteRule /* /peuterspeelzaal? [R=301,L]
RewriteRule ^peuterspeelzaal$ index.php?id=21 [L]
I'm guessing you are rewriting in both directions to ensure that old links are redirected to the new friendly urls?
You could just add a dummy parameter to all your "friendly" rewrites so that they don't match the other rule:
RewriteCond %{query_string} ^id=21$ [NC]
RewriteRule /* /peuterspeelzaal? [R=301,L]
RewriteRule ^peuterspeelzaal$ index.php?id=21&dummy=1 [L]