Developing ExpressionEngine sites with MAMP, Git (Tower) and Beanstalk [Part 1]

There's been a few articles written in the past about developing and deploying ExpressionEngine (EE) sites with Git, most notably a three-part series by Stephen Lewis, Ryan Masuga's Version Control for ExpressionEngine Using Git Part 1 and Let's Git It On which was his presentation to EECI2010, and a couple of articles covering deploying with Git and Capistrano by George Ornbo and Dan Benjamin. Paul Burton also has a good round-up of Git resources for designers on his site.

Octodex, the Git mascot

I read all of those articles when they were first published but to be honest, a lot of it went straight over my head. Although I know how to use it, I'm no command line warrior, and with such a heavy emphasis on terminal and Git commands that I was unfamiliar with, I was struggling to see the advantages of using Git in my workflow. I could see the benefits of using it for version control locally, and in fact started out using it just for that several months before finally getting around to realising more of its potential.

Part of the reason it took me so long to properly get into Git was that I found it hard to find resources that explained the full advantages of using it that suited my own particular workflow, and whose language was aimed more at designers than developers. What follows is probably going to be pretty entry-level stuff for most developers, but I'm writing this in the hope that I might answer some questions that people in similar situations to me might have, and outline some of Git's benefits. But I'm by no means an expert on this subject having only been working with Git on my projects for a few months, so if I've got anything wrong or anyone has suggestions for ways of doing things better, please let me know in the comments.

How I work

I guess for people to be able to determine whether the explanations that follow will be relevant to them, it's necessary to explain a little bit about how I work. I do most of my ExpressionEngine work on my own, i.e. not with other developers involved, so one of the selling points of Git, being able to easily share code and work on it simultaneously with other developers, doesn't really apply to me.

After using EE for a while, I'd also developed my own fairly streamlined system of doing things that had eliminated a lot of the repetition that is involved in setting up and installing EE from scratch every time you start a new project.

I had a base install set up with commonly-used add-ons, a config bootstrap file, a set of basic templates saved as files, and a database that had been set up with basic fieldgroups, channels and other miscellaneous settings already in place. So whenever I needed to start a new project, I could just copy all that over, create a new database, import a dump from the default install, copy my new project's HTML and CSS into the already created EE templates, and be up and running with the skeleton of a new site in just a few minutes. And to be honest, that part of the process hasn't changed that much since using Git.

Where the biggest change in the process occurred was in deploying to a remote server. Previously I would zip up the local installation, FTP it to the server and then extract it (exporting and importing the database is still pretty much the same process). Now that step is handled with Git and Beanstalk, and I'll talk a little bit more about that in Part 2. First I'll walk through my current workflow and some of the general setting up steps. Then I'll give a little bit more info about each step as I go, but basically, it looks something like this:

  1. Install MAMP
  2. Install Git
  3. Set up a virtual host
  4. Create a database
  5. Install ExpressionEngine
  6. Customise a base install of ExpressionEngine
  7. Export the database
  8. Create a local Git repository (repo) using Tower
  9. Clone this base EE repo when starting a new project
  10. Work on your project
  11. Create a Beanstalk account
  12. Create a remote Beanstalk repo
  13. Set up a remote database
  14. Set up a Beanstalk deployment environment and deploy your site
  15. Have a nice cup of tea and milk arrowroot biscuit

That might seem like a lot of steps, but 1-8 only have to be done once (although customising your base install will probably be an ongoing concern as you refine your site-building techniques and discover new add-ons), and you don't have to have a cup of tea when you're finished. ;) The description to follow is also spread across two articles which will hopefully make it easier to digest.

What follows is also fairly Mac-specific as far as software and installers goes. I'll try to mention Windows alternatives where I can, but you'll probably have to go looking for your own instructions as to how to use them.

So… sitting comfortably? OK, let's go.

1. Install MAMP

Mamp and Mamp Pro logos combined

MAMP is probably the most popular option for getting Apache, MySQL and PHP running on a Mac. If you're on Windows, I can recommend XAMPP (which is also available for Mac) which does essentially the same thing. MAMP comes in two flavours — MAMP and MAMP Pro. Until recently I was happy to just use the base version, but I'm now using the Pro version and I'll mention a couple of advantages it has for me in a bit.

Of course, you don't have to use MAMP. You could set up Apache, MySQL and PHP yourself. OS X comes with its own built-in Apache server, but configuring settings and working with virtual hosts is easier using MAMP.

Setting up is as simple as running the installer. All done? OK, let's move on.

2. Install Git

Just like setting up Apache et al, installing Git on a Mac is fairly easy too. Just use the Git OSX Installer. For Windows there's Msysgit. That installs Git, but there's a bit more setting up to do if you want your computer to be able to communicate with remote services like Github, Beanstalk, Codebase, Springloops etc. Github Help has it fairly well covered though. If you've never used Terminal before, this'll be the first time you'll need to bust it out.

Although this guide is going to be fairly heavily slanted towards GUI tools, Git was designed to be used with the Command Line and even though you might not use them very often, it's still worth taking a bit of time to learn the basic commands you need to work with Git (see the link to Paul Burton's site mentioned above for more resources).

3. Set up a virtual host

