[wp-hackers] cheap 404 serving

"Matthias P. Würfl" mpw at taquiri.de
Tue Oct 16 13:27:31 UTC 2012

Hi Ryan!

I'm not sure if you're misunderstanding me or i'm misunderstanding 
you... :-)

Am 16.10.2012 13:18, schrieb Ryan McCue:
> "Matthias P. Würfl" wrote:
>> All the rewrite-rules i can find send every request that cannot be
>> served as static content to wordpress. It would be cheaper to check the
>> request if handeling by wordpress makes sense at all before wordpress is
>> bootstrapped.
>> - URL ends on ".html" or "/"
> Both of these can be used by WordPress (especially ending with a
> trailing slash, which most sites use). If you don't use them in your
> site, it should be fairly trivial to not send that to WP.

I meant conditions that show that this file should be served by 
Wordpress. These URIs ending "/" or ".html" should be served by 
Wordpress. Others (".jpg") should not be served by Wordpress even if the 
file doesn't exist.

>> - Accept-header contatins "text/html"
> All pages requested from WP (with the exception of RSS/Atom feeds and
> XML-RPC) will have "Accept: text/html, ...", otherwise the server would
> have no idea what to send back. I think you may be misunderstanding what
> this header does.

Headers don't *do*, they just *tell* what the client expects. If the 
Accept-header is "image/jpeg" i know theres no sense in sending this 
request to WP (correct me if I'm wrong).

>> Are there any ready-to-use recipes to serve 404 errors cheaper? For
>> Nginx? :-)
> Alright, so as far as I can tell, this breaks down into a few places:
> Anything starting with "wp-admin/", "wp-content/" or "wp-includes/" can
> be ignored, since WP rewrite rules should never touch those.
> Something like this should fix that (for nginx):
> 	location ~* ^(/wp-includes|/wp-content|/wp-admin) {
> 		try_files $uri $uri/ =404;
> 	}
> (Assuming you're not using the 404 handler for WordPress; please don't
> do that.)

I don't understand that. How can that catch all the requests to 
/favicon.ico, /robots.txt, /phpmyadmin and /othernonexistant.file? 
Where's php in here at all?

My current configuration is:

     location /acv/ {

         try_files $uri /acv/index.php?q=$uri;
         index index.php;

         location ~ ^/acv/(wp/wp-cron.php)/ {
             deny all;
         location ~ ^/acv/.*(\.txt|\.log|\.tpl|pkg.rev|readme.html)$ {
             deny all;

         location = /acv/wp/wp-admin/ {
            rewrite $uri index.php;
     location ~ \.php$ {
         try_files $uri =404;
         include /etc/nginx/fastcgi_params;

A request to a static file takes 20ms, a request to Wordpress takes 
400ms (if not cached). So far so good, but: a request to a non-existing 
"foo.gif" that is requested by the html produced by wordpress takes 
400ms as well. When i change the configuration to:

     location /acv/ {
         # EDIT: Standard: Do not send to wordpress
         try_files $uri =404;
         index index.php;

         [...] # untouched

         # EDIT: Added: send to WP if URL ends with "/".
         location ~/acv/.*/$ {
             try_files $uri /acv/index.php?q=$uri;

Then the missing "foo.gif" takes 1ms instead of 400ms. Imagine a gallery 
site where all images disappear for some reasons: the server will crash 
with the first configuration while it will stay online (and wait for 
some rsync to add the missing pictures again) and happyly serve all the 404.

So my question is: How can i send as much 404s without wordpress without 
having "false negatives".

- Matthias

More information about the wp-hackers mailing list