app軟件下載網(wǎng)站免費(fèi)進(jìn)入常用的網(wǎng)絡(luò)營(yíng)銷方法及效果
前言
知識(shí)點(diǎn)整理
Dockerfile 簡(jiǎn)介
它是一個(gè)沒(méi)有后綴名的文本文檔,里面是組合鏡像的一些命令,Docker build命令構(gòu)建鏡像時(shí),通過(guò)讀取Dockerfile中的指令的順序(自上到下)自動(dòng)生成鏡像。
Dockerfile 命令
1. FROM
指定基礎(chǔ)鏡像,并且必須是第一條指令。
如果不以任何鏡像為基礎(chǔ),那么寫(xiě)法為:FROM scratch。
同時(shí)意味著接下來(lái)所寫(xiě)的指令將作為鏡像的第一層開(kāi)始
語(yǔ)法:
FROM <image>
FROM <image>:<tag>
FROM <image>:<digest>
三種寫(xiě)法,其中和 是可選項(xiàng),如果沒(méi)有選擇,那么默認(rèn)值為latest
2. MAINTAINER
指明鏡像的歸屬者或維護(hù)團(tuán)體/機(jī)構(gòu)名稱/域名
語(yǔ)法:
MAINTAINER <name>
示例:
MAINTAINER csdn.xxx
MAINTAINER csdn
MAINTAINER csdn@qq.com
3. RUN
在生成鏡像時(shí)需要執(zhí)行的命令
Dockerfile中的RUN命令,只有在docker build 命令構(gòu)建鏡像時(shí)會(huì)自動(dòng)運(yùn)行
docker run的時(shí)候,并不會(huì)運(yùn)行
RUN命令有兩種格式
# 第一種后邊直接跟shell命令
RUN <command># 第二種是類似于函數(shù)調(diào)用, 可將executable理解成為可執(zhí)行文件,后面就是兩個(gè)參數(shù)
RUN ["executable", "param1", "param2"]
在linux操作系統(tǒng)上默認(rèn) /bin/sh -c
在windows操作系統(tǒng)上默認(rèn) cmd /S /C
注意:多行命令不要寫(xiě)多個(gè)RUN,原因是Dockerfile中每一個(gè)指令都會(huì)建立一層.
多少個(gè)RUN就構(gòu)建了多少層鏡像,會(huì)造成鏡像的臃腫、多層,不僅僅增加了構(gòu)件部署的時(shí)間,還容易出錯(cuò)。
RUN書(shū)寫(xiě)時(shí)的換行符是\
4. CMD
功能為容器啟動(dòng)時(shí)要運(yùn)行的命令
語(yǔ)法有三種寫(xiě)法
# 1. 可執(zhí)行文件加上參數(shù)的形式
CMD ["executable","param1","param2"]
CMD ["param1","param2"]# 2. shell的執(zhí)行方式和寫(xiě)法
CMD command param1 param2
舉例說(shuō)明兩種寫(xiě)法:
CMD [ "sh", "-c", "echo $HOME"
CMD [ "echo", "$HOME" ]
補(bǔ)充細(xì)節(jié):這里邊包括參數(shù)的一定要用雙引號(hào),就是",不能是單引號(hào)。千萬(wàn)不能寫(xiě)成單引號(hào)。
原因是參數(shù)傳遞后,docker解析的是一個(gè)JSON array
RUN vs CMD
RUN是構(gòu)件容器時(shí)就運(yùn)行的命令以及提交運(yùn)行結(jié)果
CMD是容器啟動(dòng)時(shí)執(zhí)行的命令,在構(gòu)件時(shí)并不運(yùn)行,構(gòu)件時(shí)緊緊指定了這個(gè)命令到底是個(gè)什么樣子。Dockerfile中多個(gè)CMD命令只有最后一個(gè)生效
5. LABEL
功能是為鏡像指定標(biāo)簽;作為MAINTAINE的補(bǔ)充,更為詳細(xì)的一些描述信息
語(yǔ)法:
LABEL <key>=<value> <key>=<value> <key>=<value> ...
一個(gè)Dockerfile種可以有多個(gè)LABEL,如下:
LABEL "com.example.vendor"="ACME Incorporated"
LABEL com.example.label-with-value="foo"
LABEL version="1.0"
LABEL description="This text illustrates that label-values can span multiple lines."
但是并不建議這樣寫(xiě),最好就寫(xiě)成一行,如太長(zhǎng)需要換行的話則使用符號(hào)
如下:
LABEL multi.label1="value1"
multi.label2="value2"
other="value3"
說(shuō)明:LABEL會(huì)繼承基礎(chǔ)鏡像種的LABEL,如遇到key相同,則值覆蓋
MAINTAINER vs LABEL
增強(qiáng)鏡像的閱讀性,不會(huì)對(duì)功能造成影響
6. EXPOSE
指定對(duì)外的端口。功能為暴漏容器運(yùn)行時(shí)的監(jiān)聽(tīng)端口給外部
但是EXPOSE并不會(huì)使容器訪問(wèn)主機(jī)的端口
如果想使得容器與主機(jī)的端口有映射關(guān)系,必須在容器啟動(dòng)的時(shí)候加上 -P參數(shù)
7. ENV
功能為設(shè)置環(huán)境變量
簡(jiǎn)單的說(shuō),它就是一個(gè)全局常量,被設(shè)置后,進(jìn)入容器內(nèi)部,在任意位置都可以訪問(wèn)這個(gè)常量的值,比如# echo $var_bl。
好比本地設(shè)置了JAVA_HOME環(huán)境變量一樣,在CMD窗口任意目錄,都可以打印/獲取該常量。
語(yǔ)法有兩種
ENV <key><value>
ENV <key>=<value> ...
兩者的區(qū)別就是第一種是一次設(shè)置一個(gè),第二種是一次設(shè)置多個(gè)
示例:
ENV WORKPATH /tmp
ENV http_proxy ""
ENV JAVA_HOME /usr/local/openjdk8
ENV test=mayun-xiaoma
ENV mycat=mimiRUN $JAVA_HOME/bin/java-jar test.jar
盡量使用環(huán)境常量,可提高程序維護(hù)性,如果JAVA_HOME需要調(diào)整為其他JDK版本,那么只需要調(diào)整一處位置即可,比如把/usr/local/openjdk8調(diào)整為jdk9。
注意:這些環(huán)境常量可以通過(guò)docker run命令的–env 或-e參數(shù)來(lái)進(jìn)行修改。
8. ADD
一個(gè)復(fù)制命令,把文件復(fù)制到景象中。
如果把虛擬機(jī)與容器想象成兩臺(tái)linux服務(wù)器的話,那么這個(gè)命令就類似于scp,只是scp需要加用戶名和密碼的權(quán)限驗(yàn)證,而ADD不用。
語(yǔ)法如下:
# <src> (為宿主機(jī)目錄+)文件;<dest>(為容器內(nèi)目錄+)文件
ADD <src>... <dest>
ADD ["<src>",... "<dest>"]
路徑的填寫(xiě)可以是容器內(nèi)的絕對(duì)路徑,也可以是相對(duì)于工作目錄的相對(duì)路徑
可以是一個(gè)本地文件或者是一個(gè)本地壓縮文件,還可以是一個(gè)url
如果把寫(xiě)成一個(gè)url,那么ADD就類似于wget命令
盡量不要把寫(xiě)成一個(gè)文件夾,如果是一個(gè)文件夾了,復(fù)制整個(gè)目錄的內(nèi)容,包括文件系統(tǒng)元數(shù)據(jù)
如以下寫(xiě)法都是可以的:
#把hello從宿主機(jī)復(fù)制到容器內(nèi)部的根路徑
ADD hello /
#把壓縮包從宿主機(jī)添加到容器的根目錄后,自動(dòng)解壓
ADD test.tar.gz /
#把hello文件復(fù)制到當(dāng)前workdir工作目錄的根目錄
ADD hello .
#僅從宿主機(jī)復(fù)制文件到容器內(nèi)部的指定目錄
COPY test.txt /etc/nginx
#復(fù)制文件,并自動(dòng)解壓到指定目錄
ADD demo.tar.gz /usr/share/nginx/html
宿主目錄,默認(rèn)是執(zhí)行docker build時(shí)所在的宿主機(jī)目錄 ;
示例中,后面的/是指容器內(nèi)部根目錄,而 . 是容器內(nèi)部的當(dāng)前目錄(默認(rèn)是WORKDIR的目錄)
9. COPY
復(fù)制命令
語(yǔ)法如下:
COPY <src>... <dest>
COPY ["<src>",... "<dest>"]
ADD vs COPY
- COPY 的只能是本地文件,ADD可以充當(dāng)wget命令添加遠(yuǎn)程文件
- ADD 是增強(qiáng)版的COPY,ADD自帶解壓,COPY不帶解壓。兩者都支持目錄中有空格。
注意:
- ADD指令不支持認(rèn)證,從遠(yuǎn)程獲取資源如果需要認(rèn)證(交互),則只能使用RUN wget或RUN curl替代。
- 如果不是需要解壓,優(yōu)先使用COPY命令,效率更高、更節(jié)省資源。
10. ENTRYPOINT
功能是啟動(dòng)時(shí)的默認(rèn)命令
語(yǔ)法如下:
ENTRYPOINT ["executable", "param1", "param2"]
ENTRYPOINT command param1 param2
CMD vs ENTRYPOINT
相同點(diǎn):
- 只能寫(xiě)一條,如果寫(xiě)了多條,那么只有最后一條生效
- 容器啟動(dòng)時(shí)才運(yùn)行,運(yùn)行時(shí)機(jī)相同
不同點(diǎn):
ENTRYPOINT不會(huì)被運(yùn)行的command覆蓋,而CMD則會(huì)被覆蓋
如果我們?cè)贒ockerfile種同時(shí)寫(xiě)了ENTRYPOINT和CMD,并且CMD指令不是一個(gè)完整的可執(zhí)行命令,那么CMD指定的內(nèi)容將會(huì)作為ENTRYPOINT的參數(shù)
如下:
FROM ubuntu
ENTRYPOINT ["top", "-b"]
CMD ["-c"]
如果我們?cè)贒ockerfile種同時(shí)寫(xiě)了ENTRYPOINT和CMD,并且CMD是一個(gè)完整的指令,那么它們兩個(gè)會(huì)互相覆蓋,誰(shuí)在最后誰(shuí)生效
如下:
FROM ubuntu
ENTRYPOINT ["top", "-b"]
CMD ls -al
那么將執(zhí)行l(wèi)s -al ,top -b不會(huì)執(zhí)行。
11. VOLUME
設(shè)置卷,掛載主機(jī)目錄??蓪?shí)現(xiàn)掛載功能,可以將內(nèi)地文件夾或者其他容器種得文件夾掛載到這個(gè)容器中
語(yǔ)法為:
VOLUME ["/data"]
說(shuō)明:
[“/data”]可以是一個(gè)JsonArray ,也可以是多個(gè)值。所以如下幾種寫(xiě)法都是正確的
VOLUME ["/var/log/"]
VOLUME /var/log
VOLUME /var/log /var/db
一般的使用場(chǎng)景為需要持久化存儲(chǔ)數(shù)據(jù)時(shí)
容器使用的是AUFS,這種文件系統(tǒng)不能持久化數(shù)據(jù),當(dāng)容器關(guān)閉后,所有的更改都會(huì)丟失。
所以當(dāng)數(shù)據(jù)需要持久化時(shí)用這個(gè)命令。
12. USER
設(shè)置啟動(dòng)容器的用戶,可以是用戶名或UID
只有下面的兩種寫(xiě)法是正確的
USER daemo
USER UID
注意:如果設(shè)置了容器以daemon用戶去運(yùn)行,那么RUN, CMD 和 ENTRYPOINT 都會(huì)以這個(gè)用戶去運(yùn)行
13. WORKDIR
WORKDIR 設(shè)置的,目錄需要是絕對(duì)路徑,如果不存在,會(huì)自動(dòng)創(chuàng)建。
在Dockerfile最外層首次出現(xiàn),則是指明通過(guò)docker exec -it 進(jìn)入容器內(nèi)部后,默認(rèn)進(jìn)入的工作目錄(無(wú)需再用cd命令切換)。
如果Dockerfile中命令比較多,需要來(lái)回切換工作目錄,則可以隨時(shí)再次定義新的WORKDIR
語(yǔ)法:
WORKDIR /path/to/workdir
設(shè)置工作目錄,對(duì)RUN,CMD,ENTRYPOINT,COPY,ADD生效。如果不存在則會(huì)創(chuàng)建,也可以設(shè)置多次。如:
WORKDIR /a
WORKDIR b
WORKDIR c
RUN pwd
pwd執(zhí)行的結(jié)果是/a/b/c
14. ARG
設(shè)置變量命令
語(yǔ)法:
# 設(shè)置變量命令,ARG命令定義了一個(gè)變量,在docker build創(chuàng)建鏡像的時(shí)候,使用 --build-arg <varname>=<value>來(lái)指定參數(shù)
ARG <name>[=<default value>]
如果用戶在build鏡像時(shí)指定了一個(gè)參數(shù)沒(méi)有定義在Dockerfile種,那么將有一個(gè)Warning
提示如下:
[Warning] One or more build-args [foo] were not consumed.
我們可以定義一個(gè)或多個(gè)參數(shù),如下:
FROM busybox
ARG user1
ARG buildno
...
也可以給參數(shù)一個(gè)默認(rèn)值:
FROM busybox
ARG user1=someuser
ARG buildno=1
...
如果我們給了ARG定義的參數(shù)默認(rèn)值,那么當(dāng)build鏡像時(shí)沒(méi)有指定參數(shù)值,將會(huì)使用這個(gè)默認(rèn)值
15. ONBUILD
這個(gè)命令只對(duì)當(dāng)前鏡像的子鏡像生效
語(yǔ)法:
ONBUILD [INSTRUCTION]
比如當(dāng)前鏡像為A,在Dockerfile中添加:
ONBUILD RUN ls -al
這個(gè) ls -al 命令不會(huì)在A鏡像構(gòu)建或啟動(dòng)的時(shí)候執(zhí)行
此時(shí)有一個(gè)鏡像B是基于A鏡像構(gòu)建的,那么這個(gè)ls -al 命令會(huì)在B鏡像構(gòu)建的時(shí)候被執(zhí)行。
16. STOPSIGNAL
作用是當(dāng)容器退出時(shí)給系統(tǒng)發(fā)送什么樣的指令
語(yǔ)法:
STOPSIGNAL signal
17. HEALTHCHECK
容器健康狀況檢查命令
語(yǔ)法有兩種:
# 在容器內(nèi)部運(yùn)行一個(gè)命令來(lái)檢查容器的健康狀況
HEALTHCHECK [OPTIONS] CMD command# 在基礎(chǔ)鏡像中取消健康檢查命令
HEALTHCHECK NONE
[OPTIONS]的選項(xiàng)支持以下三中選項(xiàng):
- interval=DURATION 兩次檢查默認(rèn)的時(shí)間間隔為30秒
- timeout=DURATION 健康檢查命令運(yùn)行超時(shí)時(shí)長(zhǎng),默認(rèn)30秒
- retries=N 當(dāng)連續(xù)失敗指定次數(shù)后,則容器被認(rèn)為是不健康的,狀態(tài)為unhealthy,默認(rèn)次數(shù)是3
注意:
HEALTHCHECK命令只能出現(xiàn)一次,如果出現(xiàn)了多次,只有最后一個(gè)生效。
CMD后邊的命令的返回值決定了本次健康檢查是否成功,具體的返回值如下:
0: success - 表示容器是健康的
1: unhealthy - 表示容器已經(jīng)不能工作了
2: reserved - 保留值
例子:
HEALTHCHECK --interval=5m --timeout=3s
CMD curl -f http://localhost/ || exit 1
健康檢查命令是:curl -f http://localhost/ || exit 1
兩次檢查的間隔時(shí)間是5秒
命令超時(shí)時(shí)間為3秒
Dockerfile案例
部署JavaWeb項(xiàng)目
新建并編輯 Dockerfile:
# 指定基于的容器鏡像
FROM tomcat
# 維護(hù)者信息
MAINTAINER "itstyle <12345678@qq.com>"
# 復(fù)制項(xiàng)目到Tomcat指定目錄
ADD test.war /usr/local/tomcat/webapps/
# 容器啟動(dòng)時(shí)執(zhí)行指令
CMD ["catalina.sh", "run"]
構(gòu)建鏡像:
docker build -t itstyle/tomcat .
PS:
- 文件名只能是Dockerfile,不同的構(gòu)建文件通過(guò)文件夾名稱來(lái)區(qū)分
- 命令最后的點(diǎn) “.” 表示讀取當(dāng)前目錄下的 Dockerfile 進(jìn)行構(gòu)建
- -t:表示為當(dāng)前鏡像命名
運(yùn)行鏡像:
docker run -d -p 8888:8080 -v /home/docker/web:/usr/local/tomcat/webapps --name app itstyle/tomcat
在 /home/docker/web 目錄下存放項(xiàng)目War
案例2:部署SpringBoot微服務(wù)
# 基礎(chǔ)鏡像:倉(cāng)庫(kù)是java
FROM java:8-jre
# 當(dāng)前鏡像的維護(hù)者和聯(lián)系方式
MAINTAINER "itstyle 12345678@qq.com"
# 掛載卷
VOLUME /tmp
# 將打包好的springBoot程序拷貝到容器中的指定位置
ADD itstyle_stats.jar /opt/app.jar
# 容器對(duì)外暴露端口
EXPOSE 8080
# 容器啟動(dòng)后需要執(zhí)行的命令
CMD java -jar /opt/app.jar
# ENTRYPOINT ["java","-jar","-Denv=DEV","/opt/app.jar"]
知識(shí)回顧
構(gòu)建鏡像
# 這里的 -f 用于指定Dockerfile文件路徑
docker bulid -t -f Dockerfile路徑
# 使用當(dāng)前目錄下的Dockerfile構(gòu)建鏡像,鏡像命名為 nginx:env
docker build . -t nginx:env
#啟動(dòng)容器
docker run -t --rm --name nginx-env nginx:env
#啟動(dòng)容器,并進(jìn)入容器內(nèi)部
docker run -it --rm --name nginx-env nginx:env /bin/sh
#直接進(jìn)入容器內(nèi)部
docker exec -it nginx:env /bin/bash
#打印環(huán)境變量
echo $mycat
#退出容器,返回宿主機(jī)
exit
本文參考鏈接