😎

Rails 7 × Dev Container での環境構築

2022/12/20に公開

Rails 7 で VS Code の拡張機能である Dev Container を使用して環境構築をしました。

概要

対象

  • Rails 7 を Docker 環境で立ち上げたい方
  • Dev Container を使用したい方

目的

Rails 7 の環境構築を通じて、以下ができるようになる。

  • 最低限 Rails で開発できる環境を構築
  • Docker に触れてみる

前提

  • Mac M1
  • データベース:MySQL

手順

1. 作業ディレクトリ作成

まずは作業するディレクトリを作ります。
ターミナルを開いて以下のコマンドを入力。

  • 作業ディレクトリ作成(好きな名前をつける)
$ mkdir yama_rails
  • 作業ディレクトリに移動
$ cd yama_rails

2. 必要なファイル作成

以下のコマンドを入力

$ touch {Dockerfile,docker-compose.yml,Gemfile,Gemfile.lock,entrypoint.sh}

このコマンドで作業ディレクトリ内に以下のファイルができます。

  • Dockerfile
  • docker-compose.yml
  • Gemfile
  • Gemfile.lock
  • entrypoint.sh

3. Dockerfile への記述

今回、データベースは MySQL を使用します。
Rails 7 では Node.js を入れずに環境構築をします。(もちろん別途入れることは可能です)

Dockerfile
FROM ruby:3.1.3

ENV LANG C.UTF-8
ENV TZ Asia/Tokyo

RUN mkdir /yama_rails
WORKDIR /yama_rails
COPY Gemfile /yama_rails/Gemfile
COPY Gemfile.lock /yama_rails/Gemfile.lock
RUN bundle install
COPY . /yama_rails

COPY entrypoint.sh /usr/bin/
RUN chmod +x /usr/bin/entrypoint.sh
ENTRYPOINT ["entrypoint.sh"]
EXPOSE 3000

CMD ["rails", "server", "-b", "0.0.0.0"]

4. docker-compose.yml への記述

docker-compose.yml
version: '3'
services:
 web:
   build: .
   # Docker の Web 立ち上げ時に毎回実行するコマンド
   command: /bin/sh -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 3000 -b '0.0.0.0'"
   volumes:
     - .:/yama_rails
   ports:
     - 3000:3000
   depends_on:
     - db
   tty: true
   stdin_open: true
 db:
   image: mysql:5.7
   # M1 の方は以下を入れる
   platform: linux/amd64
   command: mysqld --character-set-server=utf8 --collation-server=utf8_unicode_ci
   volumes:
     - db-volume:/var/lib/mysql
   environment:
     MYSQL_ROOT_PASSWORD: password
     TZ: "Asia/Tokyo"
   ports:
     - "3306:3306"
volumes:
  db-volume:

5. Gemfile への記述

Gemfile
source 'https://rubygems.org'
gem 'rails', '~>7.0.3'

6. endpoint.sh への記述

endpoint.sh
#!/bin/bash
set -e

rm -f /yama_rails/tmp/pids/server.pid

exec "$@"

7. Docker 立ち上げ

まずは Docker image を作成

$ docker-compose build

続いて、docker-compose を実行。
これで Rails で使用する大量のファイルが作られる。

$ docker-compose run --rm web rails new . --force --database=mysql

8 Docker 上でデータベース作成

まずは以下のコマンド

$ docker-compose run --rm web rails db:create

すると以下のエラーが、、、

Could not find sprockets-rails-3.4.2, mysql2-0.5.4, puma-5.6.5, importmap-rails-1.1.5, turbo-rails-1.3.2, stimulus-rails-1.2.1, jbuilder-2.11.5, bootsnap-1.15.0, debug-1.7.0, web-console-4.2.0, capybara-3.38.0, selenium-webdriver-4.7.1, webdrivers-5.2.0, sprockets-4.1.1, msgpack-1.6.0, irb-1.6.0, bindex-0.8.1, addressable-2.8.1, regexp_parser-2.6.1, xpath-3.2.0, rubyzip-2.3.2, websocket-1.2.9, public_suffix-5.0.1 in locally installed gems
Run `bundle install` to install missing gems.
ERROR: 7

ここでキャッシュを削除する Build コマンドを叩きます。

$ docker-compose build --no-cache

もう一度以下のコマンド

$ docker-compose run --rm web rails db:create

すると、エラーが以下に変わりました。

Can't connect to local MySQL server through socket '/run/mysqld/mysqld.sock' (2)
Couldn't create 'yama_rails_development' database. Please check your configuration.
rails aborted!
ActiveRecord::ConnectionNotEstablished: Can't connect to local MySQL server through socket '/run/mysqld/mysqld.sock' (2)


Caused by:
Mysql2::Error::ConnectionError: Can't connect to local MySQL server through socket '/run/mysqld/mysqld.sock' (2)

Tasks: TOP => db:create
(See full trace by running task with --trace)
ERROR: 1

どうやら Docker 上に作成する DB の情報が足りてないようです。
config/database.yml を少々編集。
今回は最低限の環境構築を目的としているので、一旦デフォルトで書かれている test や production はコメントアウトしておきます。
以下の通りpassword: password と、host: db を追記しました。

config/database.yml
default: &default
  adapter: mysql2
  encoding: utf8mb4
  pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
  username: root
  password: password
  host: localhost

development:
  <<: *default
  database: yama_rails_development
  host: db

さらにもう一度以下のコマンドで今回はエラーも出ずうまくいきました。

$ docker-compose run --rm web rails db:create
Creating yama_rails_web_run ... done
Created database 'yama_rails_development'

【Dev Container を使用しない場合】

以下コマンドでコンテナを作成・実行します。

$ docker-compose up -d

http://localhost:3000/にアクセスして以下のような画面になれば成功です!

【Dev Container を使用する場合】

まずは VS Code の拡張機能で Dev Container をインストール

続いて、画面左下にある以下のボタンをクリックし「Reopen Container」→「From 'docker-compose.yml'」→「web」→「OK」の順に選択

Workspace が存在していないと言われるので、「Open Workspace...」でワークスペースのディレクトリを選択する。(今回の場合は yama_rails)
ディレクトリを選択したら「OK」を押すとコンテナの中に入ることができました。

画面左下が以下のようになっていたら成功です。

また、このボタンを押して、「Reopen Folder Locally」を押すとコンテナから出ることができますが、また「Reopen Container」を押すと、再度ワークスペースを選択しなければなりません。

そこで、最初にコンテナに入ったときに生成された以下のファイルを編集します。
私の場合は rails ディレクトリの中に yama_rails を入れていたので、このように書いています。

.devcontainer/devcontainer.json
"workspaceFolder": "/workspaces/rails/${localWorkspaceFolderBasename}"

ターミナルでコンテナに入るには以下のコマンド

$ docker-compose exec web /bin/bash

サーバー起動は以下のコマンド

$ bundle exec rails s

これでローカルホストにアクセスして Rails の画面が表示されれば成功です。

http://localhost:3000/

お疲れ様でした◎

関連

https://zenn.dev/yama525/articles/0c3b9e3b75d9cc

Discussion