• No results found

A Git Development Environment

N/A
N/A
Protected

Academic year: 2021

Share "A Git Development Environment"

Copied!
45
0
0

Loading.... (view fulltext now)

Full text

(1)

A Git Development Environment

Installing and using Git for Drupal and WordPress site development using Ubuntu/Mint and a Hostgator Reseller or VPS account.

By: Andrew Tuline Date: February 7, 2014 Version: 2.0.0

(2)

Revisions ... 4

1. Quick Git ... 5

1. Introduction ... 5

2. Conventions ... 5

2. Let’s Get Started ... 6

3. Installing Git ... 6

4. Basic Configuration ... 6

5. Git Repositories ... 6

6. Single User ... 8

7. Gitk ... 8

8. Simple Daily workflow in a non-bare repository ... 10

9. File Status... 11

10. Setup - Cloning From Bare Repository ... 12

11. Setup - Adding to a Bare Repository ... 14

12. Using .gitignore ... 16

13. Apache and Git Directory Structure in Ubuntu ... 17

14. Prior to Downloading Projects ... Error! Bookmark not defined. 15. Downloading Projects From GitHub ... 19

16. Downloading Drupal from GitHub ... 19

17. A Drupal .gitignore ... 21

(3)

3. Public Git Repositories ... 26

1. Using bitbucket.org as your master ... 26

2. Using github.com as your master ... 27

4. Sites and Site Components ... 29

5. Site Deployment and Migration ... 31

1. Introduction to Deployment and Migration ... 31

2. Adding a Staging Server ... 31

3. Shell Script Tools ... 32

4. A Simple Deployment ... 36

5. Fix Serialization ... 40

6. Restricting Access to Staging Server ... 42

7. General Site Migration Tips ... 43

8. WordPress Site Migration ... 43

9. Drupal Site Migration ... 43

10. Gitflow ... 44

(4)

Revisions

1.04 Long standing combined Development and Git version (in serious need of significant changes).

(5)

1. Quick Git

1. Introduction

Git is quickly becoming the version control backbone of team based web site development. This document covers initial configuration of Git and builds upon that in order to develop a basic distributed workflow for WordPress and Drupal. It is not, however, a comprehensive guide to using Git.

To learn more about Git, http://sixrevisions.com/resources/git-tutorials-beginners.

2. Conventions

(6)

2. Let’s Get Started

3. Installing Git

On your Ubuntu workstation, if you haven’t already done so, Git can be installed by typing:

dev$ sudo

apt-get

install

git

4. Basic Configuration

Prior to using Git, you should setup your name and email address similar to:

dev$ git

config

--global user.name

"Joe

Blow"

dev$ git

config

--global user.email

"[email protected]"

Review your Git identity and configuration with:

dev$ git

config

-l

# lower case ‘L’

5. Git Repositories

(7)

Repository Description

Local repository It’s located on your workstation. Remote repository It’s located elsewhere.

Non-bare repository The repository includes the files you’re working on.

Bare repository The repository has no working files in the directory, just blobs and things you shouldn’t edit.

For a single user environment, you could create a local non-bare repository and just use that for web development. For an open source or distributed environment, you will be using a remote bare repository (preferably on github.com or bitbucket.org) as well as a non-bare local repository for each developer.

For a single user environment, you can create a non-bare local repository by typing:

dev$ cd

~

dev$ git

init

nonbare

dev$ cd

nonbare

dev$ ls

-al

The above command creates a non-bare repository in that the working files are in the ‘nonbare’ directory, while the Git repository is in a

hidden ‘.git’ directory beneath it. This configuration is fine for local use, however, you cannot use this as your ‘Master’ repository in a distributed environment.

You can create a bare/master repository by typing:

dev$ cd

~

dev$ git

init

--bare

barerepo

dev$ cd

barerepo

(8)

dev$ ls

-al

This is a completely different directory structure, and you will not see any of your working files here. This could even be the central repository that your team w pull from and push back to. Don’t create files in this directory.

