DockerによるPHP開発環境構築（PHP + MySQL + Nginx）

#背景
Dockerを導入したので、早速PHPの開発環境を構築してみようと思い色々調べたことを纏めました。

後半部分はほぼ作業みたいになってしまい、それぞれの意味するところをしっかり理解したら追記したいと思います。

#環境
- `Mac OS Mojave Version 10.14`
- `Docker for Mac`

#Dockerのイメージ
環境構築の前に、Dockerの環境構築イメージを頭に入れておきます。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/310353/1cc1f1a9-80a1-c98e-e692-346b4a194fee.png)


1. まず、Dockerを立ち上げると青枠の<b>Dockerホスト</b>が出来上がります。

2. <b>Dockerホスト</b>の中では、webサーバならNginxかApache、データベースならMySQLかPostgreSQL、プログラミング環境ならPHPやRubyなどを動かすことができます。

3. クラウド上の<b>Dockerレジストリ(DockerHub)</b>の中に、NginxやMySQLなどの<b>Dockerイメージ</b>が保管されているので、それらをダウンロードすると<b>Dockerホスト</b>上に<b>Dockerイメージ</b>として保存されます。
<b>Dockerイメージ</b>は、Dockerfileというもので自作することも可能です。

4. <b>Dockerイメージ</b>を<b>Dockerコンテナ</b>として実行することで、実際に使えるようになります。


これらを冷凍食品に例えるとこんな感じです。

|項目|例|役割|
|:---:|:---:|:---:|
|Dockerレジストリ|冷凍庫|Dockerイメージを公開・共有するコンポーネント|
|Dockerイメージ|冷凍食品|コンテナを動かすためのソフトウェア（土台）|
|Dokcerコンテナ|解凍して食べれる状態の食品|アプリケーションの実行環境|

#Dockerによる環境構築方法
まず、DockerでPHP開発環境を構築する場合、最低限必要となるのはWebサーバ、PHP、データベースの3つです。

次に、これらの必要なものをDockerで用意する方法は大きく分けると2パターンあります。

- `Dockerレジストリ(DockerHub)から1つずつインストールする方法`
- `docker-compose.ymlファイルに記載してまとめてインストールする方法`

筆者はdocker-compose.ymlファイルでまとめてインストールする方が楽で混乱しないと思ったので、この手法を使いたいと思います。

#Docker Compose
docker-compose.ymlファイルでまとめてインストールする際に、<b>Docker Compose</b>と呼ばれるもので一括管理します。（上の図のタコがDocker Composeのイメージになります）

Docker Composeは、複数のDockerコンテナを自動で立ち上げる構成管理ツールになります。Docker本体のインストール時に一緒にインストールされているはずです。（心配な方はコマンドラインで確認してみましょう）

Docker Composeのバージョン情報が表示されれば問題ありません。

```
$ docker-compose version
$ docker-compose version 1.23.2, build 1110ad01
```

#Step
Docker Compose は docker-compose.yml ファイルに書かれた内容に従ってコンテナーを管理しています。
まずはフォルダを1つ用意し、次のようなファイル構造となるよう準備します。あくまで例なので、好きなように変更して結構です。

```
├── docker-compose.yml
├── nginx
│   └── nginx.conf
├── php
│   ├── Dockerfile
│   └── php.ini
├── mysql
│   └── data
└── www
    └── html
        └── index.php
```

## docker-compose.yml
次に、土台となるdocker-compse.ymlを作成します。
Docker Composeは docker-compose.ymlファイルに書かれた内容に従ってコンテナーを管理しています。

```docker-compose.yml
version: '3'
services:
  nginx:
    image: nginx:latest
    ports:
      - 8080:80
    volumes:
      - ./nginx/nginx.conf:/etc/nginx/conf.d/default.conf
      - ./www/html:/var/www/html
    depends_on:
      - php
 
  php:
    build: ./php
    volumes:
      - ./www/html:/var/www/html
    depends_on:
      - db
 
  db:
    image: mysql:5.7
    ports:
      - 13306:3306
    volumes:
      - ./mysql/data:/var/lib/mysql
    environment:
      MYSQL_ROOT_PASSWORD: secret
 
  phpmyadmin:
    image: phpmyadmin/phpmyadmin:latest
    ports:
      - 8888:80
    depends_on:
      - db

```

## nginx/nginx.conf

```nginx/nginx.conf
server {
    listen 80;
    server_name _;
 
    root  /var/www/html;
    index index.php index.html;
 
    access_log /var/log/nginx/access.log;
    error_log  /var/log/nginx/error.log;
 
    location / {
        try_files $uri $uri/ /index.php$is_args$args;
    }
 
    location ~ \.php$ {
        fastcgi_pass php:9000;
        fastcgi_index index.php;    
        fastcgi_param SCRIPT_FILENAME  $document_root$fastcgi_script_name;
        include       fastcgi_params;
    }
}
```
## php/Dockerfile

```php/Dockerfile
FROM php:7.2-fpm
COPY php.ini /usr/local/etc/php/
```

## php.ini
```php.ini
date.timezone = "Asia/Tokyo"
```
## www/html/index.php

```www/html/index.php
<php
phpinfo();
```

## コンテナの起動

1.全てのファイルが用意できたら、`cdコマンド`で作業ディレクトリに移動します。

2.`$ docker-compose up -d`を入力するとPHP、MySQL、Nginxがインストールされます。

3.`$ docker ps`を入力して、コンテナが立ち上がっているか確認。


```
CONTAINER ID        IMAGE                            COMMAND                  CREATED             STATUS              PORTS                                NAMES
1c8d70c32262        nginx:latest                     "nginx -g 'daemon of…"   31 minutes ago      Up 31 minutes       0.0.0.0:8080->80/tcp                 phpproject_nginx_1
c7394112b393        phpmyadmin/phpmyadmin:latest     "/run.sh supervisord…"   31 minutes ago      Up 31 minutes       9000/tcp, 0.0.0.0:8888->80/tcp       phpproject_phpmyadmin_1
73174d360ed4        phpproject_php                   "docker-php-entrypoi…"   31 minutes ago      Up 31 minutes       9000/tcp                             phpproject_php_1
ff496b0a3cdd        mysql:5.7                        "docker-entrypoint.s…"   31 minutes ago      Up 31 minutes       33060/tcp, 0.0.0.0:13306->3306/tcp   phpproject_db_1
e1b4fae8bea7        newdeveloper/apache-php:latest   "/bin/bash /run.sh"      6 hours ago         Up 6 hours          0.0.0.0:32768->80/tcp                apache-php
````

4.ローカルホストにアクセスして、phpinfoが表示されていればOKです。

---補足---
`docker-compose up -d `で実行すると、コンテナをバックグラウンドで起動し、実行し続けた状態になります。
もし停止したい場合は、'$ docker-compose stop'コマンドを使います。

```
$ docker-compose stop
Stopping phpproject_nginx_1      ... done
Stopping phpproject_phpmyadmin_1 ... done
Stopping phpproject_php_1        ... done
Stopping phpproject_db_1         ... done
```

動かしたいときは、`cdコマンド`で作業ディレクトリに移動し、`$ docker-compose up`コマンドを使います、

```
$ docker-compose up
Starting phpproject_db_1 ... done
Starting phpproject_phpmyadmin_1 ... done
Starting phpproject_php_1        ... done
Starting phpproject_nginx_1      ... done
```

#まとめ
今回参考にしたサイトは[こちら](https://php-archive.net/php/docker-php-environment/)。
正直、Dockerがすごいのは分かったものの、よく分からないことも多いのでもっと勉強したい思います。