Docker學習筆記十:Docker build,COPY和ADD

Docker build命令詳解

Dockerfile創建完成後,可以使用docker build命令根據Dockerfile構建一個鏡像。在上一關中,我們在Dockerfile所在的文件夾下執行docker build -t myimage .這條命令,然後鏡像就被構建了。現在我們來詳細地將這條命令。該docker build的命令格式如下:

docker build [OPTIONS] 上下文路徑|URL

其中:

  • docker build: 用Dockerfile構建鏡像的命令關鍵詞;
  • -[OPTIONS]: 命令選項,常用的指令包括-t指定鏡像的名字,-f顯示指定Dockerfile,如果不使用-f,則默認將上下文路徑下的名爲Dockerfile的文件認爲是構建鏡像的“Dockerfile”;
  • 上下文路徑|URL: 指定構建鏡像的上下文的路徑,構建鏡像的過程中,可以且只可以引用上下文中的任何文件。

現在讓我們在看看docker build -t myimage .這條命令,在這條命令中,使用-t指定了鏡像名爲myimage,由於沒有使用-f指令,所以默認使用上下文路徑下名爲Dockerfile的文件認爲是構建鏡像的“Dockerfile”。最後指定上下文路徑,在這條命令中,上下文路徑是.
如果你學過Linux,你應該非常清楚上述命令中的小數點.代表的意思。在Linux中,小數點.代表着當前目錄。所以docker build -t myimage .中小數點.其實就是將當前目錄設置爲上下文路徑。

執行docker build後,會首先將上下文目錄的所有文件都打包,然後傳給Docker daemon,這樣Docker daemon收到這個上下文包後,展開就會獲得構建鏡像所需的一切文件。
如下所示,在執行完docker build後,會首先sending build context to Deckor daemon,也就是將上下文目錄下所有文件打包發給Docker daemon。所以在使用Dockerfile文件時構建鏡像時,一般將它放在一個空文件夾下,就是爲了防止將其他多餘的文件傳出去。然後依次執行Dockerfile的指令,如果指令正確執行,則繼續執行下一條,直到所有指令執行正確完畢,鏡像構建完成;如果指令執行出錯,終止鏡像構建。

[root@localhost newdir]# docker build -t myimage .
Sending build context to Docker daemon 2.048 kB
Step 1/2 : FROM ubuntu
 ---> 14f60031763d
Step 2/2 : RUN mkdir dir1
 ---> Running in c5117d908931
 ---> cb0193727724
Removing intermediate container c5117d908931
Successfully built cb0193727724

除了從本地構建以外,docker build還支持從URL構建,比如可以直接從Git repo中構建,這裏也不展開介紹了,可以查看:
Docker官方文檔

COPY指令和ADD指令

  • COPY複製文件;格式:COPY<源路徑> <目標路徑>;
    COPY指令編譯到目錄中的<源路徑>的文件或目錄複製到新的一層的內部的<目標路徑>位置。<源路徑>所指定的源必須在多箇中,即必須是一部分根目錄的相對路徑!<目標路徑>可以是容器內部的絕對路徑,也可以是相對於工作目錄的相對路徑(工作目錄可以用WORKDIR指令來指定,後面介紹)。目標路徑不需要預先創建,如果目錄不存在會在複製文件前先行創建目錄。
  • ADD更高級的文件複製;格式:ADD<源路徑> <目標路徑>;
    ADD與COPY指令在功能上十分相似,但是在COPY的基礎上增加了一些功能。例如,源路徑可以是一個指向一個網絡文件的URL,這種情況下,Docker引擎會試圖下載這個URL指向的文件到<目標路徑>去。

此外,當<源路徑>爲一個tar壓縮文件時,該壓縮文件在被複制到容器中時會被解壓提取。但是使用COPY指令將將tar壓縮文件複製到<目標路徑>中。如下圖所示:

[root@localhost tempdir]# docker build -t myimage .
Sending build context to Docker daemon  12.8 kB
Step 1/2 : FROM ubuntu
 ---> 14f60031763d
Step 2/2 : COPY ./hello.txt.tar /dir1/
 ---> 070559867e22
Removing intermediate container 1e55f9f19333
Successfully built 070559867e22
[root@localhost tempdir]# docker run myimage ls /dir1/
hello.txt.tar

而ADD指令如果<源路徑>爲一個tar壓縮文件的話,ADD指令將會自動解壓縮這個壓縮文件到<目標路徑>去。如下所示:

[root@localhost tempdir]# docker build -t myimage .
Sending build context to Docker daemon  12.8 kB
Step 1/2 : FROM ubuntu
 ---> 14f60031763d
Step 2/2 : ADD ./hello.txt.tar /dir1/
 ---> ead6431f75ba
Removing intermediate container f5fdcd97e196
Successfully built ead6431f75ba
[root@localhost tempdir]# docker run myimage ls /dir1/
hello.txt

這樣,如果你只需要tar包中的文件內容而不需要tar包,不要先COPY ./hello.txt.tar.gz,然後RUN tar –xvf hello.txt.tar.gz && rm hello.txt.tar.gz。請直接使用ADD指令,ADD ./hello.txt.tar.gz

因爲,這些的每一層重建完就不會再發生改變,後一層上的任何改變只發生在自己這一層。諸如此類,刪除前一層文件的操作,實際不是真的刪除前一層的文件,,而是僅在當前層標記爲該文件已刪除。在最終容器運行的時候,雖然不會看到這個文件,但實際上該文件會一直跟隨。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章