A rather challenging request that may be received is the conditional GET, which typically means a request with an If-Modified-Since header. The HTTP specification has this to say:

The semantics of the GET method change to a "conditional GET" if the request message 
includes an If-Modified-Since, If-Unmodified-Since, If-Match, If-None-Match, or If-
Range header field.  A conditional GET method requests that the entity be transferred 
only under the circumstances described by the conditional header field(s). The 
conditional GET method is intended to reduce unnecessary network usage by allowing
cached entities to be refreshed without requiring multiple requests or transferring 
data already held by the client.

So how can we reduce the unnecessary network usage in such a case? mod_perl makes it easy by providing access to Apache's meets_conditions( ) function (which lives in Apache::File). The Last-Modified (and possibly ETag) headers must be set up before calling this method. If the return value of this method is anything other than OK, then this value is the one that should be returned from the handler when we have finished. Apache handles the rest for us. For example:

if ((my $result = $r->meets_conditions) != OK) {
    return $result;
}
#else ... go and send the response body ...

If we have a Squid accelerator running, it will often handle the conditionals for us, and we can enjoy its extremely fast responses for such requests by reading the access.log file. Just grep for TCP_IMS_HIT/304. However, there are circumstances under which Squid may not be allowed to use its cache. That is why the origin server (which is the server we are programming) needs to handle conditional GETs as well, even if a Squid accelerator is running.