My Approach to Apache Virtual Hosts in OS X

The development workflow
If I was developing a site locally on my Mac for a site called http://www.cooldomain.com/ I’d develop it under the domain dev.cooldomain.com that I’m hosting locally on my OS X powered Mac. This way I know, whenever I type dev. before the domain name it’s the local copy and when I have www. before the domain name it’s the live site.

Setting up vhosts
First I create a folder in my home directory called webserver this is where I keep all of my locally hosted sites. For a site called www.cooldomain.com I create a folder within the webserver folder called cooldomain. I then create 2 folders inside that folder first logs (for log files) and then public_html. Your site will be served from the public_html folder.

how the webserver fodler structure looks

For the sake of consistency I’m going to pick a single OSX GUI text editor for this tutorial. TextWrangler is free, installs a handy command line tool (edit) and it works well so we’ll go with it. (Feel free to use emacs, vi, pico, TextMate, SubEthaEdit or any editor that supports plain text editing.)

First we’ll refresh the list of binaries (since we may have just installed the TextWrangler Command Line Tool). Fire up the terminal and type:

rehash

Next, we’ll change to the hosts file (/etc) directory and make a backup copy of the hosts file

cd /etc/

sudo cp hosts hosts.backup

Now, we’ll edit the file as a root user in TextWrangler

sudo edit hosts

Once the hosts file is open in TextWrangler, scroll down to the end and add two lines

# lookupd -flushcache
127.0.0.1   dev.cooldomain.com

The first line is merely a coment that will remind us to flush the lookupd cache whenever we edit the hosts file. The second line tells the machine to send all requests for dev.cooldomain.com to this machine and not out to the ‘net.

Save the file after you’ve added these lines and switch back to the terminal and type:

lookupd -flushcache

Now, we’re gonna edit the httpd.conf file. First change to the httpd.conf directory and make a backup copy of the httpd.conf file

cd /etc/httpd/

sudo cp httpd.conf httpd.conf.backup

Now, we’ll edit the file as a root user in TextWrangler

sudo edit httpd.conf

