暇人じゃない

Middleman の S3 へのデプロイを Wercker で自動化する

このブログは Middleman でビルドして、S3 でホスティングしている。

現在は手元のマシンから middleman-s3_sync を使って S3 にデプロイしている。 そこで、middleman-s3_sync を使ったこれまでと同じワークフローで Wercker で自動デプロイできるようにした。

ところで middleman-s3_sync を使う必要がなく、Wercker のみで完結したい人は、 Wercker に S3 へデプロイするための Deploy Target が用意されているので、以下のページを参照すると良い。

Wercker の設定

まずは App を作る。自分の場合はプライベートで作成した。

作成した App の Pipeline に以下の環境変数を定義する。

アクセスキーやトークンなどはプロテクトにすること。
ステージング用のバケットが不要なら AWS_S3_*_STAGING は、Slack の通知が不要なら SLACK_WEBHOOK_URL は設定しなくてよい。

設定ファイル、コード

各設定、コードについて説明する。

wercker.yml

box: wercker/rvm

build:
    steps:
        - bundle-install
        - script:
            name: Deploy to S3 and Ping sitemap
            code: bundle exec rake publish

    after-steps:
        - wantedly/pretty-slack-notify:
            webhook_url: $SLACK_WEBHOOK_URL

https://github.com/chocoby/chocoby.jp/blob/master/wercker.yml

middleman でビルド、S3 へデプロイして Google に ping する処理を、後述する publish という rake タスクに定義している。 手元のマシンでも同じコマンドを実行すればデプロイできる。

また、after-steps でビルド結果を Slack に通知している。Wercker の Pipeline で定義した SLACK_WEBHOOK_URL の環境変数はここで使用する。 Slack への通知は以下の記事を参考にした。記事では API トークンを指定しているが、現在は Webhook URL を設定するようになっているので注意。

Rakefile

SITEMAP_URL = 'http://chocoby.jp/blog/sitemap.xml'

desc 'Publish'
task :publish do
  cmd_with_bundler 'middleman build'
  cmd_with_bundler 'middleman s3_sync'

  puts "Pinging sitemap to Google: #{SITEMAP_URL}"
  system "curl http://www.google.com/webmasters/tools/ping?sitemap=#{SITEMAP_URL}"
end

def cmd_with_bundler(cmd)
  system "bundle exec #{cmd}"
end

https://github.com/chocoby/chocoby.jp/blob/master/Rakefile

publish タスク。 middleman でビルド、S3 へデプロイして Google に ping する。コマンドを実行しているだけ。

config.rb

activate :s3_sync do |sync|
  if ENV['CI'] && ENV['WERCKER_GIT_BRANCH']
    branch = ENV['WERCKER_GIT_BRANCH']

    sync.bucket = (branch == 'master') ? ENV['AWS_S3_BUCKET'] : ENV['AWS_S3_BUCKET_STAGING']
    sync.region = (branch == 'master') ? ENV['AWS_S3_REGION'] : ENV['AWS_S3_REGION_STAGING']
  else
    sync.bucket = ENV['AWS_S3_BUCKET']
    sync.region = ENV['AWS_S3_REGION']
  end

  sync.aws_access_key_id     = ENV['AWS_ACCESS_KEY_ID']
  sync.aws_secret_access_key = ENV['AWS_SECRET_ACCESS_KEY']

  sync.after_build = false
end

https://github.com/chocoby/chocoby.jp/blob/master/config.rb

config.rb から middleman-s3_sync に関する部分を抜粋した。

Wercker でビルドする際は環境変数 CItrue に、環境変数 WERCKER_GIT_BRANCH がブランチ名になる。 push したブランチが master の場合は AWS_S3_BUCKET のバケットを、それ以外の場合は AWS_S3_BUCKET_STAGING のバケットをデプロイ先のバケットとする。 ステージング環境が不要なのであれば分岐させる必要はなく、AWS_S3_BUCKETAWS_S3_REGION を参照するだけでよい。

Wercker によって定義される環境変数についてはヘルプを参照のこと。

.envrc

export AWS_ACCESS_KEY_ID=""
export AWS_SECRET_ACCESS_KEY=""
export AWS_S3_BUCKET="chocoby.jp"
export AWS_S3_REGION="ap-northeast-1"

https://github.com/chocoby/chocoby.jp/blob/master/.envrc.sample

direnv を使用してデプロイに関する設定を管理している。
.envrc に定義しておけばディレクトリに入った時に direnv が環境変数を export してくれる。便利。

以上で設定は完了。
リポジトリに push すると Wercker によってビルドとデプロイが始まるはず。

Wercker の有料化

現在はベータということで利用は無料だが、いつかは有料になるだろう。
とても便利なサービスなだけにどのような価格設定になるのか気になる。

まとめ