##結論
Docker公式の「Quickstart: Compose and Rails」に書いてます。
なのでスラスラ理解できる方は下記リンク先へどうぞ
https://docs.docker.com/compose/rails/
公式のクイックスタートは全部英語で書かれていて、
知能の低い僕は疲れてしまいますので
こちらの公式ガイドを少しずつ紐解きながら環境構築します。
http://docs.docker.jp/glossary.html
http://docs.docker.jp/engine/articles/dockerfile_best-practice.html
こちらのdockerガイドとベストプラクティス集が詳しい、かつ分かりやすいです。
##Dockerとは?
多くの方々が分かりやすくDocker、コンテナ技術について解説してくれてますので
そちらを読みましょう。
<解説リンク>
https://knowledge.sakura.ad.jp/13265/
https://qiita.com/kotaro-dr/items/b1024c7d200a75b992fc
##Dockerfile
FROM ruby:2.5
RUN apt-get update -qq && apt-get install -y nodejs postgresql-client
RUN mkdir /myapp
WORKDIR /myapp
COPY Gemfile /myapp/Gemfile
COPY Gemfile.lock /myapp/Gemfile.lock
RUN bundle install
COPY . /myapp
# Add a script to be executed every time the container starts.
COPY entrypoint.sh /usr/bin/
RUN chmod +x /usr/bin/entrypoint.sh
ENTRYPOINT ["entrypoint.sh"]
EXPOSE 3000
# Start the main process.
CMD ["rails", "server", "-b", "0.0.0.0"]
これをとりあえず使ってね!らしい。
しかしなんとなくで使うのは気持ち悪いのでコマンドを見ていく。
[FROM] 使用するイメージとバージョン
[RUN] コマンドの実行。railsに必要な必要なnodejsとpostgeqsqlをインストールしている
[WORKDIR] そのままの意味。作業ディレクトリを設定します。
[COPY] ローカルのファイルをコンテナへコピーする
[ENTRYPOINT] 一番最初に実行するコマンド(ここではentrypoint.shを参照)
[EXPOSE] コンテナがリッスンするport番号
[CMD] イメージ内部のソフトウェア実行(つまりRailsのことですね)
##Gemfile
source 'https://rubygems.org'
gem 'rails', '~>5'
rails newをするとGemfileはrails用に書き換えられます。
バージョンは適宜変更しましょう。
##Gemfile.lock
空の状態でGemfile.lockファイルを作ります。
$ touch Gemfile.lock
##entrypoint.sh
#!/bin/bash
set -e
# Remove a potentially pre-existing server.pid for Rails.
rm -f /myapp/tmp/pids/server.pid
# Then exec the container's main process (what's set as CMD in the Dockerfile).
exec "$@"
set -e は 「エラーが発生するとスクリプトを終了する」オプション
rm ではrailsのpidを削除
exec "$@"でCMDで渡されたコマンドを実行しています。(rails s)
##docker-compose.yml
公式によるとdocker-composeは魔法が起こる場所らしいです(ステキ
version: '3'
services:
db:
image: postgres
volumes:
- ./tmp/db:/var/lib/postgresql/data
web:
build: .
command: bash -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 3000 -b '0.0.0.0'"
volumes:
- .:/myapp
ports:
- "3000:3000"
depends_on:
- db
一番重要であろうdocker-compose.ymlです。
docker-composeについてもdockerガイドに分かりやすい説明が記載されています。
こちらも何が起こっているか見ていきましょう。
[version] docker-composeのバージョンです。2019年4月現在最新は'3'です。
[services] この下のハッシュにサービスを作りましょう。なんでも良いですが通常はwebとdbと名付けます。
[image] 使用するimage
[volumes] ディレクトリのマウント設定(dbデータなどを残せます。。)
[build] Dockerfiletなどがあるパス(基本的にカレントディレクトリ)
[command] コマンド(pid削除してからrails s)
[ports] ポート番号。[ホスト:コンテナ]で設定。
[depends_on] 依存関係を示していて、起動順を制御できます。ここではdb→webへと起動します。
volumeについては
https://qiita.com/gounx2/items/23b0dc8b8b95cc629f32
を参考にしました。
##Rails newしよう!
Dockerfile, docker-compose.yml, entrypoint.sh, Gemfile, Gemfile.lock
が揃ったのでrails newします。
$ docker-compose run web rails new . --force --no-deps --database=postgresql --skip-bundle
DBはpostgresql、Gemfileがあるためforce(上書き)オプション付き
--no-depsはリンクしたサービスを起動しない設定。
最後にbundleしますのでここではbundleをskipします。
webのimageがビルドされてその中でrails newコマンドが実行されます。
##bundle install
Gemfileが更新されたのでビルドを実行しましょう
$ docker-compose build
##Rails側のDB設定
default: &default
adapter: postgresql
encoding: unicode
host: db
username: postgres
password:
pool: 5
development:
<<: *default
database: myapp_development
test:
<<: *default
database: myapp_test
config/database.ymlを上記の通りに変更します。
Railsはデフォルトでhost:localhostとなりますので
hostを先ほど作成したdbに変更します。
##コンテナの起動
$ docker-compose up
docker-compose.yml通りにdbサービスが起動し、webサービスが起動します。
##DB作成
$ docker-compose run web rake db:create
あとはdb:createすれば完了です。
マイグレーションする必要があるときは上のコマンドをdb:migrateに変えて実行しましょう。