docker入門實戰

基本概念

Docker 是一個開源的應用容器引擎,讓開發者能夠打包他們的應用以及依賴包到一個可移植的容器中,而後發佈到任何流行的 Linux 機器上。html

Docker是一個從新定義了程序開發測試、交付和部署過程的開放平臺,Docker則能夠稱爲構建一次,處處運行,這就是docker提出的「Build once,Run anywhere」java

 

備註:java提出的是」 compile Once,Run Anywhere」python

Docker與linux內核的關係

docker與linux內核的關係mysql

 

Cgroup: 對資源進行限制(如對物理資源CPU、內存、I/O的限制)linux

Namespace:對進程進行隔離web

Chroot: 能改變當前運行的進程和子進程的根目錄redis

AUFS:聯合文件系統,Docker利用AUFS將不一樣的Layer結合到1個image中去sql

Docker架構

 

Docker採用C/S架構,客戶端與服務器端不必定要在一塊兒。客戶端能夠運行在windows、linux等機器上,而後服務器端必須運行在linux 64bit的操做系統上。docker

Docker「組件間」關係

 

ü  主機:運行容器的機器json

ü  鏡像:文件的層次結構,以及包含如何運行容器的元數據, Dockerfile中的每條命令都會在文件系統中建立一個新的層次結構,文件系統在這些層次上構建起來,鏡像就構建於這些聯合的文件系統之上

ü  容器:一個從鏡像中啓動,包含正在運行的程序的進程

ü  Registry(鏡像倉庫):存放鏡像的地方,如Docker Hub

ü  Volumn(卷):將物理機的文件夾掛載到容器內部.與openstack的volumn不同,openstack中的卷是塊存儲,不能共享。而這裏的volumn能夠共享。

ü  Dockerfile:用於建立鏡像的腳本

Docker應用場景

面向開發人員:快速開發、交付應用程序

主要體如今三個方面:

ü  代碼一致:

在沒有docker以前,開發、測試、生成環境可能不同,如發佈某個服務的端口時,開發是1000,而生產是2000,這就致使配置文件不一致。然而使用docker後,我在容器內的端口都是同樣的,而容器對外暴露的端口可能不同。

ü  開發環境與生產環境的一致性

咱們知道,在生產環境的部署比較複雜,服務很是繁多。經過docker,咱們能夠單機版上經過容器來模擬生產環境的分佈式環境。從而讓開發人員的開發更有效率。

ü  快速部署

 能夠將docker理解爲輕量級的虛擬機,啓動docker容器速度很快,啓動虛擬機很慢。

面向運維人員:下降運維成本

ü  節約安裝各類軟件的時間。

     在沒有docker以前,在部署程序以前,勢必要搭建環境,而搭建環境很花費時間,還要解決環境的各類依賴,而docker經過鏡像機制,將你的代碼和運行環境直接打包成鏡像,扔到容器啓動便可。

ü  下降運維成本。

在沒有docker以前,因爲技術不斷髮展,運維也要不停的學習各類軟件的使用技能,如Node.js、redis等。有了docker,根本不用關係這些技術(或者少關心),只須要關注容器就能夠了,可以正常的發佈容器,中止容器、刪除容器、遷移容器就能夠了。

面向企業: Paas層的實現

Coding.net、Oschina這些代碼託管平臺,有個功能即提供給用戶程序的演示環境,我不知道他們底層到底採用的什麼技術,可是若是Iaas層的openstack,給用戶直接提供虛擬機,先得太「笨重」,由於虛擬機自己對物理機的開銷就比較大,若是採用Docker,我1臺物理機能夠部署多個容器,能夠下降企業的採購物理機的費用,並且運行效率上應該比採用Iaas層的方案快。

 

Docker基本命令

Docker安裝相關命令

參考: https://docs.docker.com/installation/ubuntulinux/

這裏以在unbuntu14.04上安裝爲例:

Ø  建立docker用戶並將其歸入docker這個用戶組

#useradd docker -g docker

 

