Rails
docker

dockerをつかってrailsの開発をしてみる

More than 3 years have passed since last update.

railsアプリをDocker化してみる - QiitaでアプリだけDocker化するのはさほど難しくないという話をした。
この場合はDBは既存のものが使えるから気軽に使えそうという話をした。

今回はDockerだけでRails開発をしてみようと思う。
HerokuのデフォルトがPostgreSQLなのでPostgreSQLを例にする。

Railsプロジェクトの作成

rails new をしよう。

docker run --rm -it -v "$(pwd)":/usr/src/app -w /usr/src/app rails rails new hello -d postgresql

Dockerがインストールされていればrubyなんていらない。
Windowsでも戦えそうだが試してない。
夢が広がる。

しかし、rails rails newというのはなんだか格好悪い。

ちゃんとローカルのファイルシステムに作成されている。

$ cd hello
$ tree .
.
├── Gemfile
├── Gemfile.lock
├── README.rdoc
├── Rakefile
├── app
│   ├── assets
│   │   ├── images
│   │   ├── javascripts
│   │   │   └── application.js
│   │   └── stylesheets
│   │       └── application.css
│   ├── controllers
│   │   ├── application_controller.rb
│   │   └── concerns
│   ├── helpers
│   │   └── application_helper.rb
│   ├── mailers
│   ├── models
│   │   └── concerns
│   └── views
│       └── layouts
│           └── application.html.erb
├── bin
│   ├── bundle
│   ├── rails
│   ├── rake
│   ├── setup
│   └── spring
├── config
│   ├── application.rb
│   ├── boot.rb
│   ├── database.yml
│   ├── environment.rb
│   ├── environments
│   │   ├── development.rb
│   │   ├── production.rb
│   │   └── test.rb
│   ├── initializers
│   │   ├── assets.rb
│   │   ├── backtrace_silencers.rb
│   │   ├── cookies_serializer.rb
│   │   ├── filter_parameter_logging.rb
│   │   ├── inflections.rb
│   │   ├── mime_types.rb
│   │   ├── session_store.rb
│   │   └── wrap_parameters.rb
│   ├── locales
│   │   └── en.yml
│   ├── routes.rb
│   └── secrets.yml
├── config.ru
├── db
│   └── seeds.rb
├── lib
│   ├── assets
│   └── tasks
├── log
├── public
│   ├── 404.html
│   ├── 422.html
│   ├── 500.html
│   ├── favicon.ico
│   └── robots.txt
├── test
│   ├── controllers
│   ├── fixtures
│   ├── helpers
│   ├── integration
│   ├── mailers
│   ├── models
│   └── test_helper.rb
├── tmp
│   └── cache
│       └── assets
└── vendor
    └── assets
        ├── javascripts
        └── stylesheets

38 directories, 40 files

データベースサーバを起動

docker run -d --name hello-db postgres

rails new するとき hello という名前にしたので hello-db という名前にした。

停止したくなったら

docker stop hello-db

再開する時は

docker start hello-db

いらなくなったら(当然データは消える)

docker rm hello-db

開発用イメージの作成

開発時にrailsを実行するためのイメージをつくる。
つまり、Dockerfileをかく。

FROM rails:onbuild

ENV DB_USER postgres
ENV DB_PASSWORD password
ENV DB_NAME hello
ENV DB_ADAPTER postgres
ENV DATABASE_URL ${DB_ADAPTER}://${DB_USER}:${DB_PASSWORD}@db/${DB_NAME}

そうしたらこのDockerfileを基にイメージを作成しよう。

docker build -t hello .

イメージの名前はhelloにした。
このコマンドはGemfileを書き換えたときは実行する。

現実的には.dockerignoreをかいておいたほうがよい。

rails serverの起動

イメージができたので起動してbin/rails sをすればよい。
他のコマンドも実行しやすいように bash で起動してから操作するのもありだと思う。

docker run --rm -it -p 3000:3000 -v $(pwd):/usr/src/app --link hello-db:db hello bash
bin/rake db:create db:migrate
bin/rails s -b 0.0.0.0

boot2dockerを利用している場合はIPの確認をしよう。

boot2docker ip

http://xxx.xxx.xx.xx:3000/ にでもアクセスすれば動作していることが確認できると思う。
適当にscaffoldなどしてみるとよいと思います。

bin/rails sしていたのとCtrl+cでとめて

bin/rails g scaffold bookmark name:string url:string
bin/rake db:migrate
bin/rails s

http://xxx.xxx.xx.xx:3000/bookmarks にでもアクセスしてみればよいです。

ローカルのファイルシステムのファイルも更新されているのことを確認してみると良いと思います。

あとはCIでイメージつくったり、CIでイメージ内でテストしたりすると幸せになれそうな気がする。

コマンドの長さに耐えられない

figを使いましょう。
Macであればbrew install figでインストールできます。

figを使う場合はfig.ymlを作成します。

fig.yml
db:
  image: postgres
  ports:
    - "5432"
web:
  build: .
  command: bin/rails s -b 0.0.0.0
  volumes:
    - .:/usr/src/app
  ports:
    - "3000:3000"
  links:
    - db

あとはfig upを実行します。
railsのコマンドを使いたい場合は

fig run web rails g scaffold name:string url:string

のようにfig run webの後にコマンドを続けます。

蛇足: figを使わずシェルスクリプトでなんとかしている例がこの記事の過去のバージョンに記述しています。興味があればみてみてください。

まとめ

Docker楽しい。
しかし、イメージのダウンロードがつらい。

ついでに、githubにアップしておいた。

dockerが使える状態にしてあれば、

git clone https://github.com/eiel/docker-rails-develop-sample.git
cd docker-rails-develop-sample
fig up
fig run bin/rake db:setup

で動作確認ができるんじゃないだろうか。
boot2dockerを使用している場合はboot2docker ipでIPを確認してください。