■目次
Docker概要Docker for MacDocker for Windows(Windows10 Home では使用不可)Docker Toolboxイメージの利用(Apache + PHP 環境の構築)イメージを作成イメージをファイルとして保存イメージの連携(Apache + PHP + MySQL 環境の構築)Docker Composeデータベースの永続化読み書きの制限フォルダ共有で一部を除外古い通信方法Docker Compose と Dockerfile の併用Docker Compose の内容を一部上書き同一ネットワークの他端末からのブラウザアクセス現状のまとめコマンドまとめその他の環境構築例Cronでの定期実行Laradockによる開発環境構築WordPressCentOSでDockerを使用するEC2でDockerを使用するホストOSとコンテナで相互にファイルを読み書き(Linux環境)メモ
■Docker概要
コンテナ型のアプリケーション実行環境 当初は開発環境やテスト環境における利用が多かったが、 現在ではパブリッククラウドからオンプレミスシステムまで、さまざまなシーンで急速に普及しつつある DockerはLinuxの1プロセスとして動作するが、名前空間やリソースは他のプロセスやコンテナから隔離して扱われる そのため、コンテナ内のアプリケーションから見ると独立したコンピュータ上で実行されているかのようになる 「namespace」「cgroups」「仮想NIC」といった、既存のLinuxの技術を組み合わせて実現している Vagrantでは「Linux環境自体を一から構築して使う。扱いは通常のLinuxサーバに近い」という方針になるが、 Dockerでは「必要なイメージを組み合わせて環境を構築する。使い捨ての環境を手軽に導入できる」という方針になる Dockerは軽量なテキストで環境を管理できるので、gitなどでの配布が容易 また一般的なApache+PHP以外、例えばnginx環境を各々が作成する場合も同様に管理できる (Windowsにnginxをインストールする方法を調べて…とする必要がない) ただし最初にcomposeを作成する必要はある Dockerについて基本から最近追加された機能までまとめ - Qiita https://qiita.com/yuki_ycino/items/b94ae2bf7d78685cd6f5 Docker入門(第一回)〜Dockerとは何か、何が良いのか〜 | さくらのナレッジ https://knowledge.sakura.ad.jp/13265/ 超入門Docker:第1回 Dockerとは - @IT http://www.atmarkit.co.jp/ait/articles/1701/30/news037.html 知らぬはエンジニアの恥。今さら聞けない【コンテナ/仮想化技術】11選 - paiza開発日誌 http://paiza.hatenablog.com/entry/2014/10/21/%E7%9F%A5%E3%82%89%E3%81%AC%E3%81%AF%E3%82%A8%E3%83%B3%... 原理原則で理解するDocker - Qiita https://qiita.com/tajima_taso/items/28938415846dcc2e83ff Linux コンテナの内部を知ろう / OSC 2018 Kyoto - Speaker Deck https://speakerdeck.com/tenforward/osc-2018-kyoto コンテナ技術入門 - 仮想化との違いを知り、要素技術を触って学ぼう - エンジニアHub|若手Webエンジニアのキャリアを考える! https://employment.en-japan.com/engineerhub/entry/2019/02/05/103000 入門 Docker https://y-ohgi.com/introduction-docker/ いまさらDockerに入門したので分かりやすくまとめます - Qiita https://qiita.com/gold-kou/items/44860fbda1a34a001fc1
■Docker for Mac
Windowsよりも、Macの方が簡単にインストールできるはず 【初心者向け】MacにDockerを手軽にインストールする方法! | Aprico https://aprico-media.com/posts/2375 DockerをMacにインストールする(更新: 2019/7/13) - Qiita https://qiita.com/kurkuru/items/127fa99ef5b2f0288b81 Macならではな問題はあるみたいなので注意 「Mac版は重い」と言われているみたい Docker for Macでは定期的にdisk imageをお掃除する必要がある - モヒカンは正義 https://blog.pinkumohikan.com/entry/cleanup-docker-disk-image
■Docker for Windows(Windows10 Home では使用不可)
Windows管理者のためのDocker入門:無償の「Docker for Windows」で手軽にLinuxコンテナを利用する (1/2) - @IT http://www.atmarkit.co.jp/ait/articles/1609/01/news053.html https://docs.docker.com/docker-for-windows/install/ の「Get Docker for Windows (Stable)」からDockerをダウンロード&実行 …と思ったが、いきなりエラーになってインストールできない 俺のDocker - Windows10にインストール - Qiita https://qiita.com/Ogaaaan/items/99fe54f052ca450889f7 Windows10 Home では使えない。Professional にする必要がある Homeの環境は多そうなので、Docker for Windows は使いづらいかも
■Docker Toolbox
Windows10にDockerでLAMP環境を構築する - Qiita https://qiita.com/kamonamban/items/e0150a2a7a4d28db10c4 Windows10マシンにDocker Toolbox を入れて個人用の開発環境を作る - Qiita https://qiita.com/osuo/items/99a2b7413ce75f8217be Docker Toolboxのインストール:Windows編 - Qiita https://qiita.com/maemori/items/52b1639fba4b1e68fccd Docker Toolbox だと、Windows10 Home でも使える Docker Toolbox は Docker 環境を簡単に構築するためのインストーラらしい ■インストール Docker Toolboxを使ってみる | GWT Center https://www.gwtcenter.com/using-docker-toolbox を参考にインストール まずは以下からDockerの最新版(DockerToolbox-19.03.1.exe)をダウンロード&インストール Releases - docker/toolbox https://github.com/docker/toolbox/releases Welcome画面が表示されるので、確認してNext インストール先が表示されるので、確認してNext コンポーネントの追加が表示されるので、確認してNext 追加作業について表示されるので、「Install VirtualBox with NDIS5 driver[default NDIS6]」にチェックを入れてNext インストール内容を確認してInstall Finishをクリックして完了 Docker Toolboxのインストール:Windows編 - Qiita https://qiita.com/maemori/items/52b1639fba4b1e68fccd インストールは主にこのページを参考にした ■インストールエラーメモ(2019年8月) あらかじめVirtualBox6.0をインストールしていたが、Docker起動時に以下のエラーになった Error setting up host only network on machine start: The host-only adapter we just created is not visible. This is a well known VirtualBox bug. You might want to uninstall it and reinstall at least version 5.0.12 that is is supposed to fix this issue Looks like something went wrong in step ´Checking status on default´... Press any key to continue... 5.0.12 なら動作するようだが、いったんVer5の最終版である VirtualBox-6.0.10-132072-Win.exe をダウンロード&インストール そうするとDockerを起動できるようになった。Vagrantも起動できる ■インストールエラーメモ(2018年) インストールが完了するとVirtualBoxが5.2になっていた バージョン問題でVagrantが起動しなくなった Dockerも起動途中でエラーになる VirtualBoxを5.1に戻すと、VagrantもDockerも起動するようになった (ただしその後のWindowsアップデートの影響で、5.1では動かなくなったので5.2に上げた が、環境によっては 5.1.30 でないと動かない。などがあり謎) Kitematic (Alpha) はエラーになって起動しなかった(DockerのGUI) 起動後、もともとインストールしていた Oracle VM VirtualBox が起動しなくなった …が、Windowsを再起動すると、再度起動するようになった いったん放置 ■起動 Docker Quickstart Terminal を起動 コンソールが開いて処理が始まった 数分で完了し、コンソールが入力待ち状態になった この時点で、再度「Oracle VM VirtualBox」を起動させると、 新たに「default」サーバが追加されて起動中になっていた 「Dockerを起動=VirtualBoxでDocker用の仮想マシンを起動」となっているみたい $ docker run hello-world Unable to find image 'hello-world:latest' locally … 初回実行時はイメージがダウンロードされる latest: Pulling from library/hello-world b04784fba78d: Pull complete Digest: sha256:f3b3b28a45160805bb16542c9531888519430e9e6d6ffc09d72261b0d26ff74f Status: Downloaded newer image for hello-world:latest Hello from Docker! … 2回目からはここからの表示となる This message shows that your installation appears to be working correctly. 〜略〜 動作確認コマンドを試すと、正常に動いているみたい $ docker images REPOSITORY TAG IMAGE ID CREATED SIZE hello-world latest 725dcfab7d63 2 weeks ago 1.84kB $ docker-machine ls NAME ACTIVE DRIVER STATE URL SWARM DOCKER ERRORS default * virtualbox Running tcp://192.168.99.100:2376 v17.06.0-ce イメージとマシンが追加されている
■イメージの利用(Apache + PHP 環境の構築)
ベースとなるイメージが、Docker公式イメージとして利用できる Apacheやnginxなど、よく使われるものはたいてい揃っている(公式以外のイメージもある) Docker Hubのオフィシャルイメージを使ったLAMP環境(Apache+PHP+MySQL)構築 - Qiita https://qiita.com/naga3/items/be1a062075db9339762d ■Apache+PHPのイメージを取得 $ docker run -d php:5.6-apache … PHP+ApacheのイメージをDocker Hubから取得し、バックグラウンド(-d)でコンテナを起動 $ docker images … 取得したイメージ一覧を表示 $ docker ps … 起動しているコンテナ一覧を表示 「-d」を指定しない場合、フォアグラウンドで起動される この場合、プロセスの標準入出力・標準エラーをコンソールに出力する ■ブラウザで確認 $ docker run -p 80:80 -d php:5.6-apache … ホストの80番ポートとコンテナの80番ポートを結びつけて、コンテナを起動 $ docker ps … 起動しているコンテナ一覧を表示 $ docker-machine ip … dockerのアドレスを確認 192.168.99.100 ブラウザで以下にアクセスし、「403 Forbidden」が表示されれば成功 http://192.168.99.100/ ■コンテナを削除する場合 $ docker ps … コンテナのIDを確認 CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 06256413da0f php:5.6-apache "docker-php-entryp..." 14 minutes ago Up 14 minutes 0.0.0.0:80->80/tcp thirsty_bardeen 957ba4371700 hello-world "/hello" 38 minutes ago Exited (0) 38 minutes ago vigorous_colden $ docker rm -f 06256413da0f … ID「06256413da0f」のコンテナを削除する場合 $ docker rm -f $(docker ps -a -q) … すべてのコンテナを削除する場合 ■イメージを削除する場合 $ docker images … イメージのIDを確認 REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE docker-whale latest 2f37bab81128 About a minute ago 274.1 MB hello-world latest 0a6ba66e537a 2 weeks ago 960 B $ docker rmi 2f37bab81128 … ID「2f37bab81128」のイメージを削除する場合 ■コンテンツを作成 $ docker run --name php -p 80:80 -d php:5.6-apache … コンテナに「php」という名前を付けて起動 $ docker exec -it php bash … phpコンテナのターミナルに接続 # echo '<?php phpinfo();' > index.php … index.php を作成(初期状態ではviはインストールされていない) ブラウザで以下にアクセスし、phpinfoが表示されれば成功 http://192.168.99.100/ # exit $ docker rm -f $(docker ps -a -q) … 確認できたら削除 docker exec -itって実際は何をしてるの?【90日目】 - エンジニアのひよこ_level10 https://www.nyamucoro.com/entry/2018/01/11/224932 ■フォルダ共有(C:\Users 配下を対象にする) ※Windows側とファイルを共有 Vagrantとは違い、コンテナを終了させるとデータも初期化されるため、データ保持のためにも 以下、作業フォルダが C:\Users\refirio であるとする docker\test\code\index.php を作成し、以下の内容を記述
<?php phpinfo() ?>
$ docker run --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:5.6-apache … docker\test\code と /var/www/html を共有 $ docker exec -it php bash … phpコンテナのターミナルに接続 # ls /var/www/html … 同期されたファイルを確認 # exit ブラウザで以下にアクセスし、phpinfoが表示されれば成功 http://192.168.99.100/ $ docker rm -f $(docker ps -a -q) … 確認できたら削除 「$PWD」は現在のフォルダを表す $PWD/docker/test/code:/var/www/html をフルパスで指定する場合、以下のようにする。相対パスでは指定できないみたい /c/Users/refirio/docker/test/code:/var/www/html ■フォルダ共有(C:\Users 配下以外を対象にする) C:\Users 配下以外をフォルダ共有対象にして起動しようとすると、以下のようなエラーになる ERROR: for php Cannot start service php: oci runtime error: container_linux.go:262: starting container process caused "chdir to cwd (\"/var/www/html\") set in config.json failed: no such file or directory" C:\Users 配下以外を対象にしたい場合、マウントの指定を行う必要がある ここでは ・Docker用のマシン名は「default」である ・C:\localhost\home\test\public_html\docker を作業フォルダにする という場合を想定する Dockerを起動させている場合、「Oracle VM VirtualBox マネージャ」で「default」の電源をオフにしておく VboxManageでVirtualBox共有フォルダを追加する (初回のみ実行する) >cd C:\Program Files\Oracle\VirtualBox >VBoxManage sharedfolder add default --name data --hostpath "C:\localhost\home\test\public_html\docker" 「Docker Quickstart Terminal」を起動し、マウントを行う (Dockerを起動させるたび実行する) docker-machine ssh default 'sudo mkdir -p /c/localhost/home/test/public_html/docker' docker-machine ssh default 'sudo mount -t vboxsf -o uid=0,gid=0 data /c/localhost/home/test/public_html/docker' 以降は通常どおりの手順で起動できる Dockerにホストのフォルダをマウントしたい! - Qiita https://qiita.com/dojineko/items/f623894ef2436bef890e
■イメージを作成
■イメージを作成(commitコマンド) ※実際にコンテナに対して行った操作内容をもとに、イメージを作成する $ docker run --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:5.6-apache $ docker exec -it php bash … phpコンテナのターミナルに接続 # touch /root/test1.txt … テストファイルを作成しておく # touch /root/test2.txt # exit $ docker diff php … コンテナ「php」内の差分を表示(テストファイルの存在を確認する) $ docker commit php php:create_file … コンテナ「php」のイメージを「php:create_file」という名前で作成 $ docker run --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:create_file … 作成したイメージから起動 $ docker exec -it php bash … phpコンテナのターミナルに接続 # ls /root … テストファイルを確認する $ docker rm -f $(docker ps -a -q) … 作成済みのコンテナをいったん削除 ■イメージを作成(buildコマンド) ※コンテナへの操作内容をDockerfile(テキストファイル)に記載し、それをもとにイメージを作成する ※Dockerfileさえ渡せば、他の人も同じ環境を再現できる ※操作内容が明確になり、gitで変更履歴を管理することもできるため、原則としてこちらの方法を推奨 $ docker images … 上で作成したイメージのIDを確認 $ docker rmi 9dbd220d50c7 … 削除しておく docker\php_create_file\Dockerfile … Dockerfileを作成
FROM php:5.6-apache RUN touch /root/test1.txt RUN touch /root/test2.txt
$ docker build -t php:create_file docker/php_create_file … Dockerfileをもとに、新しいイメージをビルド $ docker images … 作成されたイメージ(custom)を確認 $ docker run --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:create_file … 作成したイメージから起動 $ docker exec -it php bash … phpコンテナのターミナルに接続 # ls /root … テストファイルを確認する $ docker rm -f $(docker ps -a -q) … 作成済みのコンテナをいったん削除
■イメージをファイルとして保存
$ docker save php:create_file > docker/images/php_create_file.tar … 「php:create_file」イメージを「php_create_file.tar」として保存 $ docker images … 上で作成したイメージのIDを確認 $ docker rmi 0515d11a2846 … 削除しておく $ docker load < docker/images/php_create_file.tar … 保存したイメージを読み込む $ docker images … 読み込んだイメージを確認
■イメージの連携(Apache + PHP + MySQL 環境の構築)
■MySQLのイメージを取得 ※Apache+PHPのイメージにMySQLをインストール …という方法でも構築できるが、Dockerの場合は一般的に「Apache+PHPのイメージとMySQLのイメージを取得し、連携させる」のようにする $ docker run --name mysql -e MYSQL_ROOT_PASSWORD=pass -d mysql:5.7 … MySQLのパスワードを「pass」にして起動 $ docker exec -it mysql bash … mysqlコンテナのターミナルに接続 # mysql -u root -p … MySQLに接続 $ docker rm -f $(docker ps -a -q) … 確認できたら削除 「MYSQL_ROOT_PASSWORD」は環境変数と呼ばれるもの。これに値をセットすることで、コンテナに設定の指定を行うことができる 環境変数は、コンテナのターミナルに接続して「env」と入力すれば一覧表示できる 起動直後にMySQLにログインしようとすると、以下のエラーになることがある ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/var/run/mysqld/mysqld.sock' (2) 何度か試していると以下のエラーに変わることがある ERROR 1045 (28000): Access denied for user 'root'@'localhost' (using password: YES) さらに何度か試しているとログインできた。その後は普通にアクセスできる MySQLが完全に起動するまでタイムラグがあるみたい。焦らずに1〜2分程度待つ Dockerの公式MySQLイメージの使い方を徹底的に解説するよ - DQNEO起業日記 http://dqn.sakusakutto.jp/2015/10/docker_mysqld_tutorial.html ■PHPとMySQLの連携(準備) ※Apache+PHPのイメージに、MySQLを扱うためのライブラリを追加する それを新しいイメージとして保存する docker\test\php\Dockerfile … Dockerfileを作成
FROM php:5.6-apache RUN apt-get update && \ docker-php-ext-install pdo_mysql mysqli mbstring
$ docker build -t php:custom docker/test/php … Dockerfileをもとに、新しいイメージをビルド $ docker images … 作成されたイメージ(custom)を確認 docker/test/php をフルパスで指定する場合、以下のようにする。フォルダ共有のときとはルールが違うので注意 C:/Users/refirio/docker/test/php ■PHPとMySQLの連携 ※ネットワークを作成し、そこに参加させることでコンテナを連携させることができる ※PHPコンテナ起動時に「--link mysql:mysql」のように指定することで、コンテナを連携させることもできる。が、それは古い方法で非推奨 $ docker network ls … ネットワークを確認。はじめは3つ NETWORK ID NAME DRIVER SCOPE 620a2ccffb63 bridge bridge local 8b789d2d1514 host host local 16b9ed4aa1c6 none null local $ docker network create my_network … ネットワーク「my_network」を作成 $ docker network ls … ネットワークの追加を確認 NETWORK ID NAME DRIVER SCOPE 620a2ccffb63 bridge bridge local 8b789d2d1514 host host local 2234c63a488d my_network bridge local 16b9ed4aa1c6 none null local $ docker run --net my_network --name mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 … ネットワークを指定してMySQLコンテナを起動 MySQLのパスワードは「pass」にして、データベース「test」を作成する $ docker run --net my_network --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:custom … ネットワークを指定してPHPコンテナを起動 $ docker exec -it php bash … phpコンテナのターミナルに接続 $ exit $ docker exec -it mysql bash … mysqlコンテナのターミナルに接続 $ mysql -u root -p … MySQLに接続 mysql> show databases; … testデータベースを確認(「MYSQL_DATABASE=test」によって自動作成されている) mysql> create database test; … 別途データベースを作成する場合 mysql> exit; /c/Users/refirio/docker/test/code(/var/www/html)内に適当なデータベース管理ツールを設置し、テーブルを作成&データ登録&表示をテスト http://www.php-labo.net/download/new/db_admin/ の場合、以下の接続情報でアクセスできた
define('HTTP_URL', 'http://192.168.99.100/db_admin/'); define('ADMIN_PASSWORD', '1234'); define('DATABASE_TYPE', 'mysql'); define('DATABASE_HOST', 'mysql'); define('DATABASE_PORT', ''); define('DATABASE_USER', 'root'); define('DATABASE_PASSWORD', 'pass'); define('DATABASE_CHARSET', ''); define('DATABASE_NAME', 'test');
以下で登録テスト
CREATE TABLE address( no INT, name VARCHAR(80), tel VARCHAR(80) ); INSERT INTO address(no, name, tel) VALUES(1, '山田太郎', '090-1234-5678'); INSERT INTO address(no, name, tel) VALUES(2, "山田花子", "090-2345-6789"); SELECT * FROM address;
※DATABASE_CHARSETを指定すると、データ登録時に 「Incorrect string value: '\xE5\xB1\xB1\xE7\x94\xB0...' for column 'name' at row 1」 のエラーになった $ docker ps … コンテナを確認する場合 $ docker rm -f $(docker ps -a -q) … コンテナを削除する場合 ■次回起動時 以下で起動する フォルダ共有している以外のデータは削除されているので、テーブルの作成などは都度必要 $ docker run --net my_network --name mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 $ docker run --net my_network --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:custom 以下でアクセスできる http://192.168.99.100/ http://192.168.99.100/db_admin/
■Docker Compose
docker run で起動する場合、一度に起動すべきコンテナの数が多くなると管理しづらくなるので、Docker Compose で管理するといい これなら依存管理の手間が無くなり、さらに起動コードや関連ファイルを丸ごとGitで管理することもできる 当初はシェルスクリプトを作成するなど独自に対応する必要があったが、 公式に手順が用意されたので人によっての方法の差異を防げるようになった docker-compose.yml の現在のバージョンは3なので、「version: '3'」と指定する docker-composeを使うと複数コンテナの管理が便利に - Qiita https://qiita.com/y_hokkey/items/d51e69c6ff4015e85fce ■ファイルの準備 C:\Users\refirio\docker\ 内に以下を作成するとする (PHP+MySQLの環境を作る例) compose_test\html\index.php
<?php phpinfo() ?>
compose_test\docker\mysql\my.cnf
[mysqld] character-set-server=utf8
compose_test\docker\docker-compose.yml
version: '3' networks: my_network: services: mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf environment: MYSQL_ROOT_PASSWORD: pass MYSQL_DATABASE: test networks: - my_network image: mysql:5.7 php: container_name: php volumes: - ..:/var/www ports: - 80:80 networks: - my_network image: php:custom
■起動 各ファイルを用意できたら以下で起動する $ cd /c/Users/refirio/docker/compose_test/docker $ docker-compose up … docker-compose.ymlをもとに起動 ログが以下でストップするが、こういうものみたい [Note] Beginning of list of non-natively partitioned tables [Note] End of list of non-natively partitioned tables ブラウザから http://192.168.99.100/ にアクセスすると、以下のようなアクセスログが表示される php | 192.168.99.1 - - [16/Dec/2017:08:56:09 +0000] "GET / HTTP/1.1" 200 24541 "-" "Mozilla/5.0 以下略 Ctrl+C で終了できるが、コンテナも終了される 「docker exec -it php bash」のように接続したければ、バックグラウンドで起動する必要がある ■起動(バックグラウンド) $ cd /c/Users/refirio/docker/compose_test/docker $ docker-compose up -d … docker-compose.ymlをもとにバックグラウンドで起動 $ docker ps … コンテナを確認 $ docker exec -it php bash … phpコンテナのターミナルに接続 $ exit $ docker exec -it mysql bash … mysqlコンテナのターミナルに接続 $ mysql -u root -p … testデータベースを作成 mysql> create database test; mysql> exit; $ exit /c/Users/refirio/docker/compose_test/code(/var/www/html)内に適当なデータベース管理ツールを設置し、テーブルを作成&データ登録&表示をテスト http://www.php-labo.net/download/new/db_admin/ の場合、以下の接続情報でアクセスできた
define('HTTP_URL', 'http://192.168.99.100/db_admin/'); define('ADMIN_PASSWORD', '1234'); define('DATABASE_TYPE', 'mysql'); define('DATABASE_HOST', 'mysql'); define('DATABASE_PORT', ''); define('DATABASE_USER', 'root'); define('DATABASE_PASSWORD', 'pass'); define('DATABASE_CHARSET', ''); define('DATABASE_NAME', 'test');
$ docker-compose down … コンテナを終了 $ docker rm -f $(docker ps -a -q) … 「docker rm」でも終了できる
■データベースの永続化
マイグレーションやシーダーで管理するとオーバーヘッドが大きくなりすぎる …という場合、データベースもフォルダ共有の対象にすればデータを保持できる ※後述の「トラブル代替案」ように、フォルダ共有ではなくデータボリュームを使う方が良さそう フォルダ共有だと、環境によっては正しく動作しなかった ※docker-compose.ymlでrootパスワードなどを指定している場合、変更しても永続化済みのデータには影響しない つまり「何故かパスワードの変更が反映されない」となるので注意 手動でパスワードなどを変更するか、永続化済みのデータを初期化するなどする ※データベースを永続化していると、MySQLコンテナが完全に起動するまでの時間が短くなっているかも? 諸々のデータ作成が短縮できるから…かもしれない ■docker run の場合 -v $PWD/docker/test/data:/var/lib/mysql を追加して起動する /var/lib/mysql を同期すれば、MySQLのデータを保持できる /docker/test/data フォルダはあらかじめ作成しておく $ docker run --net my_network --name mysql -v $PWD/docker/test/data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 $ docker run --net my_network --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:custom ■Docker Compose の場合 - ./database:/var/lib/mysql を追加して起動する。意味は上と同じ compose_test\docker\docker-compose.yml
version: '3' networks: my_network: services: mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf - ./database:/var/lib/mysql environment: MYSQL_ROOT_PASSWORD: pass MYSQL_DATABASE: test networks: - my_network image: mysql:5.7 php: container_name: php volumes: - ..:/var/www ports: - 80:80 networks: - my_network image: php:custom
■トラブル 2018/01/06 にWindowsアップデートするとDockerが起動しなくなった 再インストールで起動するようになったが、データベースの永続化ができないようになっていた Composeを使う使わないにかかわらず永続化できず、MariaDBの場合でも同じ 「-d」なしで起動すると以下のようなエラーを確認できるが、原因不明のまま解決せず Windows側で権限管理やファイルシステムの仕様が変更されたとか?
$ docker run --name mysql -v $PWD/docker/test/data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test mysql:5.7 Initializing database 2018-01-06T17:47:41.143661Z 0 [Warning] TIMESTAMP with implicit DEFAULT value is deprecated. Please use --explicit_defaults_for_timestamp server option (see documentation for more details). 2018-01-06T17:47:41.150773Z 0 [Warning] Setting lower_case_table_names=2 because file system for /var/lib/mysql/ is case insensitive 2018-01-06T17:47:41.627330Z 0 [ERROR] InnoDB: Operating system error number 22 in a file operation. 2018-01-06T17:47:41.627674Z 0 [ERROR] InnoDB: Error number 22 means 'Invalid argument' 2018-01-06T17:47:41.628023Z 0 [ERROR] InnoDB: File ./ib_logfile101: 'aio write' returned OS error 122. Cannot continue operation 2018-01-06T17:47:41.628357Z 0 [ERROR] InnoDB: Cannot continue operation.
次の手段へ データはbusyboxに保存するのが定番らしいので試す $ docker run --net my_network --name storage -v /var/lib/mysql -d busybox $ docker run --net my_network --name mysql --volumes-from storage -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 とすればmysqlのデータをbusyboxに保存できる が、mysqlコンテナを再起動してもデータは消えないが、busyboxを再起動するとデータが消える よってbusyboxからエクスポート&インポートする必要があるが、それだとmysqlをデータ同期無しで使っている状態と変わらない 次の手段へ コンテナとローカルでデータ転送ができるらしいので試す 以下のようにすればデータ転送ができる コンテナからローカルへ $ docker cp mysql:/var/lib/mysql /Users/refirio/docker/backup … 絶対パスの場合 $ docker cp mysql:/var/lib/mysql ./docker/backup … 相対パスの場合 ローカルからコンテナへ $ docker cp /Users/refirio/docker/backup mysql:/var/lib/mysql … 絶対パスの場合 $ docker cp ./docker/backup mysql:/var/lib/mysql … 相対パスの場合 が、ローカルからコンテナに転送すると所有者がrootになる。chownで所有者を変更してもmysqlからは読み込めなかった 権限なども調整が必要かも 非常に面倒なので、phpMyAdminのようなツールでエクスポート&インポートする方が現実的 つまりは実質、データベースは永続化せずに作業する状態となり、かなり面倒 ■トラブル代替案 ホストの特定のパスではなく、データボリュームになら保存できた むしろ、ファイルシステムや権限の問題を回避するためにも、データボリュームを使う方がいいみたい データボリュームに保存したデータベースをバックアップしたければ、phpMyAdminなどのツールを使う dockerコマンドから起動する場合(「mysql_data」に保存) $ docker volume ls ... ボリュームを確認 $ docker volume create --name mysql_data ... 明示的に作成できるが省略可 $ docker run --net my_network --name mysql -v mysql_data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 $ docker exec -it mysql bash $ mysql -u root -p Docker Compose から起動する場合、以下のように指定する(「compose_mysql_data」に保存する場合)
services: mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf - compose_mysql_data:/var/lib/mysql
ボリュームの削除は以下のようにする $ docker volume ls ... ボリュームを確認 $ docker volume rm compose_mysql_data ... ボリュームを削除 Dockerのデータ永続化関連について - Qiita https://qiita.com/onokatio/items/fcc9f8f94f8533bb030a dockerのデータボリュームとそのバックアップ方法 - Qiita https://qiita.com/74th/items/41393f506d223850f2c3 Docker Data Volume を理解する - Carpe Diem http://christina04.hatenablog.com/entry/2016/05/04/134323
■読み書きの制限
以下のように「:ro」を付けてボリュームを指定すると、読み込み専用(Read-Only)になる - ..:/var/www:ro 以下のように「:rw」を付けてボリュームを指定すると、読み書き可能(Read-Write)になる - ./database:/var/lib/mysql:rw
■フォルダ共有で一部を除外
以下のようにすれば、共有の除外になるみたい プログラムはフォルダ共有したいが、PHPのvenderは各々の環境で作らせたい。のような場合に活用できそう
volumes: - ./server:/home/app/nodeapp - /home/app/nodeapp/node_modules - www:/home/app/nodeapp/out
Dockerでnginx+node.jsのSPA構成を試す - Qiita https://qiita.com/KeitaMoromizato/items/bfc3e22dae47211eff4f
■古い通信方法
※PHPコンテナ起動時に「--link mysql:mysql」のようにMySQLコンテナを指定することで、コンテナを連携させることができる が、それは古い方法で今は非推奨 ※これまで紹介したように、ネットワークを作成し、そこに参加させることでコンテナを連携させる方法が推奨されている 通信できない例 $ docker run --name mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 $ docker run --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 -d php:custom 「--link」で通信(非推奨の古い方法だが、参考までに) $ docker run --name mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=test -d mysql:5.7 $ docker run --name php -v $PWD/docker/test/code:/var/www/html -p 80:80 --link mysql:mysql -d php:custom Docker Compose での「--link」使用例(非推奨の古い方法だが、参考までに)
mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf environment: MYSQL_ROOT_PASSWORD: pass MYSQL_DATABASE: test image: mysql:5.7 php: container_name: php volumes: - ..:/var/www ports: - 80:80 links: - mysql:mysql image: php:custom
■Docker Compose と Dockerfile の併用
例えば以下のファイルを作成しておく compose_test\php\Dockerfile FROM php:custom RUN touch /root/test1.txt RUN touch /root/test2.txt compose_test\docker\docker-compose.yml の最後を以下のように修正すると、phpフォルダ内のDockerfileから起動されるようになる image: php:custom ↓ build: php
■Docker Compose の内容を一部上書き
docker-compose.yml と同じ場所に docker-compose.override.yml を置くと、起動時に自動で読み込まれる docker-compose.override.yml に設定を書いておくと、その部分が上書きして利用される 「プロジェクト共通の docker-compose を使うが、一部の設定を手元の開発環境に合わせて変更したい」 という場合に利用できる 例えば以下の内容を記述しておくと、作成されるデータベースの名前が test から test2 に変更される
version: '3' services: mysql: environment: MYSQL_DATABASE: test2
サービスの拡張と Compose ファイル - Docker-docs-ja 17.06.Beta ドキュメント http://docs.docker.jp/compose/extends.html
■同一ネットワークの他端末からのブラウザアクセス
※XAMPPやSkypeが80番ポートを使っている場合、あらかじめソフトを終了させておく Docker Quickstart Terminal から以下を実行することにより、 SSHのポートフォワーディングでネットワーク上にポートを公開する (DockerのIPアドレスが 192.168.99.100 であるとする) $ ssh -fNCL 0.0.0.0:80:localhost:80 docker@192.168.99.100 … SSHをバックグラウンドで起動 The authenticity of host '192.168.99.100 (192.168.99.100)' can't be established. ECDSA key fingerprint is SHA256:MU512WSVjrCJ8FHD45UtuOjzAB0UJeaG5zxOMCojEK8. Are you sure you want to continue connecting (yes/no)? … 「yes」を入力(初回のみ) Warning: Permanently added '192.168.99.100' (ECDSA) to the list of known hosts. docker@192.168.99.100's password: … 「tcuser」を入力 これで自身からは http://192.168.99.100/ だけでなく、 http://127.0.0.1/ http://localhost/ でもDockerにアクセスできるようになる コマンドプロンプトから以下を実行 (自身のPCのIPアドレスを調べる) >ipconfig IPv4 アドレス . . . . . . . . . . . .: 192.168.1.6 自身のIPアドレス http://192.168.1.6/ でもDockerにアクセスできることを確認する この状態なら、同一ネットワークの他端末からのブラウザアクセスが可能 バックグラウンドで起動しているSSHを終了させる場合、以下のようにする $ ps … SSHを確認 PID PPID PGID WINPID TTY UID STIME COMMAND 10220 8708 10220 6160 cons0 197609 14:49:45 /usr/bin/ps 8708 1 8708 11020 cons0 197609 14:35:13 /usr/bin/bash 5388 1 5388 5388 ? 197609 14:45:28 /usr/bin/ssh $ kill 5388 … SSHを終了 Windows - WindowsのDockerのコンテナに外部からアクセスしたい。(54259)|teratail https://teratail.com/questions/54259 ここまでできれば、Dockerを開発環境として使えそう
■現状のまとめ
PHP+MySQLの環境を作る例 ■ファイルの作成 C:\Users\refirio\docker\ 内に以下を作成するとする apache_php5_mysql\html\index.php
<?php phpinfo() ?>
apache_php5_mysql\docker\mysql\Dockerfile
FROM mysql:5.7
apache_php5_mysql\docker\mysql\my.cnf
[mysqld] character-set-server=utf8
apache_php5_mysql\docker\php\Dockerfile
FROM php:5.6-apache RUN apt-get update && \ docker-php-ext-install pdo_mysql mysqli mbstring
apache_php5_mysql\docker\php\php.ini
date.timezone = Asia/Tokyo
apache_php5_mysql\docker\docker-compose.yml
version: '3' networks: compose_network: volumes: compose_mysql_data: services: mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf:ro - compose_mysql_data:/var/lib/mysql:rw environment: TZ: Asia/Tokyo MYSQL_ROOT_PASSWORD: rootpass MYSQL_USER: user MYSQL_PASSWORD: userpass MYSQL_DATABASE: test networks: - compose_network build: ./mysql php: container_name: php volumes: - ./php/php.ini:/usr/local/etc/php/conf.d/php.ini:ro - ..:/var/www:rw environment: TZ: Asia/Tokyo ports: - 80:80 networks: - compose_network build: ./php
■設定の上書き docker-compose.yml と同じ階層に docker-compose.override.yml を置くと、その設定内容が優先される apache_php5_mysql\docker\docker-compose.yml
version: '3' services: mysql: environment: MYSQL_USER: user MYSQL_PASSWORD: userpass
■よく使用するコマンド $ cd /c/Users/refirio/docker/apache_php5_mysql/docker $ docker-compose build … ビルドする場合(構成を変更した場合など) $ docker-compose up -d … 起動 $ docker-compose down … 終了 $ docker exec -it php bash … phpコンテナのターミナルに接続する場合 $ docker exec -it mysql bash … mysqlコンテナのターミナルに接続する場合 $ mysql -u root -p … MySQLに接続 $ docker volume ls ... ボリュームを確認 $ docker volume rm compose_mysql_data ... ボリュームを削除 ■ブラウザからのアクセス http://192.168.99.100/ 以下のようなコードで、PHPからMySQLに接続できる エラーになる場合、mysqlコンテナの起動が完了していない可能性があるので待つ
<?php try { $pdo = new PDO( 'mysql:dbname=test;host=mysql', 'user', 'userpass' ); $stmt = $pdo->query('SELECT NOW() AS now;'); $data = $stmt->fetch(PDO::FETCH_ASSOC); echo "<p>" . $data['now'] . "</p>\n"; } catch (PDOException $e) { exit($e->getMessage()); } $pdo = null;
■コマンドまとめ
# イメージをまとめてビルド。イメージがローカルになければプル docker-compose build # イメージをまとめてプル docker-compose pull # 「docker-compose build」や「docker-compose pull」をした後に実行 docker-compose up -d # 関係するコンテナすべてのログを出力 docker-compose logs # 関係するコンテナをすべて停止 docker-compose stop # 関係するコンテナをすべて削除 docker-compose rm # 関係するコンテナをすべて再起動 docker-compose restart # 関係するコンテナをすべて停止して削除 docker-compose down # 起動しているコンテナを一覧 docker ps # 取得したイメージを一覧 docker images # イメージを一括削除 docker rmi `docker images | sed -ne '2,$p' -e 's/ */ /g' | awk '{print $1":"$2}'` # 作成したボリュームを一覧 docker volume ls # 未使用ボリュームを一括削除 docker volume prune # 作成したネットワークを一覧 docker network ls # 未使用ネットワークを一括削除 docker network prune # llを使用する(コンテナ内でエイリアスを設定する場合の例) alias ll="ls -l" # Vimを使用する(コンテナ内でインストールする場合の例) apt-get update apt-get install vim
■その他の環境構築例
■PHP7+GD ※Dockerfileのみ抜粋 libfreetype6-dev, libjpeg62-turbo-dev, libpng-dev を事前にインストールする必要がある また、docker-php-ext-configure gd --with-jpeg-dir=/usr がないとJpegが扱えない ※最後の rm や a2enmod の部分は省略できるか。要検証 apache_php7_mysql\docker\php\Dockerfile
FROM php:7.3-apache RUN apt-get update && apt-get install -y \ libfreetype6-dev \ libjpeg62-turbo-dev \ libpng-dev \ && docker-php-ext-configure gd --with-jpeg-dir=/usr \ && docker-php-ext-install gd pdo_mysql mysqli mbstring \ && apt-get clean \ && rm -rf /var/lib/apt/lists/* \ && a2enmod rewrite
PHP GD をインストールするための Dockerfile の少し複雑な内容メモ - oki2a24 https://oki2a24.com/2018/08/29/how-to-install-php-gd-to-php-5-6-apache-with-dockerfile/ KUSANAGI RODのphp7でphp-gdのJPEGを有効にする - Qiita https://qiita.com/tpywao/items/1243b0311561beaf77d2 ■nginx C:\Users\refirio\docker\ 内に以下を作成するとする ※nginx.conf の「sendfile off;」は、これが無いとHTMLファイルを更新しても反映されない(キャッシュされる) 後から追加した場合、Dockerを起動しなおせばいい(buildまでは不要) ただしHTMLファイルに何らかの変更をするまではキャッシュされ続けるみたい ※「location / { }」のブロックは省略しても大丈夫みたい nginx\html\index.html
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>nginx</title> </head> <body> <h1>nginx</h1> <p>テストページ。</p> </body> </html>
nginx\docker\nginx\Dockerfile
FROM nginx:1.12
nginx\docker\nginx\nginx.conf
server { listen 80 default_server; server_name _; index index.html; root /var/www/html; sendfile off; location / { } }
nginx\docker\docker-compose.yml
version: '3' services: nginx: container_name: nginx volumes: - ./nginx/nginx.conf:/etc/nginx/conf.d/nginx.conf:ro - ..:/var/www:rw environment: TZ: Asia/Tokyo ports: - 80:80 build: ./nginx
起動方法 $ cd /c/Users/refirio/docker/nginx/docker $ docker-compose build $ docker-compose up -d http://192.168.99.100/ でアクセスできる 各コンテナに接続する場合 $ docker exec -it nginx bash 終了方法 $ docker-compose down ■nginx(ホスト名でのアクセスについて) nginx.conf の以下の部分を
listen 80 default_server; server_name _;
一例だが以下のように設定すると、
server_name nginx.test;
C:/windows/System32/drivers/etc/hosts で以下の設定をして http://nginx.test/ にアクセスする必要がある
192.168.99.100 nginx.test
バーチャルホストが前提の場合は問題ないが、Dockerなら通常1つの環境で1つのアプリケーションを扱う 開発環境として使うならhostsの設定無しでアクセスできる方が手軽で良さそう ■nginx+PHP7 C:\Users\refirio\docker\ 内に以下を作成するとする nginx_php7\html\index.php
<?php phpinfo() ?>
nginx_php7\docker\mysql\Dockerfile
FROM mysql:5.7
nginx_php7\docker\mysql\my.cnf
[mysqld] character-set-server=utf8
nginx_php7\docker\nginx\Dockerfile
FROM nginx:1.12
nginx_php7\docker\nginx\nginx.conf
server { listen 80 default_server; server_name _; index index.php index.html; root /var/www/html; sendfile off; location / { } location ~ \.php$ { fastcgi_pass php:9000; fastcgi_index index.php; fastcgi_param SCRIPT_FILENAME $document_root/$fastcgi_script_name; include fastcgi_params; } }
nginx_php7\docker\php\Dockerfile
FROM php:7.0-fpm RUN apt-get update && \ docker-php-ext-install pdo_mysql mysqli mbstring
nginx_php7\docker\php\php.ini
date.timezone = Asia/Tokyo
nginx_php7\docker\docker-compose.yml
version: '3' networks: compose_network: volumes: compose_mysql_data: services: mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf:ro - compose_mysql_data:/var/lib/mysql:rw environment: TZ: Asia/Tokyo MYSQL_ROOT_PASSWORD: rootpass MYSQL_USER: user MYSQL_PASSWORD: userpass MYSQL_DATABASE: test networks: - compose_network build: ./mysql php: container_name: php volumes: - ./php/php.ini:/usr/local/etc/php/conf.d/php.ini:ro - ..:/var/www:rw environment: TZ: Asia/Tokyo networks: - compose_network build: ./php nginx: container_name: nginx volumes: - ./nginx/nginx.conf:/etc/nginx/conf.d/nginx.conf:ro - ..:/var/www:rw environment: TZ: Asia/Tokyo ports: - 80:80 networks: - compose_network build: ./nginx
起動方法 $ cd /c/Users/refirio/docker/nginx_php7/docker $ docker-compose build $ docker-compose up -d http://192.168.99.100/ でアクセスできる 各コンテナに接続する場合 $ docker exec -it nginx bash $ docker exec -it php bash $ docker exec -it mysql bash 終了方法 $ docker-compose down Docker + Nginx + PHP-FPM なら40秒くらいで環境を準備できる docker-compose が楽しくなってきました。 - Qiita https://qiita.com/mochizukikotaro/items/b398076cb57492980447 CentOSにてnginxでPHPを動かす - Qiita https://qiita.com/utano320/items/36b6eac2bbd5bb5657f6 CentOS 6.5でnginxを動かす為の最低限の設定 - Qiita https://qiita.com/ksworks/items/cbc7b73c62c5e115d830 nginxで /welcomeとかを静的ファイルにマッピングする - Qiita https://qiita.com/sarukun99/items/e30cc945ec6243ebac57 【php】nginxとphp-fpmが動く環境を手っ取り早く入れるメモ - tweeeetyのぶろぐ的めも http://tweeeety.hateblo.jp/entry/2015/07/05/224827 nginx と PHP-FPM の仕組みをちゃんと理解しながら PHP の実行環境を構築する - Qiita https://qiita.com/kotarella1110/items/634f6fafeb33ae0f51dc ■nginx+PHP7(URLルーティングの例) nginx_php7\html\index.php
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>nginx + PHP7</title> </head> <body> <h1>nginx + PHP7</h1> <?php if (!isset($_SERVER['REQUEST_URI'])) { $_SERVER['REQUEST_URI'] = '/'; $_SERVER['SCRIPT_NAME'] = '/index.php'; } $request_uri = explode('/', strtok($_SERVER['REQUEST_URI'], '?')); $script_name = explode('/', $_SERVER['SCRIPT_NAME']); for ($i = 0; $i < sizeof($script_name); $i++) { if ($request_uri[$i] === $script_name[$i]) { unset($request_uri[$i]); } } $_params = array_values(array_map('urldecode', $request_uri)); print('<pre>'); print_r($_params); print('</pre>'); ?> </body> </html>
nginx_php7\docker\nginx\nginx.conf
server { listen 80 default_server; server_name _; index index.php index.html; root /var/www/html; sendfile off; location / { try_files $uri /index.php?$query_string; … URLルーティング用に追加 } location ~ \.php$ { fastcgi_pass php:9000; fastcgi_index index.php; fastcgi_param SCRIPT_FILENAME $document_root/$fastcgi_script_name; include fastcgi_params; } }
http://192.168.99.100/ http://192.168.99.100/test1 http://192.168.99.100/test1/test2 などでアクセスし、PHPでパラメータを解釈できていることを確認する ■nginx+PHP7(Laravelの使用例) ※Laradockによる開発環境構築は「Laradockによる開発環境構築」を参照 ※あらかじめ、nginx+PHP7でURLルーティングありで http://192.168.99.100/ にアクセスできるところまで構築しておく phpコンテナで作業(nginxコンテナではPHPを使えない) $ docker exec -it php bash programming.txt の内容をもとに、Composerをインストール&動作確認 # composer さらに関連ツールをインストール # apt-get install git # apt-get install zip unzip 上記作業はDockerを再起動しても保持されていたが、いったん停止してから起動すると消えていた docker/php/Dockerfile に記載しておく方が良さそう(要検証) composerでLaravelをインストール create-projectを実行した際 「Do not run Composer as root/super user! See https://getcomposer.org/root for details」 と表示されるが、開発環境なので気にせず進めた(しばらく放置すると進んだ) # mkdir /var/www/vhosts # cd /var/www/vhosts # composer create-project --prefer-dist laravel/laravel blog インストール完了後、ドキュメントルートをLaravelのものに変更 C:\Users\Yamano\docker\laravel\docker\nginx\nginx.conf
root /var/www/html; ↓ root /var/www/vhosts/blog/public;
Dockerを再起動 # exit $ docker-compose restart 以下にアクセスすると、Laravelの画面が表示される http://192.168.99.100/ 以降は動作確認。要点のみ 日本語化などを試す $ docker exec -it php bash # cd ../blog # composer require laravel-ja/comja5 # vendor/bin/comja5 # vendor/bin/comja5 -c # vendor/bin/comja5 -f データベースへのアクセスを試す。あらかじめ、mysqlコンテナ側でデータベースを作成し、userがアクセスできるようにしておく $ docker exec -it mysql bash > CREATE DATABASE `laravel-blog` CHARACTER SET utf8mb4; > GRANT ALL PRIVILEGES ON `laravel-blog`.* TO user IDENTIFIED BY 'userpass'; phpコンテナからマイグレーションを試す $ docker exec -it php bash # php artisan migrate Laravelの基本機能は使えているみたい はじめてのLaravel5+Docker - Qiita https://qiita.com/kukimo/items/c044ad42fffac062e2f5 ■PHP+PostgreSQL C:\Users\refirio\docker\ 内に以下を作成するとする apache_php5_postgresql\html\index.php
<?php phpinfo() ?>
apache_php5_postgresql\docker\php\Dockerfile
FROM php:5.6-apache RUN apt-get update && apt-get install -y libpq-dev && docker-php-ext-install pdo pdo_pgsql mbstring
apache_php5_postgresql\docker\php\php.ini
date.timezone = Asia/Tokyo
apache_php5_postgresql\docker\postgresql\Dockerfile
FROM postgres:9.2
apache_php5_postgresql\docker\docker-compose.yml
version: '3' networks: compose_network: volumes: compose_postgresql_data: services: postgresql: container_name: postgresql volumes: - compose_postgresql_data:/var/lib/postgresql/data:rw environment: TZ: Asia/Tokyo POSTGRES_USER: user POSTGRES_PASSWORD: userpass POSTGRES_DB: test networks: - compose_network build: ./postgresql php: container_name: php volumes: - ./php/php.ini:/usr/local/etc/php/conf.d/php.ini:ro - ..:/var/www:rw environment: TZ: Asia/Tokyo ports: - 80:80 networks: - compose_network build: ./php
$ cd /c/Users/refirio/docker/apache_php5_postgresql/docker $ docker-compose build … ビルドする場合(構成を変更した場合など) $ docker-compose up -d … 起動 $ docker-compose down … 終了 $ docker exec -it php bash … phpコンテナのターミナルに接続する場合 $ docker exec -it postgresql bash … postgresqlコンテナのターミナルに接続する場合 root@bca889e7662a:/# psql -U user test … PostgreSQLに接続(「psql -l」だと「role "root" does not exist」というエラーになる) psql (9.2.23) Type "help" for help. test=# SELECT * FROM test LIMIT 100; no | name ----+------------ 1 | 山田タロウ 2 | 山田ハナコ (2 rows) http://192.168.99.100/ 以下のようなコードで、PHPからPostgreSQLに接続できる エラーになる場合、postgresqlコンテナの起動が完了していない可能性があるので待つ
<?php try { $pdo = new PDO( 'pgsql:dbname=test;host=postgresql', 'user', 'userpass' ); $stmt = $pdo->query('SELECT NOW() AS now;'); $data = $stmt->fetch(PDO::FETCH_ASSOC); echo "<p>" . $data['now'] . "</p>\n"; } catch (PDOException $e) { exit($e->getMessage()); } $pdo = null;
PHPからPostgreSQLに接続し、以下のコードで動作確認を行う CREATE TABLE test(no INT, name TEXT); INSERT INTO test VALUES(1, '山田タロウ'); INSERT INTO test VALUES(2, '山田ハナコ'); SELECT * FROM test; [備忘録]Dockerでapache+php+postgresql環境 - Qiita https://qiita.com/cyclon2joker/items/39e620d3d16fa1f6edf0 「postgresql-dev libpq-dev」は無くても動いた。付けておくべきかは要検証 portの指定は無くても動いた。付けておくべきかは要検証 ■nginx+Node.js C:\Users\refirio\docker\ 内に以下を作成するとする (common.css はテストで作成しているのみで、他から参照されていない。node.jsからMySQLへの接続は未確認) nginx_node\html\css\common.css
@charset "utf-8"; body { line-height: 1.4; margin: 0 auto; padding: 10px 20px; background-color: #FFFFFF; color: #000000; font-size: 80%; font-family: "ヒラギノ角ゴ Pro W3", "Hiragino Kaku Gothic Pro", "メイリオ", Meiryo, "MS Pゴシック", sans-serif; }
nginx_node\docker\mysql\Dockerfile
FROM mysql:5.7
nginx_node\docker\mysql\my.cnf
[mysqld] character-set-server=utf8
nginx_node\docker\nginx\Dockerfile
FROM nginx:1.12
nginx_node\docker\nginx\nginx.conf
server { listen 80 default_server; server_name _; index index.php index.html; root /var/www/html; sendfile off; location / { proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $http_host; proxy_set_header X-NginX-Proxy true; proxy_pass http://node:3000/; } location ~ .*\.(jpg|JPG|gif|GIF|png|PNG|swf|SWF|css|CSS|js|JS|inc|INC|ico|ICO) { } }
nginx_node\docker\node\Dockerfile
FROM node:8.4
nginx_node\docker\node\server.js
const http = require('http'); const port = 3000; http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello World!\n'); }).listen(port); console.log('Server running at port ' + port + '.');
nginx_node\docker\docker-compose.yml
version: '3' networks: compose_network: volumes: compose_mysql_data: services: mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf:ro - compose_mysql_data:/var/lib/mysql:rw environment: TZ: Asia/Tokyo MYSQL_ROOT_PASSWORD: rootpass MYSQL_USER: user MYSQL_PASSWORD: userpass MYSQL_DATABASE: test networks: - compose_network build: ./mysql node: container_name: node volumes: - ./node:/var/nodeapp:rw command: node /var/nodeapp/server.js environment: TZ: Asia/Tokyo PORT: 3000 ports: - 3000:3000 networks: - compose_network build: ./node nginx: container_name: nginx volumes: - ./nginx/nginx.conf:/etc/nginx/conf.d/nginx.conf:ro - ..:/var/www:rw environment: TZ: Asia/Tokyo ports: - 80:80 networks: - compose_network build: ./nginx
起動方法 $ cd /c/Users/refirio/docker/nginx_node/docker $ docker-compose build $ docker-compose up -d http://192.168.99.100:3000/ ... node.js http://192.168.99.100/ ... nginx経由でnode.js ■Node.js(Docker Compose なしで単体起動する場合) dockerコンテナ上でnode.jsのサーバを起動し、ホスト端末からアクセスする - Qiita https://qiita.com/hotdrop_77/items/a2ca316c97ba4b748d9a C:\Users\refirio\docker\node\server.js
const http = require('http'); const port = 3000; http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello World.\n'); }).listen(port); console.log('Server running at port ' + port + '.');
$ docker run -v /c/Users/refirio/docker/node:/var/nodeapp -p 3000:3000 -it node:8.4.0 /bin/bash # node /var/nodeapp/server.js http://192.168.99.100:3000/ でアクセスできる # node /var/nodeapp/server.js の代わりに以下も有効? # cd /var/nodeapp # node server.js & curl localhost:3000 # exit $ docker rm -f $(docker ps -a -q) 上記手順で起動できた 以下は本番環境での稼働手順の参考に AWS EC2でNodeを動作させる - Qiita https://qiita.com/oishihiroaki/items/bc663eb1282d87c46e97
■Cronでの定期実行
※未検証 ホスト側でCronを設定し、ログもホスト側に記録されるようにするのが無難か ホスト側のCronで docker run する - Qiita https://qiita.com/acro5piano/items/a9ec64f78e7da304a661 [Docker] ホストマシンのcronからコンテナ内のphpコマンドを実行する │ M0DE https://www.m0de.ml/c0d3man/posts/k78e5r2n1cty0ygv3ie5 Dockerコンテナをホスト側のcronで実行する - 202号室の手記 http://paperlefthand.hateblo.jp/entry/2017/06/14/214834 ただし以下ページの解説では「起動用スクリプトから起動しています」のように紹介されているので、すんなり実行できるかどうかは要検証 Docker + Cron環境を実現する3つの方法 - Qiita https://qiita.com/YuukiMiyoshi/items/bb7f14436d60d4bd8a8b 以下はDocker内で行う例 ログの出力などに問題が無いかは要確認 Dockerを用いたcronでの定時処理 - Qiita https://qiita.com/midoribi/items/496dcb6f8307ce7e2af0
■Laradockによる開発環境構築
Homesteadは必要なものが揃った開発環境だが、実運用ではこんな多機能なサーバを用意することはまず無い 本番環境に近づけた開発環境を用意できるように、Docker用の環境が提供された Laradockを使ってLaravel 5.5環境を構築する - Qiita https://qiita.com/rock619/items/62c2ab2252c405e26479 Laravel使った開発にLaradockを使うというのはどうだろう - Qiita https://qiita.com/niisan-tokyo/items/d4485b8bb4fbfcfcc6be ■前提 ・/c/Users/refirio/docker/laravel を作業ディレクトリとする(ここが共有ディレクトリとして設定される) ・/c/Users/refirio/docker/laravel/laradock にLaradockをインストールするものとする ・/c/Users/refirio/docker/laravel/blog にプロジェクトをインストールするものとする(複数プロジェクトがあれば、同階層に作成する) ・MySQLはデフォルトで8が使用されるが、セキュリティが強化されて扱いづらいので5.7に変更して使用する 【Docker】MySQL8.0系を使う時に発生する問題について - websandbag ブログ http://blog.websandbag.com/entry/2018/05/17/121730 ■Laradockの起動 $ cd /c/Users/refirio/docker/laravel $ git clone https://github.com/laradock/laradock.git /c/Users/refirio/docker/laravel/laradock … Laradockの入手 $ cd laradock $ cp env-example .env … .envファイル(Laradockの設定ファイル)の作成 Laradock の .env を編集(MySQLのバージョンを5.7にする)
MYSQL_VERSION=latest ↓ MYSQL_VERSION=5.7
$ docker-compose up -d nginx mysql workspace phpmyadmin … コンテナの初期化(初回は非常に時間がかかる) $ docker ps http://192.168.99.100/ (この時点では「404 Not Found」と表示される) ■Laravelの起動 workspaceコンテナからLaravelを操作できる これはcomposerやnodeなど、Laravelに必要なツール一式が格納されたコンテナ $ docker-compose exec --user=laradock workspace bash … 仮想環境へログイン $ composer create-project --prefer-dist "laravel/laravel=5.5.*" blog … Laravelをインストール $ exit … 仮想環境をいったん抜ける Laradock の .env を編集(公開ディレクトリをblog内のpublicにする)
APP_CODE_PATH_HOST=../ ↓ APP_CODE_PATH_HOST=../blog
$ docker-compose stop … 仮想環境を再起動(いったん停止させてから起動) $ docker-compose up -d nginx mysql workspace phpmyadmin $ docker-compose exec --user=laradock workspace bash … 仮想環境へ再度ログインする場合 $ php artisan --version ■PHPからMySQLへの接続 いったんPure-PHPでMySQLへの接続を検証してみる /var/www/public/mysql.php
<?php try { $pdo = new PDO( 'mysql:dbname=blog;host=mysql', 'laradock', 'secret' ); $stmt = $pdo->query('SELECT NOW() AS now;'); $data = $stmt->fetch(PDO::FETCH_ASSOC); echo "<p>" . $data['now'] . "</p>\n"; } catch (PDOException $e) { exit($e->getMessage()); } $pdo = null;
実行すると以下のエラーになる(この時点では、laradockユーザもblogデータベースも作っていないので当然) SQLSTATE[HY000] [1045] Access denied for user 'laradock'@'172.20.0.6' (using password: YES) 以下のように、MySQLコンテナでユーザを作成するとアクセスできるようになる $ docker-compose exec mysql bash # mysql -u root -p root > CREATE USER 'laradock'@'172.20.0.6' IDENTIFIED BY 'secret'; > GRANT ALL PRIVILEGES ON blog.* TO laradock; > CREATE DATABASE blog DEFAULT CHARACTER SET utf8mb4; ■phpMyAdminの利用 以下にphpMyAdminがある http://192.168.99.100:8080/ サーバ: mysql ユーザ名: laradock パスワード: secret ログインしようとすると以下のエラーになる(phpMyAdminコンテナからの接続設定をしていないため) mysqli_real_connect(): (HY000/1045): Access denied for user 'laradock'@'172.20.0.5' (using password: YES) ユーザを作成するとアクセスできるようになる > CREATE USER 'laradock'@'172.20.0.5' IDENTIFIED BY 'secret'; ■LaravelからMySQLへの接続 マイグレーションしようとすると以下のエラーになる(workspaceコンテナからの接続設定をしていないため) $ docker-compose exec --user=laradock workspace bash $ php artisan migrate SQLSTATE[HY000] [1045] Access denied for user 'laradock'@'172.20.0.4' (using password: YES) ユーザを作成するとマイグレーションできるようになる > CREATE USER 'laradock'@'172.20.0.4' IDENTIFIED BY 'secret'; ■次回からの起動 以下で起動できる しばらく待たないと「502 Bad Gateway」のエラーになる可能性があるので注意 $ cd /c/Users/refirio/docker/laravel/laradock $ docker-compose up -d nginx mysql workspace phpmyadmin 以下でLaravelの操作ができる $ docker-compose exec --user=laradock workspace bash $ php artisan --version 以下でMySQLの操作ができる $ docker-compose exec mysql bash # mysql -u root -p root ■MySQLコンテナが起動しなくなった場合 Laradock の .env を以下のように編集すると、その後MySQLコンテナが起動しなくなった
MYSQL_VERSION=latest ↓ MYSQL_VERSION=5.7
LaradockでMySQLがどうしても立ち上がらない人あつまれー! - Qiita https://qiita.com/lara_bell/items/d4bd1340a5cc7dfcfcb4 MySQLのデータは、.envの以下の場所で永続化されている
# Choose storage path on your machine. For all storage systems DATA_PATH_HOST=~/.laradock/data
壊れたデータが残っている可能性がある。以下のフォルダを削除して各コンテナを再起動すると、MySQLコンテナが起動する C:\Users\refirio\.laradock ■参考 Laradockを使ってLaravel 5.5環境を構築する - Qiita https://qiita.com/rock619/items/62c2ab2252c405e26479 LaradockでMySQL5.5を使う(Docker + Laravel) - Qiita https://qiita.com/mom0tomo/items/40219773c705b5175825 DockerとLaradockでPHPフレームワークとCMSの開発環境を構築する【MySQL( latest)8.0.11対応】 - Qiita https://qiita.com/2no553/items/c1da7bb6dfed68c5af1b
■WordPress
ミドルウェアだけでなく、アプリケーションも含めて構築できる 以下はGit管理も想定した例 ■ファイルの作成 C:\Users\refirio\docker\ 内に以下を作成するとする wordpress\.gitignore
Thumbs.db .DS_Store /docker/docker-compose.override.yml /html/wp-config.php /html/.htaccess /html/.htpasswd /html/index.php /html/license.txt /html/readme.html /html/wp-*.php /html/xmlrpc.php /html/wp-admin/* /html/wp-content/* !/html/wp-content/themes /html/wp-content/themes/* !/html/wp-content/themes/simple /html/wp-includes/* /html/tool/*
wordpress\html\wp-content\themes\simple テーマを配置 wordpress\docker\wordpress\Dockerfile
FROM wordpress:5-php7.2-apache RUN apt-get update && \ docker-php-ext-install pdo_mysql mysqli mbstring RUN curl --location --output /usr/local/bin/mhsendmail https://github.com/mailhog/mhsendmail/releases/download/v0.2.0/mhsendmail_linux_amd64 RUN chmod +x /usr/local/bin/mhsendmail RUN echo 'sendmail_path="/usr/local/bin/mhsendmail --smtp-addr=mailhog:1025 --from=no-reply@docker.dev"' > /usr/local/etc/php/conf.d/mailhog.ini RUN usermod -u 1000 www-data && \ groupmod -g 1000 www-data
wordpress\docker\wordpress\php.ini
date.timezone = Asia/Tokyo
wordpress\docker\mysql\Dockerfile
FROM mysql:5.7
wordpress\docker\mysql\my.cnf
[mysqld] character-set-server=utf8
wordpress\docker\mailhog\Dockerfile
FROM mailhog/mailhog
wordpress\docker\docker-compose.yml
version: '3' networks: compose_network: volumes: compose_wordpress_data: services: mailhog: container_name: mailhog ports: - 8025:8025 - 1025:1025 networks: - compose_network build: ./mailhog mysql: container_name: mysql volumes: - ./mysql/my.cnf:/etc/mysql/conf.d/my.cnf:ro - compose_wordpress_data:/var/lib/mysql:rw environment: TZ: Asia/Tokyo MYSQL_ROOT_PASSWORD: rootpass MYSQL_USER: user MYSQL_PASSWORD: userpass MYSQL_DATABASE: wordpress networks: - compose_network build: ./mysql wordpress: container_name: wordpress volumes: - ./wordpress/php.ini:/usr/local/etc/php/conf.d/php.ini:ro - ../html:/var/www/html environment: WORDPRESS_DB_HOST: mysql WORDPRESS_DB_USER: user WORDPRESS_DB_PASSWORD: userpass WORDPRESS_DB_NAME: wordpress ports: - 80:80 networks: - compose_network build: ./wordpress
■設定の上書き docker-compose.yml と同じ階層に docker-compose.override.yml を置くと、その設定内容が優先される wordpress\docker\docker-compose.yml
version: '3' services: mysql: environment: MYSQL_ROOT_PASSWORD: rootpass MYSQL_USER: user MYSQL_PASSWORD: userpass MYSQL_DATABASE: wordpress wordpress: environment: WORDPRESS_DB_HOST: mysql WORDPRESS_DB_USER: user WORDPRESS_DB_PASSWORD: userpass WORDPRESS_DB_NAME: wordpress
■よく使用するコマンド ※初回は特に、起動まで時間がかかる httpでアクセスできなくても、mysqlに接続できなくても、しばらく待てば解決することがある $ cd /c/Users/refirio/docker/wordpress/docker $ docker-compose build … ビルドする場合(構成を変更した場合など) $ docker-compose up -d … 起動 $ docker-compose down … 終了 $ docker exec -it php bash … phpコンテナのターミナルに接続する場合 $ docker exec -it mysql bash … mysqlコンテナのターミナルに接続する場合 $ mysql -u root -p … MySQLに接続 $ docker volume ls ... ボリュームを確認 $ docker volume rm compose_wordpress_data ... ボリュームを削除 ■ブラウザからのアクセス http://192.168.99.100/ http://192.168.99.100:8025/
■CentOSでDockerを使用する
※現状意図したように稼働させられていない
Vagrant.configure(2) do |config| config.vm.box = "centos72" config.vm.box_check_update = false config.vm.define "controller" do |node| node.vm.hostname = "controller.localhost" node.vm.synced_folder "C:/vagrant/ansible/controller", "/var/code" node.vm.network :forwarded_port, id: "ssh", guest: 22, host: 2210 node.vm.network "private_network", ip: "192.168.33.10" end end
この環境でApache+PHPを稼働させようとすると、以下のエラーになる $ docker run --name php -p 80:80 php:5.6-apache AH00534: apache2: Configuration error: No MPM loaded. nginxだと問題なく起動できる $ docker run --name php -p 80:80 -d nginx:1.12 Apache2.2でも問題なく起動できる $ docker run --name php -p 80:80 -d devilbox/apache-2.2 PHPバージョンアップのときもそうだったが、Apache2.4には色々と問題があるかも? 要確認
■EC2でDockerを使用する
通常の手順でEC2を作成し、SSHでアクセスできることを確認しておく ここでは Amazon Linux 2 を使うものとする 通常の手順で言語・タイムゾーン・アップデート・開発ツールインストール・メール送信など最低限のものを設定しておく ※Amazon Linux 2 の場合、DockerはExtrasリポジトリからインストールすることもできるみたい ■インストール # yum install -y docker … dockerをインストール # service docker start … dockerを起動 # docker info … dockerの起動を確認 # docker run hello-world … hello-worldの起動を確認 # docker images ■一般ユーザでDockerを実行できるようにする # groupadd docker … dockerグループを作成(環境によっては作成済みみたい) # usermod -a -G docker ec2-user … ec2-userをdockerグループに入れる。これでec2-userがdockerコマンドを実行できる # service docker restart … dockerを再起動(必須) # exit $ docker info … 上記変更は、再接続後に反映されるので注意 ■Apache+PHPの動作確認 $ docker run --name php -p 80:80 -d php:7.1-apache … 「php」という名前を付けてApacheの起動を確認 $ docker images $ docker ps $ docker exec -it php bash … phpコンテナのターミナルに接続 # echo '<?php phpinfo();' > index.php … index.php を作成(初期状態ではviはインストールされていない) # exit ブラウザで以下にアクセスし、phpinfoの内容が表示されれば成功 (コンテンツを何も作成していない場合、「403 Forbidden」が表示される) http://3.112.217.223/ $ docker rm -f $(docker ps -a -q) … いったんすべてのプロセスを削除 $ docker ps ■Docker Compose を使用する 最新のバージョンは https://github.com/docker/compose/releases/ で確認できる 今回は検証時最新版の 1.24.0 を使用する $ sudo su - # curl -L https://github.com/docker/compose/releases/download/1.24.0/docker-compose-$(uname -s)-$(uname -m) -o /usr/local/bin/docker-compose # chmod +x /usr/local/bin/docker-compose # docker-compose --version # exit $ docker-compose --version … ec2-userでも実行できることを確認する ■Docker Compose の動作確認 /home/ec2-user/docker/wordpress にWordPress用の Docker Compose を配置するものとする 起動中のコンテナがあれば、終了させておく $ cd /home/ec2-user/docker/wordpress/docker $ docker-compose build $ docker-compose up -d $ docker-compose down $ docker volume ls $ docker volume rm docker_compose_wordpress_data http://3.112.217.223 http://3.112.217.223/wp-login.php admin / i#JFy5c8OrGKPqqKa0 ■Gitからの連携 $ git --version git version 2.17.2 $ cd $ ssh-keygen -t rsa $ ll .ssh/ $ cat .ssh/id_rsa.pub ssh-rsa AAAAB〜略〜ULJMP ec2-user@ip-10-0-0-51.ap-northeast-1.compute.internal $ cd $ mkdir -p docker/wordpress $ cd docker/wordpress/ $ git clone git@bitbucket.org:yamano-terraport/docker_wordpress.git /home/ec2-user/docker/wordpress 以降「Docker Compose の動作確認」と同じ操作方法で大丈夫だったが、何故か日本語版にならなかった テーマを配置するためにGitにより作成された wp-content ディレクトリ内に書き込めないのが原因みたい 同じくメディアのアップロードもできない 解決策は、このファイルの「ホストOSとコンテナで相互にファイルを読み書き(Linux環境)」を参照 PHPアプリケーションの設計によってはこの問題は発生しない ■メモ Dockerが配置したものを直接FTPで上書きできない 以下で解決するかと思ったが、 # mkdir /home/ec2-user/docker/wordpress/html # chown ec2-user. /home/ec2-user/docker/wordpress/html # chmod 0777 /home/ec2-user/docker/wordpress/html # chmod g+s /home/ec2-user/docker/wordpress/html Dockerによって作成されたファイルは以下の所有者になってしまう # ll -rw-r--r-- 1 33 tape 420 12月 1 2017 index.php rootによって作成されたファイルは以下のように ec2-user グループになるので謎 # ll -rw-r--r-- 1 root ec2-user 10 5月 16 12:05 test.txt …だったが、このファイル内「ホストOSとコンテナで相互にファイルを読み書き(Linux環境)」の方法で一応は解決した より良い方法が無いかは、また検証したい ■参考 AWS EC2インスタンスにdockerとdocker-composeをインストールして簡単なWEBサービスを立ち上げる方法 - Qiita https://qiita.com/y-do/items/e127211b32296d65803a EC2上でDockerのnginxコンテナを動かしてアクセスを確認した - やる気がストロングZERO https://yaruki-strong-zero.hatenablog.jp/entry/ec2_docker_nginx AWS EC2 Amazon LinuxでDocker, Docker Composeをインストールする - Qiita https://qiita.com/shinespark/items/a8019b7ca99e4a30d286 ECSを試す際は以下も参考になるかも 知識0から Docker 環境を AWS の ECS でデプロイするまで - istyle Tech Blog https://techblog.istyle.co.jp/archives/1652
■ホストOSとコンテナで相互にファイルを読み書き(Linux環境)
WordPressを実行しても、何故か日本語版にならなかった テーマを配置するためにGitにより作成された wp-content ディレクトリ内に書き込めないのが原因みたい 同じくメディアのアップロードもできない drwxrwxr-x 4 ec2-user ec2-user 52 5月 16 17:26 wp-content ■コンテナ内で確認 Dockerにより作成されたファイルは、コンテナ内では以下のように見える # ls -l total 200 -rw-r--r-- 1 www-data www-data 420 Nov 30 2017 index.php -rw-r--r-- 1 www-data www-data 19935 Jan 1 20:37 license.txt -rw-r--r-- 1 www-data www-data 7447 Apr 8 22:59 readme.html ec2-userにより作成されたファイルは、コンテナ内では以下のように見える idが 1000 のユーザはいないため数字表示 # ls -l .. total 4 drwxrwxr-x 5 1000 1000 4096 May 16 08:41 html www-data は以下のIDを持つ # id www-data uid=33(www-data) gid=33(www-data) groups=33(www-data) ■コンテナ外で確認 Dockerにより作成されたファイルは、コンテナ外では以下のように見える idが 33 のユーザはいないため数字表示 $ ll 合計 200 -rw-r--r-- 1 33 tape 420 12月 1 2017 index.php -rw-r--r-- 1 33 tape 19935 1月 2 05:37 license.txt -rw-r--r-- 1 33 tape 7447 4月 9 07:59 readme.html ■解決策 Docker: マウントしたVolumeにApacheが書き込めないとき - Qiita https://qiita.com/suin/items/3a0361102af83d0b69aa dockerでvolumeをマウントしたときのファイルのowner問題 - Qiita https://qiita.com/yohm/items/047b2e68d008ebb0f001 「ユーザ・グループを1000:1000にする」という方法で対処してみる 「1000」が決め打ちなのが気にはなる(システム以外で最初に作成されたユーザが 1000 となる)が、 Linux(EC2)とWindowsの両方で大丈夫だったのでいったん良しとする $ vi docker/wordpress/Dockerfile … ファイルの最後に以下を追記 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - RUN usermod -u 1000 www-data && \ groupmod -g 1000 www-data - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ■再実行例 最初から実行しなおしたい場合の例 コンテナを終了し、データベースを削除し、不要なファイルを削除してからGitに一致させている $ cd /home/ec2-user/docker/wordpress/docker $ docker-compose down $ docker volume rm docker_compose_wordpress_data $ cd /home/ec2-user/docker/wordpress $ sudo rm -rf html $ git reset --hard origin/master
■メモ
以下、引き続き検証メモ ■Node.js(Docker Compose なしで単体起動する場合) Node.js ウェブ・アプリの Docker 化 - Docker-docs-ja 1.11.0 ドキュメント http://docs.docker.jp/engine/examples/nodejs_web_app.html 起動したが、CentOS6のダウンロードからなので時間がかかる? Node.js用のイメージがあれば、その方が良さそう docker build -t refirio/centos-node-hello . docker images docker run -p 49160:8080 -d refirio/centos-node-hello curl -i 192.168.99.100:49160 http://192.168.99.100:49160/ 以下なども参考にして、再度構築を試したい 3000版ポートでnode.jsにアクセスできるようにして、 さらにnginx経由でポート指定無しでアクセスできるようにしてみる nginx無しで80版ポートにアクセスさせられるかも試したい Dockerでnginx+node.jsのSPA構成を試す - Qiita https://qiita.com/KeitaMoromizato/items/bfc3e22dae47211eff4f ■Ruby on Rails Docker + Ruby on Rails 5 のメモ - Qiita https://qiita.com/yuki-maru/items/3ee8e52cebbfc036c023 この手順でRailsを起動できた http://192.168.99.100:3000/ 次回からは以下で起動できる $ cd /c/Users/refirio/docker/compose_ruby $ docker-compose build $ docker-compose up -d $ docker-compose down docker-compose.yml を以下のように編集すると、http://192.168.99.100/ でアクセスできた
web: build: . command: bundle exec rails s -p 80 -b '0.0.0.0' volumes: - .:/myapp ports: - "80:80"
■疑問点とメモ ・dockerのgit管理 汎用的な環境というより、特定の案件の環境を管理するためのもの。だと思う それなら、プログラムと同じリポジドリで管理すれば良さそう ・fake s3 というものがあるらしい。ローカルでs3を試せるらしい LocalStack というのもよく使われるみたい ・上の手順で docker-compose build した場合、REPOSITORYもTAGも「<none>」のイメージが作られる?こういうもの?名前は指定できる? 以下で環境を立ち上げるとどうなるか試す http://koni.hateblo.jp/entry/2017/01/28/150522 ・apache_php5_mysql のファイル構成は以下も参考に再考する http://koni.hateblo.jp/entry/2017/01/28/150522 ・カスタムイメージを作成した場合、それも同梱するか つまりイメージ自体に手を加えたら、各々の環境でイメージをインポートしなおしてもらう Dockerは専用リポジトリで管理すべきか ・custom.cnf はこの名前でいいか と思ったが、公式の推奨手順みたい Dockerの公式MySQLイメージの使い方を徹底的に解説するよ - DQNEO起業日記 http://dqn.sakusakutto.jp/2015/10/docker_mysqld_tutorial.html ・複数人が同じ開発環境を再現する場合、イメージを更新した場合はどうするか 小さな更新なら Docker Compose や Dockerfile の CMD で実行すれば良さそう 大きな修正なら、Docker Hub などで管理しておく必要がある?でも Docker Hub のプライベートリポジトリは有料みたい イメージ自体をリポジトリに入れて、必要なときにインポートしてもらえばいいかも? docker - コマンドはdocker-compose.ymlとDockerfileのどちらで定義するほうがいい? - スタック・オーバーフロー https://ja.stackoverflow.com/questions/30495/%E3%82%B3%E3%83%9E%E3%83%B3%E3%83%89%E3%81%AFdocker-com... ・本番環境に使う場合、Amazon ECS を検証したい ・VagrantにDockerをインストールする方法。本番環境のCentOSなどにも応用できるかも http://tech.respect-pal.jp/docker_tutorial/ ■以下を参考に、上の構成を調整する ファイルの設定内容のを参考に https://qiita.com/osyoyu/items/a039b7e05abc6e97fb25 php.iniの配置方法の参考に https://github.com/koni/docker-php-nginx-mysql-memcached/ 復習に良い https://dev.classmethod.jp/tool/docker/develop-with-docker/ 参考に https://qiita.com/aild_arch_bfmv/items/d47caf37b79e855af95f ■Docker で Amazon Linux を動かす amazonlinux - Docker Hub https://hub.docker.com/_/amazonlinux/ Docker for Windows から Amazon Linux を起動してみた | KDL 情's Cafe BLOG https://blog.ismg.kdl.co.jp/virtualization/docker/docker_run_amazonlinux DockerにAmazon Linuxを入れて、Nginxが動くようにする - Qiita https://qiita.com/areaz_/items/4f79a7c0175c7ef20cc0 ■Fargate AWS Fargate(サーバーやクラスターの管理が不要なコンテナの使用)| AWS https://aws.amazon.com/jp/fargate/ AWS Fargateとは? - Qiita https://qiita.com/riywo/items/1a5b50028542d9bb06cc 2019年1月にAWS Fargateが大幅値下げしたのでEC2との価格比を確認してみた | DevelopersIO https://dev.classmethod.jp/cloud/aws/compare-fees-for-fargat-and-ec2-2019-1/ ■Kubernetes 今さら人に聞けない Kubernetes とは? - Qiita https://qiita.com/MahoTakara/items/85096f8b2632c802ab22 10分くらいでわかる、KubernetesとEKSの何が便利なのか - Qiita https://qiita.com/masachaco/items/3e50a1ac65cdd661a734 数時間で完全理解!わりとゴツいKubernetesハンズオン!! - Qiita https://qiita.com/Kta-M/items/ce475c0063d3d3f36d5d Amazon EKS(AWS でマネージド Kubernetes を実行)| AWS https://aws.amazon.com/jp/eks/ コンテナ移行ってこんなに大変? 〜「家族アルバム みてね」を支えるインフラの裏側〜 / Container migration in FamilyAlbum - Speaker Deck https://speakerdeck.com/isaoshimizu/container-migration-in-familyalbum ■引き続き参考にしたいページ Dockerのイメージ削除時のエラー「Error response from daemon: Conflict, cannot delete image」対策 - tsunokawaのはてなダイアリー http://tsunokawa.hatenablog.com/entry/2016/04/26/000507 そろそろDockerを始めないとやばいと思い始めたあなたへ | 東北ギーク http://tech.respect-pal.jp/docker_tutorial/ docker-composeを使うと複数コンテナの管理が便利に - Qiita https://qiita.com/y_hokkey/items/d51e69c6ff4015e85fce docker-composeのvolumesで指定したホストのディレクトリがマウントされずハマった | Black Everyday Company https://kuroeveryday.blogspot.jp/2016/11/docker-compose-volumes.html Dockerで作る最強のWeb開発環境2017 - Qiita https://qiita.com/osyoyu/items/a039b7e05abc6e97fb25 Dockerで開発環境構築を10倍楽にしたはなし - KAYAC engineers' blog http://techblog.kayac.com/developing-with-docker-compose 社内用Docker環境をつくる〜Docker Registry on EC2とDocker for AWSについて〜 | Recruit Jobs TECHBLOG https://techblog.recruitjobs.net/development/docker-registry-on-ec2_and_docker-for-aws AWS ECSでDockerコンテナ管理入門(基本的な使い方、Blue/Green Deployment、AutoScalingなどいろいろ試してみた) - Qiita https://qiita.com/uzresk/items/6acc90e80b0a79b961ce Amazon EC2 Container Serviceで構築されたシステムでDockerコンテナを入れ替える | Developers.IO https://dev.classmethod.jp/cloud/aws/switch-docker-container-using-ecs/ Amazon EC2 Container Service コンソールチュートリアルをやってみた | Developers.IO https://dev.classmethod.jp/tool/docker/try-the-amazon-ecs-console-tutorial/ Dockerfileを書くときに気をつけていること10選 - Qiita https://qiita.com/c18t/items/f3a911ef01f124071c95 さくらVPSでdocker使って5分でWordPressを構築する - Qiita https://qiita.com/haruto167/items/0faba1b67ceb14e035e0 Amazon Linux 2 でdockerを使ってみる (Apache2.4) - Qiita https://qiita.com/reflet/items/3b818fbfb14ba5c7ef47 CentOS7にDockerをインストールしてみた。 - Qiita https://qiita.com/ysuzuki963/items/a31c31735e5b8bed06fe 【アップデート】ECSタスク定義を利用したローカル環境でのテスト実行が可能に! | DevelopersIO https://dev.classmethod.jp/cloud/aws/ecs-local/