Ø  更新源

#sudo apt-get update

 

Ø  安裝依賴包

#sudo apt-getinstall linux-image-generic-lts-trusty

 

Ø  重啓

#sudo reboot

 

Ø  安裝docker

#sudo apt-getinstall wget     // 能夠經過命令which wget是否已安裝

#wget -qO-https://get.docker.com/ | sh   //獲取最新版本

 

Ø  驗證安裝是否成功

#sudo docker runhello-world

 

Docker服務相關命令

Docker服務啓動|重啓|中止

#service docker start    //啓動

#service docker restart  //重啓

#service docker stop    //中止

Docker服務對應的版本查看

# sudo docker version

Docker環境查看

#sudo docker info

Containers: 5

Images: 129

Storage Driver: aufs

 Root Dir: /var/lib/docker/aufs

 Backing Filesystem: extfs

 Dirs: 139

Execution Driver: native-0.2

Kernel Version:3.13.0-32-generic

Operating System: Ubuntu14.04.1 LTS

CPUs: 2

Total Memory: 3.673 GiB

Name: docker

ID: OWRW:DDDW:MQZD:CCKM:JDKM:5ZEP:LTBB:YG3H:QI7G:EMDE:MSMR:XDFK

Username: ningyougang

Registry:[https://index.docker.io/v1/]

WARNING: No swap limit support

Docker命令幫助

#sudo docker  //查看docker的全部命令

#sudo docker command --help  //查看單個docker命令的幫助,如docker ru--help

 

Docker容器相關命令

啓動一次性運行的容器

入門級例子:從ubuntu:14.04鏡像啓動一個容器,成功後在容器內部執行/bin/echo ‘hello world’命令,若是當前物理機沒有該鏡像,則執行docker pull從Docker Hub獲取鏡像,執行成功後,容器立馬中止

#sudo docker runubuntu:14.04 /bin/echo 'Hello world'

 

參數解釋

dockerrun:docker中的啓動容器命令

Ubuntu:鏡像名稱

14:04:鏡像TAG,若是不指定TAG,docker使用最新的發行版TAG:latest

/bin/echo ‘Helloworld’:在容器內執行的命令

 

該命令執行過程

l  若是本地有ubuntu這個image就從它建立容器,不然從公有倉庫下載

l  從image建立容器

l  分配一個文件系統,並在只讀的image層外面掛載一層可讀寫的層

l  從宿主主機配置的網橋接口中橋接一個虛擬接口到容器中去

l  從地址池配置1個ip地址給容器

l  執行你指定的程序,在這裏啓動一個/bin/bash

啓動交互模式容器

以交互模式啓動一個容器(具體參數意義請執行dockerrun --help)

$ sudo docker run -t-i ubuntu:14.04 /bin/bash

 

參數解釋

-t:開啓一個終端

-i:以交互模式運行

啓動後臺模式容器

之後臺模式運行一個容器

#sudo docker run -dubuntu:14.04 /bin/sh -c "while true; do echo hello world; sleep 1;done"

1e5535038e285177d5214659a068137486f96ee5c2e85a4ac52dc83f2ebe4147

 

參數解釋

-d:之後臺Daemon方式運行,執行成功後會返回一個該容器的ID

 

以映射端口方式啓動一個Web容器

# sudo docker run -d -P training/webapp Python app.py

 

參數解釋

-d:之後臺Daemon方式運行,執行成功後會返回一個該容器的ID

-P:端口映射,外部端口到容器端口的映射規則由docker負責

-p:本身指定端口映射規則,格式爲:-p 外部端口:容器端口

經過docker ps -l,能夠查看到其PORTS列的端口映射規則

 

固然你也能夠,手工指定端口映射規則來啓動Web容器

#sudo docker run -d -p 5000:5000 training/webapp pythonapp.py

 

備註:-p 完整的參數爲:-p ip:hostport:port,將當前物理機的ip的端口映射到容器的端口

 

若是你想經過很快捷的方式查看容器的端口

#sudo docker port 容器ID或容器名稱

 

查看容器的具體信息

以JSON的格式返回容器的具體信息

#sudo docker inspect容器ID或容器名稱

進入容器執行命令

#sudo docker exec -it 容器ID /bin/bash

 

備註:通常對運行着的後臺容器,執行該命令。查看其容器內部的狀況。

查看容器的日誌

$sudo docker logs 容器ID或容器名稱

 

參數解釋

-f:以滾動的形式查看日誌,相似於linux的tail -f XXX.log

 

退出當前容器

$sudo exit  //在容器內部執行該命令(或crtl+D),通常在交互模式下退出當前容器

 

備註:容器仍然運行着

建立容器

# sudo docker create--name ubuntContainer ubuntu:14.04 /bin/echo 'Hello world'

重啓容器

#sudo docker restart 容器ID

暫停容器

#sudo docker pause 容器ID  //暫停

#sudo docker unpause 容器ID //解除暫停

中止容器

$sudo docker stop 容器ID或容器名稱

 

#docker stop $(docker ps -q -a)  //一次性中止全部容器,慎用

殺死容器

$sudo docker kill 容器ID或容器名稱

刪除容器

$sudo docker rm 容器ID或容器名稱   //刪除容器,正在運行的容器不能刪除

#sudo docker rm $(docker ps -q -a)  //一次性刪除全部容器,慎用

 

單個主機間的容器訪問

下面咱們經過mysql_server容器與mysql_client容器的互聯來了解link

Ø  建立mysql_server鏡像,並生成一個容器

#cd /

#mkdir mysql_server

#vi Dockerfile

FROM centos:centos6

MAINTAINER ningyougang "xxxx@qq.com" 

  

RUN yum install -y MySQL-server mysql 

  

RUN /etc/init.d/mysqld start &&\ 

    mysql -e"grant all privileges on *.* to 'root'@'%' identified by'mysql';"&&\ 

    mysql -e"grant all privileges on *.* to 'root'@'localhost' identified by'mysql';"&&\ 

    mysql -u root-pmysql -e "show databases;" 

  

EXPOSE 3306 

  

CMD ["/usr/bin/mysqld_safe"]

 

# sudo docker build -t ningyougang/mysql_server .  //生成鏡像

#sudo docker run --name=mysql_server -d -Pningyougang/mysql_server //生成mysql_server容器

Ø  建立mysql_client鏡像,並生成一個link到mysql_server的client容器

#cd /

#mkdir mysql_client

#vi Dockerfile

FROM centos:centos6 

MAINTAINER ningyougang "xxxx@qq.com" 

  

RUN yum install -y mysql

 

#sudo docker build -t ningyougang/mysql_client .  //生成鏡像

#sudo dockerrun --name=mysql_client1 --link=mysql_server:db -t -i ningyougang/mysql_client/usr/bin/mysql -h db -u root -pmysq            //生成mysql_client容器

 

參數解釋

--link:<name or id>:alias

 

經過上面的命令,link中的別名(alias)db便是mysql_client鏈接mysql_server的鏈接串

 

Ø  進入mysql_client研究其link的實現細節

#sudo docker exec-it bfc6cb037165 /bin/bash    //以交互模式進入mysql_client容器內部

[root@bfc6cb037165/]# env | grep DB  //查看與DB(也就是alias)相關的環境變量

DB_NAME=/mysql_client2/db

DB_PORT=tcp://172.17.0.25:3306

DB_PORT_3306_TCP_PORT=3306

DB_PORT_3306_TCP_PROTO=tcp

DB_PORT_3306_TCP_ADDR=172.17.0.25

DB_PORT_3306_TCP=tcp://172.17.0.25:3306

 

 [root@bfc6cb037165 /]#vi /etc/hosts

172.17.0.27     bfc6cb037165      #docker生成的mysql_client的IP、域名

172.17.0.25     db               #docker生成的mysql_server的IP、域名

 

總結:能夠發現docker在mysql_client內經過生成別名的環境變量和profile相關的主機和域名的配置,打通了客戶端到服務器端的tcp鏈接通道,而對於上層的應用,不須要關注IP、端口這些細節,只須要經過別名來訪問便可

 

 

Docker網絡

參考: http://www.open-open.com/doc/view/f720084681bb434bbed132d2bc1493ac

 

跨主機間的容器訪問

Ø  使用自定義網橋鏈接跨主機容器

N/A,待寫

Ø  使用Ambassador實現跨主機容器

N/A, 待寫

Ø  kubernetes

N/A, 待寫

數據管理

Ø  把物理機的目錄掛載到容器裏

以交互模式啓動一個容器,將物理機的/src/webapp掛載到/opt/webapp下

#sudodocker run -t -i  -v /src/webapp:/opt/webappubuntu:14.04 /bin/bash

參數解釋

-v 物理機目錄:容器目錄:讀寫權限

 其中默認的權限爲可讀寫,  ro:只讀

Ø  把物理機的文件掛載到容器裏

#sudo dockerrun -t -i  -v/src/webapp/test.html:/opt/webapp/test.html ubuntu:14.04 /bin/bash

 

Ø  把容器掛載到另一個容器

#sudo docker create -v /dbdata --name dbdata ubuntu:14.04  //建立容器

#sudodocker run -it --volumes-from dbdata ubuntu:12.04 /bin/bash //啓動容器捲來自dbdata

參數解釋

-volumn-from:捲來自哪一個容器

 

Ø  把容器掛載做爲數據備份

#sudo docker run --volumes-from dbdata -v $(pwd):/backup--name worker ubuntu tar cvf /backup/backup.tar /dbdata

命令解釋

首先利用ubuntu鏡像建立一個容器worker.使用—volumes-from dbdata參數來讓容器掛載dbdata容器的數據卷;使用 –v $(pwd):/backup參數來掛載本機的當前目錄到worker容器的/backup目錄

Woker容器啓動後,執行tar命令將/dbdata壓縮到/backup/backup.tar,這樣就到物理機的當前目錄了

Ø  把容器掛載做爲數據遷移

#sudo docker run -v/dbdata --name dbdata2 ubuntu /bin/bash

#sudo docker run--volumes-from dbdata2 -v $(pwd):/backup busybox tar  xvf /backup/.tar

掛載到某個容器

#sudo docker attach 容器ID

顯示運行容器的進程信息

#sudo docker top 容器ID

 

從容器內部拷貝文件到物理機

#sudo docker cp cd0f61fb8256:/opt/a.html /

列出容器裏被改變的文件夾或文件

#sudo docker diff 容器ID

列表解釋

list列表會顯示出三種事件,A 增長的,D 刪除的,C 被改變的 

Docker鏡像相關命令

鏡像查看

#sudo docker images  //在本機進行鏡像查看

 

 

#sudo docker inspect 鏡像ID   //查看單個鏡像的具體信息,以JSON格式返回

獲取鏡像

# sudo docker pull centos    //從DockerHub獲取鏡像

 

查詢鏡像

#sudo docker search 鏡像名稱  //從DockerHub按照鏡像名稱模擬查詢鏡像

製做鏡像

ü  經過Dockerfile構建鏡像

#sudo cd /              //來到根「/」下

#sudo mkdir redis       //建立redis文件夾

#touch Dockerfile       //建立Dockerfile文件,文件內容見以下灰色部分

FROM        ubuntu:14.04

RUN         apt-get update && apt-getinstall -y redis-server

EXPOSE      6379

ENTRYPOINT  ["/usr/bin/redis-server"]

 

#sudo docker build -t ningyougang/redis .     //經過dockerbuild製做鏡像

參數解釋

-t:tag名稱

.:當前Dockerfile的路徑,在此處表示當前文件夾下

 

ü  對運行着的容器commit鏡像

# sudo docker commit -m "Added json gem" -a"Kate Smith" 0b2616b0e5a8 ouruser/sinatra:v2

參數解釋

-m:提交註釋,如此處你加了什麼特別的功能

-a:做者

0b2616b0e5a8:運行着的容器ID

ouruser/sinatra:v2:給當前提交的鏡像起名字並打標籤

 

備註:從上面能夠看出,咱們能夠經過dockercommit來建立鏡像,可是這種方式有點凌亂並且很難複製,更好的方式是經過Dockerfile來構建鏡像,由於它步驟清晰而且容易複製

給鏡像打標籤

#sudo docker tag 5db5f8471261 ouruser/sinatra:devel  //當commit or build後,對鏡像打標籤

參數解釋

5db5f8471261:此處的id爲鏡像ID

 

備註:向私有倉庫push鏡像也要打標籤

推送鏡像到公共庫DockerHub

#sudo docker push ouruser/sinatra

 

下面介紹下DockerHub

DockerHub是存放鏡像的遠程倉庫,這裏簡單介紹下,如何使用

Ø  註冊

首先在https://hub.docker.com/account/signup/完成賬號註冊

 

Ø  登陸

賬號註冊成功後,在https://hub.docker.com/account/login/,便可登陸

 

除了經過登陸頁面,您也能夠經過命令行,經過指令sudo docker login登陸

 

Ø  查詢鏡像

點擊「Browse Repos」(或輸入https://registry.hub.docker.com/),進入鏡像查詢頁面

 

在此頁面,您能夠錄入你感興趣的鏡像名稱,進行模糊查詢

固然你也能夠經過docker search  XXX進行鏡像查詢

 

Ø  使用Docker賬號綁定GitHub賬號,進行自動化構建

須要細化,沒有來得及研究

推送鏡像到私有庫

ü  下載私有倉庫鏡像

# docker pull registry           #從DockerHub下載registry鏡像,裏面含私庫的運行環境,#固然你也能夠本身下載源碼包,本身安裝

 

ü  推送以前打tag

# docker tag 704ca5ad68c5 192.168.202.213:5000/newtouch/activemq #打標籤(必須先打標籤,#在推送)

該命令格式爲:docker tag $ID $IP:$port/$name。push到私庫上必須先打個tag,而tag名稱的格式爲:$IP:$port/$name, 我的感受此處設計不太好或我本身沒有找到更好的辦法。若是設計良好應該能夠直接push,不用打標籤.

ü  Push tag到鏡像

#docker push 192.168.202.213:5000/newtouch/activemq    #將此tag推送到私有庫

 

ü  Push到倉庫後,遠程查看

#curl http://192.168.202.213:5000/v1/search             #push以後,遠程查看

 

ü  在另一個docker客戶端,從私有倉庫下載

#docker pull 192.168.202.213:5000/newtouch/activemq

 

Docker tag報https錯誤問題解決:

vi /etc/default/docker     #紅色部分是添加的部分,重啓docker服務

# Docker Upstart and SysVinitconfiguration file

 

# Customize location of Dockerbinary (especially for development testing).

#DOCKER="/usr/local/bin/docker"

 

# Use DOCKER_OPTS to modify thedaemon startup options.

#DOCKER_OPTS="--dns8.8.8.8 --dns 8.8.4.4"

DOCKER_OPTS="--insecure-registry 192.168.202.213:5000"

 

# If you need Docker to use anHTTP proxy, it can also be specified here.

#exporthttp_proxy="http://127.0.0.1:3128/"

 

# This is also a handy place totweak where Docker's temporary files go.

#exportTMPDIR="/mnt/bigdrive/docker-tmp"

 

刪除鏡像

#sudo docker rmi 鏡像ID

列出鏡像的變動歷史

# docker history

Docker運維相關命令

在物理機下查看有哪些容器

$ sudo docker ps       //查看有那些正在運行着的容器

 

參數解釋

-l:最近的一個容器,有可能沒有運行

-a:查看全部的容器,包含運行和沒有運行的容器

實時打印全部容器的系統事件

#sudo docker events

相關文章
相關標籤/搜索