On site.twocopy (see Section 3.9, "Two Copies of Apache", later in this chapter) we run two different versions of Apache, each serving a different URL. It would be rather unusual to do this in real life. It is more common to run a number of virtual Apaches that steer incoming requests on different URLs -- usually with the same IP address -- to different sets of documents. These might well be home pages for members of your organization or your clients.
In the first edition of this book we showed how to do this for Apache 1.2 and HTTP/1.0. The result was rather clumsy, with a main host and a virtual host, but it coped with HTTP/1.0 clients. However, the setup can now be done much more neatly with the NameVirtualHost directive. The possible combinations of IP-based and name-based hosts can become quite complex. A full explanation with examples and the underlying theology can be found at http://www.apache.org/docs/vhosts but it has to be said that several of the possible permutations are unlikely to be very useful in practice.
This is by far the preferred method of managing virtual hosts, taking advantage of the ability of HTTP/1.1-compliant browsers to send the name of the site they want to access. At .../site.virtual/Name-based we have www.butterthlies.com and sales. butterthlies.com on 192.168.123.2. Of course, these sites must be registered on the Web (or if you are dummying the setup as we did, included in /etc/hosts). The Config file is as follows:
User webuser Group webgroup NameVirtualHost 192.168.123.2 <VirtualHost www.butterthlies.com> ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/customers ServerName www.butterthlies.com ErrorLog /usr/www/site.virtual/name-based/logs/error_log TransferLog /usr/www/site.virtual/name-based/logs/access_log </VirtualHost> <VirtualHost sales.butterthlies.com> ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/salesmen ServerName sales.butterthlies.com ErrorLog /usr/www/site.virtual/name-based/logs/error_log TransferLog /usr/www/site.virtual/name-based/logs/access_log </VirtualHost>
The key directive is NameVirtualHost , which tells Apache that requests to that IP number will be subdivided by name. It might seem that the ServerName directives play a crucial part, but they just provide a name for Apache to return to the client. The <VirtualHost> sections now are identified by the name of the site we want them to serve. If this directive were left out, Apache would issue a helpful warning that www.butterthlies.com and sales.butterthlies.com were overlapping (i.e., rival interpretations of the same IP number) and that perhaps we needed a NameVirtualHost directive. Which indeed we would.
The virtual sites can all share log files, as shown in the given Config file, or they can use separate ones.
NameVirtualHost address[:port] Server config
NameVirtualHost allows you to specify the IP addresses of your name-based virtual hosts. Optionally, you can add a port number. The IP address has to match with the IP address at the top of a <VirtualHost> block, which must include a ServerName directive followed by the registered name. The effect is that when Apache receives a request addressed to a named host, it scans the <VirtualHost> blocks having the same IP number that was declared with a NameVirtualHost directive to find one that includes the requested ServerName. Conversely, if you have not used NameVirtualHost, Apache looks for a <VirtualHost> block with the correct IP address and uses the ServerName in the reply. One use of this is to prevent people from getting to hosts blocked by the firewall by using the IP of an open host and the name of a blocked one.
In the authors' experience, most of the Web still uses IP-based hosting, because although almost all clients use browsers that support HTTP/1.1, there is still a tiny proportion that doesn't, and who wants to lose business unnecessarily? However, the Web is running out of numbers, and sooner or later, people will have to move to name-based hosting.
This is how to configure Apache to do IP-based virtual hosting. The Config file is:
User webuser Group webgroup <VirtualHost 192.168.123.2> ServerName www.butterthlies.com ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/customers ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost> <VirtualHost 192.168.123.3> ServerName sales.butterthlies-IP.com ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/salesmen ServerName sales.butterthlies.com ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost>
This responds nicely to requests to http://www.butterthlies.com and http://sales-IP.butterthlies.com. The way our machine was set up, it also served up the customers' page to a request on http://www.sales.com -- which is to be expected since they share a common IP number.
You can, of course, mix the two techniques. <VirtualHost> blocks that have been NameVirtualHost'ed will respond to requests to named servers; others will respond to requests to the appropriate IP numbers:
User webuser Group webgroup NameVirtualHost 192.168.123.2 <VirtualHost www.butterthlies.com> ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/customers ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost> <VirtualHost sales.butterthlies.com> ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/salesmen ServerName sales.butterthlies.com ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost> <VirtualHost 192.168.123.3> ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/salesmen ServerName sales.butterthlies.com ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost>
The two named sites are dealt with by the NameVirtualHost directive, whereas requests to sales-IP.butterthlies.com, which we have set up to be 192.168.123.3, are dealt with by the third <VirtualHost> block.
Port-based virtual hosting follows on from IP-based hosting. The main advantage of this technique is that it makes it possible for a webmaster to test a lot of sites using only one IP address/hostname, or, in a pinch, host a large number of sites without using name-based hosts and without using lots of IP numbers. Unfortunately, most people don't like their web server having a funny port number.
User webuser Group webgroup Listen 80 Listen 8080 <VirtualHost 192.168.123.2:80> ServerName www.butterthlies.com ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/customers ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost> <VirtualHost 192.168.123.2:8080> ServerName sales-IP.butterthlies.com ServerAdmin sales@butterthlies.com DocumentRoot /usr/www/site.virtual/htdocs/salesmen ServerName sales.butterthlies.com ErrorLog /usr/www/site.virtual/IP-based/logs/error_log TransferLog /usr/www/site.virtual/IP-based/logs/access_log </VirtualHost>
The Listen directives tell Apache to watch ports 80 and 8080. If you set Apache going and access http://www.butterthlies.com, you arrive on port 80, the default, and see the customers' site; if you access http://www.butterthlies.com:8080, you get the salespeople's site.
Copyright © 2001 O'Reilly & Associates. All rights reserved.