Most web developers work remotely at some point and will need to access the main repository from a remote location. As a result, the master repository should be stored on on a host such as GitHub or BitBucket. DIY’ers could even install their own web enabled Git Hosting with Gitlab locally or on their Hostgator VPS.

6. Single User

In a single user environment, we’ve created a non-bare repository. We can now add files to this directory, and once done, you need to add and commit those updates:

dev$ cd

~/nonbare

dev$ touch

test.txt

dev$ git

add

.

# ‘.’ refers to all files

dev$ git

commit

-m

"Initial commit."

To check the status of the repository:

dev$ git

status

dev# On branch master

nothing to commit (working directory clean)

7. Gitk

(9)

dev$ sudo

apt-get

install

gitk

To run gitk, we need to ‘cd’ into a repository with a repository in it. Let’s look at our previous non-bare repository:

dev$ cd

~/nonbare

dev$ gitk

# you must exit before getting the prompt back

or

(10)

8. Simple Daily workflow in a non-bare repository

From the previous chapter, we created a non-bare repository. Here’s a simple daily workflow for it:

dev$ cd

~/nonbare

dev$ git

checkout

-b

branch-name

# come up with a name, ‘-b’ creates a branch

DO SOME EDITS

dev$ git

add

.

dev$ git diff

# to see the changes vs previously committed files

dev$ git

commit

-m

"Detailed

message."

# you can go back for some more edits

AT THE END OF A WORK SESSION

dev$ cd ~/nonbare

dev$ git

checkout

master

dev$ git

merge

branch-name

# merge those changes

dev$ git log

dev$ git status

dev$ git

branch

-d

branch-name

# you can then delete that temporary branch

Perform adds/commits in small chunks. At the end of a session, you can then checkout the master and perform a merge. To review the various versions of the repository, type:

(11)

dev$ git

log

commit

d7ec9a

9129719759797923742397239472394729

Author: Joe Blow [email protected]

Date: Mon Jan 14 14:03:16 2013 -0800

Added text to a file.

commit cf23669a92948298474297423974239742397423

Author: Joe Blow [email protected]

Date: Mon Jan 14 14:03:16 2013 -0800

Initial commit.

If, for any reason, you have made a mistake in your working files, you can revert back to a previous version with:

dev$ git

reset

--hard

d7ec9a

# use the first several digits of a previous commit hash

OR

dev$ git

reset

--hard

HEAD~

# to go back to the previous commit

Note: We will be using this simple workflow a lot in our upcoming examples.

9. File Status

(12)

File Status Description

Untracked You have created a file in your non-bare working directory. Staged/Tracked That file is now tracked via the Git 'add' command.

Committed/Tracked That file has now been committed to the repository with the Git 'commit' command. This is a good place to be.

Not Staged/Tracked A previously tracked file has been further edited, but not re-added or committed.

Once you have performed a successful commit to the non-bare repository, you should see:

dev$ git

status

dev# On branch master

# or branch-name

nothing to commit

# working directory clean

10.

Setup - Cloning From Bare Repository

The following section sets up your environment by first create a bare repository and then cloning it to a working/non-bare repository.

dev$ cd

~

dev$ rm -rf barerepo

# delete our previous repo

dev$ git init --bare barerepo

(13)

dev$ cd ~

dev$ rm -rf myproject

dev$ git

clone

barerepo

myproject

# 'myproject' is now a non-bare repository

Cloning into 'myproject'…

warning: You appear to have cloned an empty repository.

done.

dev$ cd

myproject

dev$ touch

text.txt

dev$ git

add

.

dev$ git

commit

-m

"Initial

commit."

dev$ git

push -u origin master

# can do just a 'git push' after first time

At any time, you can check the status of your repository and see the results of your actions with the following commands:

dev$ git

status

dev$ git

log

dev$ gitk

# if you have it installed

Tip: It's important that you pull from the bare repository at the start of your work session and push it back when done. Let’s have a look at the modified daily workflow now that we’re using a non-bare repository:

dev$ cd

~/myproject

dev$ git

pull

dev$ git

checkout

-b

branch-name

#create a branch

(14)

dev$ git

add

.

dev$ git diff

dev$ git

