Docker for Windowsでローカル開発環境(LAMP)を作るのにどハマリしたので備忘録。

# はじめに
　筆者は普段業務でMacを使用し、ローカル開発環境にはVagrantを用いてPHPの開発を行っています。
この度C#などWindows系の言語も触れたいがために私物開発PCとしてWindowsを導入しました。

　せっかくWindows10 Proにしたので、Dockerに慣れるのも兼ねてVagrant+Virtualboxではなく
Hyper-V+Docker for WindowsでPHPのローカル開発環境を作ってみよう！などと酔狂なことを考えた結果
見事にどハマリしたのでその備忘録としてここに記しておきます。ちなみにQiita初投稿です。

# ※注意
　現段階でまだ理解出来ていないところも多く、下記の点は予めご留意頂けると有り難いです。

- プロセスごとにコンテナに分けてません。1コンテナにLAMP環境押し込めちゃいました。  
　※コンテナごとの連携方法が分かってないです。。
- Dockerfileがよく分からない状態でやったので、ここでは使用していません。  
　※PHPなどのインストールはひたすらyumです。

理解出来た段階で追記するかもです。

# 実行環境
- Windows10 Pro  
※Hyper-Vを使用するので、Homeでは動きません。
- Docker for Windows
- PowerShell  
※不要かもしれませんが、後述するKitematicから呼び出されたのがコレだったので一応。
- GitBash  
※これも不要かもしれませんが。。

# 下準備
## Hyper-Vの設定
　これをやらないと何も始まりません。
こんな設定が必要な段階で既にVagrantより設定が面倒です←

### Hyper-Vを有効にする

```
「スタート」右クリック→「プログラムと機能」→「Windowsの機能の有効化または無効化」
```

「Hyper-V」の項目を探し出して、チェックが入っていなければチェックを入れます。

## Dockerの導入・設定
### インストール
https://docs.docker.com/docker-for-windows/
無難にStable版をインストール。

