Forum Moderators: phranque
I want to redirect users from all sudirectories of my domain to a script. This should happen transparently. To accomplish this, I wanted to use mod_rewrite. But I'm at a dead end now, really.
Structure is like this:
which contains directories (they, too, contain subdirectories) and files. Now if someone tries to access a file, this should work like normal. [tombstone.mydomain.net...] should work like normal. Trying to accesshttp://tombstone.mydomain.net/usr/bin/ should redirect the user to [tombstone.mydomain.net...] though. How would i go about doing this?
I have tried this:
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [L]
RewriteRule ^([^/]+)/$ index.php?$1 [L]
but it doesn't really work as expected. It works alright if i go to [tombstone.mydomain.net...] and the directory does *NOT* exist. If the directory DOES exist, however, I won't be redirected.
What do I need to do? Oh and it only works with level 1 subdirectories...
Any help is appreciated!
Welcome to WebmasterWorld!
I'm not sure I understand the distinctions your trying to make between what should be redirected and what shouldn't. But here's what your code does, line-by-line:
# Turn on RewriteEngine
RewriteEngine on
# IF the requested resource exists as a directory
RewriteCond %{REQUEST_FILENAME} -d
# Then, for any requested resource, do no rewrite, and quit processing RewriteRules
RewriteRule ^.*$ - [L]
# ELSE, rewrite anything that contains at least one character not equal to a slash and followed
# only by a siash to index.php, with a query string equal to the characters preceding the slash.
RewriteRule ^([^/]+)/$ index.php?$1 [L]
Sometimes, it is helpful to provide examples of what you want to redirect *and* what you don't want to redirect -- the more variations in the examples, the better. If the above is not helpful, you might want to expand on your first post with some more examples.
A further comment: You may have picked /usr/bin just as an example, but it's highly unusual to have this level of "visibility" from HTTP. I would not configure a server so that this level of directory is visible. It is more usual to have http:www.example.com/index.php point to a file located in /usr/www/cgi-bin or /usr/public_html using the Alias or ScriptAlias directive, rather than requiring (or allowing) someone to request index.php as http:example.com/usr/www/index.php.
Again, this may just be the example URL you chose, and not anything wrong with your server configuration. If so, just ignore this comment.
Jim
thank you for your fast and detailed answer. I'm afraid that this is my first time of using mod_rewrite and so I still don't have an idea of what exactly I'm doing there.
Reading your translated code, I will try to make some kind of pseudo code. Correct me if this is wrong:
Rewrite Engine Onif ( RequestedFile == Directory )
{
exit;
} else {
rewrite;
}
If above pseudo code is correct, then I missed the point of what I wanted to do, completely.
So here are a few examples of what I want to accomplish:
REDIRECT:
mydomain.com/var/mp3/ --> mydomain.com/index.php?/var/mp3/
mydomain.com/var/ --> mydomain.com/index.php?/var/
mydomain.com/somedirectory/ --> mydomain.com/index.php?/somedirectory/
mydomain.com/ --> mydomain.com/index.php?/
DO NOT REDIRECT:
mydomain.com/var/mp3/somemp3file.mp3
mydomain.com/var/someotherfile
mydomain.com/yetsomeotherfile
>> A further comment: You may have picked /usr/bin
>> just as an example, but it's highly unusual to have
>> this level of "visibility" from HTTP. I would not
>> configure a server so that this level of directory
>> is visible.
Thank you for your word of advice and your concern.
As you said, I only picked it as an example. What I'm trying to do is rewriting the apache directory listing, which has been disabled by my host (OPTION statements in .htaccess aren't read). I'm rewriting this for a semi-public fileserver which has indeed a directory structure with /usr/bin directories. Just a habit, I guess (In Windows, my Program Files directory is also named /bin, my My Files directory is called /home and the harddisk is "usr"). I just like to sort my files on the fileserver and since I like the simplicity of *NIX file-/directory-names, I'm using the same on the server.
Now, the code looks like this:
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^([^/]+)/$ index.php?$1 [L]
RewriteRule ^.*$ - [L]
and does what it's supposed to do. It redirects every subdirectory within the "/" root directory to my index.php file.
http:myserver.net/mp3 now becomes http:myserver.net/index.php?/mp3 but it all happens transparently. Exactly what I wanted. Thank you very much!
There is only a small problem left. Sub-sub diectories don't get redirected.
http:myserver.net/mp3/misc/ does NOT become http:myserver.net/index.php?/mp3/misc/
Although I don't see, why.
It's because you used a start-anchored pattern that rejects slashes in the RewriteRule, so it will accept one and only one slash in the URL. "[^/]+" means, "one or more characters, but no slashes." So, therefore, "^[^/]+/$" means, "Starts with one or more characters (but no slashes), ending with a slash." The parentheses create the back-reference $1 for use in the substitution, but they don't affect whether the pattern matches in this case, so I omitted them from the description.
Try this instead:
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^(.+)/$ index.php?$1 [L]
Also, your second RewriteRule won't do anything except unconditionally by-pass any subsequent RewriteRules, so I left it off.
[added] There is a nice short regular expressions tutorial cited in our forum charter [webmasterworld.com], if that might be of help. [/added]
Jim