commit

-m

"Detailed

message."

# Repeat as required

AT THE END OF A WORK SESSION

dev$ git

checkout

master

dev$ git

merge

branch-name

dev$ git

push origin master

dev$ git log

dev$ git status

dev$ git

branch

-d

branch-name

# Delete the branch when done.

As a reminder, perform edits/adds/commits in small chunks. At the end of a session, you can then checkout the master and perform a merge.

11.

Setup - Adding to a Bare Repository

Rather than clone from a bare repository to start, let’s assume we already have some files and want to setup our repositories for them.

dev$ cd

~

dev$ rm -rf barerepo

# delete the old one, again

dev$ git init --bare barerepo

(15)

dev$ rm -rf myproject

# delete the old one

dev$ mkdir myproject

dev$ cd

myproject

dev$ touch

text.txt

dev$ git init

dev$ git

add

.

dev$ git

commit

-m

"Initial

commit."

dev$ git

remote

add

origin

~/barerepo

# add our bare repository

dev$ git

push -u origin master

# only do this the first time

Again, at any time, you can check the status of your repository:

dev$ git

status

Reminder: Don’t forget to pull from the bare repository at the start of your work session and push it back when done.

Our daily workflow will be EXACTLY the same as before in that we:  Pull the latest changes

 Create a temporary branch  Edit the files

 Add/commit them  Checkout the master  Merge the changes  Push the changes

(16)

12.

Using .gitignore

Sometimes, you will want to exclude various files in your Git respository. These could be log files or files that are unique to each server, such as site configuration files. In order to do so, let’s create a ‘.gitignore’ file on the development workstation:

dev$ cd ~myproject

dev$ vi .gitignore

It could contain:

# Site configuration

*.log

.htaccess

Once complete, type:

dev$ git add .

dev$ git commit -m "Added .gitignore"

dev$ git push origin master

. . .

dev$ git status

From now on, any log files as well as the .htaccess file will not be incorporated into the Git repository. Many development houses use different .gitignore files. I’ll include some examples from Github later in the document, but look around the Internet to see what works for you.

(17)

13.

Apache and Git Directory Structure in Ubuntu

Let’s starting to develop a basic workflow in a real development directory as shown below:

Development Workstation

Directory Description

/var/www/client1.dev ~ directory for client1’s development tools in Ubuntu.

/var/www/client1.dev/www ~ directory for client1’s web site (Apache points here). It will be a non-bare repository.

~/git Interim home directory for our bare git repositories. We’ll eventually host this elsewhere.

~/git/client1.git Bare repository for client1.

From the previous document, we should not have to use ‘sudo’ in /var/www, as we have already set the permissions to allow the ‘www-data’ group to write to the directories, and have added ‘username’ to that www-data group. In addition, we have set the sticky bit so that the ‘www-data’ group will become the owner of any files/directories created beneath /var/www.

If they don’t already exist, create the git and client1 directories:

dev$ mkdir

/var/www/client1.dev

# development scripts for client1 go in here

dev$ mkdir

/var/www/client1.dev/www

# the actual web site goes here

dev$ cd

/var/www/client1.dev/www

dev$ touch index.html

# let’s create something first

dev$ git

init

# create a non-bare working repository

dev$ git add .

(18)

dev$ cd

~

dev$ mkdir

git

# make the git repositories directory

dev$ git

init

--bare ~/git/client1.git

# create a bare repository

dev$ cd

/var/www/client1.dev/www

dev$ git

remote

add

origin

~/git/client1.git

# add our bare repository

dev$ git

push -u origin master

We should already have an Apache host created for client1.dev. As a reminder:

dev$ sudo

vi

/etc/apache2/sites-enabled/client1.dev.conf

Add the following:

<VirtualHost

*:80>

DocumentRoot

"/var/www/client1.dev/www"

ServerName

client1.dev

ServerAlias www.client1.dev

</VirtualHost>

Edit /etc/hosts with vi and add:

(19)

dev$ sudo

/etc/init.d/apache2

restart

