Forum Moderators: phranque

Message Too Old, No Replies

Multi variable conditional mod rewrite challenge

Im having an issue with what is, to me, a complex mod_rewrite

         

devknob

1:01 am on Jun 23, 2008 (gmt 0)

10+ Year Member



Im trying to do a conditional multi-variable rewrite.
Here is the code, this currently gives me a Internal Server Error, I will comment in with a // what I am trying to accomplish


RewriteEngine On
Options +FollowSymLinks
Options All -Indexes
RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-d

RewriteRule ^/([^/]+)$ /dod.php?do=$1 [PT]
// If only 1 requested subdirectory, rewrite to dod.php, if not, pass thru
RewriteRule ^/([^/]+)/([^.]+)$ /keys.php?city=$2&st=$1 [PT]
// If only 2 requested subdirectory, rewrite to dod.php, if not, pass thru

RewriteRule ^/([^/]+)/([^.]+)/([^.]+)$ /do.php?city=$2&st=$1&key=$3 [PT]
// If only 3 requested subdirectory, rewrite to dod.php, if not, pass thru


Not sure what the problem is. Please help.

devknob

1:15 am on Jun 23, 2008 (gmt 0)

10+ Year Member



ok now I removed some additional code at the bottom and I am not getting the Internal server error, however, its just not working as it is supposed to or at all that I can indicate.

jdMorgan

1:46 am on Jun 23, 2008 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



Your comments indicate a misunderstanding of the RewriteRule flags.

Comments typically precede a line of code, and are indicated as comments by preceding them with "#".

Here's what your code is actually doing:


# Turn on the rewrite engine
RewriteEngine On
# Enable mod_rewrite
Options +FollowSymLinks
# OK, forget that and start over, enable all options except Indexes and MultiViews
Options All -Indexes
# Redundantly declare the default RewriteBase setting
RewriteBase /
#
# If the requested filename does not resolve to an existing directory
RewriteCond %{REQUEST_FILENAME} !-d
# then rewrite all top-level directory requests to dod.php, leaving the destination in URL format
RewriteRule ^/([^/]+)$ /dod.php?do=$1 [PT]
#
# else:
# Rewrite all first-level subdirectory requests to keys.php, leaving the destination in URL format
RewriteRule ^/([^/]+)/([^.]+)$ /keys.php?city=$2&st=$1 [PT]
#
# Rewrite all second-level subdirectory [i]extensionless[/i] requests ro do.php, leaving the destination in URL format
RewriteRule ^/([^/]+)/([^.]+)/([^.]+)$ /do.php?city=$2&st=$1&key=$3 [PT]

The RewriteCond affects only the first RewriteRule, and the [PT] flag is probably not doing what you expect.

The RewriteRule flag is applied IF the pattern matches and the substitution is made; It does not constitute an "else" statement.

I'll leave it at that for now, since I don't know what direction you might want to go in from here.

Jim

[edited by: jdMorgan at 2:07 am (utc) on June 23, 2008]

devknob

2:06 am on Jun 23, 2008 (gmt 0)

10+ Year Member



so maybe this is a little closer?

RewriteEngine On
Options All -Indexes
RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^/([^/]+)$ /dod.php?do=$1 [L]
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^/([^/]+)/([^.]+)$ /keys.php?city=$2&st=$1 [L]
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^/([^/]+)/([^.]+)/([^.]+)$ /do.php?city=$2&st=$1&key=$3 [L]

I put in [L] because I read that would end rewriting after that point. Im just trying to make it to where if
site.com/$1 /dod.php?do=$1
site.com/$1/$2 /keys.php?city=$2&st=$1
site.com/$1/$2/$3 /keys.php?city=$2&st=$1&key=$3

If that makes any sense.

jdMorgan

2:13 am on Jun 23, 2008 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



The regular-expressions patterns are inconsistent. what are the characteristics of each part of the URL-path that you want to pass as cariables to the script? As it stands now, some may not contain periods, while others may not contain slashes.

You can also use either a "skip" or a "quit" flag to stopprocessing if the requested URL resolves to an existing directory. This means the code only has to call the OS once to go check the disk, instead of three times as you have it now:


Options All -Indexes
RewriteEngine On
#
# Skip next three rules if requested URL-path resolves to existing directory
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule .* - [S=3]
#
RewriteRule ^/([^/]+)$ /dod.php?do=$1 [L]
RewriteRule ^/([^/]+)/([^.]+)$ /keys.php?city=$2&st=$1 [L]
RewriteRule ^/([^/]+)/([^.]+)/([^.]+)$ /do.php?city=$2&st=$1&key=$3 [L]

Also, I presume this code is going into httpd.conf or conf.d, and not into .htaccess?

Jim

devknob

2:28 am on Jun 23, 2008 (gmt 0)

10+ Year Member



.htaccess

devknob

2:38 am on Jun 23, 2008 (gmt 0)

10+ Year Member



The only text to be contained within variables are like /CA/Oakland/ltl-trucking

so just letters and -

I copied and pasted your response into .htaccess and it didnt work.

jdMorgan

2:48 am on Jun 23, 2008 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member



That code won't work in .htaccess, which is why I presumed that it was to go elsewhere.

Options All -Indexes
RewriteEngine on
#
# Skip next three rules if requested URL-path resolves to existing directory
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule .* - [S=3]
#
RewriteRule ^([a-z\-]+)$ /dod.php?do=$1 [NC,L]
RewriteRule ^([a-z\-]+)/([a-z\-]+)$ /keys.php?city=$2&st=$1 [NC,L]
RewriteRule ^([a-z\-]+)/([a-z\-]+)/([a-z\-]+)$ /do.php?city=$2&st=$1&key=$3 [NC,L]

Note that in code to be used in .htaccess the leading slash, which is the path to the current .htaccess directory, must be removed.

Jim

devknob

2:58 am on Jun 23, 2008 (gmt 0)

10+ Year Member



Awesome, this works perfect. Thank you jdMorgan