mod_rewrite strange infinite recursions - .htaccess

Server is Apache 2.4.18, PHP ver 7.0...
Intro:
On php side I rawurlencode($name) when creating html link.
REQUEST_URI looks like this:
/lang/cat1/cat2/product with bla (this/that) -- works
/lang/cat1/cat2/product with bla (this/ that) -- infinite internal redirect
The difference is only in one space this/ that vs. this/that
VirtualHost:
# I have tried different combinations of
AllowEncodedSlashes On
AllowEncodedSlashes NoDecode.
htaccess:
<IfModule mod_rewrite.c>
Options +FollowSymLinks -MultiViews #different combinations
RewriteEngine On
# tried different combinations
#RewriteCond %{REQUEST_URI} !^/?file\.php$
#RewriteCond %{ENV:REDIRECT_STATUS} ^$
#RewriteCond %{ENV:REDIRECT_STATUS} !200
RewriteRule .? file.php [L] # END
</IfModule>
All I want is standard front controller, ALL requests should go to file.php That works in 99.99% of cases. But ruri with bla/ in it goes to infinite recursions.
Questions:
Why is this happening?
How to solve it?

You need to uncomment your last rewrite condition.
Try :
<IfModule mod_rewrite.c>
Options +FollowSymLinks -MultiViews #different combinations
RewriteEngine On
# tried different combinations
#RewriteCond %{REQUEST_URI} !^/?file\.php$
#RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteCond %{ENV:REDIRECT_STATUS} !200
# END
</IfModule>
Otherwise your rule will redirect /file.php to itself.
On apache 2.4 you can simply use END flag to terminate the rewrite processing :
RewriteEngine on
RewriteRule .? file.php [END]

I have found a solution on another forum.
Solution was painfully simple. But might help someone.
One guy sad: Be brave, understand that there is nothing wrong with your htaccess! But you still have recursions. So bug is somewhere in php code.
That destroyed my htaccess fixation allowing me to dive into business and fw code. Bug was found few hours later. One of url functions had premature rawurldecode(). Cool for lazy programin, not so cool if you have products with encoded / in names.
But the answer to question "Did this work before?" was misleading also. "Yes, sure. It must be because of resent migration."
Riiight ;)

Related

to clean and short the using .htaccess

I know many user have asked this question but i have tried everything still not understand the problem
I have url like this
http://localhost/test/storelocator.php?page=store
Now i want to like this
http://localhost/spawake/storelocator
My htaccess
# Turn Rewrite Engine On
RewriteEngine on
# Rewrite for storelocator.php
RewriteRule ^storelocator storelocator.php [NC, L]
but showing me the error in all the pages Internal Server Error So anyone can plz hep
Remove space after NC
Disable MultiViews option
Restrict your pattern by using end anchor.
Your .htaccess:
Option -MultiViews
RewriteEngine on
RewriteBase /spawake/fbdemo/
# Rewrite for storelocator.php
RewriteRule ^storelocator/?$ storelocator.php [NC,L]

.htaccess file ignored on Ubuntu server

I have recently moved to a new server for my website, and i activated mod_rewrite with success, but some files still not working !
Like this one:
RewriteRule ^activate\/(.*)\/(.*)$ activate.php?Email=$1&hash=$2
I have made all necessary changes on my VPS (Ubuntu) !
Any idea ?
Like this lines work well:
RewriteRule ^search\/(.*)\/([a-zA-Z0-9_-]+)$ search.php?view=$1&p=$2
RewriteRule ^search$ searchResults.php
RewriteRule ^term$ term.php
RewriteRule ^faq$ faq.php
# Non-working line...
RewriteRule ^activate\/(.*)\/(.*)$ activate.php?Email=$1&hash=$2
Note that mod_rewrite are enabled and all other lines work well only this one !
First thing, you must define a RewriteBase because of your two rules (first and last) that create both virtual directories.
Then, you should disable MultiViews option to make term or faq rule work without problem.
Finally, you can rewrite your patterns in a more generic way (or at least in a better way, more precise). Also, don't forget L flag ([L]) after each rule, otherwise mod_rewrite continues to evaluate next rules.
You can replace your current code in your htaccess by this one (assuming your htaccess is in root folder)
Options -MultiViews
RewriteEngine On
RewriteBase /
RewriteRule ^search/([^/]+)/([^/]+)$ search.php?view=$1&p=$2 [L]
RewriteRule ^search$ searchResults.php [L]
RewriteRule ^term$ term.php [L]
RewriteRule ^faq$ faq.php [L]
RewriteRule ^activate/([^/]+)/([^/]+)$ activate.php?Email=$1&hash=$2 [L]

