Skip navigation

Say you have 10 different versions of the same image, like your feedburner count. Here is some sweet htaccess rewriterules and caching directives you can use to show a different version based on the time.

RewriteEngine On
RewriteBase /

RewriteCond %{TIME_SEC} ^.([0-9]) [NC]
RewriteRule ^feed\.gif$ /feed%1.gif [NC,L]

RewriteEngine On
RewriteBase /
RewriteRule !\.gif - [S=4]

RewriteCond %{TIME_SEC} ^(0|4|8|12|16|22|26|30|34|38|42|46|50|54|58)$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^feed\.gif$ /zi/feed1.gif [S=3]

RewriteCond %{TIME_SEC} ^(1|5|9|13|17|23|27|31|35|39|43|47|51|55|59)$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^feed\.gif$ /zi/feed2.gif [S=2]

RewriteCond %{TIME_SEC} ^(2|6|10|14|18|24|28|32|36|40|44|48|52|56|60)$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^feed\.gif$ /zi/feed3.gif [S=1]

RewriteCond %{TIME_SEC} ^(3|7|11|15|19|25|29|33|37|41|45|49|53|57)$
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^feed\.gif$ /zi/feed4.gif

In order for the image to be reloaded on each page-view of the site, I set up some anti-caching headers in my .htaccess file. First I unset the far-future Expires headers that I normally send with images, and then I instruct browsers to check the image every request to see if it has been modified.

Header unset Expires
Header unset Last-Modified
FileETag None
Header set Cache-Control "no-cache, must-revalidate"

Awesome! You can read the full article here: Rewriting Feedburner Counter, Cache, and more with htaccess rewrite..

For full article see: Redirecting subdomains to directories in apache.

Note: It is likely you will need root access to carry out apache config alterations

If you want to be able to redirect to so that is shown in the address bar here’s a quick and dirty how to:

First off if you want any subdomain to be able to be redirected first you need to set-up your DNS correctly. In my case this was as simple as going to the people that host my domain and adding an A record with the wildcard * that pointed to my server’s ip address. Bear in mind your DNS settings may take a while to work so be patient. Before you proceed you should check that resolves to the ip address of your server. You can check this by running:


This should respond with something like this:

