Laravel アプリケーションを、 Circle CI 経由で AWS ElasticBeanstalk に自動デプロイ

  • 4
    いいね
  • 0
    コメント

Laravel で作っているアプリケーションのデプロイ自動化に成功した。

プルリクをマージしたら、勝手にEBにデプロイしてくれる。

設定は飛ばして、作成したファイルのみ記載する。

概要

  • Laravel 5.1
  • PHP 7.0

deploy.png

Circle CI 関連の設定

Circle CI 内のコンテナで実行すること、またデプロイブランチの設定

circle.yml
machine:
  timezone: Asia/Tokyo
  php:
    version: 7.0.4
  environment:
    APP_ENV: testing
    APP_KEY: base64:***************/*******************=
deployment:
  develop:
    branch: develop
    commands:
      - bash ./ci/setup-eb.sh
      - bash ./ci/deploy-circle.sh dev
  production:
    branch: master
    commands:
      - bash ./ci/setup-eb.sh
      - bash ./ci/deploy-circle.sh production

EBの設定。アクセスキーは環境変数で与えるため、Circle CI 側で設定しておく。

ci/setup-eb.sh
#!/bin/bash

set -xue

sudo apt-get install -y python-dev
pip install awsebcli

mkdir /home/ubuntu/.aws
touch /home/ubuntu/.aws/config
chmod 600 /home/ubuntu/.aws/config
echo "[profile eb-cli]" > /home/ubuntu/.aws/config
echo "aws_access_key_id=$AWS_ACCESS_KEY_ID" >> /home/ubuntu/.aws/config
echo "aws_secret_access_key=$AWS_SECRET_ACCESS_KEY" >> /home/ubuntu/.aws/config

デプロイシェル。

eb deploy で、プロジェクトに現在あるファイルをそのままEBのコンテナに持っていく。
下手にデプロイツールを使うより、 eb deploy した方が良い。理由は

  • ダウンタイム無し
  • オートスケールなどで複数のインスタンスで動いている場合、全てのインスタンスにデプロイしてくれる
ci/deploy-circle.sh
#!/bin/bash
# Usage: bash ci/deploy-circle.sh [dev|production]

set -xeu

# Ensure this script is executed in Circle CI
echo $CIRCLE_SHA1

deploy_env=$1

if [ ${deploy_env} = 'dev' ] ; then
    eb use ****_dev
    cp .env.dev .env
elif [ ${deploy_env} = 'production' ] ; then
    eb use ****_prod
    cp .env.production .env
fi

gulp --production

eb deploy

ここはポリシー次第だが、私の会社では .env ファイルをリポジトリに含めているため、上記のスクリプトにしている。

tree
project
  |- .env.example
  |- .env.dev
  `- .env.production

.ebignore.gitignore と同じような記法で、 eb deploy で含めたくないファイルを指定できる。
デプロイ時間を短縮するのに大事。

.ebignore
bin
docker
.elasticbeanstalk
.env.*
*.bak
.git
node_modules
tests
tags

# Elastic Beanstalk Files
.elasticbeanstalk/*

EBの設定

EBのリージョンなどの設定。

.elasticbeanstalk/config.yml
branch-defaults:
  develop:
    environment: ****

global:
  application_name: ****
  default_ec2_keyname: ****
  default_platform: arn:aws:elasticbeanstalk:ap-northeast-1::platform/PHP 7.0 running
    on 64bit Amazon Linux/2.3.0
  default_region: ap-northeast-1
  instance_profile: null
  platform_name: null
  platform_version: null
  profile: eb-cli
  sc: git
  workspace_type: Application

EBのコンテナ内でデプロイのタイミングで行うコマンド。
Apacheを利用している場合。

.ebextensions/deploy.config
container_commands:
  01-artisan:
    command: |
      sudo php artisan clear-compiled
      sudo php artisan optimize
      sudo php artisan config:cache
      sudo php artisan view:clear
      php artisan migrate
files:
  "/opt/elasticbeanstalk/hooks/appdeploy/post/99_make_storage_writable.sh":
    mode: "000755"
    owner: root
    group: root
    content: |
      #!/usr/bin/env bash
      sudo chmod -R 700 /var/app/current/storage
      sudo chmod -R 700 /var/app/current/public
      sudo chmod -R 700 /var/app/current/bootstrap/cache/services.json
      sudo php /var/app/current/artisan clear-compiled
      sudo php /var/app/current/artisan optimize
      sudo php /var/app/current/artisan config:cache
      sudo php /var/app/current/artisan route:cache
      sudo php /var/app/current/artisan view:clear
  "/etc/httpd/conf.d/ssl_rewrite.conf":
      mode: "000644"
      owner: root
      group: root
      content: |
          RewriteEngine On
          <If "-n '%{HTTP:X-Forwarded-Proto}' && %{HTTP:X-Forwarded-Proto} != 'https'">
          RewriteRule (.*) https://%{HTTP_HOST}%{REQUEST_URI} [R,L]
          </If>

ここで結構はまった。

01-artisan でキャッシュを消しておかないと、 Circle CI 以外からデプロイする場合に設定がおかしくなるので注意。