Your client1.dev web site should now have both a non-bare repository as well as a local bare repository and you can begin development. Don’t forget that you’ll be working in /var/www/client1.dev/www and pushing/pulling from the bare repository located at

~username/git/client1.git.

If you’re downloading Drupal or WordPress, you’ll need to clone it and then re-create your repositories. That’s coming up next.

14.

Downloading Projects From GitHub

Both Drupal and WordPress can be downloaded from a popular repository called GitHub. Rather than start a project from scratch, let’s download a baseline copy and develop our project from there.

In the previous example, we cloned a working directory from an empty bare repository, after which we could make our changes and then push them back.

In the case of Drupal or WordPress, we need to clone from GitHub, and then remove all ties from that source so we can use our own non-bare and bare repositories. For the first examples, we’ll do so on our development workstation. We’ll expand the scope later.

15.

Downloading Drupal from GitHub

The trick with downloading Drupal as well as WordPress from GitHub is that you’re not just downloading the latest version as you would a .zip file. Rather, you’re downloading the entire repository of versions. Let’s download Drupal and then checkout the latest version. Here’s a reference:

http://drupal.org/node/3060/git-instructions/7.x

dev$ rm -rf /var/www/client1.dev/www

# just to be safe

dev$ mkdir /var/www/client1.dev/www

dev$ cd

/var/www/client1.dev/www

dev$ git

clone --branch

7.x

http://git.drupal.org/project/drupal.git

.

# don’t forget the ' .'

(20)

OR

dev$ git clone --branch 7.x git://github.com/drupal/drupal.git .

dev$ ls

. . .

dev$ git

branch

-a

# list the branches

dev$ git

checkout

7.19

# or whatever the current release is

We then need to remove the links to GitHub and create our own repositories:

dev$ rm

-rf

.git

# Deletes Git along with everything else except 7.19

This leaves us with a pristine version of Drupal 7.19, and without any version control. Let’s create a non-bare repository for it in this directory, and then create and push it to bare repository as follows:

dev$ cd

~

dev$ rm

-rf

git/client1.git

# remove your old bare repository

dev$ git

init

--bare

git/client1.git

# create an empty bare repository

dev$ cd

/var/www/client1.dev/www

dev$ git

init

# create the non-bare repository

dev$ git

add

.

dev$ git

commit

-m

"Drupal 7.19 initial commit."

dev$ git

status

dev$ git remote add origin ~/git/client1.git

dev$ git push -u origin master

(21)

From here, you can now start on your daily workflow (see section Error! Reference source not found.). Note: You can also use ‘drush’ to download Drupal with the following command:

dev$ cd /var/www/client1.dev

dev$ rm -rf www

dev$ mkdir www

dev$ cd www

dev$ drush dl drupal

# which downloads the latest recommended release

# to a directory called drupal-7.19

$ shopt -s dotglob nullglob

# so we can include any hidden files during our mv

# just be careful not to move a .git directory to a non-repository

$ mv drupal-7.19/* .

# moves ALL files to current directory

$ rmdir drupal-7.19

At this point, you can create your database and go through the Drupal installation procedures. Once complete, you can then initialize your local repository.

16.

A Drupal .gitignore

# Ignore configuration files that may contain sensitive information.

sites/*/settings*.php

# Ignore paths that contain user-generated content.

sites/*/files

sites/*/private

.DS_Store

(22)

.cvs

*.sql

*.bak

*.swp

*.log

Thumbs.db

You might also want to look at https://github.com/github/gitignore/blob/master/Drupal.gitignore.

17.

Downloading WordPress

As with Drupal, when downloading WordPress from GitHub, you’re not just downloading the latest version as you would a .zip file. You’re downloading the entire repository of versions. In order to develop for a specific version, we need to do the following:

dev$ rm -rf /var/www/client1.dev/www

dev$ mkdir /var/www/client1.dev/www

dev$ cd

/var/www/client1.dev/www

dev$ git

clone http://github.com/WordPress/WordPress.git

.

# don’t forget the ' .'

dev$ ls

# you should see a bunch of WordPress files

Now we need to checkout the latest release of WordPress, in this case version 3.6.1:

