欧美性猛交XXXX免费看蜜桃,成人网18免费韩国,亚洲国产成人精品区综合,欧美日韩一区二区三区高清不卡,亚洲综合一区二区精品久久

打開(kāi)APP
userphoto
未登錄

開(kāi)通VIP,暢享免費電子書(shū)等14項超值服

開(kāi)通VIP
Dockerfile詳解與最佳實(shí)踐

Dockerfile是一個(gè)文本文件,包含了一條條指令,每條指令對應構建一層鏡像,Docker基于它來(lái)構建一個(gè)完整鏡像。本文介紹Dockerfile的常用指令及相應的最佳實(shí)踐建議。

1. 理解構建上下文(build context)

Docker鏡像通過(guò)docker build指令構建,該指令執行時(shí)當前的工作目錄就是docker構建的上下文,即build context,上下文中的文件及目錄都會(huì )作為構建上下文內容發(fā)送給Docker Daemon。

docker build --no-cache -t helloapp:v2 -f dockerfiles/Dockerfile context

如上 –no-cache 表示鏡像構建時(shí)不使用緩存,-f 指定Dockerfile文件位置, context 指定build context目錄。

將一些非必要的文件包含到build context中,會(huì )導致build context過(guò)大,從而導致鏡像過(guò)大,會(huì )增加鏡像構建、推送及拉取的時(shí)間,以及容器運行時(shí)的大小。

執行docker build時(shí)會(huì )顯示build context的大小,

Sending build context to Docker daemon  187.8MB

最佳實(shí)踐建議

  1. 使用.dockerignore來(lái)排除不需要加入到build context中的文件,類(lèi)似于.gitignore
  2. 不要安裝不必要的包,所有包含的東西都是鏡像必須的,非必須的不要包含。
  3. 解耦應用,如果應用有分層,解耦應用到多個(gè)容器,便于橫向擴展,如web應用程序棧包含web服務(wù)應用,數據庫,緩存等。
  4. 最少化鏡像層數:只有RUN、COPY、ADD指令會(huì )創(chuàng )建鏡像層,其它指令創(chuàng )建臨時(shí)的中間鏡像,不會(huì )增大鏡像構建的大小
  5. 如果可能,盡可能使用多階段構建,只復制你需要的組件到最終鏡像,這使得你可以在中間構建階段包含工具與debug信息,同時(shí)又不會(huì )增大最終鏡像的大小。
  6. 排序多行參數:將參數按字母排序,有利于避免包重復,及后續的維護與提高易讀性

2. FROM

作用FROM指定基礎鏡像,每一個(gè)定制鏡像,必須以一個(gè)現有鏡像為基礎。因此一個(gè)Dockerfile中FROM是必須的指令,并且必須是第一條。使用格式,

FROM <image>:<tag>
# 注釋以#開(kāi)頭?;A鏡像的tag可不指定,默認使用latest
# 示例:FROM mysql:5.7

最佳實(shí)踐建議

  1. 如果不想以任何鏡像為基礎,則可以使用FROM scratch
  2. 盡量使用官方鏡像作為基礎鏡像
  3. 推薦使用Alpine鏡像,因為它足夠輕量級(小于5MB),但麻雀雖小五臟俱全,基本具有Linux的基礎功能

3. RUN

作用用來(lái)執行命令行命令,是最常用的指令之一。使用格式,

# shell格式,跟直接在命令行輸入命令一行
RUN <命令>
# 示例:RUN mkdir -p /usr/src/redis
# exec格式,類(lèi)似于函數調用
RUN ["可執行文件", "參數1", "參數2"]

RUN指令創(chuàng )建的中間鏡像會(huì )被緩存,并會(huì )在下次構建中使用。如果不想使用這些緩存鏡像,可以在構建指令中指定–no-cache參數,如:docker build --no-cache