### Dockerのネットワーク設定をする
　デフォルトのままではコンテナ→外部ネットワークの通信が不可能だそうで、今度はその設定です。
VirtualBoxで言うところの「ホストオンリーネットワーク」というやつですね。
Hyper-Vマネージャーから設定します。
こちらを参考にさせて頂きました。
[Docker for Windows (Hyper-V) を試してみたよ - Qiita](http://qiita.com/arenahito/items/83162f8ce73077cad3c4#%E3%82%B3%E3%83%B3%E3%83%86%E3%83%8A%E3%81%8B%E3%82%89%E5%A4%96%E9%83%A8%E3%83%8D%E3%83%83%E3%83%88%E3%83%AF%E3%83%BC%E3%82%AF%E3%81%AB%E6%8E%A5%E7%B6%9A)

　ちなみに私の環境ではこの設定後にWiFiが繋がらなくなりました。
再起動したら治ったので、同様な場合は再起動を。

### 共有ドライブの設定
　Docker for Windowsをインストールすると、タスクトレイにDockerのクジラアイコンが常駐するようになります。
クジラを右クリックしてやるとメニューが開けます。
Dockerの設定画面はこの中に入っています。

```
クジラ右クリック→「Settings」
```

　共有ドライブの設定をしてしまいましょう。
これを入れておくと、後述のKitematicから共有ボリュームの設定する時にエラーにならなくて済みます。
**ホストPCとコンテナの中でファイルの共有を行う**ための設定です。

```
「Shared Drives」→任意のドライブにチェック
```

私のPCではCドライブしか無いので、Cドライブにチェックを入れました。

## Kitematicをダウンロード
　Kitematicとは、Dockerコンテナの管理をGUIベースで行うことが出来るようになる便利ツールです。
全部が全部GUIでやれるわけではなくて、結局**割とコマンドを打つ羽目になる**のですが、
**後で心折れないためにも**使える所では使っちゃいます。

　なぜか単体では配布していない(Docker Toolboxの一部？)ので、以下の手順で導入します。

```
クジラ右クリック→「Open Kitematic」→アラート画面が出たら「Download」
```

　zipでダウンロードされるので、解凍したらそのフォルダをDockerのフォルダに移動します。
インストール時にパスを変えていなければ恐らく下記のパスになっているはずです。

```
C:\Program Files\Docker\Kitematic
```

ここに置くことで、クジラアイコンから開けるようになります。

# いよいよDocker
## ベースコンテナの導入
　ベースとなるコンテナにはCentOSを使用します。
このCentOSコンテナの中にLAMPを全部押し込んじゃいます。

1. まずはKitematicを立ち上げる
2. 左下「Docker CLI」からPowerShellを呼び出す
3. CentOSイメージをdocker pullしてくる  

```
docker pull centos
```

　※タグを指定しなかったので、タグにはlatestが指定されてCentOS7のイメージがpullされてきます。
4. CentOSイメージをdocker runする  

```
docker run --privileged -itd -p 8080:80 -v ホストPCのプロジェクトパス:/var/www/html --name 任意のコンテナ名 -d centos:latest /sbin/init
```

　※**[privilegedオプションと、行末に/sbin/initを付けるのがミソです。(後述)](#※注意)**
　※**必ず、この段階で「-v」オプションを付けること。ボリュームの指定をしないとフォルダ同期が出来ないみたいです。**
　　これについては下記が分かりやすかったです。
　　[DockerのVolume機能について実験してみたことをまとめます - Qiita](http://qiita.com/namutaka/items/f6a574f75f0997a1bb1d)
　※ポートフォワーディングはKitematicで後付け可。一応最低限80番ポートへのルーティングだけしてみました。  
5. docker psでコンテナが出来上がったことを確認する

```
docker ps
```

## コンテナ内にもろもろインストール
　いちいちPowerShellから`docker exec コンテナID`としなくても、Kitematicから任意のコンテナに対してexec出来ます。
(結局開くのはPowerShellなのですが)

　あとはVagrantでのローカル開発環境構築と同じ要領で、必要なものをインストールしていきます。
ひたすらyum installです。
別記事でLAMP環境構築についてまとめてみました。
[個人的ローカル開発環境(LAMP環境・PHP7.1)構築メモ - Qiita](http://qiita.com/saken649/items/9bfff67c53ee6ba4d6f7)


### ※注意
　ただ単にdocker runするだけだと、LAMP環境構築でsystemctlコマンド使用時に
「Failed to get D-Bus connection: No connection to service manager.」エラーが出ます。

[Failed to get D-Bus connection: No connection to service manager.の対処 - Qiita](http://qiita.com/tukiyo3/items/b24e4dc62de59d4a7570)
上記記事によれば、このエラーを回避するためには、

> - 特権モードにする(--privileged)
> - コンテナで起動されるコマンドは/sbin/initにする

とのことなので、先述の通り**docker runする際はこの2つのオプションを必ず指定**します。
これに行き着くまでが非常に時間掛かりました。。

# 疎通確認
　ここまでで一通りの設定が出来たはずなので、無事繋がっているか確認します。
先程docker runする際に8080番ポートから80番ポートへのルーティングを行ったので、
ブラウザから下記でアクセス出来ます。

```
localhost:8080
```

ホストOSのプロジェクトフォルダにファイルが無ければApacheのトップページが、
ファイルがあればそのトップページが表示されるはずです。

# イメージ化
　必要であればイメージ化してしまいましょう。
docker runするだけでLAMP環境の入ったコンテナがいくらでも作れるはずです。

```
docker commit コンテナ名 lamp71:latest
```

lamp71というイメージ名にしてみました。

# まとめ
　Dockerにそもそもまだ慣れていないこともあり、ここまで構築するだけで非常に時間が掛かってしまいました。
もう少し上手く出来れば、Vagrant以上に手軽なローカル開発環境が構築出来るのでは？というのが所管です。
…そもそもDockerの使い方としてこれ合ってるのか？というのはありますが。

　ただ、せっかく純正でHyper-Vという環境がWindowsには入っているので、それを活用出来るという意味では試みた甲斐はありました。
非常に疲れましたが。

# TODO
- Netbeansと連携してのコーディングが上手くいくか  
　※9000番ポートさえポートフォワードすればデバッガも使えるのか
- Dockerfileの有効活用
- 1コンテナに全部押し込めないで、プロセスごとにコンテナ化する