40
48

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

GitLabからwebhook+PHPで超簡易自動デプロイシステムを作る

Last updated at Posted at 2015-09-12

GitLabのreleaseブランチにpushイベントがあったとき(⊃ マージされた時)にreleaseブランチに自動反映できるようにします。
GitLab CI等のCIツールを入れるほどじゃない小さなアプリケーションを複数人で高速にサクッと開発していきたいときには、これぐらいでもいいのかなと考えています。

スクリプトは非常に簡単にPHPで書きます。

初心者向け:そもそもWebhookって何?

特定のアクションをトリガーとしてある指定したURLにHTTPリクエストを送ることのできるAPIのことです。
GitLabのwebhookではpushイベントをトリガーにできるので、
あとはURLだけ指定すれば決まったリクエストがpushイベントのたびに送られます。

これを使うと、特定のブランチにpushイベントが有ったときに何らか動作をさせる、という動作が可能になる、というわけです。

ぱっとググッたらここがわかりやすかったです。
https://sendgrid.kke.co.jp/blog/?p=1851

どんなふうに作るか

GitLabはpushイベント時にwebhookが使えるので、
http://webhook.mydomain.com/release.phpで叩き、
同サーバー内のアプリケーションのディレクトリでgit pull origin releaseを実行させるようにする。

スクリプト

release.php
<?php

$secret_key = "secretkey"; // GitLab以外からのリクエストを受け付けないためのキー
$git_username = "bot"; // gitlabのログインパスワード
$git_password = "password"; // gitlabのログインパスワード
$log_file = '/path/to/webhook_log.txt';
$date = (new DateTime())->format('Y-m-d H:i:s');
$path_to_repository = '/path/to/repository';
$branch_name = 'release';
$git = '/usr/local/bin/git';

if ( !isset($_GET['key']) || !($_GET['key']==$secret_key) ) {
    echo "Invalid key";
    $is_logged = error_log("[{$date}] Error: Invalid key\n",3,$log_file);
    exit;
}

$json_string = file_get_contents('php://input');
$json = json_decode($json_string,true);

error_log("[{$date}] Pushed to {$json['ref']}\n",3,$log_file);

if ($json['ref']=="refs/heads/{$branch_name}") { // releaseブランチのpushイベントの時のみ実行
    $git_remote = "http://{$git_username}:{$git_password}@gitlab.mydomain.com/group/repository_name.git";
    $command = "cd {$path_to_repository} && ${git} pull {$git_remote} {$branch_name} 2>&1";
    exec($command, $output, $exit_status);

    if ($exit_status > 0) {
        $error_msg = "[{$date}] Error: \n";
        foreach ($output as $line) {
            $error_msg .= "    {$line}\n";
        }
        error_log($error_msg,3,$log_file);
    } else {
        error_log("[{$date}] Updated successfully\n",3,$log_file);
    }
}

webhook.mydomain.comのようなサブドメインを作ってApacheなどでvirtualhostを作り、このドキュメントルートにこのrelease.phpを入れればOK。

また、git pull origin releaseが実行されるのはApacheの実行ユーザーなので、コマンドやリポジトリのパスは絶対パスで指定したほうがいい。またリポジトリの所有権をApacheの実行ユーザーにしておいている。

GitLabのpushイベントのPOSTデータの中身は以下を参照。
https://gitlab.com/gitlab-org/gitlab-ce/blob/master/doc/web_hooks/web_hooks.md

GitLabでの設定

リポジトリのsettingの中にwebhookという項目があるので、そこでpushにチェックを入れて以下のURLを入力すればOK。

http://webhook.mydomain.com/release.php?key=secretkey

secretkeyは攻撃を受けないためのささやかな対策。

終わりに

超簡単ですがこれで反映ができるようになりました。
スクリプトはまだまだ改善の余地あり。
エラーじゃないのにerror_logでログはいてたり、権限設定がすごく面倒だったり。

あと、自動デプロイだけではバグが本番で見つかった場合に戻すのが手動なので、git cloneしなおしてシンボリックリンクを張り替える形式にしたほうがよいのかもしれないです。

40
48
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
40
48

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?