Docker實戰-編寫Dockerfile

1、編譯鏡像

1. 編譯鏡像php

    Dockerfile相似於Makfile,用戶使用docker build就能夠編譯鏡像,使用該命令能夠設置編譯鏡像時使用的CPU數量、內存大小、文件路徑等docker

語法:docker build [OPTIONS] PATH| URL| - 
常見選項: 
          -t 設置鏡像的名稱和TAG,格式爲name:tag 
          -f Dockerfile的名稱,默認爲PATH/Dockerfile 
例子:docker build -f ~/php.Dockerfile . 
注意:PATH是編譯鏡像使用的工做目錄,Docker Daemon在編譯開始時,會掃描PATH中的全部文件,能夠在編譯目錄中加入.dockerignore過濾不須要的文件shell

    Docker Daemon從Dockerfile中順序讀取指令,生成一個臨時容器,在容器中執行指令,容器編譯成功後會提交做爲鏡像層加入最終鏡像,爲了加快編譯過程,Docker Daemon採用了緩存機制,若是在緩存中找到了須要的中間鏡像則直接使用該鏡像而不生成臨時容器(編譯時可使用選項–no-cache選擇不使用緩存)ubuntu

2. dockerignore文件數組

    編譯開始前,Docker Daemon會讀取編譯目錄中的.dockerignore文件,忽略其中的文件和目錄,在其中可使用通配符(?表明一個字符,*表明零個或任意個字符),使用通配符時,總會出現那麼幾個例外,這時可使用!+文件名,Docker Daemon會讀取!後面的文件緩存

