I've got a live EE site and I need to put it under version control using multi-environment config settings.

My goal is to set a git workflow, so these would be the steps I believe are right for my needs: I just want to track templates, css, js and html changes.


1 - Using SFTP, download all production files to my local machine

2 - Dump a production SQL database.

3 - Then, on my local machine I make a fresh install of ExpressionEngine, using the same EE version as the live site.

4 - I put in place Focuslab config settings for local, staging and production.

5 - Add all production files to my local web root

6 - Import the dumped database

7 - Site is ready in local.

8 - Then, I add .gitgnore to ignore all upload images, media and cache.

9 - Git init

10 - My local site is ready.

11 - Then, I go to the staging server to create the staging site just by repeating 3, 4, 5 and 6 steps.

12 - Now, on local I will be able to test addons, for instance, and git push them to the staging site.


  • On the production server I should modify config to use the Focuslab config settings?

  • I guess, even though I'm not tracking uploaded content, I still have to synchronise production database with the local db, every time I make a change in local, like using a new addon?

Any ideas?

  • Before you begin any of this, do you have ssh access to your production (live site) server? Commented Oct 31, 2013 at 12:54
  • Yes, I do have ssh access to the production server. Commented Oct 31, 2013 at 13:00
  • Details added below. If you need steps for setting up a staging site too, I can add that later. Commented Oct 31, 2013 at 14:15

1 Answer 1


I'll add to this as needed.

Since you have ssh access to the server, start there.

1) Connect via ssh to the production server via Terminal (or iTerm app). cd to the root of your site (or the directory where you want to track changes).

2) Type the following:

git config --global user.name "SITE NAME Prod Server"
git config --global user.email [email protected] use company or your email
git init
git add .
git commit -am "initial commit, all files added"

Now you have your site files tracked on your production server. For good practice (and ease), next you'll set up a central repo "hub". (See comments below for some thoughts on this.)

3) Sign up for Bitbucket (or pay for GitHub). Note: you can't put an EE site on a public repo.

4) Back on your production ssh connection, create an ssh public/private key pair.

cd ~
ssh-keygen -t rsa -C "[email protected]"
Follow step 2 of GitHub's helpful instructions: https://help.github.com/articles/generating-ssh-keys#step-2-generate-a-new-ssh-key

5) Copy your key to your computer's clipboard from Terminal

pbcopy < ~/.ssh/id_rsa.pub

6) Add this key to Bitbucket so you can push to their server. See how: step 6 here.

7) Create an empty repo on Bitbucket.

8) Now let's connect your server's repo to your new Bitbucket repo. Back in Terminal, type:
cd /path/to/your/project
git status - make sure you are actually in your repo
git remote add origin https://[email protected]/USERNAME/MY-REPO.git - Use your Bitbucket username and repo short name.
You should see it processing to send the files. After it's done, check Bitbucket and make sure your source files are there now.

9) Pull the repo to your local machine (or staging/dev server). Grab the ssh clone command from Bitbucket for your repo (it will be something like git clone [email protected]:USERNAME/MY-REPO.git).

Using terminal, go to your local machine's (or staging/dev server's) directory where you want to add the site files. Note that this will create a root folder, so I usually name my repo folder 'public_html`.

Type your clone command:
git clone [email protected]:USERNAME/MY-REPO.git public_html

10) To be able push to Bitbucket from your local machine (or staging/dev server), follow steps 4-6 for your local machine (or staging/dev server).

From here, you are connected from local to production.

11) Add a .gitignore file to your local root directory (in this example, /public_html/.gitignore) to ignore all upload images, media and cache (and whatever else you don't want to track). Don't ignore the .gitignore file because you want it added to your other environments too.
Example .gitignore file for EE.

If you find that your newly ignored files are still being tracked, try this:

git commit -am "your commit message" (you need to first commit current changes)
git rm -r --cached .
(Or if you just want to cherry pick a file: git rm --cached path/to/file/to/ignore)
git add .
git commit -m "fixed untracked files"

12) Add Focus Lab's EE master config (follow their instructions) paying special attention to set the correct production and local database info.

If you have a team and each developer will be working on the site with his/her own local database, it is helpful to make a copy of config.local.php (rename to EXAMPLE.config.local.php), then ignore config.local.php so the local db settings are not committed and pushed.

13) Export your live site's database and import it into your local site's database.
Do whatever other steps you may need to get your local site running properly. Sync upload directories and/or templates in EE, as needed.

You should be running an exact copy of your live site now.

14) Once you have your local site running with the Master Config, commit those changes.
git commit -am "message describing changes for this commit"

Make changes locally, commit, push (git push origin master). Then pull from your server via ssh connection (git pull origin master) when you're ready to make those changes live. Or setup an auto-deploy hook/action for your server. Any database changes you make locally will have to replicated on the live site, so make careful note of them!

  • 2
    If you have git running on the server, why bother with Bitbucket in the middle? Why not push directly from local? Commented Oct 31, 2013 at 14:38
  • 3
    If you have a team, you need a central hub. Commented Oct 31, 2013 at 14:43
  • Ah right, I think I get you... would it be the case that if developer-A and developer-B both commit->push the same file with conflicting changes then git wouldn't complain about that? Also, could you not have that "central" origin repo running on the server instead of at a third-party? Then use git hooks to trigger the pull from origin? Commented Oct 31, 2013 at 14:49
  • You should always git status and git pull before git push. You can't push a conflict. It'll be rejected. When you pull, if there's a conflict, you fix it then commit and push the fix. Yes, the central origin repo can be on any server (I used to do this), but Bitbucket does it so well for free. I prefer it now. Commented Oct 31, 2013 at 14:54
  • If I understand this process, at the end making changes live requires two steps: 1. Locally push to bitbucket (git push origin master) and 2. From the server git pull origin master. It sounds great. Hope you find the time to add steps for setting up a staging site. Commented Oct 31, 2013 at 16:44

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.