dev$ git

branch

-a

# list branches

dev$ git

checkout

3.6.1

# checkout the latest

(23)

This leaves us with a pristine version of WordPress 3.6.1, and without any version control. As with Drupal, we could initialize our Git repositories, create the database and install WordPress on the Server.

18.

A WordPress .gitignore

There are numerous .gitignore configurations for WordPress; some include the WordPress core files and some don’t. Here’s one from github:

https://github.com/github/gitignore/blob/master/WordPress.gitignore

.htaccess

wp-config.php

wp-content/uploads/

wp-content/blogs.dir/

wp-content/upgrade/

wp-content/backup-db/

wp-content/advanced-cache.php

wp-content/wp-cache-config.php

sitemap.xml

*.log

wp-content/cache/

wp-content/backups/

sitemap.xml.gz

You might also want to look at http://www.stumiller.me/what-should-be-excluded-in-a-wordpress-gitignore-file/.

WordPress will create a .htaccess file if you change the Permalinks to ‘Post name’ on the wp-admin/options-permalink.php page. These .htaccess files may be slightly different between client1.dev and client1.mycompany.com, so this file has been added to the .gitignore file as well.

(24)

19.

Installing WordPress on Ubuntu

We’ve downloaded WordPress, but we haven’t actually ran the install scripts yet.

Go ahead and create a database on the Ubuntu server with either phpMyAdmin or in the terminal. Keep in mind that the database isn’t under version control and will eventually have to be put on the staging server.

Also, remember that your settings files will be located at:

/var/www/client1.dev/www/wp-config.php

This is important to keep in mind, because when you’re configuring WordPress on either your staging server (client1.mycompany.com) or your development workstation (client1.dev), the URL and database settings will be different. You will need to take this into account when using Git by using the .gitignore file as discussed later on.

Go ahead and run the WordPress installation by opening a browser in Ubuntu and typing (I assume you have already added an entry in the hosts table for it):

(25)

Here’s some insecure settings:

(26)

3. Public Git Repositories

Rather than host our bare master repository locally, we’re going to host it on a public server so that we can access it anywhere.

1. Using bitbucket.org as your master

You should consider using a host such as bitbucket.org or github.com for hosting your master repository. I’m using bitbucket.org, as they provide free hosting for private repositories as long the team has 5 or fewer members.

To do so, create an account on Bitbucket, add your SSH key from your development workstation and then create a bare repository called ‘Client1’.

(27)

On your development workstation, you should then be able to:

dev$ cd /var/www/client1.dev

dev$ rm -rf www

dev$ mkdir www

dev$ cd www

dev$ git init

dev$ touch index.html

dev$ git add index.html

dev$ git commit -m "Initial commit"

. . .

# and any other updates

dev$ git remote add origin ssh://[email protected]/mycompany/client1.git

# use SSH and not HTTPS

dev$ git push -u origin master

# initial push

dev$ git push origin master

# all further pushes

The advantages of using Bitbucket are that it provides a web front end to display the status of your repository. It gives you the option to provide an issue tracker and a wiki for your project. You can also share files with your clients.

Note: If you haven’t shared your Ubuntu SSH key, you can use HTTPS and then manually type in your username/password.

2. Using github.com as your master

You can use github.com for your master repository for no charge as long as it is a public repository. Once you have created an account, add your Ubuntu SSH key to github, then create an empty repository on github called client1.git. Then go to your development workstation and:

dev$ cd /var/www/client1.dev/www

(28)

dev$ git push -u origin master

# initial push

(29)

4. Sites and Site Components

Let’ recap the architecture we’re going to be using. In my Web Development Environment document, we have several servers as follows:

The challenge is that not all of the content will be the same on each. Let’s break this down into separate components and consider how we should manage and deploy them.

Sites www.bitbucket.org Git Repository Bare Repo client1.mycompany.com Staging Server DB client1.dev Devel Workstation Working Repo & Web Site DB www.client1.com Production Server DB Web Site Web Site

