隨着Docker技術的不斷成熟,愈來愈多的企業開始考慮使用Dockerhtml
Docker是一個開源的容器引擎,它有助於更快地交付應用。 Docker可將應用程序和基礎設施 層隔離,而且能將基礎設施看成程序同樣進行管理。使用 Docker可更快地打包、測試以及部 署應用程序,並能夠縮短從編寫到部署運行代碼的週期。java
1.更高效的利用系統資源python
docker對系統資源的利用率更高,不管是應用執行速度,內存損耗或者文件存儲速度,都要比傳統虛擬機技術更高效。所以,相比虛擬機技術,一個相同配置的主機每每能夠運行更多數量的應用。mysql
2.更快速的啓動時間linux
傳統的虛擬機技術啓動應用服務每每須要數分鐘,而docker容器應用,因爲直接運行於宿主內核,無需啓動完整的操做系統,所以能夠作到秒級,甚至毫秒級的啓動時間,大大的節約了開發測試,部署的時間。nginx
3.一致的運行環境web
開發過程當中常見的一個問題是環境一致問題,因爲開發環境,測試環境,生產環境不一致,致使有些bug並未在開發過程當中發現。而docker的鏡像提供了除內核外完整的運行時環境,確保環境一致性,從而不會在出現「這段代碼在我機器上沒問題」這類問題。面試
4.持續支付和部署redis
對開發和運維人員來講,最但願就是一次建立和部署,能夠在任意的地方運行。(定製應用鏡像來實現集成、持續支付、部署。開發人員能夠經過dockerfile來進行鏡像構建,並結合持續集成系統進行集成測試,而運維人員則能夠直接在生產環境中快速部署該鏡像,甚至結合持續部署系統進行自動部署)。並且使用dockerfile使鏡像構建透明化,不只僅開發團隊能夠理解應用運行環境,也方便運維團隊理解應用運行所需條件,幫助更好的生產環境中部署該鏡像。sql
5.更輕鬆的遷移
因爲docker確保了執行環境的一致性,使得應用的遷移更加的容易。docker能夠在不少平臺上運行,不管是物理機、虛擬機、公有云、私有云、甚至是筆記本、其運行結果是一致的。所以用戶能夠很輕易的將在一個平臺上運行的應用,遷移到另外一個平臺上,而不用擔憂運行環境的變化致使應用沒法正常運行的狀況。
6.更輕鬆的維護和拓展
docker使用的分層存儲以及鏡像的技術,使得應用重複部分的複用更爲容易,也使得應用的維護更新更加簡單,基於基礎鏡像進一步擴展鏡像也變得十分簡單。此外,docker團隊同各個開源項目團隊一塊兒維護了一大批高質量的官網鏡像,既能夠直接在生產環境使用,又能夠做爲基礎進一步定製,大大的下降了應用服務的鏡像製做成本。
Docker daemon是一個運行在宿主機( DOCKER-HOST)的後臺進程。可經過 Docker 客戶端與之通訊。
Docker客戶端是 Docker的用戶界面,它能夠接受用戶命令和配置標識,並與 Docker daemon通訊。圖中, docker build等都是 Docker的相關命令。
容器是鏡像的可運行實例。鏡像和容器的關係有點相似於面向對象中,類和對象的關係。 可經過 Docker API或者 CLI命令來啓停、移動、刪除容器。
Docker Registry是一個集中存儲與分發鏡像的服務。構建完 Docker鏡像後,就可在當前 宿主機上運行。但若是想要在其餘機器上運行這個鏡像,就須要手動複製。此時可藉助 Docker Registry來避免鏡像的手動複製。 一個 Docker Registry可包含多個 Docker倉庫,每一個倉庫可包含多個鏡像標籤,每一個標 籤對應一個 Docker鏡像。這跟 Maven的倉庫有點相似,若是把 Docker Registry比做 Maven倉庫的話,那麼 Docker倉庫就可理解爲某jar包的路徑,而鏡像標籤則可理解爲jar 包的版本號。
Docker Registry可分爲公有Docker Registry和私有Docker Registry。 最常⽤的Docker Registry莫過於官⽅的Docker Hub, 這也是默認的Docker Registry。 Docker Hub上存 放着⼤量優秀的鏡像, 咱們可以使⽤Docker命令下載並使⽤。
Docker 是一個開源的商業產品,有兩個版本:社區版(Community Edition,縮寫爲 CE)和 企業版(Enterprise Edition,縮寫爲 EE)。企業版包含了一些收費服務,我的開發者通常用 不到。下面的介紹都針對社區版。
Docker CE 的安裝請參考官方文檔,咱們這裏以CentOS爲例:
一、Docker 要求 CentOS 系統的內核版本高於 3.10
經過 uname -r 命令查看你當前的內核版本
二、使用 root 權限登陸 Centos。確保 yum 包更新到最新。
三、卸載舊版本(若是安裝過舊版本的話)
四、安裝須要的軟件包, yum-util 提供yum-config-manager功能,另外兩個是 devicemapper驅動依賴的
五、設置yum源,並更新 yum 的包索引
六、能夠查看全部倉庫中全部docker版本,並選擇特定版本安裝
七、安裝docker
八、啓動並加入開機啓動
九、驗證安裝是否成功(有client和service兩部分表示docker安裝啓動都成功了)
//TODO
十、卸載docker
可以使用 docker search命令搜索存放在 Docker Hub中的鏡像。執行該命令後, Docker就會 在Docker Hub中搜索含有 java這個關鍵詞的鏡像倉庫。
以上列表包含五列,含義以下:
注意:若是執行命令執行超時,能夠須要配置鏡像加速器
Error response from daemon: Get index.docker.io/v1/search?q… read tcp 52.200.132.201:443: i/o timeout 咱們能夠藉助阿里雲的鏡像加速器,登陸阿里雲
咱們能夠藉助國內的鏡像加速器。阿里雲、騰訊雲都有對應功能。
這裏咱們使用阿里雲
cr.console.aliyun.com/cn-qingdao/…
查看有沒有 daemon.json。這是docker默認的配置文件。 若是沒有新建,若是有,則修改
{
"registry-mirrors": ["https://qs852e0r.mirror.aliyuncs.com"]
複製代碼
}
保存退出。 重啓docker服務
使用命令docker pull命令便可從 Docker Registry上下載鏡像,執行該命令後,Docker會從 Docker Hub中的 java倉庫下載最新版本的 Java鏡像。若是要下載指定版本則在java後面加冒 號指定版本,例如:docker pull java:8
使用 docker images命令便可列出已下載的鏡像
以上列表含義以下 -
使用 docker rmi命令便可刪除指定鏡像
使用如下docker run命令便可新建並啓動一個容器,該命令是最經常使用的命令,它有不少選項, 下面將列舉一些經常使用的選項。
-d選項:表示後臺運行
-P選項:隨機端口映射
-p選項:指定端口映射,有如下四種格式。
-- ip:hostPort:containerPort
-- ip::containerPort
-- hostPort:containerPort
-- containerPort
--net選項:指定網絡模式,該選項有如下可選參數:
--net=bridge:默認選項,表示鏈接到默認的網橋。
--net=host:容器使用宿主機的網絡。告訴 Docker 不要將容器網絡放到隔離的名字空間中,即不要容器化容器內的網絡。此時容器使用本地主機的網絡,它擁有徹底的本地主機接口訪問權限。容器進程能夠跟主機其 它 root 進程同樣能夠打開低範圍的端口,能夠訪問本地網絡服務好比 D-bus,還可讓容器作一些影響整個主機系統的事情,好比重啓主機。所以使用這個選項的時候要很是當心。若是進一步的使用 --privileged=true,容器會被容許直接配置主機的網絡堆棧
--net=container:NAME-or-ID:讓 Docker 將新建容器的進程放到一個已存在容器的網絡棧中,新容器進程有本身的文件系統、進程列表和資源限制,但會和已存在的容器共享 IP 地址和端口等網絡資源,二者進程能夠直接經過 lo 環回接口通訊。
--net=none:讓 Docker 將新容器放到隔離的網絡棧中,可是不進行網絡配置。以後,用戶能夠本身進行配置。
這樣就能啓動一個 Nginx容器。在本例中,爲 docker run添加了兩個參數,含義以下: -d 後臺運行 -p 宿主機端口:容器端口 #開放容器端口到宿主機端口
訪問 http://Docker宿主機 IP:91/,將會看到nginx的主界面以下:
//todo 圖片
使用 docker run命令建立容器時,會先檢查本地是否存在指定鏡像。若是本地 不存在該名稱的鏡像, Docker就會自動從 Docker Hub下載鏡像並啓動一個 Docker容器。
//todo
如需列出全部容器(包括已中止的容器),可以使用-a參數。該列表包含了7列,含義以下
使用 docker stop命令,便可中止容器
其中f0b1c8ab3633是容器 ID,固然也可以使用 docker stop容器名稱來中止指定容器
可以使用 docker kill命令發送 SIGKILL信號來強制中止容器
使用docker run命令,便可新建並啓動一個容器。對於已中止的容器,可以使用 docker start命 令來啓動
使用docker exec命令用於進入一個正在運行的docker容器。若是docker run命令運行容器的 時候,沒有使用-it參數,就要用這個命令進入容器。一旦進入了容器,就能夠在容器的 Shell 執行命令了
使用 docker rm命令便可刪除指定容器
該命令只能刪除已中止的容器,如需刪除正在運行的容器,可以使用-f參數
Dockerfile是一個文本文件,其中包含了若干條指令,指令描述了構建鏡像的細節 先來編寫一個最簡單的Dockerfile,之前文下載的Nginx鏡像爲例,來編寫一個Dockerfile修 改該Nginx鏡像的首頁。
一、新建文件夾/app,在app目錄下新建一個名爲Dockerfile的文件,在裏面增長以下內容: FROM nginx RUN echo '
二、在Dockerfile所在路徑執行如下命令構建鏡像: # docker build -t nginx:tuling . 其中,-t指定鏡像名字,命令最後的點(.)表示Dockerfile文件所在路徑
三、執行如下命令,便可使用該鏡像啓動一個 Docker容器 # docker run -d -p 92:80 nginx:tuling
四、訪問 http://Docker宿主機IP:92/,可看到下圖所示界面
Dockerfile經常使用指令
指令 | 描述 | 指令 | 描述 |
---|---|---|---|
FROM | 構造的新鏡像是基於哪一個鏡像例如:FROM centos:v1 | COPY | 拷貝文件或者目錄到鏡像,用法同ADD例如:COPY ./startup.sh /startup.sh |
MAINTAINER | 維護者信息例如:MAINTAINER yanglin | ENTRYPOINT | 運行容器時執行的shell命令例如:ENTRYPOINT ["/bin/bash","-c","/startup.sh"]ENTRYPOINT /bin/bash -c '/startup.sh' |
RUN | 構建鏡像時運行的shell命令例如:RUN ["yum", "install", "http"]RUN yum install httpd | VOLUME | 指定容器掛載點到宿主機自動生成的目錄或者其餘容器例如:VOLUME ["/path/to/dir"] |
CMD | 運行容器時執行的shell命令例如:CMD ["-c","/startup.sh"]CMD ["/usr/sbin/sshd","-D"]CMD /usr/sbin/sshd -D | USER | 爲RUN,CMD,ENTRYPOINT執行命令指定運行用戶例如:USER www鏡像構建完成後,經過docker run運行容器時,能夠經過-u參數來覆蓋所指定的用戶。 |
EXPOSE | 指定於外界交互的端口,即容器在運行時監聽的端口EXPOSE 8081 8082 | WORKDIR | 爲RUN,CMD,ENTRYPOINT,COPY和ADD設置工做目錄例如:WORKDIR /data |
ENV | 設置容器內環境變量例如:ENV MYSQL_ROOT_PASSWORD 123456 | HEALTHCHECK | 健康檢查HEALTHCHECK --interval=5m --timeout=3s CMD curl -f http://localhost/ ||exit 1 |
ADD | 拷貝文件或者目錄到鏡像,若是是URL或者壓縮包會自動下載或者自動解壓例如:ADD hom* /mydir/ ADD test relativeDir/ | ARG | 在構建鏡像時指定一些參數例如:FROM centos:6ARG age=100 |
注意:RUN命令在 image 文件的構建階段執行,執行結果都會打包進入 image 文件;CMD 命令則是在容器啓動後執行。另外,一個 Dockerfile 能夠包含多個RUN命令,可是隻能有一 個CMD命令。 注意,指定了CMD命令之後,docker container run命令就不能附加命令了(好比前面 的/bin/bash),不然它會覆蓋CMD命令。
使用Dockerfile構建微服務鏡像
使用Dockerfile構建微服務鏡像 以項目05-ms-eureka-server爲例,將該微服務的可運行jar包構建成docker鏡像 一、將jar包上傳linux服務器/app/eureka目錄,在jar包所在目錄建立名爲Dockerfile的文件
二、在Dockerfile中添加如下內容 # 基於哪一個鏡像 From java:8 # 複製文件到容器 ADD microservice-eureka-server-0.0.1-SNAPSHOT.jar /app.jar # 聲明須要暴露的端口 EXPOSE 8761 # 配置容器啓動後執行的命令 ENTRYPOINT ["java","-jar","/app.jar"]
三、使用docker build命令構建鏡像 # docker build -t microservice-eureka-server:0.0.1 . # 格式: docker build -t 鏡像名稱:標籤 Dockerfile的相對位置 在這裏,使用-t選項指定了鏡像的標籤。執行該命令後,終端將會輸出以下的內容
//todo
四、啓動鏡像,加-d可在後臺啓動
#docker run -p 8761:8761 microservice-eureka-server:0.0.1
使用 -v 能夠掛載一個主機上的目錄到容器的目錄
五、訪問http://Docker宿主機IP:8761/,可正常顯示Eureka Server首頁
然而微服務架構的應用系統通常包含若干個微服務,每一個微服務通常都會部署多個實例,若是每一個微服務都要手動啓停,那麼效率之低,維護量之大可想而知。使用 Docker Compose 能夠輕鬆、高效的管理容器,它是一個用於定義和運行多容器 Docker 的應用程序工具。
Docker Compose的安裝 Compose的安裝有多種方式,
例如經過shell安裝、經過pip安裝、以及將compose做爲容器安裝等等。本文講解經過pip安裝的方式。其 他安裝方式若有興趣,能夠查看Docker的官方文檔:docs.docker.com/compose/ins…
一、安裝python-pip
二、安裝docker-compose
三、待安裝完成後,執行查詢版本的命令
Compose的使用很是簡單,只須要編寫一個docker-compose.yml,而後使用docker-compose 命令操做便可。docker-compose.yml描述了 容器的配置,而docker-compose 命令描述了對容器的操做。咱們首先經過一個示例快速入門: 還記得上節課,咱們使用Dockerfile爲項目microservice-eureka-server構建Docker鏡像嗎?咱們還以此項目爲例測試。
咱們在microservice-eureka-server-0.0.1-SNAPSHOT.jar所在目錄的上一級目錄,
建立docker-compose.yml 文件。 目錄樹結構以下:
├── docker-compose.yml
└── eureka
├── Dockerfile
└── microservice-eureka-server-0.0.1-SNAPSHOT.jar
而後在docker-compose.yml 中添加內容以下:
eureka: #指定服務名
build: ./eureka #指定Dockfile所在路勁
ports:
expose:
在docker-compose.yml 所在路徑執行:
Compose就會自動構建鏡像並使用鏡像啓動容器。也可以使用 docker-compose up -d後臺啓動並運行這些容器
訪問:http://宿主機IP:8761/ ,發現能夠正常啓動。
Docker Compose將所管理的容器分爲三層,分別是工程( project),服務(service)以及容器( container)。 Docker Compose運 行目錄下的全部文件( docker-compose.yml、 extends文件或環境變量文件等)組成一個工程(默認爲 docker-compose.yml所在目 錄的目錄名稱)。一個工程可包含多個服務,每一個服務中定義了容器運行的鏡像、參數和依賴,一個服務可包括多個容器實例。
上節示例裏工程名稱是 docker-compose.yml所在的目錄名。該工程包含了1個服務,服務名稱是 eureka,執行 docker-compose up 時,啓動了eureka服務的1個容器實例
image
指定鏡像名稱或者鏡像id,若是該鏡像在本地不存在,Compose會嘗試pull下來。
示例:
image: java
build
指定Dockerfile文件的路徑。能夠是一個路徑,例如:
build: ./dir
也能夠是一個對象,用以指定Dockerfile和參數,例如:
build:
context: ./dir
dockerfile: Dockerfile-alternate
args:
buildno: 1
command
覆蓋容器啓動後默認執行的命令。
示例:
command: bundle exec thin -p 3000
也能夠是一個list,相似於Dockerfile總的CMD指令,格式以下: command: [bundle, exec, thin, -p, 3000]
links
連接到其餘服務中的容器。能夠指定服務名稱和連接的別名使用SERVICE:ALIAS 的形式,或者只指定服務名稱,示例:
web:
links:
db
db:database
redis
external_links
表示連接到dockercompose.yml外部的容器,甚至並不是Compose管理的容器,特別是對於那些提供共享容器或共同服務。格式跟links類 似,示例:
external_links:
redis_1
project_db_1:mysql
project_db_1:postgresql
ports
暴露端口信息。使用宿主端口:容器端口的格式,或者僅僅指定容器的端口(此時宿主機將會隨機指定端口),相似於docker run -p ,示 例:
ports:
"3000"
"3000-3005"
"8000:8000"
"9090-9091:8080-8081"
"49100:22"
"127.0.0.1:8001:8001"
"127.0.0.1:5000-5010:5000-5010"
expose
暴露端口,只將端口暴露給鏈接的服務,而不暴露給宿主機,示例:
expose:
"3000"
"8000"
volumes
卷掛載路徑設置。能夠設置宿主機路徑 (HOST:CONTAINER) 或加上訪問模式 (HOST:CONTAINER:ro)。示例:
volumes:
volumes_from
從另外一個服務或者容器掛載卷。能夠指定只讀或者可讀寫,若是訪問模式沒有指定,則默認是可讀寫。示例: volumes_from:
volumes_from:
service_name
service_name:ro
container:container_name
container:container_name:rw
environment
設置環境變量。可使用數組或者字典兩種方式。只有一個key的環境變量能夠在運行Compose的機器上找到對應的值,這有助於加密的 或者特殊主機的值。示例:
environment:
RACK_ENV: development
SHOW: 'true'
SESSION_SECRET:
environment:
RACK_ENV=development
SHOW=true
SESSION_SECRET
env_file
從文件中獲取環境變量,能夠爲單獨的文件路徑或列表。若是經過 docker-compose -f FILE 指定了模板文件,則 env_file 中路徑會基於 模板文件路徑。若是有變量名稱與 environment 指令衝突,則以envirment 爲準。示例:
env_file: .env
env_file:
./common.env
./apps/web.env
/opt/secrets.env
extends
繼承另外一個服務,基於已有的服務進行擴展。
net
設置網絡模式。示例:
net: "bridge"
net: "host"
net: "none"
net: "container:[service name or container name/id]"
dns
配置dns服務器。能夠是一個值,也能夠是一個列表。示例:
dns: 8.8.8.8
dns:
8.8.8.8
9.9.9.9
dns_search
配置DNS的搜索域,能夠是一個值,也能夠是一個列表,示例:
dns_search: example.com
dns_search:
dc1.example.com
dc2.example.com
其餘
dockercompose.yml 還有不少其餘命令,本文僅挑選經常使用命令進行講解,其餘不不做贅述。若是感興趣的,能夠參考dockercompose.yml文件官方文檔:docs.docker.com/compose/com…file/
福利領取 更多面試題關注B哥公衆號:java2b(微信搜索)