Changed part of path and need to redirect old to new

I have updated country code in the base path and I am attempting the redirect users that end up going to:
www.example.com/uk/etc1/etc2/etc..
www.example.com/gb/etc1/etc2/etc..
But also sometimes also www.example.com/uk#etc
I thought this would be fairly trivial in mod_rewrite I cant get anything to work.
The closest I feel I have come is the following rule, but nothing happens when I land on uk.
<IfModule mod_rewrite.c>
Options +FollowSymLinks
RewriteEngine on
RewriteRule .* index.php [L] #this is active already on the page
RewriteRule ^/uk(.*) /gb(.*) [R]
</IfModule>
Edit:
This seems closer but I am getting stuck in an endless loop:
RewriteRule ^uk(.*) /gb$1 [R]
Edit 2 / (3) Answer:
This seems to redirect correctly(is correct):
RewriteRule ^uk(.*)$ /gb$1 [R=302,L]
RewriteRule .* index.php [L]
But the formatting is broken on the page, looks like some loop problem.
But the formatting is incorrect, If I swap the two RewriteRules the formatting is correct but the uk => gb conversion doesn't seem to get called at all.
Answer
Be careful of Rewriteconditions, I failed to notice the significance of them and I removed them for the original index.php rewrite which meant it could not locate any media.
I failed to take notice of the rewrite conditions which applied for the original index.php
This should do the trick:
Options +FollowSymLinks
DirectoryIndex index.php
RewriteEngine on
RewriteRule ^/uk(.*) /gb$1 [R=301,L]

how to achieve subdomain url rewrite using modrewrite

I want to redirect website user to www.mywebsite/users.php?user=xyz when the user types http://xyz.mywebsite.com into the address bar where http://xyz.mywebsite.com is virtual and doesnt exist.
I am a beginner and doesnt know much about url rewriting. Tried to search google and stack overflow but didnt got the solution.
I started with this
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{HTTP_HOST} ^([^.]+).mobilehealthnig.com$
RewriteRule (.*) http://www.mywebsite.com/users.php?subdomain=%1
</IfModule>
also tried this but none of these are working for me
RewriteEngine On
RewriteCond %{HTTP_HOST} !^www.mywebsite.com
RewriteCond %{HTTP_HOST} ([^.]+).mywebsite.com
RewriteRule ^(.*)$ /users.php?subdoamin=%1
Ok, based on your additional input I suggest this setup:
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{HTTP_HOST} ^(.+)\.mywebsite\.com$
RewriteRule (.*) http://www.mywebsite.com/users.php?subdomain=%1 [L]
</IfModule>
If that does not work (I take that from your comment), you have to check where the actual problem is:
does rewriting work at all?
does this rule do anything atall? what?
is that rule ignored? why?
What absolutely makes most sense in such cases is to turn on rewrite logging to see and understand what is actually happening inside the rewrite engine. Please take a look at the two commands RewriteLog and RewriteLogLevel inside the manual mentioned. Enable a log level of maybe 7 and look what is logged when you make a single request. It should give you an idea of where to look for the cause of the problem.

.htaccess mask - SEO

Looking to put the following into my htaccess file:
User visits http://mysite.com/test/test/123
User is actually visiting http://mysite.com/test/index.php?q=123
I have seen it done before but I can't figure it out. The user is not supposed to see that they are visiting the second url. This is particularly useful for SEO. Can anyone help me on this one?
Updated Code for Answer:
Options -Multiviews
rewriterule ^test\/([a-zA-Z]+)\/([0-9]+)$ test\/index\.php?id=$3 [L]
*Note: The Options -Multiviews is needed for GoDaddy hosting to enable mod_rewrite.*
Be sure mod_rewrite is on:
RewriteEngine on
RewriteRule ^test/([a-zA-Z0-9_-]+)/([0-9]+)\.html$ test.php?id=$2
Double test
RewriteEngine On
RewriteRule ^test/test/([^/]*)$ /test/index.php?q=$1 [L]
Single test
RewriteEngine On
RewriteRule ^test/([^/]*)$ /test/index.php?q=$1 [L]

Resources