Dockerをついに使ってみる:用語、イメージ、立ち上げ編

前回でインストールまではできたので、動かしたい…
[Dockerをついに使ってみる:インストール編
](https://qiita.com/pank24ever/items/8177594df6780525c05d)

ところですが、どう使っていくかの流れや
でてくる用語の解説やイメージをつけるための記事を書いていきます

##動作環境
MacOS
Docker version 19.03.12

##使っていく流れ
・`ホストPC(自分のローカルのPC)にDockerをインストール`(Docker for Mac)
・**Dockerイメージを作成**する(ゲームソフト)
→`dockerhub`から取得する
・Docker Image(**イメージ**)を使って**コンテナを作成**(**build、ビルド**)する
・Docker Imageを元に、Docker Container(**コンテナ**)を作り、仮想環境を有効にする(**run、ラン**)

コンテナとは…１つのLinux仮想マシンのようなもの

わかりやすくいうと
**イメージ**…クラス(ゲームソフト)
**コンテナ**…インスタンス(セーブデータ)

###ほしいイメージがない場合は…
作成することもできる、それは
**Dockerfileを書く**ということ
→Docker上で動作する`コンテナの構成情報を記述するため`のファイルのこと
Dockerfileを元に、**Docker Image**を作る(**build、ビルド**)

今回は、Dockerfileを書くところから！

##Dockerfileを作成する
touch Dockerfileして、エディタで編集してもOKだそうだが
**vim**で編集する

```
pwd
/Users/ユーザー名/environment/rails
~/environment/rails

❯ ls
~/environment/rails

❯ touch Dockerfile
~/environment/rails

❯ ls
Dockerfile
~/environment/rails

❯ vi Dockerfile
```

```go:environment/rails/Dockerfile
//Rubyリポジトリの2.4.5のタグのイメージを指す
FROM ruby:2.4.5
//コンテナで実行するコマンドを意味する
// 必要なパッケージのインストール
// build-essentialとnodejsのパッケージをインストールしている
RUN apt-get update -qq && apt-get install -y build-essential nodejs
// ルートディレクトリ内に、appディレクトリを作成している。Railsアプリはここで作成する
// 作業ディレクトリの作成、設定
RUN mkdir /app
// 作業ディレクトリを指す
WORKDIR /app
// ホストPCにあるファイルを /app 内にコピーしている
COPY Gemfile /app/Gemfile
COPY Gemfile.lock /app/Gemfile.lock
RUN bundle install
// アプリの内容をすべて /app 内にコピーしている
COPY . /app
```
→上記の内容が**コンテナとして保存**される

##Gmefile、Gmefile.lockを作成する
こちらも同じようにtouchコマンドで作成してもよい

```
pwd
/Users/ユーザー名/environment/rails
~/environment/rails

❯ ls
~/environment/rails

❯ touch Gemfile
~/environment/rails

❯ touch Gemfile.lock
~/environment/rails

❯ ls
Dockerfile Gemfile Gemfile.lock
~/environment/rails

❯ vi Gemfile
```

Gemfileを編集する

```rb:environment/rails/Gemfile
source 'https://rubygems.org'
gem 'rails', '5.0.0.1'
```

次に、Gemfile.lockですが中身は空のままでいい

```go:environment/rails/Gemfile.lock

```
通常、直接編集するものではなく 「bundle install」コマンドを実行後
Gemがインストールされ、**自動的**にGemfile.lockに**記載してくれる**ため

## docker-compose.ymlを作成、編集
「.yml」はRailsでよく使用されるフォーマット

```go:docker_compose.yml
// docker_compose.ymlのバージョンを表す
version: '3'
services:
  // Railsのコンテナ
  web:
    // docker-compose.ymlと同じディレクトリにあるファイルを
    // 元にイメージを作成して使用することを意味する
    build: .
    // コンテナを実行したときにデフォルトで実行されるコマンドを設定
    // -b でバインドするIPアドレスを設定している
    command: bundle exec rails s -p 3000 -b '0.0.0.0'
    // PC上のディレクトリをコンテナの「/app」ディレクトリにマウントしている
    // PC上のdocker-compose.ymlがおいてあるフォルダが、コンテナ上の
    // 「/app」ディレクトリに共有される
    // つまり、PC上で修正したコードがコンテナにも反映される
    volumes:
      - .:/app
    // コンテナの外部にポート番号を公開するように設定
    // 設定しないとPCからコンテナで動作しているRailsに通信ができない
    // <コンテナ外に公開するポート番号>:<コンテナ内部の転送先ポート番号>
    ports:
      - 3000:3000
    // Railsが起動する前にMySQLサーバーが先に起動するように設定
    depends_on:
      - db
    // 「tty」と「stdin_open」はRailsで「pry」を使用する際に必要な設定
    tty: true
    stdin_open: true
  // MySQLサーバーのコンテナ
  db:
    // app 5.7のバージョンを使用
    image: mysql:5.7
    // 「db-volume」という名前で、PC上に作成した領域を
    // コンテナの「:/var/lib/mysql」にマウントしている
    // 設定しないとコンテナ上でデータが保存される
    // コンテナを削除したらデータが消えるので注意する
    volumes:
      - db-volume:/var/lib/mysql
    // コンテナ内に設定する環境変数を定義している

    // ルートユーザーで使用するパスワードを設定
    environment:
      MYSQL_ROOT_PASSWORD: password
volumes:
```
→「web」と「db」がここでは**サービス名**になる

##Railsアプリを作成して、起動してみる

```ファイルがあるディレクトリ
 docker compose run web rails new . --force --database=mysql
```
「`docker compose run web`」…webサービスのコンテナで、後ろにある
**コマンドを実行するためのコマンド**
「`rails new . --force --database=mysql`」… 「`rails new .`」で
**コンテナ上の作業ディレクトリ**である「/app」上にファイルを**作成**する

「`--force`」オプション…**既存のフィルがあっても上書き**するために使用する
Gemファイル等があっても上書きするために使用する

**build**する

```
docker-compose build
```

buildが完了したら、Railsで使用するDBの設定ファイルを編集する

##database.ymlを編集する

```
vim config/database.yml
```

最低限のパスワードと、ホストの指定を行う

```:config/database.yml
# MySQL. Versions 5.0 and up are supported.
#
# Install the MySQL driver
#   gem install mysql2
#
# Ensure the MySQL gem is defined in your Gemfile
#   gem 'mysql2'
#
# And be sure to use new-style password hashing:
#   http://dev.mysql.com/doc/refman/5.7/en/old-client.html
#
default: &default
  adapter: mysql2
  encoding: utf8
  pool: 5
  username: root
  // MYSQL_ROOT_PASSWORD環境変数の`password`
  password: password
  //MYSQLサーバーのコンテナである`db`
  host: db
```

に編集する

##Dockerを起動する

```
// 現在のディレクトリにある「docker-compose.yml」に基づいて
// コンテナを起動させるコマンド
docker-compose up -d
```
Railsサーバーと、MySQLサーバーのコマンドが起動する
起動しているが、まだ開発環境用のDBが作成されていないので
次で作成する

###コンテナが起動しているか確認する

```
docker-compose ps
```

##DBを作成する

```
docker-compose run web bundle exec rake db:create
```

先程とほぼ同じ
`docker-compose run web bundle exec`以降のコマンドが
コンテナ内で実行されるコマンド

Railsのrakeタスクコマンド、DBが存在しない場合
作成してくれる

##Railsアプリが起動しているか確認する
お約束の
ブラウザでlocalhost:3000にアクセスしてサーバーの起動を確認

無事にあの画面がでていればOK！

##参考記事、動画
https://www.udemy.com/course/rails-kj
https://qiita.com/gold-kou/items/44860fbda1a34a001fc1
https://qiita.com/azul915/items/5b7063cbc80192343fc0