(30)

 A public Git server (www.bitbucket.org) with a bare repository.  3 web sites, each with a database and files

 The development workstation has a non-bare repository. Databases

 The databases may contain URL’s and file paths unique to each server, which are easy to edit.  WordPress databases contain serialized strings, which are not easy to edit.

 We won’t include the database in the Git repository. It’s big and doesn’t fit nicely in there. Files

 .htaccess may be unique to each server.  .gitignore may be unique to each server.

 settings.php and wp-config.php are unique to each server.  Drupal and WordPress core files should NOT be edited/hacked.  User uploaded content is often binary and LARGE.

 There will be the core application files.

 There will be new/modified themes which should be under version control.

 There will be additional/modified modules/plugins which should be under version control. Git Repositories

 Only your development environment should use a non-bare Git repository.  Use a bare repository for the master repository.

(31)

5. Site Deployment and Migration

1. Introduction to Deployment and Migration

As I spent more time studying Git, site deployment and migration, I thought of different ways to do it. At one point, I had almost everything contained in the Git repository, including the database, and thought of using a Git hook to move everything over, including the database, however further reading deemed that not a good idea.

When I go back and think of why we’re using Git in the first place, it’s to track the functionality that we are modifying. Therefore, let’s limit our use of the Git repository as much as possible. When we go to deploy content to a staging or production server, rather than incorporate it into Git and use a ‘git push’ command to deploy content, we’ll use some form of file copy. In this case, we’ll use the the ‘rsync’ command over SSH.

2. Adding a Staging Server

The purpose of adding a staging server is to show your work in progress to your client, while still maintaining full control over it. To add our staging server client1.mycompany.com, we need to create that subdomain in CPanel. In doing so, it will the the ‘~mycompany/client1’ subdirectory. Select ‘Subdomains’:

(32)

From there, you should have a directory at ‘/home/mycompany/public_html/client1’ and when browsing to it with http://client1.mycompany.com, you should see:

3. Shell Script Tools

The following files can be downloaded from ‘github.com:atuline/migrate-scripts.git’.

Here’s a number of commands/shell scripts that should come in handy to support file and database migration to the staging server. I keep these in the ‘/var/www/client1.dev’ directory on the development workstation. They include:

(33)

copydb.sh Copy a previously dumped and edited .sql file from the development workstation to the staging server.

createdb.sh Create the database on the development workstation. createdb_stg.sh Create the database on the staging server.

dropdb.sh Delete the database on the development workstation. dropdb_stg.sh Delete the database on the staging server.

dumpdb.sh Dump the database on your development workstation to a .sql file. exclude.txt Contains list of files to exclude from the syncfiles.sh script. fix-serialization.php Called by replace.sh to fix serialization strings for a WordPress

database.

fixperms.sh Configures the file/directory permissions for Apache. importdb.sh Import a .sql file to the development workstation database. importdb_stg.sh Import a .sql file to the staging server database. The MySQL

username/password for that database must already exist.

infile.txt URL and directories to be modified when migrating a database from the development workstation to the staging server. It’s used by replace.sh

replace.sh Use this to change the text strings in your development workstation .sql file to that of the staging server. The contents of the existing .sql file will be changed.

syncfiles.sh Use the rsync command to synchronize/copy files from the development workstation to the staging server.

copydb.sh

(34)

createdb.sh

#!/bin/sh

mysql -uroot -ppassword "create database client1_dev";

mysql -uroot -ppassword "grant all on client1_dev.* to root@localhost";

createdb_stg.sh

#!/bin/sh

ssh www.mycompany.com.com 'mysql -e "create database mycompany_client1"'

ssh www.mycompany.com 'mysql -e "grant all on mycompany_client1.* to mycompany_client1"'

dropdb.sh

#!/bin/sh

mysqladmin -uroot -ppassword drop client1_dev;

dropdb_stg.sh

#!/bin/sh

ssh www.mycompany.com 'mysqladmin drop mycompany_client1'

dumpdb.sh

(35)

exclude.txt

.htaccess

.gitignore

fix-serialization.php

See the github.com source for this.

fixperms.sh

sudo find www -type f -exec chmod 0644 {} \;

sudo find www -type d -exec chmod 2755 {} \;

