the famous deploy webhook at work

So from our last article, we needed to move from Travis CI as our deployment mechanism to something faster and more efficient and Github Web-hooks came to mind. What are webhooks?

Webhooks allow you to build or set up GitHub Apps which subscribe to certain events on GitHub.com. When one of those events is triggered, we’ll send a HTTP POST payload to the webhook’s configured URL.

So when we make a commit or merge anything a payload is instantly sent out to the webhook configured URL. No delays, Nothing.

Install git…

After you’ve installed git, make sure it’s a relatively new version

$ git --version

Setup git (optionally if you haven’t do so)

$ git config --global user.name "Server"$ git config --global user.email "server@server.com"

Create an ssh directory for the apache user

$ sudo mkdir /var/www/.ssh$ sudo chown -R www-data:www-data /var/www/.ssh/

Generate a deploy key for apache user

$ sudo -Hu www-data ssh-keygen -t rsa 
$ sudo cat /var/www/.ssh/id_rsa.pub

Add the SSH key to your user

  1. https://github.com/settings/ssh
  2. Create a new key
  3. Paste the deploy key you generated on the server

Grab a deployment script for your site

<?php
// Forked from https://gist.github.com/1809044
// Available from https://gist.github.com/nichtich/5290675#file-deploy-php
$TITLE   = 'Git Deployment Hamster';
$VERSION = '0.11';
echo <<<EOT
<!DOCTYPE HTML>
<html lang="en-US">
<head>
	<meta charset="UTF-8">
	<title>$TITLE</title>
</head>
<body style="background-color: #000000; color: #FFFFFF; font-weight: bold; padding: 0 10px;">
<pre>
  o-o    $TITLE
 /\"/   v$VERSION
(`=*=') 
 ^---^`-.
EOT;
// Check whether client is allowed to trigger an update
$allowed_ips = array(
	'207.97.227.', '50.57.128.', '108.171.174.', '50.57.231.', '204.232.175.', '192.30.252.', // GitHub
	'195.37.139.','193.174.' // VZG
);
$allowed = false;
$headers = apache_request_headers();
if (@$headers["X-Forwarded-For"]) {
    $ips = explode(",",$headers["X-Forwarded-For"]);
    $ip  = $ips[0];
} else {
    $ip = $_SERVER['REMOTE_ADDR'];
}
foreach ($allowed_ips as $allow) {
    if (stripos($ip, $allow) !== false) {
        $allowed = true;
        break;
    }
}
if (!$allowed) {
	header('HTTP/1.1 403 Forbidden');
 	echo "<span style="color: #ff0000">Sorry, no hamster - better convince your parents!</span>n";
    echo "</pre>n</body>n</html>";
    exit;
}
flush();
// Actually run the update
$commands = array(
	'echo $PWD',
	'whoami',
	'git pull',
	'git status',
	'git submodule sync',
	'git submodule update',
	'git submodule status',
    'test -e /usr/share/update-notifier/notify-reboot-required && echo "system restart required"',
);
$output = "n";
$log = "####### ".date('Y-m-d H:i:s'). " #######n";
foreach($commands AS $command){
    // Run it
    $tmp = shell_exec("$command 2>&1");
    // Output
    $output .= "<span style="color: #6BE234;">$</span> <span style="color: #729FCF;">{$command}n</span>";
    $output .= htmlentities(trim($tmp)) . "n";
    $log  .= "$ $commandn".trim($tmp)."n";
}
$log .= "n";
file_put_contents ('deploy-log.txt',$log,FILE_APPEND);
echo $output; 
?>
</pre>
</body>
</html>

Add, commit and push this to github

$ git add deploy.php$ git commit -m 'Added git deployment script'$ git push -u origin master

Set up service hook

  1. https://github.com/YOUR_USERNAME/REPO/admin/hooks
  2. Select the Post-Receive URL service hook
  3. Enter the URL to your deployment script — http://localhost/deploy.php
  4. Click Update Settings

Sources


Thanks to Gabriel Umoh for the assists

Speak with an expert on our team to discuss Cloud solutions tailored to your business.

You’ll receive free recommendations tailored to your business.