Once the file is open in TextWrangler, do a find (cmd-f) for NameVirtualHost and be sure the following line is not commented out (with a # in front of it) if it is remove the #:

NameVirtualHost *:80

Next set up your vhost configuration at the bottom of the document. You can copy and paste the following code remembering to change yourusername with your actual username and cooldomain with the name of the folder you created in the webserver folder earlier.

<VirtualHost *:80>
    ServerAdmin youradminaddress@email.com
    ServerName dev.cooldomain.com
    DocumentRoot /Users/yourusername/webserver/cooldomain/public_html
    ErrorLog /Users/yourusername/webserver/cooldomain/logs/dev.cooldomain.com-error_log.log
    CustomLog /Users/yourusername/webserver/cooldomain/logs/dev.cooldomain.com-access_log.log common
       <Directory /Users/yourusername/webserver/cooldomain/public_html>
         Options Indexes ExecCGI FollowSymLinks MultiViews
         AddHandler cgi-script .cgi
         AllowOverride all
         Order allow,deny
         Allow from all
       </Directory>
</VirtualHost>

Once you’re done modifying the httpd.conf file, save it return to the terminal to check your changes.

running

apachectl configtest

will tell you if there are any errors in your httpd.conf file. If you’ve got errors, go back to the httpd.conf file and check everything you changed or added.

If you get

Syntax OK

You’re ready to restart apache. Restarting apache can be done from the command line via

sudo apachectl restart or sudo apachectl graceful

or via the sharing preferences pane (clicking stop and then start will effectively restart apache).

That’s it. Just put your site inside the public_html you created earlier, fire up a web browser and type in the domain name (dev.cooldomain.com in this example). Apache should serve it up with no hassles at all.

This is just one approach to vhosting under OS X that happens to work for me. Here are references to two others:
Enabling Virtual Hosts on MacOS X (evolt.org)
Virtual Hosting on Mac OS X (patrickgibson.com)

2 Responses to “My Approach to Apache Virtual Hosts in OS X”


  • Just stumbled across this article now (a little late) — this is exactly the way I do localhosting on OS X. FWIW, I like this method much better than the two others you referenced as it more closely reflects real-world usage.

  • Everything worked like you said except iI can’t access the page.
    It says Forbidden You don’t have pemission to access / on the server.

Leave a Reply




![how the webserver fodler structure looks](http://jumpserve.com/blanco/images/webserver-vhosts-osx.jpg "Webserver folder structure") For the sake of consistency I'm going to pick a single OSX GUI text editor for this tutorial. [TextWrangler](http://barebones.com/products/textwrangler/) is free, installs a handy command line tool (edit) and it works well so we'll go with it. (Feel free to use emacs, vi, pico, TextMate, SubEthaEdit or any editor that supports plain text editing.) First we'll refresh the list of binaries (since we may have just installed the TextWrangler Command Line Tool). Fire up the terminal and type: rehash Next, we'll change to the hosts file (/etc) directory and make a backup copy of the hosts file cd /etc/ sudo cp hosts hosts.backup Now, we'll edit the file as a root user in TextWrangler sudo edit hosts Once the hosts file is open in TextWrangler, scroll down to the end and add two lines # lookupd -flushcache 127.0.0.1 dev.cooldomain.com The first line is merely a coment that will remind us to flush the lookupd cache whenever we edit the hosts file. The second line tells the machine to send all requests for dev.cooldomain.com to this machine and not out to the 'net. Save the file after you've added these lines and switch back to the terminal and type: lookupd -flushcache Now, we're gonna edit the httpd.conf file. First change to the httpd.conf directory and make a backup copy of the httpd.conf file cd /etc/httpd/ sudo cp httpd.conf httpd.conf.backup Now, we'll edit the file as a root user in TextWrangler sudo edit httpd.conf Once the file is open in TextWrangler, do a find (cmd-f) for NameVirtualHost and be sure the following line is not commented out (with a `#` in front of it) if it is remove the `#`: NameVirtualHost *:80 Next set up your vhost configuration at the bottom of the document. You can copy and paste the following code remembering to change `yourusername` with your actual username and `cooldomain` with the name of the folder you created in the webserver folder earlier. ServerAdmin youradminaddress@email.com ServerName dev.cooldomain.com DocumentRoot /Users/yourusername/webserver/cooldomain/public_html ErrorLog /Users/yourusername/webserver/cooldomain/logs/dev.cooldomain.com-error_log.log CustomLog /Users/yourusername/webserver/cooldomain/logs/dev.cooldomain.com-access_log.log common Options Indexes ExecCGI FollowSymLinks MultiViews AddHandler cgi-script .cgi AllowOverride all Order allow,deny Allow from all Once you're done modifying the httpd.conf file, save it return to the terminal to check your changes. running apachectl configtest will tell you if there are any errors in your httpd.conf file. If you've got errors, go back to the httpd.conf file and check everything you changed or added. If you get Syntax OK You're ready to restart apache. Restarting apache can be done from the command line via `sudo apachectl restart` or `sudo apachectl graceful` or via the sharing preferences pane (clicking stop and then start will effectively restart apache). That's it. Just put your site inside the _public\_html_ you created earlier, fire up a web browser and type in the domain name (dev.cooldomain.com in this example). Apache should serve it up with no hassles at all. This is just one approach to vhosting under OS X that happens to work for me. Here are references to two others: [Enabling Virtual Hosts on MacOS X (evolt.org)](http://www.evolt.org/MacOSX_vhosts/) [Virtual Hosting on Mac OS X (patrickgibson.com)](http://www.patrickgibson.com/news/andsuch/000091.php) [post_title] => My Approach to Apache Virtual Hosts in OS X [post_category] => 0 [post_excerpt] => [post_lat] => [post_lon] => [post_status] => publish [comment_status] => open [ping_status] => open [post_password] => [post_name] => apache-vhosts-osx [to_ping] => [pinged] => [post_modified] => 2005-12-29 00:59:55 [post_modified_gmt] => 2005-12-29 05:59:55 [post_content_filtered] => [post_parent] => 0 [guid] => http://jumpserve.com/blanco/?p=620 [menu_order] => 0 [post_type] => post [post_mime_type] => [comment_count] => 3 [ancestors] => Array ( ) ) [comments] => Array ( [0] => stdClass Object ( [comment_ID] => 246 [comment_post_ID] => 620 [comment_author] => Packagethief [comment_author_email] => packagethief@gmail.com [comment_author_url] => http://quotedprintable.com [comment_author_IP] => 24.150.169.65 [comment_date] => 2005-07-13 19:15:15 [comment_date_gmt] => 2005-07-14 00:15:15 [comment_content] => Just stumbled across this article now (a little late) -- this is *exactly* the way I do localhosting on OS X. FWIW, I like this method much better than the two others you referenced as it more closely reflects real-world usage. [comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Mozilla/5.0 (Macintosh; U; PPC Mac OS X; en) AppleWebKit/412.6 (KHTML, like Gecko) Safari/412.2 [comment_type] => [comment_parent] => 0 ) [1] => stdClass Object ( [comment_ID] => 247 [comment_post_ID] => 620 [comment_author] => Adam [comment_author_email] => Mr.Gadget@sbcglobal.net [comment_author_url] => [comment_author_IP] => 67.126.213.70 [comment_date] => 2005-07-25 06:15:44 [comment_date_gmt] => 2005-07-25 11:15:44 [comment_content] => Everything worked like you said except iI can't access the page. It says Forbidden You don't have pemission to access / on the server. [comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.7.8) Gecko/20050511 Firefox/1.0.4 [comment_type] => [comment_parent] => 0 ) [2] => stdClass Object ( [comment_ID] => 380 [comment_post_ID] => 620 [comment_author] => transient : It’s my data [comment_author_email] => [comment_author_url] => http://log.phile.eu/all/2006/its-my-data/ [comment_author_IP] => 207.7.108.37 [comment_date] => 2006-04-15 15:33:13 [comment_date_gmt] => 2006-04-15 20:33:13 [comment_content] =>

[...] Following elements on this page, in OS X using Terminal: [...]

[comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Incutio XML-RPC -- WordPress/2.0.2 [comment_type] => pingback [comment_parent] => 0 ) ) [comment_count] => 3 [current_comment] => -1 [comment] => [found_posts] => 0 [max_num_pages] => 0 [max_num_comment_pages] => 1 [is_single] => 1 [is_preview] => [is_page] => [is_archive] => [is_date] => [is_year] => [is_month] => [is_day] => [is_time] => [is_author] => [is_category] => [is_tag] => [is_tax] => [is_search] => [is_feed] => [is_comment_feed] => [is_trackback] => [is_home] => [is_404] => [is_comments_popup] => [is_admin] => [is_attachment] => [is_singular] => 1 [is_robots] => [is_posts_page] => [is_paged] => [query] => Array ( [year] => 2005 [monthnum] => 05 [day] => 27 [name] => apache-vhosts-osx ) [posts] => Array ( [0] => stdClass Object ( [ID] => 620 [post_author] => 2 [post_date] => 2005-05-27 20:43:57 [post_date_gmt] => 2005-05-28 01:43:57 [post_content] => **The development workflow** If I was developing a site locally on my Mac for a site called http://www.cooldomain.com/ I'd develop it under the domain dev.cooldomain.com that I'm hosting locally on my OS X powered Mac. This way I know, whenever I type dev. before the domain name it's the local copy and when I have www. before the domain name it's the live site. **Setting up vhosts** First I create a folder in my home directory called _webserver_ this is where I keep all of my locally hosted sites. For a site called www.cooldomain.com I create a folder within the _webserver_ folder called _cooldomain_. I then create 2 folders inside that folder first _logs_ (for log files) and then _public\_html_. Your site will be served from the _public\_html_ folder. ![how the webserver fodler structure looks](http://jumpserve.com/blanco/images/webserver-vhosts-osx.jpg "Webserver folder structure") For the sake of consistency I'm going to pick a single OSX GUI text editor for this tutorial. [TextWrangler](http://barebones.com/products/textwrangler/) is free, installs a handy command line tool (edit) and it works well so we'll go with it. (Feel free to use emacs, vi, pico, TextMate, SubEthaEdit or any editor that supports plain text editing.) First we'll refresh the list of binaries (since we may have just installed the TextWrangler Command Line Tool). Fire up the terminal and type: rehash Next, we'll change to the hosts file (/etc) directory and make a backup copy of the hosts file cd /etc/ sudo cp hosts hosts.backup Now, we'll edit the file as a root user in TextWrangler sudo edit hosts Once the hosts file is open in TextWrangler, scroll down to the end and add two lines # lookupd -flushcache 127.0.0.1 dev.cooldomain.com The first line is merely a coment that will remind us to flush the lookupd cache whenever we edit the hosts file. The second line tells the machine to send all requests for dev.cooldomain.com to this machine and not out to the 'net. Save the file after you've added these lines and switch back to the terminal and type: lookupd -flushcache Now, we're gonna edit the httpd.conf file. First change to the httpd.conf directory and make a backup copy of the httpd.conf file cd /etc/httpd/ sudo cp httpd.conf httpd.conf.backup Now, we'll edit the file as a root user in TextWrangler sudo edit httpd.conf Once the file is open in TextWrangler, do a find (cmd-f) for NameVirtualHost and be sure the following line is not commented out (with a `#` in front of it) if it is remove the `#`: NameVirtualHost *:80 Next set up your vhost configuration at the bottom of the document. You can copy and paste the following code remembering to change `yourusername` with your actual username and `cooldomain` with the name of the folder you created in the webserver folder earlier. ServerAdmin youradminaddress@email.com ServerName dev.cooldomain.com DocumentRoot /Users/yourusername/webserver/cooldomain/public_html ErrorLog /Users/yourusername/webserver/cooldomain/logs/dev.cooldomain.com-error_log.log CustomLog /Users/yourusername/webserver/cooldomain/logs/dev.cooldomain.com-access_log.log common Options Indexes ExecCGI FollowSymLinks MultiViews AddHandler cgi-script .cgi AllowOverride all Order allow,deny Allow from all Once you're done modifying the httpd.conf file, save it return to the terminal to check your changes. running apachectl configtest will tell you if there are any errors in your httpd.conf file. If you've got errors, go back to the httpd.conf file and check everything you changed or added. If you get Syntax OK You're ready to restart apache. Restarting apache can be done from the command line via `sudo apachectl restart` or `sudo apachectl graceful` or via the sharing preferences pane (clicking stop and then start will effectively restart apache). That's it. Just put your site inside the _public\_html_ you created earlier, fire up a web browser and type in the domain name (dev.cooldomain.com in this example). Apache should serve it up with no hassles at all. This is just one approach to vhosting under OS X that happens to work for me. Here are references to two others: [Enabling Virtual Hosts on MacOS X (evolt.org)](http://www.evolt.org/MacOSX_vhosts/) [Virtual Hosting on Mac OS X (patrickgibson.com)](http://www.patrickgibson.com/news/andsuch/000091.php) [post_title] => My Approach to Apache Virtual Hosts in OS X [post_category] => 0 [post_excerpt] => [post_lat] => [post_lon] => [post_status] => publish [comment_status] => open [ping_status] => open [post_password] => [post_name] => apache-vhosts-osx [to_ping] => [pinged] => [post_modified] => 2005-12-29 00:59:55 [post_modified_gmt] => 2005-12-29 05:59:55 [post_content_filtered] => [post_parent] => 0 [guid] => http://jumpserve.com/blanco/?p=620 [menu_order] => 0 [post_type] => post [post_mime_type] => [comment_count] => 3 [ancestors] => Array ( ) ) ) [comments_by_type] => Array ( [comment] => Array ( [0] => stdClass Object ( [comment_ID] => 246 [comment_post_ID] => 620 [comment_author] => Packagethief [comment_author_email] => packagethief@gmail.com [comment_author_url] => http://quotedprintable.com [comment_author_IP] => 24.150.169.65 [comment_date] => 2005-07-13 19:15:15 [comment_date_gmt] => 2005-07-14 00:15:15 [comment_content] => Just stumbled across this article now (a little late) -- this is *exactly* the way I do localhosting on OS X. FWIW, I like this method much better than the two others you referenced as it more closely reflects real-world usage. [comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Mozilla/5.0 (Macintosh; U; PPC Mac OS X; en) AppleWebKit/412.6 (KHTML, like Gecko) Safari/412.2 [comment_type] => [comment_parent] => 0 ) [1] => stdClass Object ( [comment_ID] => 247 [comment_post_ID] => 620 [comment_author] => Adam [comment_author_email] => Mr.Gadget@sbcglobal.net [comment_author_url] => [comment_author_IP] => 67.126.213.70 [comment_date] => 2005-07-25 06:15:44 [comment_date_gmt] => 2005-07-25 11:15:44 [comment_content] => Everything worked like you said except iI can't access the page. It says Forbidden You don't have pemission to access / on the server. [comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.7.8) Gecko/20050511 Firefox/1.0.4 [comment_type] => [comment_parent] => 0 ) ) [trackback] => Array ( ) [pingback] => Array ( [0] => stdClass Object ( [comment_ID] => 380 [comment_post_ID] => 620 [comment_author] => transient : It’s my data [comment_author_email] => [comment_author_url] => http://log.phile.eu/all/2006/its-my-data/ [comment_author_IP] => 207.7.108.37 [comment_date] => 2006-04-15 15:33:13 [comment_date_gmt] => 2006-04-15 20:33:13 [comment_content] =>

[...] Following elements on this page, in OS X using Terminal: [...]

[comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Incutio XML-RPC -- WordPress/2.0.2 [comment_type] => pingback [comment_parent] => 0 ) ) [pings] => Array ( [0] => stdClass Object ( [comment_ID] => 380 [comment_post_ID] => 620 [comment_author] => transient : It’s my data [comment_author_email] => [comment_author_url] => http://log.phile.eu/all/2006/its-my-data/ [comment_author_IP] => 207.7.108.37 [comment_date] => 2006-04-15 15:33:13 [comment_date_gmt] => 2006-04-15 20:33:13 [comment_content] =>

[...] Following elements on this page, in OS X using Terminal: [...]

[comment_karma] => 0 [comment_approved] => 1 [user_id] => 0 [comment_agent] => Incutio XML-RPC -- WordPress/2.0.2 [comment_type] => pingback [comment_parent] => 0 ) ) ) )

