Serve local web pages via name not IP number

29.11.2008
Today's hint is about OS X 10.5's built-in Web server, and how you can make it easy to access sites you're running off that server. In case you weren't aware, the built-in OS X web server is the industry-standard web server that powers literally thousands of web sites around the world. As of OS X 10.5.5, it's Apache version 2.2.9.

So what can you do with OS X's built-in Web server? Almost anything, though the one thing you probably can't do is use it to serve web pages to the outside world, at least not easily. Many ISPs don't allow web servers to run on a standard home account, and even if they do, your firewall and/or router may make it difficult for users to reach your site. If you get around those problems, you'll still need to arrange for a domain name to point to your home machine--and again, your ISP may make that difficult. You can solve some of these issues by using a service such as , which lets you assign a domain name to an ever-changing home IP address. You'll still have issues if your ISP won't allow you to host sites, however.

So if you can't serve sites to the outside world, why then might you want to run a web server anyway? Perhaps, like me, your job requires you to maintain a web site, and you'd like to keep a copy of it locally for testing. Or perhaps you'd like to try out some of the popular blogging web applications (, ) or some of the available (, for instance, which powers ) on your own Mac before you decide to launch a site with a web hosting company. (As an aside, this is exactly how macosxhints.com got started--I installed Geeklog locally and ran it on my own Mac for a couple of months before I launched the site to the public. In many ways, the built-in OS X web server is the one piece of technology most responsible for my launching macosxhints.)

Whatever the reason, OS X makes it super easy to run a web server on your very own Mac. You can enable the built-in web server by clicking the Web Sharing button in the Sharing System Preferences panel. Once enabled, you'll see a couple of links in the area to the right of all the sharing options; one lists your computer's web site URL, and the other lists the URL for your personal site. For most users, these addresses will appear as a series of (IP address) numbers--in my case, they're listed as http://192.168.1.44 and http://192.168.1.44/~robg, respectively. If I open Safari or any other web browser and enter those URLs, I'll see the standard pages as shown in the image at right--that's the computer page at the top, and my personal page at the bottom.

While this works well enough, wouldn't it be nicer to access your locally-hosted sites via domain name, just like you do on the "real" Internet? With a couple of relatively easy edits in the Terminal, you can do just that. Apache includes support for what they call name-based virtual hosts, and by enabling those, you can name your server and its hosted sites anything you like. Here's what you need to do.

These instructions assume that you'll be installing your sites in your user's Sites folder, and that you'll place each different package you want to use (WordPress, Movable Type, etc.) in its own sub-directory, which is a pretty standard practice. They also assume you're using 10.5; this method will not work in 10.4, as it doesn't use Apache 2. It also assumes that you don't need to access any sites stored in the standard /Library -> WebServer -> Documents folder--I do have a relatively simple fix for that problem near the end of this hint, though.

Name your server

The first thing you need to do is come up with the name you'd like to use for your server--keep it short and simple, and restrict it to one word without any punctuation. The whole idea is to make it easy to type. For this example, I'm assuming the server will be called mysites, which would let you type http://mysites into your browser's URL bar.

Once you've come up with a name for your server, you need to tell OS X to look for that name locally before it tries to find it on the Internet. To do this, we'll make a simple change in the /etc/hosts file. My instructions assume you'll be using a Terminal-based text editor, such as vi or nano, but programs wuch as BBEdit and that offer a command-line interface could also be used--really, any text editor that lets you edit with root account privileges would do the trick.

Edit the hosts file in Terminal by typing sudo nano /etc/hosts, and then enter your password when prompted. The nano editor will open, displaying something like this:

Add a row just above the 255.255... line by pressing Return with the cursor at the start of that line, then use the arrow keys to move up, and add this entry:

Replace mysites with whatever name you've chosen for your server, and then save the file and quit the editor (press Control-X to exit, Y to save your changes, and then Return to accept the filename if you're using nano).

Set up Apache

Now that you've named your server, you need to tell Apache how to convert mysites into the IP address of your Mac, so that it can display your web pages. The file you need to modify can be found in /etc/apache2/users, so cd there as a first step: cd /etc/apache2/users. In this folder, you'll find a ".conf" file for each user on your Mac. You want to edit the file for your user, again with root privileges; type sudo nano username.conf (where username is your short username) and enter your password when prompted. Move the cursor to the bottom of the file, and add these lines:

Replace username with your user's short username, and change mysites to the server name you used when editing the hosts file. Save the file and quit the editor.

If you also need access to sites in the standard /Library -> WebServer -> Documents folder, you need to edit one additional file. First, move into the right directory with cd /etc/apache2/extra, and then edit the httpd-vhosts.conf file (again, using sudo). Add these lines at the end:

Save the file, and you'll be able to access those sites by typing http://localhost in the URL address bar, while using your named server will show pages in your user's Sites folder.

Try it out

Those are the only required edits. To make your changes take effect, however, there are two things you need to do. First, as Leopard caches DNS queries, we need to clear the cache to make it read our hosts file again. In Terminal, enter this command then press Return: dscacheutil -flushcache. The other thing you need to do is restart the Apache web server. You can do this in the Sharing System Preferences panel by toggling the Web Sharing off and back on, or in Terminal, you can use this command: sudo apachectl graceful.

Once Apache restarts, test your new named server by opening your favorite browser and typing your server name in the URL bar: http://mysites. If you haven't replaced the default page in your user's Sites folder yet, that's what you should see when the page loads. Now, as you install various web packages into sub-folders, you can access them as http://mysites/wordpress or http://mysites/geeklog, etc. (If you prefer, you could even name your sub-folders as completely separate sites--just duplicate the above changes to the hosts and .conf files, but with your new server name and path directly to a sub-folder.)

If you have other Macs in your home that you'd like to use to access your served pages, you can do that easily, too. Just edit the hosts file on the other Mac as above, but instead of using 127.0.0.1 as the server address, use the IP address of the Mac running the web server (which you can easily find in the Web Sharing System Preferences panel). Remember to clear the cache after editing the file, and you can then access the host Mac's served pages using the defined server name.

I hope the above is clear and easy to follow--I've tested it on two different Macs here, and it works as described. If you have any troubles getting it working, however, please post a question and I'll do my best to answer it. Remember that this hint is for internally-hosted sites only, and it doesn't do anything about providing access for users outside your local network.