Take the 2-minute tour ×
Server Fault is a question and answer site for professional system and network administrators. It's 100% free, no registration required.

I have several RewriteRules in an Apache VirtualHost configuration. I'd like to be able to test the current URL (after the preceeding rewrites) against some condition. The problem is that the variable %REQUEST_URI is set at the beginning of processing and doesn't change after every rule. There is very little documentation on those variables; is there is some way to use RewriteCond to test against the current URL?

I've enabled the rewrite log and it's apparent that even after the first RewriteRule is matched and re-written, %REQUEST_URI is still set to '/'

#Map '/' and '' to '/home'
RewriteRule ^/?$ /home

#Check for cached page
RewriteCond %{DOCUMENT_ROOT}/system/cache%{REQUEST_URI}.html -f
RewriteRule ^(.+)$ /system/cache/$1.html [QSA,L]

Is there any simple way to accomplish this?

Edit: Here is an excerpt from the RewriteLog, I don't think an internal sub-request is happening.

(3) applying pattern '^/?$' to uri '/'
(2) rewrite '/' -> '/home'
(3) applying pattern '^([^.]+)$' to uri '/home'
(4) RewriteCond: input='/var/www/vhosts/example.com/subdomains/demo/rails/public/system/cache/.html' pattern='-f' => not-matched
(3) applying pattern '^.*$' to uri '/home'
(4) RewriteCond: input='/var/www/vhosts/example.com/subdomains/demo/rails/public/system/maintenance.html' pattern='-f' => not-matched
(3) applying pattern '^/(.*)$' to uri '/home'
(4) RewriteCond: input='/home' pattern='!-f' => matched
(2) rewrite '/home' -> 'http://127.0.0.1:8100/home'
(2) forcing proxy-throughput with http://127.0.0.1:8100/home
(1) go-ahead with proxy request proxy:http://127.0.0.1:8100/home [OK]
share|improve this question
add comment

2 Answers 2

up vote 2 down vote accepted

You can access the "current" URI via a backreference. From the RewriteRule documentation...

TestString is a string which can contain the following expanded constructs in addition to plain text:

  • RewriteRule backreferences: These are backreferences of the form $N (0 <= N <= 9), which provide access to the grouped parts (in parentheses) of the pattern, from the RewriteRule which is subject to the current set of RewriteCond conditions.

You can handle the initial slash more cleanly too — the request URI always starts with a /. (The shortest request you can make is GET / HTTP/1.0.) The solution is...

# Map '/' to '/home'
RewriteRule ^/$ /home

# Check for cached page
RewriteCond %{DOCUMENT_ROOT}/system/cache/$1.html -f
RewriteRule ^/(.+)$ /system/cache/$1.html [QSA,L]
share|improve this answer
add comment

Main question: You shouldn't need to worry about it. Yes, your second rule won't match on the initial request, but your rewrite to /home will generate an internal subrequest, which will then match the caching rule.

Side question: We use $1 when we mean $1. :) $0 refers to the entire pattern match, where $1 refers to the first capturing group (parenthesized chunk) within the match. (That does mean that your second rule could be as easily written RewriteRule .+ /system/cache/$0.html. People often consider this less clear than using explicit capturing like you're doing, though.)

share|improve this answer
    
I don't think an internal subrequest is happening, see my edit above. It's passed through to the proxy, then Rails handles the request.. not what I want. –  Daniel Beardsley Jul 3 '09 at 21:11
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.