docker-composeを使って一瞬でLAMP+SSL環境を作る方法
この記事を読むと得られる情報
1コマンドで
- Nginx(SSL化用リバースプロキシ)
- MariaDB
- CentOS7
- Apache
- php
のコンテナが下記の簡略図で立ち上がり、gitかなにかでwebアプリコンテンツをDocumentRootに置けば、すぐに使えるようになる。

本稿のレベルとしては
「dockerとdocker-composeが何なのかはなんとなく知ってるけど、あんまり使ったことない人」向けです。
それぞれの基本知識としては下記を斜め読みすれば十分だと思います。
- dockerについて
- docker-composeについて
俺はさっさと環境ができれば、どうだっていいんじゃーって人は
「デプロイ」までで実施できます。
各機能の詳細や、詳細な関係が気になる人は最後まで読んで見てください!
環境用意
CentOS Linux release 7.4.1708 (Core)
下記で示すDockerとdocker-composeのバージョンさえ合ってればなんでもいいです。
macOS High Sierra 10.13.4でも動作確認済みですが、本記事はCentOSでの実施手順です。
Docker version 18.03.0-ce, build 0520e24
# dockerインストール手順
# dockerリポジトリを追加
sudo wget https://download.docker.com/linux/centos/docker-ce.repo
# インストール
sudo yum install docker-ce
# dockerの起動
sudo systemctl start docker
# docekrの自動起動設定
sudo systemctl enable docker
# ユーザーでdockerが使えるようにグループ設定
sudo groupadd docker
sudo gpasswd -a $USER docker
# docker再起動
sudo systemctl restart docker
# バージョン確認
docker -v
> Docker version 18.03.0-ce, build 0520e24
docker-compose version 1.20.1, build 5d8c71b 以上
# docker-composeインストール手順
# 資材ダウンロード
sudo curl -L https://github.com/docker/compose/releases/download/1.20.1/docker-compose-`uname -s`-`uname -m` -o /usr/local/bin/docker-compose
# 実行権限を付与
sudo chmod +x /usr/local/bin/docker-compose
# バージョン確認
docker-compose -v
> docker-compose version 1.20.1, build 5d8c71b
【任意】DDNSへの登録(ドメイン)
SSL化に必要なドメインを取得します。
無料かつ、IPの変化に対応できるDDNSとしておすすめはMyDNSです。
任意のドメインを入手しておいてください。
後述しますが、hogehoge.mydns.jpなど人気なドメインは避けたほうが良いです。
構築
カレントディレクトリは任意ですが、ユーザーディレクトリがいいと思います。
カレントディレクトリに下記のようなファイルを構築します。
# ディレクトリ構成
.
├── db
│ ├── Dockerfile
│ ├── init.d/
│ ├── init.s/
│ ├── my.cnf
│ └── vol/
├── docker-compose.yml
└── web
├── Dockerfile
├── conf
│ └── httpd.conf
├── html/
└── php.ini
docker-compose.yml
docker-compose.ymlはyml形式で書かれたファイルで、名前の通りdocker-composeの設定ファイルです。
ここで各種dockerコンテナ(今回はCentOSとNginx、MariaDB)の設定を記述します。
# docker-composeのバージョン宣言
version: '2'
services:
# MariaDBの設定
maria:
# Dockerfileの場所
build: ./db
# コンテナ名の定義
container_name: maria
# 環境変数の設定 docker runの-eオプションに対応
environment:
# MariaDBのrootユーザーのパスワード
MYSQL_ROOT_PASSWORD: hogehoge
# データ保存場所指定
volumes:
# データベースの永続化を定義
- ./db/vol:/var/lib/mysql
# データベースの初期化スクリプト置き場
- ./db/init.s:/docker-entrypoint-initdb.d
# データベースの初期データ置き場
- ./db/init.d:/var/lib/ram
# 所属するネットワークとIPを指定
networks:
br0:
ipv4_address: 192.168.200.2
# httpdの設定
httpd:
# Dockerfuleの場所
build: ./web
# コンテナ名の定義
container_name: httpd
# データの保存場所
volumes:
# DocumentRootのホスト側とのリンク
- ./web/html:/var/www/html
# 直前の起動コンテナの設定
depends_on:
- maria
# 所属するネットワークとIPを指定
networks:
br0:
ipv4_address: 192.168.200.3
#リバースプロキシの設定
https-portal:
# イメージの定義
image: steveltn/https-portal:1
# ポートフォワーディング
ports:
- '80:80'
- '443:443'
# NATの設定
extra_hosts:
- '"DDNSで取得したDNS":127.0.0.1'
# コンテナ同士の接続
links:
- httpd
# 環境変数の設定
environment:
# 本番用
DOMAINS: '"DDNSで取得したDNS" -> http://httpd'
STAGE: 'production'
# 所属するネットワークとIPを指定
networks:
br0:
ipv4_address: 192.168.200.4
# 新規ブリッチを定義
networks:
br0:
driver: bridge
ipam:
config:
- subnet: 192.168.200.0/24
gateway: 192.168.200.1
db/Dockerfile
# ベースイメージを定義
FROM mariadb:5.5
# my.cnfを定義
COPY ./my.cnf /etc/
web/Dockerfile
# 元とするイメージ名
FROM centos:latest
# 各種ミドルウェア
RUN yum install -y php | true
RUN yum install -y php-mysql | true
RUN yum install -y net-tools | true
RUN yum update -y
# 各種設定ファイルのコピー
COPY ./conf/httpd.conf /etc/httpd/conf/
COPY ./php.ini /etc/
# ポートの解放
EXPOSE 80
# httpdの起動
CMD /usr/sbin/httpd -DFOREGROUND
各種設定ファイル
- db/my.cnf
- 普段のmariaDBで使用してるものを用意
- web/conf/httpd.conf & web/php.ini
- こちらも普段使用しているapacheの設定ファイルと、php.iniファイルを用意
- web/html/*
- デプロイしたいwebアプリの資材をここに入れてください
デプロイ
さて、いよいよコンテナの立ち上げです。
docker-compose.ymlがあるディレクトリまで移り
# コンテナの立ち上げ
docker-compose up -d --build
# 動作の確認
docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
60c73d6a06f2 steveltn/https-portal:1 "/init" 8 hours ago Up 8 hours 0.0.0.0:80->80/tcp, 0.0.0.0:443->443/tcp dockerlamp_https-portal_1
7af11daaa0f9 dockerlamp_httpd "/bin/sh -c '/usr/sb…" 8 hours ago Up 8 hours 80/tcp httpd
ac12e8c7ce8c dockerlamp_maria "docker-entrypoint.s…" 8 hours ago Up 8 hours 3306/tcp maria
となれば、完了!!
取得したドメイン名でアクセスして、アプリの動作を確認してください。
Q&A
- コンテナが正常に起動しない
$ docker-compose logs
で各種コンテナの状況が確認できます
- 証明書の発行時にドメイン上限に引っかかって発行できない
- 今回の証明書はletsencryptを使用してます
- 人気ドメインでの取得場合、証明書の制限で発行できない可能性があります
詳細
ネットワーク関係
序盤に簡単なネットワーク構成を書きましたが実際にはこんな感じ

NginxとmariaDBとCentOSベースのコンテナの3つが起動してます。
NginxとmariaDBは設定内容が簡単なことから分かる通り、そのまま使用しています。
CentOSのコンテナのみweb/Dockerfileでyumを使った初期インストールでApacheやphpを導入しています。
(そこを変更すればpythonだって環境を作ることが可能です)
コンテナ同士はdocker-compose.ymlの最後に記したネットワーク内での相互通信を行っています。
インターネット(外部)との通信はdocker-compose.ymlのNginxの部分で設定した部分(port) で定義しており、
ローカルマシンの対応するポートとポートフォワーディングで通信を行っています。
また今回はlet’s encryptではなくオレオレ証明書でアクセスでアクセスすることも可能です。
既存環境に手を加えずにサクッとHTTPS化する (NAT配下でもok)
さらに、docker-compose.ymlからhttps-portalの設定を全削除して、webでポートフォワーディングを設定すればDDNSも不要になります。
オプションディレクトリの説明
3章で空のディレクトリを複数作りましたが、それぞれ役割があります。
db/init.s
docker-compose.ymlの./db/init.s:/docker-entrypoint-initdb.d
にも書いてありますが
init.sに入れたファイルはmariaのコンテナのdocker-entrypoint-initdb.dにコピーされます。
コンテナ側のdocker-entrypoint-initdb.dというディレクトリは特殊で
ここに入れられたshファイルや、sqlファイルはコンテナ立ち上げ時にアスキーコード順に実行されます。
なので、ここにはDBの初期データを流し込むスクリプトファイルなどを入れます。
db/init.d
docker-compose.ymlの./db/init.d:/var/lib/ram
にも書いてありますが
init.dに入れたファイルはmariaのコンテナの/var/lib/ramにコピーされます。
ここは単純にコピーされるだけなので
init.sで実施されるスクリプトが読みに来るDBのダンプデータなどを入れます。
5-2-3. db/vol
ここはDBのデータそのものが入ります。
テーブルスキームや、カラムの値などが入っています。
ここのデータをコピーしておけばバックアップとして使えます。
ディスカッション
コメント一覧
まだ、コメントがありません