importdb.sh

#!/bin/sh

mysql -uroot -psierrasys8 client1_dev < client1_dev.sql;

importdb_stg.sh

#!/bin/sh

ssh www.mycompany.com 'mysql mycompany_client1 < /home/mycompany/mycompany_client1.sql'

infile.txt

(36)

/var/www/client1/www

/home/mycompany/public_html/client1

replace.sh

See the github.com source for this.

syncfiles.sh

#!/bin/sh

rsync -e 'ssh' -avl --delete --stats --progress --exclude-from '/var/www/client1.dev/exclude.txt'

/var/www/client1/dev/www

www.mycompany

.com:/home/mycompany/public_html/client1

This script copies the files from your development workstation to the staging server with the exeception of the excluded file(s). It uses less bandwidth than a regular ‘scp’ command and will delete files on the remote host if they are no longer in the source.

See: http://articles.slicehost.com/2007/10/9/backing-up-your-files-with-rsync

4. A Simple Deployment

The following section does the following:

1. Create a simple site with a non-bare repository on our development workstation at client1.dev. 2. Create a bare master repository called client1.git on bitbucket.org.

3. Create a staging site at client1.mycompany.com.

4. Copy/migrate files and database to client1.mycompany.com.

(37)

Central Repository

Hostname bitbucket.org

Git repository name (bare) client1.git

Staging Server

Web hostname client1.mycompany.com

Web directory /home/mycompany/public_html/client1

Development Workstation

Hostname client1.dev

Tools directory /var/www/client1.dev

Git repository directory (non-bare) /var/www/client1.dev/www

Web directory /var/www/client1.dev/www

First, let’s create a simple development site and create a central repository as well as a live site.

dev$ cd /var/www

dev$ rm -rf client1.dev

dev$ mkdir client1.dev

# Our scripts go in here

(38)

dev$ mkdir www

# Actual site goes in here

dev$ cd www

dev$ git init

dev$ touch index.html

dev$ git add .

dev$ git commit -m "Initial commit."

# Our dev site is now set up

Let’s now create and push to our main repository at bitbucket.org and import our Ubuntu SSH key into the Bitbucket account. Then, click on the ‘Create’ button to create your ‘client1.git’ repository:

(39)

Now, let’s define and push to our master repository:

dev$ cd /var/www/client1.dev/www

dev$ git remote add origin ssh://[email protected]/mycompany/client1.git

dev$ git push -u origin master

# initial push

dev$ git push origin master

# all further pushes

We can pretty well duplicate these steps when creating the live server, so we won’t cover that here. Just give it another name in Git, such as ‘Live’.

But what about the actual staging server web site?

Rather than add the complexity of a Git repository to the staging server, we’ll use a combination of rsync and database scripts in order to update the staging server. Assuming the following:

 WordPress is configured and running on the development workstation.

 A database user is already configured on the staging server (via phpMyAdmin).  Infile.txt is already configured with source/destination text strings.

I would edit for proper naming and use the following scripts (in order):

1. syncfiles.sh - to synchronize all of the files (they may require the group:file owner to be changed on the staging server). 2. dumpdb.sh - to dump the development workstation database to a .sql file.

3. replace.sh - to replace the development workstation URL’s and directories in the database with that of the staging server. 4. dropdb_stg.sh - to remove the outdated database on the staging server.

(40)

5. createdb_stg.sh - to create a new database on the staging server 6. copydb.sh - to copy the modified .sql file to the staging server.

7. importdb_stg.sh - to import the modified .sql file on the staging server.

If you get through the above section without any issues, I will be absolutely astounded.

If you had some problems, the next section provides additional background information.

5. Fix Serialization

Let’s look at content unique to the web server in WordPress, and possibly in Drupal if any content has been added.

Data Type Example String Changes Editing it

URL unique to the site client1.dev will be client1.mycompany.com Easy to change Path unique to the site /var/www/client1/www will be /home/mycompany/client1 Easy to change Serialized strings s:11:"client1.dev" will be s:21:"client1.mycompany.com" Difficult to change