SERVER

Array
(
    [REDIRECT_STATUS] => 200
    [HTTP_HOST] => jumpserve.com
    [HTTP_USER_AGENT] => CCBot/1.0 (+http://www.commoncrawl.org/bot.html)
    [HTTP_ACCEPT] => Accept: application/xhtml+xml,text/html;q=0.9,text/plain;
    [HTTP_ACCEPT_LANGUAGE] => en-us,en;q=0.5
    [HTTP_ACCEPT_ENCODING] => gzip
    [HTTP_ACCEPT_CHARSET] => ISO-8859-1,utf-8;q=0.7,*;q=0.7
    [HTTP_CONNECTION] => close
    [HTTP_CACHE_CONTROL] => no-cache
    [HTTP_PRAGMA] => no-cache
    [PATH] => /bin:/usr/bin:/sbin:/usr/sbin
    [SERVER_SIGNATURE] => 
    [SERVER_SOFTWARE] => Apache
    [SERVER_NAME] => jumpserve.com
    [SERVER_ADDR] => 207.7.108.21
    [SERVER_PORT] => 80
    [REMOTE_ADDR] => 38.103.63.61
    [DOCUMENT_ROOT] => /users/home/blanco/domains/jumpserve.com/public_html
    [SERVER_ADMIN] => web@one.textdrive.com
    [SCRIPT_FILENAME] => /users/home/blanco/domains/jumpserve.com/public_html/blanco/index.php
    [REMOTE_PORT] => 43151
    [REDIRECT_URL] => /blanco/archives/2005/05/27/apache-vhosts-osx/
    [GATEWAY_INTERFACE] => CGI/1.1
    [SERVER_PROTOCOL] => HTTP/1.1
    [REQUEST_METHOD] => GET
    [QUERY_STRING] => 
    [REQUEST_URI] => /blanco/archives/2005/05/27/apache-vhosts-osx/
    [SCRIPT_NAME] => /blanco/index.php
    [PHP_SELF] => /blanco/index.php
    [REQUEST_TIME] => 1231449340
)

REQUEST

Array
(
)
-->