最佳實(shí)踐建議

  1. 將比較長(cháng)的復雜的指令通過(guò) \ 分為多行,讓Dockerfile文件可讀性、可理解性、可維護性更高,將多個(gè)指令通過(guò) && 連接,減少鏡像的層數
  2. 確保每一層只添加必需的東西,任何無(wú)關(guān)的東西都應該清理掉,如所有下載、展開(kāi)的文件,apt 緩存文件等,以盡可能減少鏡像各層的大小
  3. 將RUN apt-get update 與 RUN apt-get install 組合成一條RUN指令(將apt-get update單獨作為一條指令會(huì )因為緩存問(wèn)題導致后續的apt-get install 指令失?。?/li>

比如先按如下Dockerfile創(chuàng )建了一個(gè)鏡像

FROM ubuntu:18.04
RUN apt-get update
RUN apt-get install -y curl

一段時(shí)間后,再按以下Dockerfile創(chuàng )建另一個(gè)鏡像

FROM ubuntu:18.04
RUN apt-get update
RUN apt-get install -y curl nginx

因為RUN指令創(chuàng )建的鏡像層會(huì )被緩存,所以下面鏡像的RUN apt-get update并不會(huì )執行,直接使用了前面構建的鏡像層,這樣,curl、nginx就可能安裝已經(jīng)過(guò)時(shí)的版本。

因此 在 apt-get update 之后立即接 && apt-get install -y ,這叫做“ cache busting”(緩存破壞),也可以通過(guò)指定包的版本,來(lái)達到同樣的目的,這叫“ version pinning” (版本指定)示例:

RUN apt-get update && apt-get install -y     reprepro     ruby1.9.1     ruby1.9.1-dev     #刪除apt 緩存減少鏡像層的大小
    && rm -rf /var/lib/apt/lists/*
  1. 使用管道(pipes)。一些RUN指令依賴(lài)于從一個(gè)指令管道輸出到另一個(gè),如RUN wget -O - https://some.site | wc -l > /number

Docker使用/bin/sh -c 解釋器來(lái)執行這些指令,只會(huì )評估管道最后一條命令的退出碼來(lái)確定是否成功,如上例中只要wc -l成功了就算wget失敗,也會(huì )認為是成功的。如果要使管道命令的任何一步報錯都導致指令失敗,則可通過(guò)加 set -o pipefile && 來(lái)實(shí)現,如

RUN set -o pipefail && wget -O - https://some.site | wc -l > /number

不是所有的shell都支持-o pipefail選項,如果不支持的話(huà)可以使用如下形式,顯式地指定一個(gè)支持的shell

RUN ["/bin/bash", "-c", "set -o pipefail && wget -O - https://some.site | wc -l > /number"]

4. COPY | ADD

作用COPY從構建上下文的目錄中復制文件/目錄到鏡像層的目標路徑。使用格式,

COPY [--chown=<user>:<group>] <源路徑>... <目標路徑>
COPY [--chown=<user>:<group>] ["<源路徑1>",... "<目標路徑>"]

同RUN一樣,也有兩種格式。源文件可以多個(gè),甚至可以是通配符,目標路徑是容器的絕對路徑,可以是相對工作目錄(WORKDIR指定)的相對路徑,目標路徑不存在時(shí)會(huì )自動(dòng)創(chuàng )建。使用--chown=<user>:<group>來(lái)改變文件的所屬用戶(hù)與組。ADD與COPY的使用格式與性質(zhì)差不多,但功能更豐富,如源路徑可以是URL(下載后放到目標路徑下,文件權限為600),也可以為tar壓縮包,壓縮格式為gzip,bzip2及xz的情況下,ADD 指令將會(huì )自動(dòng)解壓縮這個(gè)壓縮文件到目標路徑去

最佳實(shí)踐建議

  1. 如果在Dockerfile中有多處需要使用不同的文件,分別使用COPY,而不是一次性COPY所有的,這可以保證每一步的構建緩存只會(huì )在對應文件改變時(shí),才會(huì )失效。比如COPY requirements.txt /tmp/
    RUN pip install --requirement /tmp/requirements.txt
    COPY . /tmp/

如果把COPY . /tmp/ 放在RUN上面,將使RUN層鏡像緩存失效的場(chǎng)景更多——因為 . 目錄(當前目錄)中任何一個(gè)文件的改變都會(huì )導致緩存失效。

  1. 因為鏡像大小的原因, 使用ADD來(lái)獲取遠程包是非常不推薦的,應該使用curl或wget,這種方式可以在不再需要使用時(shí)刪除對應文件,而不需要增加額外的層,如,應避免如下用法ADD http://example.com/big.tar.xz /usr/src/things/
    RUN tar -xJf /usr/src/things/big.tar.xz -C /usr/src/things
    RUN make -C /usr/src/things all

而應使用

RUN mkdir -p /usr/src/things     && curl -SL http://example.com/big.tar.xz     | tar -xJC /usr/src/things     && make -C /usr/src/things all
  1. 如果不需要使用ADD的自動(dòng)解壓特性,盡量使用COPY(語(yǔ)義更清晰)

5. CMD

作用CMD指定容器的啟動(dòng)命令。容器實(shí)質(zhì)就是進(jìn)程,進(jìn)程就需要啟動(dòng)命令及參數,CMD指令就是用于指定默認的容器主進(jìn)程的啟動(dòng)命令的。使用格式

# shell格式
CMD <命令>
# exec格式
CMD ["可執行文件", "參數1", "參數2"...]
# 參數列表格式,在指定了ENTRYPOINT指令后,用CMD來(lái)指定具體的參數
CMD ["參數1", "參數2"...]

在容器運行時(shí)可以指定新的命令來(lái)覆蓋Dockerfile中設置的這個(gè)默認命令

最佳實(shí)踐建議

  1. 服務(wù)類(lèi)鏡像建議:CMD ["apache2","-DFOREGROUND"],CMD ["nginx", "-g", "daemon off;"] 容器進(jìn)程都應以前臺運行,不能以后臺服務(wù)的形式運行,否則啟動(dòng)就退出了。
  2. 其它鏡像,建議給一個(gè)交互式的shell,如bash,python,perl等:CMD ["python"], CMD ["php", "-a"]

6. ENTRYPOINT

作用ENTRYPOINT的目的和CMD一樣,都是在指定容器啟動(dòng)時(shí)要運行的程序及參數。ENTRYPOINT在運行時(shí)也可以替代,不過(guò)比CMD要略顯繁瑣,需要通過(guò)docker run的參數 –entrypoint 來(lái)指定。如果指定了ENTRYPOINT,則CMD將只是提供參數,傳遞給ENTRYPOINT。使用ENTRYPOINT可以在容器運行時(shí)直接為默認啟動(dòng)程序添加參數。與RUN指令格式一樣,ENTRYPOINT也分為exec格式和shell格式。

最佳實(shí)踐建議

  1. ENTRYPOINT可用來(lái)指定鏡像的主命令,允許鏡像能像命令一樣運行,可以使用CMD來(lái)作為默認的標志(參數),如ENTRYPOINT ["s3cmd"]
    CMD ["--help"]

直接run時(shí),相當于執行了s3cmd --help。也可以使用shell腳本,在腳本中做一些預處理的工作,如

COPY ./docker-entrypoint.sh /
ENTRYPOINT ["/docker-entrypoint.sh"]
CMD ["postgres"]

7. LABEL

作用為鏡像添加label以方便組織鏡像,記錄licensce信息,幫助自動(dòng)化實(shí)現等等。字符串中包含空格需要轉義或包含在引號中, 如

# Set one or more individual labels
LABEL com.example.version="0.0.1-beta"
LABEL vendor1="ACME Incorporated"
LABEL com.example.release-date="2019-09-12"
LABEL com.example.version.is-production=""
# Set multiple labels on one line
LABEL com.example.version="0.0.1-beta" com.example.release-date="2019-09-12"
# Set multiple labels at once, using line-continuation characters to break long lines
LABEL vendor=ACME\ Incorporated       com.example.is-beta=       com.example.is-production=""       com.example.version="0.0.1-beta"       com.example.release-date="2019-09-12"

8. ENV

作用ENV設置環(huán)境變量,無(wú)論是后面的其它指令,如 RUN(使用 $環(huán)境變量key 的形式) ,還是運行時(shí)的應用,都可以直接使用這里定義的環(huán)境變量。使用格式有兩種,

#只能設置一個(gè)key value
ENV <key> <value>
#可以設置多個(gè),value中如果包含空格可以使用\來(lái)進(jìn)行轉義,也可以通過(guò)""括起來(lái);也可以用反斜線(xiàn)來(lái)續行
ENV <key1>=<value1> <key2>=<value2>...

除了RUN,還有這些指令可以引用環(huán)境變量:ADD 、 COPY 、 ENV 、 EXPOSE 、 LABEL 、 USER 、 WORKDIR 、 VOLUME 、STOPSIGNAL 、 ONBUILD

最佳實(shí)踐建議

  1. 定義環(huán)境變量,更新PATH環(huán)境變量,如要使 CMD [“nginx”] 運行,可設置環(huán)境變量 ENV PATH /usr/local/nginx/bin:$PATH
  2. ENV也可以用于定義常量,便于維護

9. ARG

作用ARG設置構建參數,即docker build命令時(shí)傳入的參數。和ENV的效果差不多,都是設置環(huán)境變量,不同的是,ARG設置的是構建環(huán)境的環(huán)境變量,在容器運行時(shí)是不會(huì )存在這些環(huán)境變量的。Dockerfile中的ARG指令是定義參數名稱(chēng),以及默認值(可選)。該默認值可以在執行構建命令docker build時(shí)用 –build-arg <參數名>=<值> 來(lái)覆蓋。使用格式,

ARG <參數名>[=<默認值>]
```
**最佳實(shí)踐建議**
1. 不要使用ARG來(lái)保存密碼之類(lèi)的信息,因為通過(guò)docker history還是可以看到docker build執行時(shí)的所有值
2. 使用ARG,對于使用CI系統(持續集成),用同樣的構建流程構建不同的 Dockerfile 的時(shí)候比較有幫助,避免構建命令必須根據每個(gè) Dockerfile 的內容修改
## 10. WORKDIR
**作用**
WORKDIR用于指定工作目錄(或當前目錄),以后各層的當前目錄就被改為指定的目錄,如該目錄不存在,會(huì )自動(dòng)創(chuàng  )建。使用格式,
```shell
WORKDIR <工作目錄路徑>
```
**最佳實(shí)踐建議**
1. WORKDIR應該使用絕對路徑,顯得更為清楚、可靠
2. 使用WORKDIR,避免使用`RUN cd … && do-something`,可讀性差,難以維護
## 11. VOLUME
**作用**
VOLUME用于定義匿名卷。容器運行時(shí)應該盡量保持容器存儲層不發(fā)生寫(xiě)操作,應該將數據寫(xiě)入存儲卷。VOLUME就是為了防止運行時(shí)用戶(hù)忘記將動(dòng)態(tài)文件所保存的目錄掛載為卷,我們事先在Dockerfile中指定某些目錄掛載為匿名卷,這樣在運行時(shí)如果用戶(hù)不指定掛載,其應用也可以正常運行,不會(huì )向容器存儲層寫(xiě)入大量數據。使用格式,
```shell
VOLUME ["<路徑1>", "<路徑2>"...]
VOLUME <路徑>

如 VOLUME /data, 任何向/data目錄寫(xiě)入的數據都會(huì )寫(xiě)入匿名卷??梢赃\行容器時(shí)覆蓋這個(gè)掛載設置 docker run -d -v host-path:/data xxxx

最佳實(shí)踐建議

  1. VOLUME應該被用來(lái)暴露所有的數據存儲,配置存儲,或者被容器創(chuàng )建的文件、目錄
  2. 如果數據動(dòng)態(tài)變化,強烈建議使用VOLUME

12. EXPOSE

作用EXPOSE指令是聲明運行時(shí)容器提供的服務(wù)端口,也只是一個(gè)聲明,在容器運行時(shí)并不會(huì )因為這個(gè)聲明應用就一定會(huì )開(kāi)啟這個(gè)端口的服務(wù),容器啟動(dòng)時(shí),還是需要通過(guò) -p host-port:container-port來(lái)實(shí)現映射。EXPOSE主要是幫助鏡像使用者了解這個(gè)鏡像服務(wù)的監聽(tīng)端口,以方便進(jìn)行映射配置,另一個(gè)用處是在運行時(shí)如果是使用隨機端口映射,也就是通過(guò) docker run -P的形式時(shí),會(huì )自動(dòng)隨機映射EXPOSE聲明的端口。使用格式,

EXPOSE <端口1> [<端口2>...]
```
**最佳實(shí)踐建議**
1. 應該使用常用的慣用的端口,如nginx 80,mongoDB 27017
## 13. USER
**作用**
USER指令和WORKDIR相似,都是改變環(huán)境狀態(tài)并影響以后的層。WORKDIR是改變工作目錄, USER則是改變之后的層在執行RUN , CMD以及ENTRYPOINT這類(lèi)命令時(shí)的身份。USER幫助你切換到指定的用戶(hù),這個(gè)用戶(hù)必
須是事先建立好的,否則無(wú)法切換。使用格式
```shell
USER <用戶(hù)名>[:<用戶(hù)組>]

最佳實(shí)踐建議

  1. 如果一個(gè)服務(wù)不需要權限也能運行,則使用USER來(lái)切換到非root用戶(hù),如RUN groupadd -r postgres && useradd --no-log-init -r -g postgres postgres
  2. 避免使用sudo,因為可能存在一些不可預見(jiàn)的TTY與信號轉發(fā)行為導致問(wèn)題,如果實(shí)在需要,考慮使用“gosu”。為了減少鏡像層數,應避免不斷切換USER使用gosu示例# 建立 redis 用戶(hù),并使用 gosu 換另一個(gè)用戶(hù)執行命令
    RUN groupadd -r redis && useradd -r -g redis redis
    # 下載 gosu
    RUN wget -O /usr/local/bin/gosu "https://github.com/tianon/gosu/
    releases/download/1.7/gosu-amd64" \
    && chmod +x /usr/local/bin/gosu \
    && gosu nobody true
    # 設置 CMD,并以另外的用戶(hù)執行
    CMD [ "exec", "gosu", "redis", "redis-server" ]

14. HEALTHCHECK

作用HEALTHCHECK用于檢查容器的健康狀態(tài),Docker可通過(guò)健康狀態(tài)來(lái)決定是否對容器進(jìn)行重新調度。使用格式

HEALTHCHECK [選項] CMD <命令>

支持的選項為

  • –interval=<間隔> :兩次健康檢查的間隔,默認為30秒
  • –timeout=<時(shí)長(cháng)> :執行健康檢查命令的超時(shí)時(shí)間,如果超時(shí),則本次健康檢查就被視為失敗,默認30秒
  • –retries=<次數> :當連續失敗指定的次數后,將容器狀態(tài)置為unhealthy ,默認3次

命令的返回值決定了該次健康檢查的成功與否—— 0 :成功;1 :失??;2 :保留(不要使用這個(gè)值),如:

FROM nginx
RUN apt-get update && apt-get install -y curl && rm -rf /var/lib
/apt/lists/*
HEALTHCHECK --interval=5s --timeout=3s     CMD curl -fs http://localhost/ || exit 1
```
可以使用docker ps 或docker inspect來(lái)查看容器的健康狀態(tài)。
**最佳實(shí)踐建議**
1. 如果基礎鏡像有健康檢查指令,想要屏蔽掉其健康檢查,可以使用`HEALTHCHECK NONE`
2. 對一些可能造成假死(進(jìn)程還在, 但提供不了服務(wù)了)的服務(wù)建議提供健康檢查,以便及時(shí)重新調度恢復服務(wù)
## 15. ONBUILD
**作用**
ONBUILD后跟的指令,只有當以當前鏡像為基礎鏡像,去構建下一級鏡像的時(shí)候才會(huì )被執行。使用格式
```shell
ONBUILD <其它指令>

它后面跟的是其它指令,比如 RUN , COPY 等,這些指令在當前鏡像構建時(shí)并不會(huì )被執行。ONBUILD命令在本鏡像的子鏡像中執行,把ONBUILD想象為父鏡像為子鏡像聲明的一條指令,Docker會(huì )在子鏡像所有命令之前執行ONBUILD指令。

最佳實(shí)踐建議

  1. 當在ONBUILD指令中使用ADD或COPY時(shí)要注意,如果build context中沒(méi)有指定的資源,可能導致災難性的錯誤。

16. 用緩存鏡像提高效率

Docker在構建鏡像時(shí)會(huì )復用緩存中已經(jīng)存在的鏡像,如果明確不使用緩存,則可加參數docker build --no-cache=true使用緩存鏡像的規則

  1. 從一個(gè)已存在于緩存的父鏡像開(kāi)始構建,則會(huì )將當前鏡像的下一行指令與所有繼承于那個(gè)父鏡像的子鏡像比較,如果其中沒(méi)有一個(gè)是使用相同的指令構建的,則緩存失效
  2. 大部分情況下,將Dockerfile中的指令與其中一個(gè)子鏡像簡(jiǎn)單比較就夠了,但是某些指令需要更多的檢查與說(shuō)明:對于A(yíng)DD,COPY指令,文件內容會(huì )被檢查,會(huì )計算每一個(gè)文件的checksum,checksum中不會(huì )考慮最后修改及最后訪(fǎng)問(wèn)時(shí)間,在緩存中查找時(shí),checksum會(huì )與已經(jīng)存在的鏡像進(jìn)行比較,如果文件中有修改,則緩存失效。除了ADD,COPY命令,緩存檢查不會(huì )查看容器中的文件來(lái)決定緩存匹配,如處理RUN apt-get -y update命令時(shí),容器中文件的更新不會(huì )進(jìn)行檢查來(lái)確定緩存是否命中, 這種情況下, 只會(huì )檢查指令字符串本身是否匹配。
  3. 一旦緩存失效,所有后續的指令都會(huì )產(chǎn)生新的鏡像,不會(huì )再使用緩存。

17. 其它鏡像構建方式

  1. 通過(guò)標準輸入來(lái)生成Dockerfile構建,不會(huì )發(fā)送build context(從stdin讀取build context,只包含Dockerfile),適用于一次性構建,不需要寫(xiě)Dockerfile# 將會(huì )構建一個(gè)名稱(chēng)與tag均為none的鏡像
    echo -e 'FROM busybox\nRUN echo "hello world"' | docker build -
    #或
    docker build - <<EOF
    FROM busybox
    RUN echo "hello world"
    EOF
    # 構建一個(gè)命名的鏡像
    docker build -t myimage:latest - <<EOF
    FROM busybox
    RUN echo "hello world"
    EOF

連字符 - 作為文件名告訴Docker從stdin讀取Dockerfile

  1. 使用stdin來(lái)生成Dockerfile, 但是使用當前目錄作為build context# build an image using the current directory as context, and a Dockerfile passed through stdin
    docker build -t myimage:latest -f- . <<EOF
    FROM busybox
    COPY somefile.txt .
    RUN cat /somefile.txt
    EOF
  2. 使用遠程git倉庫構建鏡像,從stdin生成Dockerfiledocker build -t myimage:latest -f - https://github.com/docker-library/hello-world.git <<EOF
    FROM busybox
    COPY hello.c .
    EOF
本站僅提供存儲服務(wù),所有內容均由用戶(hù)發(fā)布,如發(fā)現有害或侵權內容,請點(diǎn)擊舉報。
打開(kāi)APP,閱讀全文并永久保存 查看更多類(lèi)似文章
猜你喜歡
類(lèi)似文章
Docker基礎與實(shí)戰,看這一篇就夠了
Docker基礎:Dockerfile相關(guān)知識介紹
Dockerfile完全指南
Docker Dockerfile詳解
Docker容器學(xué)習梳理-Dockerfile構建鏡像
Linux虛擬化Docker之自定義JAVA基礎環(huán)境的Docker并發(fā)布
更多類(lèi)似文章 >>
生活服務(wù)
分享 收藏 導長(cháng)圖 關(guān)注 下載文章
綁定賬號成功
后續可登錄賬號暢享VIP特權!
如果VIP功能使用有故障,
可點(diǎn)擊這里聯(lián)系客服!

聯(lián)系客服

欧美性猛交XXXX免费看蜜桃,成人网18免费韩国,亚洲国产成人精品区综合,欧美日韩一区二区三区高清不卡,亚洲综合一区二区精品久久