This is a no-brainer if you're using MAMP Pro as there's a Hosts tab for this very purpose in the application's interface. Prior to upgrading to the Pro version, I used to do this step manually by editing /private/etc/apache2/extra/httpd-vhosts.conf and /private/etc/hostsand then stopping and restarting Apache. I could've used something like VirtualHostX to automate the process, but it was a technique I'd carried over from my Windows days.


4. Create a database

If you're running MAMP, it will have also installed phpMyAdmin for you which you'd probably be familiar with as it's installed on most web servers. This is something I used to do (again going back to my Windows days) but these days I use Sequel Pro, which contrary to what its name suggests, is actually donation-ware. Either way, creating empty databases is going to be pretty much the same;  where Sequel Pro has the edge over phpMyAdmin is in working with databases after they've got data in them. Using phpMyAdmin, the browser still has to send requests to the server to retrieve information, even if that server is on your local machine, but with Sequel Pro, you're editing the database files directly so it's a lot faster and more user friendly.

5. Install ExpressionEngine

Well, we've done a lot of setting up so far, but now we're finally ready to install ExpressionEngine. Download the latest version and away you go. I'm guessing there aren't likely to be too many complete EE novices reading this, but if you are, please refer to the official guide for installation instructions. Once you've installed successfully and have logged in, we'll be ready for the next step.


6. Customise a base install of ExpressionEngine

Now we're getting into the fun stuff. This is where you set up your ExpressionEngine installation with the settings, channels, custom fields, statuses, categories, templates, and add-ons that you find you use on every single project. The idea here is to save you time having to repeat doing things every time you start a new project. If you find you're setting something up repeatedly every time you're setting up EE on a new site, then it should really be set up on your base install so that it's already in place for the next job.

With settings, there are some that are only stored in the database, like channel preferences, and some that can be controlled via config files in the system folder. I use my own customised version of NSM Config Bootstrap for a lot of non-channel related settings and this gets used on every project with just a few tweaks required for each new site. The config bootstrap file also makes it very easy for your site to work in different environments, i.e. local, staging, production, without having to make changes for the different locations. This will be important later on when we start deploying the site using Git.

Because there are some settings that can only be stored in the database, however, these get set up with your base install. Things like whether to allow rich formatting buttons, or automatically turning URLs into links under a channel's preferences, or what add-ons are installed. Setting up your add-ons is an important part of this process. There are some add-ons, usually fieldtypes, which get used on every project, so it makes sense to have them on be default for every new project you start, rather than go through the process of enabling them again each time.

In terms of data, my base install doesn't contain too much because the content of a site is almost always going to be unique from site to site. But I do find that I like to use the same preferences for most channels and that nearly every site has a home page, an about page and a contact page. So my base install has a single channel set up the way I like it with entries for those three pages.


I also have a default set of templates stored in the database which I reuse on every project and which help me get up and running quickly. I use John D. Wells' template partials approach which means I have a single embed template which contains most of the markup and then much more stripped down page templates which mostly contain EE tags. The main embed template gets customised for each site, but it has a lot of stuff in it that is common each time and the basic structure of a single page template containing EE tags also is usually the same, so I always use the same set of templates as a starting point.

{exp:channel:entries channel="site" url_title="{last_segment}" disable="categories|member_data|pagination|trackbacks"}
  {embed="_embeds/index" body_class="{segment_1}" nav_active="{segment_1}" entry_id="{entry_id}"}
  {exp:partials:set name="page_title"}{title}{/exp:partials:set}
  {exp:partials:set name="content"}{body}{/exp:partials:set}
An example of a single page template containing only EE tags

All the templates I create use the same basic format as the template above with generally only the channel being called by the channel entries tag, and what goes in the content partial changing. I also have a few stock templates for a contact form and for 404 and error pages that get reused on every site too. So by storing all these in the database, they're all available for each new site that I create.

The Mountee logoIt's also worth mentioning here that I don't actually work with the templates via EE's control panel. I used to save templates as files and if I were still doing it that way, then the folder that contained those files would simply be included in my base install, and they'd be available for each new site that way. But nowadays I use Mountee which gives you the ability to work on files directly in the database but as actual files on a drive mounted on your system. Not much different than if you were still saving templates as files, but where Mountee has the advantage is that it also lets you work with snippets and global variables in the same way you can with templates (which you can't do the native EE way), and also gives you easy context-menu shortcuts for setting preferences on templates without having to access the control panel. So for me, that's two big wins right there.

Where there is a slight down side is in the versioning of these template files with Git because they don't actually exist permanently on your system; they're only there as long as you have Mountee running and the disk mounted. There is an explanation about working with Mountee and Git on their site, but my method is to just copy the files from the Mountee drive into my local version-controlled project folder. If I needed to revert back to an earlier template state, I could just find the relevant version in my repo and then copy its contents back into the template in the Mountee drive.

7. Export the database

Not much needs to be said here other than that this will be the final step of this first part of the series. You can export your database in a few different ways: you could use Sequel Pro, phpMyAdmin, or there's also a handy little utility, My Mamp Dump. Whichever method you use, this will probably be the quickest step in the process and should only take a few seconds.

So now you should have everything prepared for working on a real website project using your base EE install as a starting point. Part 2 of this series deals with actually using Git for cloning your base install and then also using it for deploying it to a remote server. Part 2 won't be too far away but if in the mean time is out now so if you have any suggestions or questions, let me know in the comments.