在Docker – 系統整潔之道 – 1中已經對Docker的一些命令和Docker鏡像的使用及操作做了記錄。 這次就利用docker進行一次真正的實例使用,使用docker搭建一個簡單的答題系統,這個系統是當時做來給網絡安全周做手機答題的系統,很簡單,代碼風格很差。
這篇主要記錄了三種docker使用的方式。
用supervisor方式運行一個多進程的docker實例創建一個ngnix和php運行的環境創建一個ngnix,php,MySQL集合運行的環境,使用docker-compose構建感覺docker的東西越看越多,從剛開始的簡簡單單的一個docker run,到現在看到要build自己的鏡像,compose,也就是以前的Fig,配置網絡,還有swarm的docker集群,一點一點來吧。
先把兩個附件寫在這里吧 此片博客中構建php+ngnix+mysql測試環境的腳本 在測試環境中的答題網站源碼
Docker 容器在啟動的時候開啟單個進程,比如,一個 ssh 或者 apache 的 daemon 服務。但我們經常需要在一個機器上開啟多個服務,這可以有很多方法,最簡單的就是把多個啟動命令放到一個啟動腳本里面,啟動的時候直接啟動這個腳本,另外就是安裝進程管理工具。這里使用進程管理工具 supervisor 來管理容器中的多個進程。使用 Supervisor 可以更好的控制、管理、重啟我們希望運行的進程。
首先創一個文件夾叫做supervisor
,目錄結構為
其中文件Dockerfile文件內容為:
#使用時哪個鏡像FROM Ubuntu:13.04MAINTAINER examples@docker.comRUN echo "deb http://archive.ubuntu.com/ubuntu PRecise main universe" > /etc/apt/sources.listRUN apt-get updateRUN apt-get upgrade -y#這里安裝 3 個軟件,還創建了 2 個 ssh 和 supervisor 服務正常運行所需要的目錄。RUN apt-get install -y --force-yes perl-base=5.14.2-6ubuntu2RUN apt-get install -y apache2.2-commonRUN apt-get install -y openssh-server apache2 supervisorRUN mkdir -p /var/run/sshdRUN mkdir -p /var/log/supervisor#添加 supervisord 的配置文件,并復制配置文件到對應目錄下面。COPY supervisord.conf /etc/supervisor/conf.d/supervisord.conf#映射了 22 和 80 端口,使用 supervisord 的可執行路徑啟動服務EXPOSE 22 80CMD ["/usr/bin/supervisord"]文件supervisord
內容為:
使用命令進行構建
sudo docker build -t supervisor輸出:
~/Docker/supervisor sudo docker build -t supervisord .PassWord:Sending build context to Docker daemon 3.584 kBStep 1 : FROM ubuntu:13.04---> a58cd502f927Step 2 : MAINTAINER examples@docker.com---> Using cache---> 15f104cdeb77Step 3 : RUN echo "deb http://archive.ubuntu.com/ubuntu precise main universe" > /etc/apt/sources.list---> Using cache---> c6bb44d794eaStep 4 : RUN apt-get update---> Using cache---> adcd83eecb0dStep 5 : RUN apt-get upgrade -y---> Using cache---> 89e045811261Step 6 : RUN apt-get install -y --force-yes perl-base=5.14.2-6ubuntu2---> Using cache---> bcdc472cc73aStep 7 : RUN apt-get install -y apache2.2-common---> Using cache---> d8991f8aa3c6Step 8 : RUN apt-get install -y openssh-server apache2 supervisor---> Using cache---> a713034800d6Step 9 : RUN mkdir -p /var/run/sshd---> Using cache---> 3138e3644958Step 10 : RUN mkdir -p /var/log/supervisor---> Using cache---> 958c08978b0cStep 11 : COPY supervisord.conf /etc/supervisor/conf.d/supervisord.conf---> 8e9a0c97a133Removing intermediate container d95b58057f73Step 12 : EXPOSE 22 80---> Running in 9cabb0865159---> b4aa8b82cd57Removing intermediate container 9cabb0865159Step 13 : CMD /usr/bin/supervisord---> Running in 237f71166211---> 569f95736129Removing intermediate container 237f71166211Successfully built 569f95736129使用docker ps
一下
發現剛才build的鏡像已經跑起來了,訪問 http://127.0.0.1:32769,可以web服務已經跑起來了。
使用命令docker exec
進入container里面看看
使用passwd修改一下密碼,然后在本機的命令行里進行ssh連接吧。
該方法就是直接使用docker命令進行構建一個ngnix,php結合運行的環境,沒有使用docker-compose。
先用戶根目錄~
下創建目錄,并將該目錄設置為Docker的共享目錄。
其中default.conf
文件內容,這是個nginx的配置文件
index.html 里寫一句 HelloW0rld,phpinfo.php里面寫一個<?php phpinfo();?>
。
然后在命令行下執行命令
docker pull php:5.6-fpm-alpinedocker pull ngnix:1.10.2docker run --name dream.php -d -v ~/Workspace/tmp/www:/var/www/html:ro php:5.6-fpmdocker run --name dream.nginx -p 80:80 -d -v ~/Workspace/tmp/www:/usr/share/nginx/html:ro -v ~/Workspace/tmp/docker/nginx/conf.d:/etc/nginx/conf.d:ro --link dream.php:php nginx:1.10.2好的,如果不出意外,就可以看到phpinfo的界面了。這個是沒有添加mysql的測試環境,直接在目錄~/Workspace/tmp/www
下面放網頁就可以直接使用了。
Supervisor給出了一種能夠在container中運行多個線程的方法,但是現在還是不知道要怎么樣把自己的web服務部署到container中,數據庫怎么建,可以有人會說直接使用SFTP將網站直接傳到container里,安裝數據庫,配環境,但是docker中一旦container被刪除,內容就沒了。像這樣將所有服務放在一個容器內的模式有個形象的非官方稱呼:Fat Container。與之相對的是將服務分拆到容器的模式。從Docker的設計可以看到,構建鏡像的過程中可以指定唯一一個容器啟動的指令,因此Docker天然適合一個容器只運行一種服務,而這也是官方更推崇的。下面就記錄一下部署一個簡單的php程序和數據庫聯動的測試環境。
整體的文件結構是這樣的 我們創建一個這樣的目錄
Docker└── test ├── data 數據庫文件夾 │ └── mysql ├── docker-compose.yml docker-compose配置文件 ├── htdocs 網站文件夾 │ ├── index.html │ └── index.php ├── log 日志文件 │ └── nginx ├── mysql mysql構建文件 │ └── Dockerfile ├── nginx nginx構建文件 │ ├── Dockerfile │ ├── conf.d │ │ └── default.conf │ └── nginx.conf └── php php構建文件 └── Dockerfilemysql目錄下的Dockerfile文件只有一行FROM mysql:5.6
,也就是直接使用mysql官方鏡像5.6,然后使用命令
構建自己的鏡像phpenv/mysql。 使用命令
docker run -p 3306:3306 -v ~/Docker/test/data/mysql:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 -it phpenv/mysql啟動鏡像,將容器的3306端口綁定到本機的3306端口,其中參數-v
后代表使用~/Docker/test/data/mysql
掛在到鏡像的/var/lib/mysql
,也就是替代源鏡像的數據庫文件目錄,讓數據庫文件目錄暴露在本機上,做到數據庫內容的持久化。MYSQL_ROOT_PASSWORD
為設置mysql的一個root密碼。
運行結果
~/Docker/test docker run -p 3306:3306 -v ~/Docker/test/data/mysql:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 -it phpenv/mysql2016-12-27 15:06:49 0 [Note] mysqld (mysqld 5.6.35) starting as process 1 ...2016-12-27 15:06:49 1 [Warning] Setting lower_case_table_names=2 because file system for /var/lib/mysql/ is case insensitive2016-12-27 15:06:49 1 [Note] Plugin 'FEDERATED' is disabled.2016-12-27 15:06:49 1 [Note] InnoDB: Using atomics to ref count buffer pool pages2016-12-27 15:06:49 1 [Note] InnoDB: The InnoDB memory heap is disabled2016-12-27 15:06:49 1 [Note] InnoDB: Mutexes and rw_locks use GCC atomic builtins2016-12-27 15:06:49 1 [Note] InnoDB: Memory barrier is not used2016-12-27 15:06:49 1 [Note] InnoDB: Compressed tables use zlib 1.2.82016-12-27 15:06:49 1 [Note] InnoDB: Using Linux native AIO2016-12-27 15:06:49 1 [Note] InnoDB: Using CPU crc32 instructions2016-12-27 15:06:49 1 [Note] InnoDB: Initializing buffer pool, size = 128.0M2016-12-27 15:06:49 1 [Note] InnoDB: Completed initialization of buffer pool2016-12-27 15:06:49 1 [Note] InnoDB: Highest supported file format is Barracuda.2016-12-27 15:06:49 1 [Note] InnoDB: 128 rollback segment(s) are active.2016-12-27 15:06:49 1 [Note] InnoDB: Waiting for purge to start2016-12-27 15:06:49 1 [Note] InnoDB: 5.6.35 started; log sequence number 16260272016-12-27 15:06:49 1 [Note] Server hostname (bind-address): '*'; port: 33062016-12-27 15:06:49 1 [Note] IPv6 is available.2016-12-27 15:06:49 1 [Note] - '::' resolves to '::';2016-12-27 15:06:49 1 [Note] Server socket created on IP: '::'.2016-12-27 15:06:49 1 [Warning] 'proxies_priv' entry '@ root@bd69eb248839' ignored in --skip-name-resolve mode.2016-12-27 15:06:49 1 [Note] Event Scheduler: Loaded 0 events2016-12-27 15:06:49 1 [Note] mysqld: ready for connections.Version: '5.6.35' socket: '/var/run/mysqld/mysqld.sock' port: 3306 MySQL Community Server (GPL)使用DBeaver連接后
查看一下當前~/Docker/test/data/mysql
數據庫目錄下的文件
新建一個庫docker_test后~/Docker/test/data/mysql
數據庫目錄下的文件
可以發現數據庫已經創建好了,也如下圖
為了驗證數據庫數據的持久型,我們先停止當前運行的container并產出它,然后從鏡像啟動一個新的container,如命令
~/Docker ? docker psCONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES970dec0f7de9 phpenv/mysql "docker-entrypoint.sh" 30 minutes ago Up 30 minutes 0.0.0.0:3306->3306/tcp berserk_brown~/Docker ? docker stop 970dec0f7de9970dec0f7de9~/Docker ? docker rm 970dec0f7de9970dec0f7de9~/Docker ? docker ps -aCONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMESc82c830770bc supervisord:latest "/usr/bin/supervisord" 35 hours ago Exited (0) 32 minutes ago supervisord~/Docker ? docker run -p 3306:3306 -v ~/Docker/test/data/mysql:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 -it phpenv/mysql2016-12-27 15:38:04 0 [Note] mysqld (mysqld 5.6.35) starting as process 1 ...2016-12-27 15:38:04 1 [Warning] Setting lower_case_table_names=2 because file system for /var/lib/mysql/ is case insensitive2016-12-27 15:38:04 1 [Note] Plugin 'FEDERATED' is disabled.2016-12-27 15:38:04 1 [Note] InnoDB: Using atomics to ref count buffer pool pages2016-12-27 15:38:04 1 [Note] InnoDB: The InnoDB memory heap is disabled2016-12-27 15:38:04 1 [Note] InnoDB: Mutexes and rw_locks use GCC atomic builtins2016-12-27 15:38:04 1 [Note] InnoDB: Memory barrier is not used2016-12-27 15:38:04 1 [Note] InnoDB: Compressed tables use zlib 1.2.82016-12-27 15:38:04 1 [Note] InnoDB: Using Linux native AIO2016-12-27 15:38:04 1 [Note] InnoDB: Using CPU crc32 instructions2016-12-27 15:38:04 1 [Note] InnoDB: Initializing buffer pool, size = 128.0M2016-12-27 15:38:04 1 [Note] InnoDB: Completed initialization of buffer pool2016-12-27 15:38:04 1 [Note] InnoDB: Highest supported file format is Barracuda.2016-12-27 15:38:04 1 [Note] InnoDB: 128 rollback segment(s) are active.2016-12-27 15:38:04 1 [Note] InnoDB: Waiting for purge to start2016-12-27 15:38:04 1 [Note] InnoDB: 5.6.35 started; log sequence number 16260372016-12-27 15:38:04 1 [Note] Server hostname (bind-address): '*'; port: 33062016-12-27 15:38:04 1 [Note] IPv6 is available.2016-12-27 15:38:04 1 [Note] - '::' resolves to '::';2016-12-27 15:38:04 1 [Note] Server socket created on IP: '::'.2016-12-27 15:38:04 1 [Warning] 'proxies_priv' entry '@ root@bd69eb248839' ignored in --skip-name-resolve mode.2016-12-27 15:38:04 1 [Note] Event Scheduler: Loaded 0 events2016-12-27 15:38:04 1 [Note] mysqld: ready for connections.Version: '5.6.35' socket: '/var/run/mysqld/mysqld.sock' port: 3306 MySQL Community Server (GPL)再次連接數據庫驗證,發現剛才新建的庫docker_test
還在,數據庫文件持久型保存了。
待完善
nginx在構建的時候要替換兩個配置文件,Dockfile
FROM nginx:1.10.2ADD nginx.conf /etc/nginx/nginx.confADD conf.d/* /etc/nginx/conf.d/掛載文件在docker-compose里進行定義。
待完善
php什么也不做,只通過Dockfile
FROM php:5.6-fpm來構建
待完善
docker-compose文件
nginx: build: ./nginx ports: - "40080:80" links: - "php" volumes: - ~/Docker/test/htdocs:/usr/share/nginx/htmlphp: build: ./php ports: - "49000:9000" links: - "mysql" volumes: - ~/Docker/test/htdocs:/var/www/htmlmysql: build: ./mysql ports: - "43306:3306" volumes: - ~/Docker/test/data/mysql:/var/lib/mysql environment: MYSQL_ROOT_PASSWORD: 123456記錄一下,首先docker-compse是用來集合構建多個鏡像的工具,這里我們集合了nginx,php,mysql來搭建一個php的測試環境,在文件中,有一個links參數,是用來連接其他實例,讓多個實例之間可以進行通信。
這里有整合文件的下載鏈接,下載后,將文件放在用戶根目錄下,命令行執行docker-compose up
,結果
訪問一下 http://localhost:40080/index.php ,正常的話,如下圖
下面的代碼是今年網絡安全周的一個手機在線答題系統,代碼很挫,大牛誤笑
源碼在這里。
將目錄直接放在~/Docker/test/htdocs
下面,然后在test目錄下執行docker-compose up
,正常情況下,就會跑起來上面的容器,然后按照代碼的README將數據庫部署就可以運行了。
原文鏈接: http://dengnanyi.com/2016/12/24/2016_12/docker-learn-3/
新聞熱點
疑難解答