■Docker概要
Dockerについて基本から最近追加された機能までまとめ - Qiita https://qiita.com/yuki_ycino/items/b94ae2bf7d78685cd6f5 超入門Docker:第1回 Dockerとは - @IT http://www.atmarkit.co.jp/ait/articles/1701/30/news037.html
■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 環境を簡単に構築するためのインストーラらしい ■インストール Install Docker Toolbox on Windows | Docker Documentation https://docs.docker.com/toolbox/toolbox_install_windows/ 「Get Docker Toolbox for Windows」からDockerをダウンロード&実行 Next Next Next 「Install VirtualBox with NDIS5 driver[default NDIS6]」にチェックを入れてNext Install Finish Docker Toolboxのインストール:Windows編 - Qiita https://qiita.com/maemori/items/52b1639fba4b1e68fccd インストールは主にこのページを参考にした インストールが完了すると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! 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 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 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) … 確認できたら削除 ■フォルダ共有(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
■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にログインしようとすると、以下のエラーになることがある 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分程度待つ ■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/
■イメージを作成
■イメージを作成(commitコマンド) ※実際にコンテナに対して行った操作内容をもとに、イメージを作成する $ 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 --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:create_file … 作成したイメージから起動 $ docker exec -it php bash … phpコンテナのターミナルに接続 # ls /root … テストファイルを確認する $ docker rm -f $(docker ps -a -q) … 作成済みのコンテナをいったん削除 ■イメージを作成(buildコマンド) ※コンテナへの操作内容をDockerfileに記載し、それをもとにイメージを作成する docker images … 上で作成したイメージのIDを確認 docker rmi 9dbd220d50c7 … 削除しておく docker\php_create_file\Dockerfile … Dockerfileを作成 FROM php:custom 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 --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: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 … 読み込んだイメージを確認
■Docker Compose
docker run で起動する場合、一度に起動すべきコンテナの数が多くなると管理しづらくなるので、Docker Compose で管理するといい これなら依存管理の手間が無くなり、さらに起動コードや関連ファイルを丸ごとGitで管理することもできる docker-compose.yml の現在のバージョンは3なので、「version: '3'」と指定する ■ファイルの準備 C:\Users\refirio\docker\ 内に以下を作成するとする 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 mysql> show databases; 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; mysql> exit; 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のデータ永続化関連について - 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
■フォルダ共有で一部を除外
以下のようにすれば、共有の除外になるみたい
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を開発環境として使えそう
■現状のまとめ
■ファイルの作成 C:\Users\refirio\docker\ 内に以下を作成するとする apache_php5\html\index.php
<?php phpinfo() ?>
apache_php5\docker\mysql\Dockerfile
FROM mysql:5.7
apache_php5\docker\mysql\my.cnf
[mysqld] character-set-server=utf8
apache_php5\docker\php\Dockerfile
FROM php:5.6-apache RUN apt-get update && \ docker-php-ext-install pdo_mysql mysqli mbstring
apache_php5\docker\php\php.ini
date.timezone = Asia/Tokyo
apache_php5\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
■よく使用するコマンド $ cd /c/Users/refirio/docker/apache_php5/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に接続 ■ブラウザからのアクセス http://192.168.99.100/ http://192.168.99.100/db_admin/ ■疑問点とメモ ・dockerのgit管理 汎用的な環境というより、特定の案件の環境を管理するためのもの。だと思う それなら、プログラムと同じリポジドリで管理すれば良さそう ・プログラムはフォルダ共有したい、venderは各々の環境で作らせたい。は大丈夫? ・fake s3 というものがあるらしい。ローカルでs3を試せるらしい ・上の手順で docker-compose build した場合、REPOSITORYもTAGも「<none>」のイメージが作られる?こういうもの?名前は指定できる? 以下で環境を立ち上げるとどうなるか試す http://koni.hateblo.jp/entry/2017/01/28/150522 ・apache_php5 のファイル構成は以下も参考に再考する 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-compose-yml%E3%81%A8dockerfile%E3%81%AE%E3%81%A9%E3%81%A1%E3%82%89%E3%81%A7%E5%AE%9A%E7%BE%A9%E3%81%99%E3%82%8B%E3%81%BB%E3%81%86%E3%81%8C%E3%81%84%E3%81%84 ・本番環境に使う場合、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のイメージ削除時のエラー「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/
■コマンドまとめ
# イメージをまとめてビルド。イメージがローカルになければプル 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 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 # Vimを使用する apt-get update apt-get install vim
■その他の環境
■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; location / { fastcgi_split_path_info ^(.+\.php)(/.+)$; fastcgi_pass php:9000; fastcgi_index index.php; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_param PATH_INFO $fastcgi_path_info; } location ~ .*\.(jpg|JPG|gif|GIF|png|PNG|swf|SWF|css|CSS|js|JS|inc|INC|ico|ICO) { } }
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/ にアクセスすると「Welcome to nginx!」が表示されたが、配置したコンテンツではない (IPアドレスでアクセスすると /usr/share/nginx/html が参照される) IPアドレスでのアクセスについて 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
バーチャルホストを設定したい場合は問題ないが、 開発環境として使うならhostsの設定無しでアクセスできる方が手軽でいいかも 各コンテナに接続する場合 $ 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+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; 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コンテナ上で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 以下、引き続き検証メモ 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"
■旧メモ
http://qiita.com/osuo/items/99a2b7413ce75f8217be 初回起動は主にこのページを参考にした http://qiita.com/kamonamban/items/e0150a2a7a4d28db10c4 以降はこのページを参考に…と思うけど、結構手順が多そう? http://koni.hateblo.jp/entry/2017/01/28/150522 少し試すくらいなら、これが判りやすいかも? ■bashコンテナで試す http://www.atmarkit.co.jp/ait/articles/1701/31/news043.html $ docker pull bash $ docker images bash-4.4# ps bash-4.4# cat /etc/os-release ■Rubyコンテナで試す http://www.atmarkit.co.jp/ait/articles/1702/01/news061.html $ docker search ruby $ docker pull ruby $ docker images $ docker run -it ruby irb(main):001:0> puts "Hello, world\n" $ docker ps -a docker rm ca5688ba4d6f … psで表示されるIDを指定 ■CentOS6+Apache2.2を試す http://qiita.com/na0AaooQ/items/31d02ae89b4501f11d5d $ docker pull centos:centos6 $ docker images $ docker run -i -t centos:centos6 /bin/bash [root@d9e1054eaec8 /]# hostname [root@d9e1054eaec8 /]# yum -y install httpd [root@d9e1054eaec8 /]# rpm -qa | grep httpd [root@d9e1054eaec8 /]# cp -p /etc/httpd/conf/httpd.conf /etc/httpd/conf/httpd.conf.ORG [root@d9e1054eaec8 /]# sed -i -e 's/\#ServerName www.example.com:80/ServerName example-web-server.example.com/g' /etc/httpd/conf/httpd.conf [root@d9e1054eaec8 /]# diff /etc/httpd/conf/httpd.conf /etc/httpd/conf/httpd.conf.ORG [root@d9e1054eaec8 /]# /etc/init.d/httpd start [root@d9e1054eaec8 /]# ps awux | grep -v grep | grep http [root@d9e1054eaec8 /]# ls -lrta /var/www/html/ [root@d9e1054eaec8 /]# echo "docker test server" >> /var/www/html/index.html [root@d9e1054eaec8 /]# curl http://127.0.0.1/ [root@d9e1054eaec8 /]# chkconfig httpd on [root@d9e1054eaec8 /]# exit docker ps -a docker commit d9e1054eaec8 centos:centos6/httpd ... 「invalid reference format」になる。今は「/」を使えないとか? docker commit d9e1054eaec8 centos:centos6_httpd docker images docker run -i -t centos:centos6_httpd /bin/bash ps awux | grep -v grep | grep http /etc/init.d/httpd start ps awux | grep -v grep | grep http curl http://127.0.0.1/ exit docker ps -a docker run -i -t -p 50050:80 centos:centos6_httpd /bin/bash # /etc/init.d/httpd start # curl http://127.0.0.1/ # Ctrl + pキーとCtrl + qキーの順に押下して、コンテナ内からログアウト curl http://127.0.0.1:50050/ … 接続できない docker run -d -t -p 8888:80 -p 2222:22 centos:centos6_httpd docker run -d -p 8888:80 centos:centos6_httpd docker start d97d6379e64c docker attach d97d6379e64c docker images docker rmi 2f37bab81128 … イメージの削除 docker ps -a docker stop d97d6379e64c … コンテナの停止 docker rm d97d6379e64c … コンテナの削除 http://www.ryuzee.com/contents/blog/6952 ■PHPの開発環境一式を試す(成功せず) http://koni.hateblo.jp/entry/2017/01/28/150522 C:\Users\refirio\Docker がDocker用の作業フォルダだとする refirio@DESKTOP-OIIH873 MINGW64 ~ $ cd Docker $ mkdir test $ cd test $ pwd /c/Users/refirio/Docker/test https://github.com/koni/docker-php-nginx-mysql-memcached の内容を C:\Users\refirio\Docker\test 内に配置 $ cd docker $ docker-compose up 5分ほどでログが止まった 完了しているように見えないが、そのまま30分ほど待っても変化なし http://localhost/ にアクセスしても接続できない 最後のログは mysql | 2017-07-04T06:54:49.480448Z 0 [Note] Beginning of list of non-natively partitioned tables だった ■メモ Dockerについて基本から最近追加された機能までまとめ - Qiita https://qiita.com/yuki_ycino/items/b94ae2bf7d78685cd6f5 超入門Docker:第1回 Dockerとは - @IT http://www.atmarkit.co.jp/ait/articles/1701/30/news037.html Dockerコンテナを作成してApache2.2を動かす - Qiita https://qiita.com/na0AaooQ/items/31d02ae89b4501f11d5d 【超簡単】Docker でモダンな PHP 開発環境を作る (PHP, MySQL, PHP-FPM, nginx, memcached) - koni blog http://koni.hateblo.jp/entry/2017/01/28/150522 Docker Hubのオフィシャルイメージを使ったLAMP環境(Apache+PHP+MySQL)構築 - Qiita https://qiita.com/naga3/items/be1a062075db9339762d