share facebook facebook facebook twitter twitter menu hatena pocket slack

2021.05.18 TUE

Docker + Rails6 + React + TypeScript の環境構築

遠藤 優輝

WRITTEN BY 遠藤 優輝

streampack の endo です。
ローカルで、Docker + Rails6 + React(react-rails) + TypeScript の環境を作る機会があり、ちょっと苦労したので備忘録になります。

Docker 上に Rails プロジェクトを作成する

まずは Docker 上に Rails プロジェクトを作成。DB は MySQL5.7。

適当なディレクトリを作り、

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

の 4 ファイルを作成する。

Gemfile

source "https://rubygems.org"
git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
gem "rails"

Gemfile.lock(空ファイル)


Dockerfile

FROM ruby:2.7.2

RUN curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | apt-key add - \
  && apt-get update \
  && echo "deb https://dl.yarnpkg.com/debian/ stable main" | tee /etc/apt/sources.list.d/yarn.list

RUN apt-get update -qq && apt-get install -y build-essential \
  libpq-dev \
  nodejs \
  yarn

RUN mkdir /myapp

ENV APP_ROOT /myapp
WORKDIR $APP_ROOT

ADD ./Gemfile $APP_ROOT/Gemfile
ADD ./Gemfile.lock $APP_ROOT/Gemfile.lock

RUN bundle install
ADD . $APP_ROOT

docker-compose.yml

version: "3"
services:
  db:
    image: mysql:5.7
    environment:
      MYSQL_ROOT_PASSWORD: password
      MYSQL_DATABASE: demo-db
    ports:
      - "3306:3306"
    volumes:
      - demo-db:/var/lib/mysql

  web:
    build: .
    command: rails s -p 3000 -b '0.0.0.0'
    volumes:
      - .:/myapp
    ports:
      - "3000:3000"
    links:
      - db

volumes:
  demo-db:

docker-compose run コマンドで Rails プロジェクトの作成。

shell

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

Rails プロジェクトを作成できたら、build する。

shell

$ docker-compose build

データベースの作成

config/database.yml を編集する。

config/database.yml

## 編集した箇所のみ抜粋
default: &default
  password: password # docker-compose.yml の MYSQL_ROOT_PASSWORD: で設定したパスワード
  host: db # localhost → db に変更

データベースを作成する。

shell

$ docker-compose run web rake db:create

Docker の起動

Docker を起動する。

shell

$ docker-compose up

http://0.0.0.0:3000 にアクセスすると、Rails の初期画面が表示される。

この時 shell に以下のようなエラーが出るときは、

shell

Cannot render console from 172.20.0.1! Allowed networks: 127.0.0.0/127.255.255.255, ::1

config/environments/development.rb に

config/environments/development.rb

Rails.application.configure do
  config.web_console.permissions = '0.0.0.0/0'
end

を追加すればエラーログが消える。

React の導入

react-rail を使って react を rails プロジェクトに導入する。

Gemfile

gem 'react-rails'

再度 build を実行する。

shell

$ docker-compose build

下記コマンドを実行する。

shell

$ docker-compose run web rails webpacker:install       # OR (on rails version < 5.0) rake webpacker:install
$ docker-compose run web rails webpacker:install:react # OR (on rails version < 5.0) rake webpacker:install:react
$ docker-compose run web rails generate react:install

実際に React が導入されているか確認する。

controller の作成。

shell

$ docker-compose run web rails g controller sample index

以下のファイルが作成されていれば OK。

app/controllers/sample_controller.rb

class SampleController < ApplicationController
  def index
  end
end

react コンポーネントファイルの作成。

shell

$ docker-compose run web rails g react:component Sample

app/javascript/components/Sample.tsx が作成されるので、以下のように修正する。

app/javascript/components/Sample.jsx

import React from "react";
const Sample = () => {
  return <>this is react sample.</>;
};

export default Sample;

view の作成。
app/views/sample/index.html.erb を作成し react コンポーネントを読み込む。

app/views/sample/index.html.erb

<%= react_component 'Sample' %>

ルーティングを追加する。

config/routes.rb

Rails.application.routes.draw do
  get "sample", to: "sample#index"
end

Docker を起動し、http://0.0.0.0:3000/sample にアクセスする。「this is react sample.」の文字が表示されていれば OK。

TypeScript の導入

React が導入できたので、以下コマンドで TypeScript 導入する。

shell

$ docker-compose run web bundle exec rails webpacker:install:typescript
$ docker-compose run web yarn add @types/react @types/react-dom

無事インスールが終えたら sample.jsx の拡張子を sample.tsx に修正する。

app/javascript/components/Sample.tsx

import React from "react";
const Sample: React.FC = () => {
  return <>this is typescript sample.</>;
};

export default Sample;

ここまで修正したら再度 http://0.0.0.0:3000/sampleにアクセスし、「this is typescript sample.」の文字が表示されていることを確認する。

JS の修正時にホットリロードさせる

Docker の場合は$ bin/webpack-dev-serverのコマンドを直接叩くとエラーがでるっぽいので docker-compose.yml を修正した。

version: "3"
services:
  db:
    image: mysql:5.7
    environment:
      MYSQL_ROOT_PASSWORD: password
      MYSQL_DATABASE: rails-front-demo-db
    ports:
      - "3306:3306"
    volumes:
      - rails-db:/var/lib/mysql

  web: &web
    build: .
    command: rails s -p 3000 -b '0.0.0.0'
    environment:
      WEBPACKER_DEV_SERVER_HOST: webpacker
    volumes:
      - .:/app_name
    ports:
      - "3000:3000"
    links:
      - db

  webpacker:
    <<: *web
    command: bundle exec bin/webpack-dev-server
    depends_on: []
    environment:
      WEBPACKER_DEV_SERVER_HMR: "true"
      WEBPACKER_DEV_SERVER_HOST: 0.0.0.0
    ports:
      - "3035:3035"
volumes:
  rails-db:

webpacker の service を追加。それに伴い web の service も修正。

$ docker-compose upで Docker を起動し、http://0.0.0.0:3000/sample にアクセスする。app/javascript/components/Sample.tsx のファイルを適当に書き換えて保存するとホットリロードすることがわかる。

まとめ

以上で Docker + Rails6 + React(react-rails) + TypeScript の環境構築ができました。Docker は初心者なので(間違っていたらご指摘ください)、諸々調べながら記述しております。react-railsRails6TypeScriptを使ってる情報は(特に最近では)意外と少なく感じたので、やはり Rails は API モードで使うのが主流なのだと思いました。react-railsを使用している方の参考になれば幸いです。

参考

Docker を使って Rails6 環境の構築をしてみる – Qiita
【Rails, React】Webpacker と TypeScript のセットアップ – Qiita
docker で webpacker が遅い問題を改善する – Qiita
GitHub – reactjs/react-rails: Integrate React.js with Rails views and controllers, the asset pipeline, or webpacker.
GitHub – rails/webpacker: Use Webpack to manage app-like JavaScript modules in Rails

元記事はこちら

Docker + Rails6 + React + TypeScript の環境構築

遠藤 優輝

遠藤 優輝

streampackチーム所属。グミが好きです。

cloudpack

cloudpackは、Amazon EC2やAmazon S3をはじめとするAWSの各種プロダクトを利用する際の、導入・設計から運用保守を含んだフルマネージドのサービスを提供し、バックアップや24時間365日の監視/障害対応、技術的な問い合わせに対するサポートなどを行っております。
AWS上のインフラ構築およびAWSを活用したシステム開発など、案件のご相談はcloudpack.jpよりご連絡ください。