[root@cheekymonkey conf]# ping
PING ( 56(84) bytes of data.
64 bytes from ( icmp_seq=0 ttl=64 time=0.058 ms
64 bytes from ( icmp_seq=1 ttl=64 time=0.040 ms
64 bytes from ( icmp_seq=2 ttl=64 time=0.071 ms
64 bytes from ( icmp_seq=3 ttl=64 time=0.028 ms

The next step is to set-up the virtual host to respond to the wildcard subdomains. In the case of plesk you have to set-up a vhost.conf file but on any other apache installation you can just edit httpd.conf and look for the <VirtualHost> that corresponds to your site. If you are using Plesk you will need to ssh in to your server and create a vhost.conf file if it doesn’t already exist here where <> is your domain:


Open that file with the command line editor of your choice and add the following directives:

ServerAlias *
RewriteEngine on
RewriteCond %{HTTP_HOST} !^www.* [NC]
RewriteCond %{HTTP_HOST} ^([^\.]+)\.domain\.com
RewriteCond /var/www/vhosts/ -d
RewriteRule ^(.*) /%1/$1 [L]

Substitute for your domain. Now here’s a quick walkthrough how these rules work. The first line ServerAlias * tells apache to accept

Next the rewrite rules work as follows:

  1. The first line of mod_rewrite !^www.* only matches urls that don’t begin with www. You don’t want to redirect to do you? Note: you could add additional lines like these to prevent re-writing other subdomains like if that should not be redirected to
  2. The second line ^([^\.]+)\.*$ captures into a backreference anything that doesn’t have a period e.g. the subdomain. The plus makes sure that there is at least one character that matches.
  3. The next condition checked is that the directory captured into the backreference does actually exist hence the -d.
  4. This last line ^(.*) /%1/$1 [L] takes the requested path and dumps it into a back reference and then rewrites it to point to the a directory (the subdomain backreference captured in the Rewrite conditions above) . In other words %1 is the subdomain backreference and $1 is the path backreference (that captured by .*). The important thing to rember is you can refer to backreferences in rewriteCond lines with % and backreferences in rewriteRules with $. Lastly the [L] (last) means doen’t further rewrite this URL. Note: You might want to leave this out if you are doing any subsequent rewrites, be sure to test what you have set-up thoroughly!!!

Now once you have made those changes if you are running plesk you will need to apply your vhost.conf changes with the following command:

/usr/local/psa/admin/sbin/websrvmng --reconfigure-vhost --vhost-name=<>

And then whether are using Plesk or not you need to restart apache e.g:

service httpd restart

This is a high-level discussion of the various ways to use CherryPy behind Apache. Individual CherryPy HOWTO’s are at:

When should you run your CherryPy app behind Apache?

The CherryPy HTTP server (before CherryPy 3.0.0 beta) doesn’t support SSL out of the box (although there is a >third-party module for it). So, if you have a simple website that doesn’t have a really high traffic website (say, less than 50 hits/second) and if you don’t need SSL, then running CherryPy exposed is fine. Otherwise, running it behind Apache is probably the right option for you.

What are the advantages?

  • You can configure Apache to serve static files directly (and free CherryPy from doing this)
  • You have access to all the mod_* modules from Apache. For instance:
    • mod_ssl so Apache can handle SSL for you and CherryPy doesn’t have to know about this (recipe here).
    • mod_gzip if you want Apache to compress your pages instead of CherryPy (Apache is probably a bit faster at this)
    • VirtualHosting/mod_rewrite/mod_proxy if you want to mix & match multiple sites. They can be served from the same CherryPy server or from multiple ones.
    • all other mod_* modules …

Are there any drawbacks?

I’ve been using this setup for many production websites for almost 4 years, some of them on Windows and some of them on Linux and quite frankly, I don’t think there are any drawbacks. The only minor thing that I can think of is that you have to install Apache and learn how to configure it. But it is not very hard and it is worth it because Apache is truly a great webserver and you can take advantage of its numerous features.

Comparing the various methods

IMHO, the best way to do this is to use mod_rewrite. I’ve tried FastCGI and the performance is about the same but it is more complex to setup.

mod_rewrite mod_proxy mod_python FastCGI SCGI
interface to CherryPy socket socket in-process socket socket
works with .htaccess Y

Getting the right Host header in CherryPy</a

One problem with this setup is that requests that arrive to CherryPy will look like they’re coming from "localhost" (the "Host" header will say "localhost:port).

This is not a problem if you’re only using relative or absolute URLs (the browser will do the right thing), but this is a problem if you’re using canonical URLs (URLs that include the protocol and domain name) generated by CherryPy. This is also a problem if you want to issue a redirect because a redirect should include a canonical URL.

This is an especially important issue because CherryPy will create redirects for you in cases where the url is missing a final ‘/’. Redirecting users to when they typed in is not likely to win you many friends.

If you are using Apache 2.0 and have control of your configuration, the easiest solution is to add the following in your (virtual) server’s conf file:

ProxyPreserveHost on

If you also want newer Apache 1.x compatibility (works for 1.3.33) or you can’t edit the Apache config file, the proxy tool will automatically use the X-Forwarded-Host header provided by Apache.

tools.proxy.on: True

For earlier Apache 1.x installations, you need to explicitly set the proxy.base, which tells CherryPy to use a different "Host" header than the one coming from the request:

tools.proxy.on: True
tools.proxy.base: ''


Code Message
100 Continue
101 Switching Protocols
102 Processing
200 OK
201 Created
202 Accepted
203 Non-Authoritative Information
204 No Content
205 Reset Content
206 Partial Content
207 Multi-Status
300 Multiple Choices
301 Moved Permanently
302 Found
303 See Other
304 Not Modified
305 Use Proxy
306 unused
307 Temporary Redirect
400 Bad Request
401 Authorization Required
402 Payment Required
403 Forbidden
404 Not Found
405 Method Not Allowed
406 Not Acceptable
407 Proxy Authentication Required
408 Request Time-out
409 Conflict
410 Gone
411 Length Required
412 Precondition Failed
413 Request Entity Too Large
414 Request-URI Too Large
415 Unsupported Media Type
416 Requested Range Not Satisfiable
417 Expectation Failed
418 unused
419 unused
420 unused
421 unused
422 Unprocessable Entity
423 Locked
424 Failed Dependency
425 No code
426 Upgrade Required
500 Internal Server Error
501 Method Not Implemented
502 Bad Gateway
503 Service Temporarily Unavailable
504 Gateway Time-out
505 HTTP Version Not Supported
506 Variant Also Negotiates
507 Insufficient Storage
508 unused
509 unused
510 Not Extended

Source: HTTP Status Codes

Measure script execution time in stages

We can use milestones in a script to track how certain sections of code are performing. The best way to achieve this is a simple function with some static variable inside. However, needs can quickly get complicated, so I built a simple static class to handle everything. Include this class in your application:

class ScriptTimer {
  static $milestones;
  function microtime_float() {
    list($utime, $time) = explode(" ", microtime());
    return ((float)$utime + (float)$time);
  function timing_milestone($name) {
    self::$milestones[] = array($name, self::microtime_float());
  function dump_profile($return = false) {
    self::$milestones[] = array('finish', self::microtime_float());
    $output = '<table border="1">'.
    foreach (self::$milestones as $elem => $data) {
      $output .= '<tr><td>'.$data[0].'</td>'.
        '<td>'.round(($elem ? $data[1] - self::$milestones[$elem - 1][1]: '0'), 5).'</td>'.
        '<td>'.round(($data[1] - self::$milestones[0][1]), 5).'</td></tr>';
    $output .= '</table>';
    if ($return) return $output;
    echo $output;
I have a wordpress blog installed in root (htdocs). Wp has kindly modified the .htaccess file to include
# BEGIN WordPress
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]

# END WordPress

ErrorDocument 404 /index.php?error=404

The simple question is, can someone please explain exactly what that code does?

RewriteBase /

Says that all the rewriting will start from the directory the .htaccess file is located in

RewriteCond %{REQUEST_FILENAME} !-f

Continues to next rewritecond if the requested file does not exist

RewriteCond %{REQUEST_FILENAME} !-d

Continues to rewriterule if the requested file is not an existing directory

RewriteRule . /index.php [L]

Rewrites any request with 1 or more characters to /index.php, which launches wordpress and handles all redirections and what to display

If you want the mydomain2 to be handled differently, create an .htaccess file in the mydomain2 sub-directory with its own errordocument. ie.

ErrorDocument 404 /mydomain2errors.php

Or, alternatively, you can turn off the wordpress htaccess rewriting for that subdirectory.

# BEGIN WordPress <IfModule mod_rewrite.c> RewriteEngine On RewriteBase / RewriteCond %{REQUEST_URI} !^/mydomain2subdirectory.*$ RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule . /index.php [L] </IfModule> # END WordPress

url rewriting using .htaccess to rewrite the url some day we’ll rewrite links to work without query strings like on askapache..

Rewriting dynamic.php?id=12 to dynamic-12.html

Redirection in which .php extension is hidden from the useragent’s address bar and dynamic url.
code>RewriteEngine on
RewriteRule ^dynamic-([0-9]+)\.html$ dynamic.php?id=$1

Rewriting dynamic.php?id=7 to dynamic/indexes-access/7.html

Alwaysdisplay the main keyword in the URL. In the following URL rewriting technique you can display the name of the dynamic in URL.

RewriteEngine on
RewriteRule ^dynamic/([a-zA-Z0-9_-]+)/([0-9]+)\.html$ dynamic.php?id=$2

Redirecting non www URL to www URL

If you type in useragent it will be redirected to If you want to do same with your website then put the following code to .htaccess file.

What is benefit of this kind of redirection?? Please check the post about SEO friendly redirect (301) redirect in php and .htaccess.

RewriteEngine On
RewriteCond %{HTTP_HOST} ^htaccessrewrite\.com$
RewriteRule (.*)$1 [R=301,L]

Redirecting the domain to a new subfolder of inside public_html.

Now you can point both domains to /www/ directory as your DOC_ROOT.

RewriteEngine On
RewriteCond %{HTTP_HOST} ^rewrite\.com$ [OR]
RewriteCond %{HTTP_HOST} ^www\.rewrite\.com$
RewriteCond %{REQUEST_URI} !^/www/
RewriteRule (.*) /www/$1

Normally, on a Unix server with the Microsoft FrontPage Server extensions installed WordPress works just fine and you are able to edit and publish pages (with Microsoft FrontPage) — until — you make a change to the permalinks (for example to the date based kind that I like /2005/04/etc). I often suggest that type of URI to folks asking about permalinks etc, as that is the method recommended by the w3c (see ).

Now, the problem is that FrontPage uses the .htaccess file (which the WordPress mod_rewrite rules must access) for its “publishing” and “web authoring” configuration. As soon as the WordPress mod_rewrite code is added to the file, two things happen — the permalinks don’t work and the Frontpage Server extensions become corrupt.

I have tried countless ways to get around this, including trying to use rewrite rules that “ignore” the %{HTTP_USERAGENT)% used by FrontPage, to using a second AccessFilename .wpaccess to the httpd.conf file, and a host of other things, and nothing worked to allow use of FrontPage and management and use of permalinks in WordPress at the same time.

The solution is actually simple, and I figured it out by accident.

If you are using, or wish to use FrontPage (or if your hosting package is pre-configured that way) along with WordPress, you’ll need to take the following simple steps on your server or have your hosting company do them for you.

Microsoft FrontPage creates the following directory


Nested within that it creates both




In addition to in your site (or WordPress) root folder in all of those directories you will find additional .htaccess files.

In all three of these directories AND in the root directory, at the top of ALL of the .htaccess files you simply need to add one line:

Options +FollowSymlinks

There may or may not already be a line in each like

Options None

Edit and save each .htaccess file and you’re done. Now everything works perfectly, including FrontPage, AND the permalinks of your choosing.

Welcome to This is your first post. Edit or delete it and start blogging!


Get every new post delivered to your Inbox.