概要
Docker, Docker Compose を使って、PHP(Laravel) + nginx + MySQL
のLEMP環境
を構築する記事です。
検索するとDockerfileやdocker-compose.ymlの書き方については色んな方が記事を書いてくださっていて、動く環境を作ること自体は難しくありませんでした。
ですが、筆者はひとつコンテナを作っては動作確認していくという過程を経てすごく理解が深まったなと思うので、ファイルの書き方だけでなく動作確認したことやその結果を含めて記事に残しておきたいと思います。
↓ 完成後のリポジトリはこちらです。
全体像
最終的なディレクトリ構成は以下の通りです。
全コンテナを管理するdocker-compose.ymlがトップレベルにあり、同じくトップレベルにあるdockerディレクトリ配下に各コンテナのDockerfileや設定ファイルを置いています。
docker_sample/
├── src // Laravelプロジェクトのソースコード
├── docker
│ ├── app // PHPコンテナ
│ │ ├── Dockerfile
│ │ └── php.ini
│ ├── db // MySQLコンテナ
│ │ ├── Dockerfile
│ │ └── my.conf
│ └── web // nginxコンテナ
│ ├── Dockerfile
│ └── default.conf
└── docker-compose.yml // 全コンテナの管理
早速一つずつコンテナを作っていきます。
PHPのコンテナ(Laravelの開発環境)
まずはLaravelの開発環境を構築するための、PHPのコンテナを作成します。
- docker-compose.ymlへの記述
- PHPコンテナ用のDockerfile
- PHPコンテナ用の設定ファイル(php.ini)
について順に説明します。
docker-compose.yml(PHP)
docker-compose.ymlのうち、PHPコンテナについての記述は以下の通りです。
※docker-compose.ymlはインデントが意味を持つので注意。
version: "3.9"
services:
app: // サービス名
build:
context: .
dockerfile: ./docker/app/Dockerfile
volumes:
- ./src/:/app
-
version:
これはPHPコンテナについてではなく
docker-compose.yml
の先頭に書く設定ですが、Composeファイルのバージョンを表しています。
今回は最新の3.9
を使います。(最新のバージョンは下記の公式サイトを参照)
Compose file -
build:
ビルドコンテキストを指定します。
- context:ビルドコンテキスト(buildを実行する場所)の設定
- dockerfile:buildするDockerfileまでのパス(docker-compose.ymlから見た相対パス)
参考記事: docker-compose.ymlのbuild設定はとりあえずcontextもdockerfileも埋めとけって話 - Qiita
-
volumes:
ホスト側の
./src/
をコンテナ側の/app
にマウントするという意味になります。※ここで
services:
の中に書いているこのvolumes:
はバインドマウント
を行っています。参考記事:Dockerのマウント3種類についてわかったことをまとめる - Qiita
何が起きているかは実際の挙動を見てみた方が分かりやすいと思うので、後ほどまた動作確認します。
Dockerfile(PHP)
Dockerfileはテキストファイルであり、Dockerイメージを作り上げるために実行する命令をこのファイルに書きます。
まず作成するDockerfileの全文がこちらです。
FROM php:8.0-fpm
ENV TZ Asia/Tokyo
RUN apt-get update && \
apt-get install -y git unzip libzip-dev libicu-dev libonig-dev && \
docker-php-ext-install intl pdo_mysql zip bcmath
COPY ./docker/app/php.ini /usr/local/etc/php/php.ini
COPY --from=composer:2.0 /usr/bin/composer /usr/bin/composer
WORKDIR /app
一つずつ説明します。
FROM php:8.0-fpm
FROM
ではイメージをビルドするためのベースイメージを設定します。
書き方は FROM イメージ名:タグ名
です。
ここではDocker HubからPHP公式のイメージをベースとして指定しています。
Php - Official Image | Docker Hub
ENV TZ Asia/Tokyo
ENV
はコンテナ内のサーバー環境変数を設定します。
RUN apt-get update && \
apt-get install -y git unzip libzip-dev libicu-dev libonig-dev && \
docker-php-ext-install intl pdo_mysql zip bcmath
RUN
にはコンテナビルド時に実行するコマンドを書きます。
&&
で複数のコマンドをつなぎ、 \
で改行します。
※ &&
と \
を使うことで複数コマンドを1レイヤーにまとめることができ、公式でもベストプラクティスのTipsとして挙げられています。
Intro Guide to Dockerfile Best Practices - Docker Blog
apt-get update
:インストール可能なパッケージの「一覧」を更新
apt-get -y install
:パッケージをインストール
docker-php-ext-install
:PHPの拡張ライブラリをインストール
※Laravelのインストールや開発に必要な(もしくは便利な)パッケージや拡張ライブラリをインストールしています。
※試しにこれらを全くインストールせず手順を進めてみると、コンテナを起動することはできますが、その後のLaravelプロジェクトを作成する時に大量のエラーに遭遇しました(笑)
COPY ./docker/app/php.ini /usr/local/etc/php/php.ini
ローカルで(後ほど)作成する php.ini
(PHPの設定ファイル)をDockerコンテナ内にコピーします。
書き方は COPY [ローカル側のパス] [コンテナ側のパス]
です。
※ローカル側のパスは、Dockerfileから見てではなくbuildコマンドを実行するディレクトリから見た相対パスです。今回はDocker composeを使ってイメージビルドを行うので、docker-compose.ymlから見た相対パスになっています。
COPY --from=composer:2.0 /usr/bin/composer /usr/bin/composer
Laravelを使うためComposerをインストールします。
この書き方によりマルチステージビルドという方法でインストールされます。
※マルチステージビルドという方法はイメージの軽量化に役立つようです。
公式ドキュメント:Use multi-stage builds
WORKDIR /app
コンテナを起動している時に $ docker-compose exec コンテナ名 bash
というコマンドを実行すると、コンテナの中でbashを実行することができるのですが、 WORKDIR
はその時のカレントディレクトリを指定しています。
設定ファイル(php.ini)
COPY ./docker/app/php.ini /usr/local/etc/php/php.ini
で出てきたPHPの設定ファイル php.ini
を作成します。
作成したファイルの中身がこちらです。
zend.exception_ignore_args = off
expose_php = on
max_execution_time = 30
max_input_vars = 1000
upload_max_filesize = 64M
post_max_size = 128M
memory_limit = 256M
error_reporting = E_ALL
display_errors = on
display_startup_errors = on
log_errors = on
error_log = /var/log/php/php-error.log
default_charset = UTF-8
[Date]
date.timezone = Asia/Tokyo
[mysqlnd]
mysqlnd.collect_memory_statistics = on
[Assertion]
zend.assertions = 1
[mbstring]
mbstring.language = Japanese
こちらの記事の開発用php.iniをまるっとお借りしました。
開発用 / 本番用の設定例と、項目ごとの説明も載っていて面白かったので、ぜひご覧ください。
参考記事:PHP7.4 ぼくのかんがえたさいきょうのphp.ini - Qiita
PHPコンテナを起動する
ここまででPHPのコンテナの準備が出来たので、実際に起動してみます。
docker-sompose.ymlのあるディレクトリで以下のコマンドを実行します。
$ docker-compose up -d --build
-
docker compose up
はdocker-compose.yml
に定義したサービスを起動します。 -
-d
「デタッチド」モードでコンテナを起動します。
(デフォルトは「アタッチド」モードで全てのコンテナログを画面上に表示する。「デタッチド」モードではバックグラウンドで動作する。) -
--build
コンテナの開始前にイメージをビルドします。
(特に変更がない場合はキャッシュが使用される。)
※ $ docker-compose build
→ $ docker-compose up -d
を順に行うのと同じです。
起動したコンテナを確認する
以下のコマンドで起動中のコンテナを一覧で確認することができます。
$ docker-compose ps
NAME COMMAND SERVICE STATUS PORTS
docker_sample-app-1 "docker-php-entrypoi…" app running 9000/tcp
STATUSがrunningになっていれば正常に起動しています。
今はPHPのコンテナしか作っていないので1つだけ表示されていますが、この後nginx, MySQLのコンテナを作り、最終的に3つのコンテナが表示されるようにします。
ここで今作業しているディレクトリの構成を確認してみます。
$ tree
.
├── src // 作成された!
├── docker
│ ├── app
│ │ ├── Dockerfile
│ │ └── php.ini
└── docker-compose.yml
するとdocker-compose.ymlに書いたバインドマウントの以下の部分を受けて、コンテナを起動したときに自動でsrcディレクトリが作成されたことが確認できます。(同様にコンテナ内にもappディレクトリが作成されています。)
volumes:
- ./src/:/app
コンテナの中に入ってみる
コンテナを起動中に以下のコマンドを実行すると、コンテナの中に入ってbashを実行することができます。
$ docker-compose exec app bash
// appの部分はサービス名を指定する
これで今コンテナの中に入れたので、Dockerfileの記述通りにコンテナが作られているか、またPHP・Composer・インストールした拡張機能が使えるか確認していきます。
// Dockerfileの「WORKDIR /app」で指定したカレントディレクトリ通りか確認
[app]:/app$ pwd
/app
// PHPのバージョン確認
[app]:/app$ php -v
PHP 8.0.15 (cli) (built: Jan 26 2022 17:38:36) ( NTS )
Copyright (c) The PHP Group
Zend Engine v4.0.15, Copyright (c) Zend Technologies
// Composerのバージョン確認
[app]:/app$ composer -v
______
/ ____/___ ____ ___ ____ ____ ________ _____
/ / / __ \/ __ `__ \/ __ \/ __ \/ ___/ _ \/ ___/
/ /___/ /_/ / / / / / / /_/ / /_/ (__ ) __/ /
\____/\____/_/ /_/ /_/ .___/\____/____/\___/_/
/_/
Composer version 2.0.14 2021-05-21 17:03:37
// gitのバージョン確認
[app]:/app$ git --version
git version 2.30.2
// インストール済の拡張機能の一覧
[app]:/app$ php -m
[PHP Modules]
bcmath
intl
pdo_mysql
zip
// たくさん出てくるので他は省略
// php.iniがコピー出来ているか確認
[app]:/app$ cat /usr/local/etc/php/php.ini
zend.exception_ignore_args = off
expose_php = on
max_execution_time = 30
max_input_vars = 1000
upload_max_filesize = 64M
post_max_size = 128M
memory_limit = 256M
error_reporting = E_ALL
display_errors = on
display_startup_errors = on
log_errors = on
error_log = /var/log/php/php-error.log
default_charset = UTF-8
[Date]
date.timezone = Asia/Tokyo
[mysqlnd]
mysqlnd.collect_memory_statistics = on
[Assertion]
zend.assertions = 1
[mbstring]
mbstring.language = Japaneseroot@0e3ba825df88
確認できたのでコンテナを抜けます。
$ exit
// もしくは ctrl + d
コンテナの外からコマンドを実行する
上記のコンテナの中で実行したコマンドは、 $ docker-compose exec サービス名 実行したいコマンド
でコンテナの外から実行することもできます。(コンテナが起動中に限る)
バインドマウントの挙動を確認する
コンテナの外からコマンドが実行できるという確認も兼ねて、バインドマウントの動きを見る為、試しに以下のコマンドを実行してみます。
// コンテナ内の/app配下にファイルを作ってみる
$ docker-compose exec app touch sample.php
$ docker-compose exec app pwd
/app
$ docker-compose exec app ls
sample.php
コンテナ内の/app配下にファイルを作成しました。
この/appという場所は、docker-compose.ymlに書いた以下の記述の通りにバインドマウントされています。
volumes:
- ./src/:/app
これにより、プロジェクトディレクトリ配下の/srcにもsample.phpが作成されています。
$ ls src
sample.php
以上より、コンテナ内の /app
に対して行ったことが、プロジェクトの /src
に反映していることが分かりました。
では次に `/src` への変更がコンテナ内の `/app` に対しても反映するか試してみます。
/src/sample.php
をエディタで開いてファイルに hello
と書きこみ、以下のコマンドを実行します。
$ docker-compose exec app cat sample.php
hello
// この時permission errorが出たら権限を変更する
$ sudo chmod -R 777 ./src
するとコンテナ内の ./app/sample.php
も編集されていることがわかります。
このようにバインドマウントにより、ホスト側のディレクトリがコンテナ内へマウント出来ていることも確認できました。
試しに作成したファイルは不要なので消しておきます。
$ rm src/sample.php
nginxのコンテナ(webサーバー)
webサーバーとなるnginxのコンテナを作成します。
PHPコンテナのときと同じく、
- docker-compose.ymlへの記述
- nginxコンテナ用のDockerfile
- nginxコンテナ用の設定ファイル(default.conf)
の流れで説明します。
docker-compose.yml(nginx)
既に作成しているdocker-compose.ymlに、nginxのコンテナについての部分を追記します。
services:
api:
// 中略
web: // サービス名
build:
context: .
dockerfile: ./docker/web/Dockerfile
ports:
- 8081:80
depends_on:
- app
volumes:
- ./src/:/app
解説していきます。
-
build:
・volumes:
ここはPHPコンテナと同様なので説明は省きます。
-
ports:
ホスト側とコンテナ間のポート番号の対応付けを設定します。
書き方はホスト側のポート番号 : コンテナのポート番号
です。※今回ホスト側(自分のPC)は既に他の開発で使っているポートとの兼ね合いで
8081
を使いました。コンテナ側はnginxのデフォルトのポート番号である80
にしています。 -
depends_on:
サービスの起動順序を制御します。
web
のdepends_on
にapp
と書いているので、app
→web
の順に起動するように指定しています。※但しこの記述なしで
$ docker-compose up -d --build
をしてみても私の環境では全く問題なく動きました。が、サービス同士の依存関係を明示的に記すという意味でも書いておくに越したことはないという判断で書いています。※ nginxとphp間でTCPによるfpm接続についてや、
depends_on
オプションについては以下の記事がすごく勉強になったので是非読んでみてください。
参考記事:【docker-compose】depends_onとサービス名解決にまつわるエトセトラ - Qiita
Dockerfile(nginx)
作成するDockerfileの全文はこちらです。
FROM nginx:1.20-alpine
ENV TZ Asia/Tokyo
COPY ./docker/web/default.conf /etc/nginx/conf.d/default.conf
FROM
, ENV
, COPY
の意味はPHPコンテナのDockerfileと同様なので詳しい説明は省略し、このファイルで設定していることを簡単にまとめます。
-
nginx公式のイメージ(Alpineベース)をベースイメージに使用
Nginx - Official Image | Docker Hub
参考記事:Dockerでよく利用されているAlpineは他のLinuxディストリビューションと比べて、どれだけ軽量なのか - プログラミングは芸術だ! -
環境変数のタイムゾーンを設定する
-
nginxの設定ファイル(default.conf)をコンテナ内にバインドマウント
※ちなみにnginxは1.18, 1.20などの偶数バージョンが安定バージョンであり、安定バージョンの使用を推奨されています。
公式ドキュメント:Installing NGINX Open Source
設定ファイル(default.conf)
./docker/web/default.conf
を作成します。
Laravel公式に用意されているnginxの設定例をべースに使います。
Laravel 8.x デプロイ
root
とfastcgi_pass
の設定のみ、このプロジェクトに合わせて書き換えています。
server {
listen 80;
server_name example.com;
root /app/public; // 書き換え
add_header X-Frame-Options "SAMEORIGIN";
add_header X-XSS-Protection "1; mode=block";
add_header X-Content-Type-Options "nosniff";
index index.php;
charset utf-8;
location / {
try_files $uri $uri/ /index.php?$query_string;
}
location = /favicon.ico { access_log off; log_not_found off; }
location = /robots.txt { access_log off; log_not_found off; }
error_page 404 /index.php;
location ~ \.php$ {
fastcgi_pass app:9000; // 書き換え
fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
include fastcgi_params;
}
location ~ /\.(?!well-known).* {
deny all;
}
}
root
リクエストのルートディレクトリです。
root /app/public;
と書いたので、 localhost:8081
(docker-compose.ymlで設定したポート番号)にアクセスすると /app/public
を見に行きます。
fastcgi_pass
FastCGIサーバーのアドレスです。
※FastCGI:Webサーバ上で動くプログラムを一度起動したらしばらく待機させることによって、プログラムの開始と終了にかかる手間を減らし、動きを速くしたりWebサーバの負荷を軽減することができる仕組み。
app:9000;
と書いたので、appコンテナの9000番ポートを指定しています。
nginxコンテナを起動する
nginxのコンテナの準備が出来たので、また実際に起動してみます。
docker-sompose.ymlのあるディレクトリで以下のコマンドを実行します。
$ docker-compose up -d --build
$ docker-compose ps
NAME COMMAND SERVICE STATUS PORTS
docker_sample-app-1 "docker-php-entrypoi…" app running 9000/tcp
docker_sample-web-1 "/docker-entrypoint.…" web running 0.0.0.0:8081->80/tcp
api(PHPのコンテナ)、web(nginxのコンテナ)の2つが起動できました。
またdocker_sample-web-1の PORTS
が 0.0.0.0:8081->80/tcp
となっており、ホスト上の8081番ポートをコンテナの80番ポートへ割り当てられていることも確認できます。
コンテナの動作確認
nginxのバージョンを確認します。
$ docker-compose exec web nginx -v
nginx version: nginx/1.20.2
コンテナの中に入ってみます。
$ docker-compose exec web bash
OCI runtime exec failed: exec failed: container_linux.go:380: starting container process caused: exec: "bash": executable file not found in $PATH: unknown
するとエラーになりました。
Alpineをベースとすると bash
は使えず、 ash
や sh
は使えるようです。
$ docker-compose exec web ash
[web]:/ $ pwd
/
無事コンテナの中に入れました。
webサーバーとしての動作確認
- リクエストに対してファイルを返しブラウザで表示できる
- nginxのコンテナからPHPのコンテナへphpを実行させることができる
上記2点を確認します。
$ mkdir src/public
$ touch src/public/test.php
test.phpを以下のように編集します。
<?php
echo 'test.phpです';
phpinfo();
http://localhost:8081/test.php
にアクセスすると以下のように表示され、webサーバーが正しく動作していることが確認できます。
試しに作成したファイルは不要なので消しておきます。
$ rm -rf src/*
MySQLのコンテナ(データベース)
データベースのMySQLコンテナを作成します。
以下の流れで説明します。
- docker-compose.ymlへの記述
- MySQLコンテナ用のDockerfile
- MySQLコンテナ用の設定ファイル(my.conf)
docker-compose.yml(MySQL)
既に作成しているdocker-compose.ymlに、MySQLのコンテナについての部分を追記します。
services:
// 中略
db: // サービス名
build:
context: .
dockerfile: ./docker/db/Dockerfile
ports:
- 3306:3306
environment:
MYSQL_DATABASE: database
MYSQL_USER: user
MYSQL_PASSWORD: password
MYSQL_ROOT_PASSWORD: password
TZ: 'Asia/Tokyo'
volumes:
- mysql-volume:/var/lib/mysql
volumes:
mysql-volume:
-
build:
・ports:
既出の通りです。
-
environment:
環境変数の設定です。
※名前やDB名・ユーザー名・パスワードは好きなものを設定します。
※実際のプロジェクト管理では、環境変数は.env
に書いて.gitignore
にするなどして、重要な情報が公開されないようにします。- MYSQL_DATABASE:DB名
- MYSQL_USER:ユーザー名
- MYSQL_PASSWORD:パスワード
- MYSQL_ROOT_PASSWORD:ルート権限のパスワード
- TZ:時間設定(Time Zone)
-
volumes:
考え方はPHPやnginxのコンテナ同様ですが、先ほどまではホスト側のディレクトリを書いていたところに
mysql-volume
と書いています。
これによりmysql-colume
という名前で作成した名前付きボリュームとコンテナ内を紐づけています。
Docker Volume
Volume
とは、コンテナを破棄してもデータを永続的に保存できるように、コンテナ外に提供されているデータの保存領域です。
Dockerの管理下でホスト上にストレージ領域を確保しており、Linux なら /var/lib/docker/volumes/
以下にあります。
参考記事:Docker、ボリューム(Volume)について真面目に調べた - Qiita
なぜVolumeが必要なのか?
コンテナが起動している間はDBのレコードは保存された状態が続きますが、例えば以下のようなコマンドでコンテナを新しく作り直したとするとデータベースの情報はゼロに戻ってしまいます。
// コンテナ削除
$ docker-compose down
// コンテナ起動
$ docker-compose up -d
これでは困るのでコンテナを破棄してもデータを残したい、、、というときにVolumesを使ってデータの永続化を行います。
※ボリュームには名前付きボリュームと匿名ボリュームがありますが、通常は管理しやすい名前付きボリュームを使うと良いかと思います。
名前付きボリュームを作成する場合は、データの永続化対象のコンテナに対して volumes:
オプションでバインドマウントを行うだけでなく、以下のようにdocker-compose.ymlのトップレベルでボリューム名を定義します。
volumes:
- mysql-volume:
Dockerfile(MySQL)
作成するDockerfileの全文はこちらです。
FROM mysql:8.0
COPY ./docker/db/my.conf /etc/my.conf
内容を簡単にまとめると、
- 公式のMySQLイメージをベースイメージに使用
Mysql - Official Image | Docker Hub - MySQLの設定ファイル(my.conf)をコンテナ内にバインドマウント
※ここで使用しているイメージではM1 Macでは動作しないという情報が見られました。どうやらOracleのMySQLチームがメンテしている mysql/mysql-server
のイメージだと動作するようです。
mysql-server | Docker Hub
設定ファイル(my.conf)
./docker/db/my.conf
を作成します。
色んな記事で作成されているmy.confを参考にさせていただきながら書きました。
参考記事:【Docker】docker-composeでmysqlのコンテナを立てる
- 文字コード
- タイムゾーン
- ログ
の設定を行っています。
[mysqld]
# character
character_set_server = utf8mb4
collation_server = utf8mb4_0900_ai_ci
# timezone
default-time-zone = SYSTEM
log_timestamps = SYSTEM
# Error Log
log-error = mysql-error.log
# Slow Query Log
slow_query_log = 1
slow_query_log_file = mysql-slow.log
long_query_time = 1.0
log_queries_not_using_indexes = 0
# General Log
general_log = 1
general_log_file = mysql-general.log
[mysql]
default-character-set = utf8mb4
[client]
default-character-set = utf8mb4
MySQLコンテナを起動する
MySQLのコンテナの準備が出来たので、また実際に起動してみます。
docker-sompose.ymlのあるディレクトリで以下のコマンドを実行します。
$ docker-compose up -d --build
$ docker-compose ps
NAME COMMAND SERVICE STATUS PORTS
docker_sample-app-1 "docker-php-entrypoi…" app running 9000/tcp
docker_sample-db-1 "docker-entrypoint.s…" db running 0.0.0.0:3306->3306/tcp
docker_sample-web-1 "/docker-entrypoint.…" web running 0.0.0.0:8081->80/tcp
api(PHPのコンテナ)、web(nginxのコンテナ)、db(MySQLのコンテナ)の3つが起動できました。
コンテナの動作確認
MySQLのバージョンを確認します。
$ docker compose exec db mysql -V
mysql Ver 8.0.28 for Linux on x86_64 (MySQL Community Server - GPL)
※この後Laravelのプロジェクトを作成したら、このDBとLaravelを接続します。
そしてマイグレーションを行ってDBにテーブルを作成してから、MySQLにログインしてDBを使う動作確認をしたいと思います。
Laravelのインストール
Laravelプロジェクトの作成
LEMP環境が構築できたので、Laravelのアプリケーションを作っていきます。
appコンテナに入り、Laravelをインストールします。
$ docker compose exec app bash
[app]:/app$ composer create-project --prefer-dist "laravel/laravel=8.*" .
[app]:/app$ php artisan -v
Laravel Framework 8.81.0
コンテナ内の/app配下にLaravelのプロジェクトが新規作成され、ホスト側の/src配下にも同じくLaravelのプロジェクトが出来ました。
localhost:8081
にアクセスして、ブラウザでもLaravelのウェルカムページが表示できることを確認します。
DB接続
appコンテナ(Laravel)からdbコンテナ(MySQL)へ接続する設定を行います。
Laravelではデータベースへの接続設定を .env
ファイルに定義しているので、 /src/.env
のDBの部分を以下のように修正します。
DB_CONNECTION=mysql
DB_HOST=db // MySQLコンテナのサービス名
DB_PORT=3306
DB_DATABASE=database
DB_USERNAME=root
DB_PASSWORD=passwor
-
DB_HOST
にはMySQLコンテナのサービス名を指定します。 - その他の項目もMySQLコンテナで設定した値(今回はdocker-compose.ymlのenvironmentで定義)と同じ値を指定します。
DBに接続出来ているか確認する為、以下のコマンドを実行してマイグレーションを行います。
$ docker compose exec app bash
[app]:/app$ php artisan migrate
Migration table created successfully.
Migrating: 2014_10_12_000000_create_users_table
Migrated: 2014_10_12_000000_create_users_table (55.42ms)
Migrating: 2014_10_12_100000_create_password_resets_table
Migrated: 2014_10_12_100000_create_password_resets_table (51.11ms)
Migrating: 2019_08_19_000000_create_failed_jobs_table
Migrated: 2019_08_19_000000_create_failed_jobs_table (45.12ms)
Migrating: 2019_12_14_000001_create_personal_access_tokens_table
Migrated: 2019_12_14_000001_create_personal_access_tokens_table (75.74ms)
MySQLを使ってみる
MySQLのコンテナに入ってDBを確認してみます。
$ docker-compose exec db bash
[db]:/$ mysql -u root -p
// パスワードを求められるので入力
[db] mysql> use database;
[db] mysql> show tables;
+------------------------+
| Tables_in_database |
+------------------------+
| failed_jobs |
| migrations |
| password_resets |
| personal_access_tokens |
| users |
+------------------------+
5 rows in set (0.00 sec)
先ほどマイグレーションを実行したので、Laravelのデフォルトで用意されているマイグレーションファイル通りにテーブルが作成されていることが確認できました。
最後に
これでDocker(Docker Compose)を使ったLEMP環境の構築が完了です。
今回作成した環境は非常にシンプルなものなので、業務で使うとなるともっと設定を細やかに行ったり、開発環境・ステージング環境・本番環境それぞれの設定ファイルを用意して設定を切り替えたりといった作業が必要になるかと思いますが、仕組みが分かればあとは全てこの延長にあるのかなと思います。
またいずれ環境ごとの設定ファイル切り替えだったり、あとはNodeのコンテナを使ってNext.jsの環境構築もやってみたいです。
参考記事