Problem:
I have been trying to write a RewriteRule with an empty REQUEST_URI for quite some time. (If the REQUEST_URI is not empty I have had no problems.)
Ironically:
I decided to create this post and while in the composing process tried just one more search without success… I had a sudden brain wave and delighted to say that this works:
.htaccess
DirectoryIndex MY_CACHE_FOLDER/cached/home index.php
# RewriteEngine On
# Maybe in Cache?
RewriteCond %{DOCUMENT_ROOT}/MY_CACHE_FOLDER/cached/%{REQUEST_URI} -f
RewriteRule ^(.+)$ /MY_CACHE_FOLDER/cached/$1 [QSA,L]
# No Cache file so fall through and use PHP Framework
RewriteCond $1 !^(index\.php|robots\.txt|favicon\.ico|Sitemap\.xml)
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php/$1 [L,NC,QSA]
I am curious to know if there could be any problems or if there is a better solution to the above script.
It’s odd to see the forward reference in your second block’s first RewriteCond … but that’s perfectly acceptable!
First block: No need for the QSA flag as that’s automatic (as long as you don’t create a new query string).
Second block: You’ve been around long enough to know that I have definite problems with two items there:
^(.)$ is the same thing (when called from the DocumentRoot) as Apache’s %{REQUEST_URI} variable so why not use it instead (replace both $1’s and change ^(.)$ to .? to guarantee a match (after the three RewriteCond statements match).
NEVER use the No Case flag on a %{REQUEST_URI} variable (i.e., a RewriteRule statement) and, again, you’re not creating a new query string so the QSA isn’t needed either.
Back again after trying your recommendations and they all seem to work fine, thank you.
# This Directive will make Apache look first
DirectoryIndex /MY_CACHE_FOLDER/cached/home index.php
RewriteEngine on
# Maybe in cached folder?
RewriteCond %{DOCUMENT_ROOT}/MY_CACHE_FOLDER/cached/%{REQUEST_URI} -f
RewriteRule ^(.+)$ /MY_CACHE_FOLDER/cached/$1 [L]
# CodeIgniter PHP Framework
RewriteCond $1 !^(index\.php|robots\.txt|favicon\.ico|Sitemap\.xml|Sitemap-static\.xml)
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.?)$ index.php/$1 [L]
As you may see from the above CodeIgniter PrettyUrls are used and if and only if the http_response_code() is set to 200 then the generated file is saved to MY_CACHE_FOLDER.
New Question:
Is it possible to also redirect /index.php to /MY_CACHE_FOLDER/cached/home file?
I’ve never seen a DirectoryIndex refer to two different directory levels (and the leading / MAY be telling Apache to use the server root [THEN the DocumentRoot] - so I’m not sure whether this will work as intended. Very interesting, though, so please comment on its success (after masking index.php). BTW, can “home” be served as a file???
The first RewriteRule block is simply redirecting to your cache IF the {REQUEST_URI} exists in the cache. I’m a bit puzzled, though, why you didn’t use %{REQUEST_URI} in the recirection (with .? for the regex) when you’d used it in the RewriteCond. It’s not wrong but seems like “changing horses in mid-stream.”
The second RewriteRule block leaves me confused … because of the index.php in the first condition and redirecting to index.php/index.php. Can that be correct?.Is index.php a “request handler” which looks at the URI trailing index.php (and with Options +MultiViews - argh, I hate that, too, 'cause it causes too many problems placing files - with or without extensions - in the path)… By the same token, “if it ain’t broke, don’t fix it!”
Of course it is (possible to redirect index.php to the cache/home file - assuming that Apache knows what to do with “home”). Simply change the name of “home” to index.php and your first RewriteRule will do that for you OR add a duplicate block specifying index.php (rather than %{REQUEST_URI} and home rather than $1. I’m not sure how the cache will treat the MultiViews of the now third RewriteRule block, though.