*/temp* 忽略PATH路徑下一級子目錄中以temp開頭的文件和目錄,如PAHT/A/temp.txt */*/temp* 忽略PATH路徑下二級子目錄中以temp開頭的文件和目錄,如PATH/A/B/temp.txt *.md !README.md 忽略全部md文件,除了README.md

 

2、Dockerfile指令詳解

    Dockerfile由多條指令組成,每條指令在編譯鏡像時執行相應的程序完成某些功能,由指令+參數組成,以逗號分隔,#做爲註釋起始符,雖然說指令不區分大小寫,可是通常指令使用大些,參數使用小寫ruby

這裏寫圖片描述

指令:FROM 
功能描述:設置基礎鏡像 
語法:FROM < image>[:< tag> | @< digest>] 
提示:鏡像都是從一個基礎鏡像(操做系統或其餘鏡像)生成,能夠在一個Dockerfile中添加多條FROM指令,一次生成多個鏡像 
注意:若是忽略tag選項,會使用latest鏡像bash


指令:MAINTAINER 
功能描述:設置鏡像做者 
語法:MAINTAINER < name>markdown


指令:RUN 
功能描述: 
語法:RUN < command> 
          RUN [「executable」,」param1」,」param2」] 
提示:RUN指令會生成容器,在容器中執行腳本,容器使用當前鏡像,腳本指令完成後,Docker Daemon會將該容器提交爲一箇中間鏡像,供後面的指令使用 
補充:RUN指令第一種方式爲shell方式,使用/bin/sh -c < command>運行腳本,能夠在其中使用\將腳本分爲多行 
          RUN指令第二種方式爲exec方式,鏡像中沒有/bin/sh或者要使用其餘shell時使用該方式,其不會調用shell命令 
例子:RUN source $HOME/.bashrc;\ 
          echo $HOMEpost

          RUN [「/bin/bash」,」-c」,」echo hello」]

          RUN [「sh」,」-c」,」echo」,」$HOME」] 使用第二種方式調用shell讀取環境變量


指令:CMD 
功能描述:設置容器的啓動命令 
語法:CMD [「executable」,」param1」,」param2」] 
          CMD [「param1」,」param2」] 
          CMD < command> 
提示:CMD第一種、第三種方式和RUN相似,第二種方式爲ENTRYPOINT參數方式,爲entrypoint提供參數列表 
注意:Dockerfile中只能有一條CMD命令,若是寫了多條則最後一條生效


指令:LABEL 
功能描述:設置鏡像的標籤 
延伸:鏡像標籤能夠經過docker inspect查看 
格式:LABEL < key>=< value> < key>=< value> … 
提示:不一樣標籤之間經過空格隔開 
注意:每條指令都會生成一個鏡像層,Docker中鏡像最多隻能有127層,若是超出Docker Daemon就會報錯,如LABEL ..=.. <僞裝這裏有個換行> LABEL ..=..合在一塊兒用空格分隔就能夠減小鏡像層數量,一樣,可使用鏈接符\將腳本分爲多行 
          鏡像會繼承基礎鏡像中的標籤,若是存在同名標籤則會覆蓋


指令:EXPOSE 
功能描述:設置鏡像暴露端口,記錄容器啓動時監聽哪些端口 
語法:EXPOSE < port> < port> … 
延伸:鏡像暴露端口能夠經過docker inspect查看 
提示:容器啓動時,Docker Daemon會掃描鏡像中暴露的端口,若是加入-P參數,Docker Daemon會把鏡像中全部暴露端口導出,併爲每一個暴露端口分配一個隨機的主機端口(暴露端口是容器監聽端口,主機端口爲外部訪問容器的端口) 
注意:EXPOSE只設置暴露端口並不導出端口,只有啓動容器時使用-P/-p才導出端口,這個時候才能經過外部訪問容器提供的服務


指令:ENV 
功能描述:設置鏡像中的環境變量 
語法:ENV < key>=< value>…|< key> < value> 
注意:環境變量在整個編譯週期都有效,第一種方式可設置多個環境變量,第二種方式只設置一個環境變量 
提示:經過${變量名}或者 $變量名使用變量,使用方式${變量名}時能夠用${變量名:-default} ${變量名:+cover}設定默認值或者覆蓋值 
          ENV設置的變量值在整個編譯過程當中老是保持不變的


指令:ADD 
功能描述:複製文件到鏡像中 
語法:ADD < src>… < dest>|[「< src>」,… 「< dest>」] 
注意:當路徑中有空格時,須要使用第二種方式 
          當src爲文件或目錄時,Docker Daemon會從編譯目錄尋找這些文件或目錄,而dest爲鏡像中的絕對路徑或者相對於WORKDIR的路徑 
提示:src爲目錄時,複製目錄中全部內容,包括文件系統的元數據,但不包括目錄自己 
          src爲壓縮文件,而且壓縮方式爲gzip,bzip2或xz時,指令會將其解壓爲目錄 
          若是src爲文件,則複製文件和元數據 
          若是dest不存在,指令會自動建立dest和缺失的上級目錄


指令:COPY 
功能描述:複製文件到鏡像中 
語法:COPY < src>… < dest>|[「< src>」,… 「< dest>」] 
提示:指令邏輯和ADD十分類似,一樣Docker Daemon會從編譯目錄尋找文件或目錄,dest爲鏡像中的絕對路徑或者相對於WORKDIR的路徑


指令:ENTRYPOINT 
功能描述:設置容器的入口程序 
語法:ENTRYPOINT [「executable」,」param1」,」param2」] 
          ENTRYPOINT command param1 param2(shell方式) 
提示:入口程序是容器啓動時執行的程序,docker run中最後的命令將做爲參數傳遞給入口程序 
          入口程序有兩種格式:exec、shell,其中shell使用/bin/sh -c運行入口程序,此時入口程序不能接收信號量 
          當Dockerfile有多條ENTRYPOINT時只有最後的ENTRYPOINT指令生效 
          若是使用腳本做爲入口程序,須要保證腳本的最後一個程序可以接收信號量,能夠在腳本最後使用exec或gosu啓動傳入腳本的命令 
注意:經過shell方式啓動入口程序時,會忽略CMD指令和docker run中的參數 
          爲了保證容器可以接受docker stop發送的信號量,須要經過exec啓動程序;若是沒有加入exec命令,則在啓動容器時容器會出現兩個進程,而且使用docker stop命令容器沒法正常退出(沒法接受SIGTERM信號),超時後docker stop發送SIGKILL,強制中止容器 
例子:FROM ubuntu <換行> ENTRYPOINT exec top -b


指令:VOLUME 
功能描述:設置容器的掛載點 
語法:VOLUME [「/data」] 
          VOLUME /data1 /data2 
提示:啓動容器時,Docker Daemon會新建掛載點,並用鏡像中的數據初始化掛載點,能夠將主機目錄或數據卷容器掛載到這些掛載點


指令:USER 
功能描述:設置RUN CMD ENTRYPOINT的用戶名或UID 
語法:USER < name>


指令:WORKDIR 
功能描述:設置RUN CMD ENTRYPOINT ADD COPY指令的工做目錄 
語法:WORKDIR < Path> 
提示:若是工做目錄不存在,則Docker Daemon會自動建立 
          Dockerfile中多個地方均可以調用WORKDIR,若是後面跟的是相對位置,則會跟在上條WORKDIR指定路徑後(如WORKDIR /A   WORKDIR B   WORKDIR C,最終路徑爲/A/B/C)


指令:ARG 
功能描述:設置編譯變量 
語法:ARG < name>[=< defaultValue>] 
注意:ARG從定義它的地方開始生效而不是調用的地方,在ARG以前調用編譯變量總爲空,在編譯鏡像時,能夠經過docker build –build-arg < var>=< value>設置變量,若是var沒有經過ARG定義則Daemon會報錯 
          可使用ENV或ARG設置RUN使用的變量,若是同名則ENV定義的值會覆蓋ARG定義的值,與ENV不一樣,ARG的變量值在編譯過程當中是可變的,會對比使用編譯緩存形成影響(ARG值不一樣則編譯過程也不一樣) 
例子:ARG CONT_IMAG_VER <換行> RUN echo $CONT_IMG_VER 
          ARG CONT_IMAG_VER <換行> RUN echo hello 
          當編譯時給ARG變量賦值hello,則兩個Dockerfile可使用相同的中間鏡像,若是不爲hello,則不能使用同一個中間鏡像


指令:ONBUILD 
功能描述:設置自徑想的編譯鉤子指令 
語法:ONBUILD [INSTRUCTION] 
提示:從該鏡像生成子鏡像,在子鏡像的編譯過程當中,首先會執行父鏡像中的ONBUILD指令,全部編譯指令均可以成爲鉤子指令


指令:STOPSIGNAL 
功能描述:設置容器退出時,Docker Daemon向容器發送的信號量 
語法:STOPSIGNAL signal 
提示:信號量能夠是數字或者信號量的名字,如9或者SIGKILL,信號量的數字說明在Linux系統管理中有簡單介紹


補充:ONBUILD流程

  • 編譯時,讀取全部ONBUILD鏡像並記錄下來,在當前編譯過程當中不執行指令
  • 生成鏡像時將全部ONBUILD指令記錄在鏡像的配置文件OnBuild關鍵字中
  • 子鏡像在執行FROM指令時會讀取基礎鏡像中的ONBUILD指令並順序執行,若是執行過程當中失敗則編譯中斷;當全部ONBUILD執行成功後開始執行子鏡像中的指令
  • 子鏡像不會繼承基礎鏡像中的ONBUILD指令

補充:CMD ENTRYPOINT和RUN的區別

    RUN指令是設置編譯鏡像時執行的腳本和程序,鏡像編譯完成後,RUN指令的生命週期結束

    容器啓動時,能夠經過CMD和ENTRYPOINT設置啓動項,其中CMD叫作容器默認啓動命令,若是在docker run命令末尾添加command,則會替換鏡像中CMD設置的啓動程序;ENRTYPOINT叫作入口程序,不能被docker run命令末尾的command替換,而是將command看成字符串,傳遞給ENTRYPOINT做爲參數

FROM ubuntu ENTRYPOINT ["ps"] //經過命令docker run --rm test啓動容器,打印ps的輸出 //經過命令docker run --rm test -ef啓動容器,打印ps -ef的輸出

    在docker run中,能夠經過–entrypoint替換鏡像中的入口程序,在Dockerfile中,應該至少有一條CMD或者ENTRYPOINT指令,若是同時定義了CMD和ENTRYPOINT則CMD會做爲參數傳遞給ENTRYPOINT

FROM ubuntu ENTRYPOINT ["ps"] CMD ["-ef"] //經過命令docker run --rm test啓動容器,打印ps -ef的輸出
相關文章
相關標籤/搜索