I’m going to use a modified copy of ‘Fix-Serialization’ originally from https://github.com/Blogestudio/Fix-Serialization as it doesn’t require you to be running WordPress to perform the database conversion. Fix-Serialization is a combination shell and PHP script which takes a database dump file and:

 Changes source URL and directory structure strings to destination URL and directory structures.  Fixes any serialized strings that have changed.

(41)

Files included:

 infile.txt (contains source and destination URL's and directory structures)

 replace.sh (run this shell script to swap strings and to call the PHP script)

 fix-serialization.txt (a descriptive file)

 fix-serialization.php (PHP script to perform serialization fixes)

How to use:

Put a dump of your WordPress database in the current directory, i.e (dumpdb.sh):

mysqldump -uroot -pmypassword client1_dev > client1_dev.sql

Create/modify infile.txt with your source and destination information similar to this:

www.client1.dev

client1.mycompany.com

/var/www/client1/www

/home/mycompany/public_html/client1

Execute the script as follows:

dev$ cd /var/www/client1

# put it in the client1 tools directory

. . .

# dump your database to this directory

dev$ sh replace.sh

# replaces current .sql file with a modified version

(42)

 https://github.com/azizur/wordpress-oneclick-migration

 http://interconnectit.com/products/search-and-replace-for-wordpress-databases/ (a standalone php script)  http://wordpress.org/extend/plugins/wp-migrate-db/ (a WordPress module)

 http://ithemes.com/purchase/backupbuddy/ (an awesome WordPress plugin)  https://github.com/interconnectit/Search-Replace-DB

6. Restricting Access to Staging Server

You might want to modify the .htaccess file on your Hostgator staging server so that visitors must enter a password to view that web site. In order to do so, you’ll require two files. They are:

 .htaccess (this may already already exist!)

 .htpasswd

In your .htaccess file, add:

AuthType Basic

AuthName "Restricted access"

AuthUserFile /home/mycompany/client1/.htpasswd

# change as appropriate of course

require valid-user

Place your .htpasswd file in the full path of your ‘~’ directory at Hostgator, typically ‘/home/mycompany’. Both files should be set with permissions of 644.

In your .htpasswd file, you’ll need to create a username and password. The password needs to be generated, so see

(43)

7. General Site Migration Tips

When migrating your site between hosts, you should take into account:

 Keep your account information organized. This includes development, staging, Git and production host names, usernames, password, database names, directories, Drupal/Wordpress usernames and passwords and setting files. Don’t forget domain registrar information, expiry and client contact information as well.

 There may be .htaccess, .gitignore and settings file differences between hosts.  Changing URL entries in the databases (edit the database dump file).

 There may be references to a different directory structure, such as /home/client1 instead of /var/www/client1/www.

 WordPress may require you to edit serialized objects, in which case, use a 3rd

party database migration utility.  URL and database configuration settings in the site configuration files.

 You may also need to change privileges/ownership of directories and files when you migrate files between hosts.  There may be different php configurations and versions. Run phpinfo();.

 Put site specific files in .gitignore.

 Don’t put a .git directory in public_html on a public server.

8. WordPress Site Migration

Changing the site URL in WordPress can be challenging. Follow this URL from the WordPress Codex.

http://codex.wordpress.org/Changing_The_Site_URL

Essentially, you need to edit wp-config.php and change the URL’s. Then there’s the database changes, which we have already covered.

9. Drupal Site Migration

Modifying Drupal to support another URL seems a lot easier than with WordPress.  http://drupal.org/node/171998.

 Optionally modify the $base_url in sites/default/settings.php.  Clear the drupal cache.

(44)

10.

Gitflow

Once you have a basic workflow and deployment in place, you’ll want to think about long term use of Git. The following link provides some more in depth examples of developing a more comprehensive Git workflow:

(45)

6. Conclusion

Between these two documents, you should have a good idea on how to: 1. setup a LAMP server

2. setup and develop in a Git environment 3. deploy to a staging (or other) server

There are a lot of different methods you can use to accomplish these goals, so feel free to use these as a starting point for your own site development.

References

Related documents