跳轉到主要內容
Dockerfile 指令 每個指令的用意與 copy-exact 範例。以 Docker 官方 Dockerfile 參考為準(截至 2026-06)。

指令一覽

指令用意
FROM指定基底映像,必須是第一條有效指令;AS <name> 替 stage 命名
RUNbuild 期間執行指令(裝套件、編譯)。每條 RUN 是一層
CMD容器啟動時的預設指令,可被 docker run 後接的指令覆蓋
ENTRYPOINT容器啟動時固定執行的進入點,docker run 的參數不覆蓋它
COPY把 context 的檔案複製進映像(最常用)
ADD同 COPY,但多了自動解壓 tar 與下載 URL(一般優先 COPY)
ENV設環境變數,留在映像、容器執行時可見
ARGbuild 期變數,--build-arg 傳入,不留在映像
WORKDIR設工作目錄(不存在會自動建),取代 RUN cd
EXPOSE文件性質宣告監聽埠,不會真的開埠
VOLUME標記某路徑為外部 volume 掛載點
USER設後續指令與容器的執行身分(建議切非 root)
LABEL加中繼資料(取代已棄用的 MAINTAINER
HEALTHCHECK定義健康檢查指令
ONBUILD延遲觸發:本映像被當基底時才執行
SHELL覆蓋 shell form 用的 shell
STOPSIGNALdocker stop 時送的信號(預設 SIGTERM)

RUN 的 shell form 與 exec form

# Shell form(包在 /bin/sh -c,會做變數展開與管線)
RUN apt-get update && apt-get install -y --no-install-recommends \
    curl git \
    && rm -rf /var/lib/apt/lists/*

# Exec form(JSON 陣列,不過 shell)
RUN ["/bin/bash", "-c", "echo $HOME"]
合併多條 RUN 成一條(用 &&\)可減少層數,並把 apt 快取在同一層清掉。

三組常混的差異

  • CMD 是「預設指令」,docker run myimg 其他指令整個覆蓋 CMD。
  • ENTRYPOINT 是「固定進入點」,docker run 後接的參數會附加在 ENTRYPOINT 之後,不覆蓋它。
  • 常見組合:ENTRYPOINT 放固定執行檔、CMD 放可被覆蓋的預設參數。
  • 兩者都用 exec form(JSON 陣列),PID 1 才是應用程式本身,才能正確收到 SIGTERM 做優雅關閉;shell form 會包一層 /bin/sh -c,signal 傳不進去。
ENTRYPOINT ["python", "app.py"]
CMD ["--port", "8000"]
# docker run img             → python app.py --port 8000
# docker run img --port 9000 → python app.py --port 9000
完整互動:
ENTRYPOINT 無ENTRYPOINT ["ep"](exec)ENTRYPOINT ep(shell)
CMD 無錯誤ep/bin/sh -c ep
CMD ["cmd"]cmdep cmd/bin/sh -c ep(CMD 被忽略)
CMD cmd/bin/sh -c cmdep /bin/sh -c cmd/bin/sh -c ep(CMD 被忽略)

其他常用指令範例

WORKDIR /app                    # 設工作目錄,相對路徑相對於前一個 WORKDIR
EXPOSE 8000                     # 文件性質,實際開埠靠 docker run -p
ENV APP_ENV=production PORT=8080
USER 1001:1001                  # 切非 root(用 UID:GID 不依賴 user database)
LABEL org.opencontainers.image.authors="dev@example.com"
HEALTHCHECK --interval=30s --timeout=3s --retries=3 \
  CMD curl -f http://localhost/ || exit 1
STOPSIGNAL SIGTERM
EXPOSE 只是宣告,不會真的開埠;USER 不存在的使用者要先 RUN useradd 建立。

接下來

官方參考:docs.docker.com/reference/dockerfile