Dockerファイルにおける RUN・CMD・ENTRYPOINT の使い分け


DockerファイルでのRUN・CMD・ENTRYPINTは似たような命令です。ですが、これらを使い分けることができると(セキュリティ的にも)大変便利です。

対象

  • Dockerの概要が分かっている人
  • Linuxにおけるシェルの概要が分かっている人

RUN

  • Dockerイメージを作成するときに実行されるコマンド
  • 1つのDokerfileに複数記載が可能

ENTRYPOINT

  • シェルを介さずにコマンドを実行する
  • 1つのDokerfileに1つしか記載できない

CMD

  • コマンドを実行する
  • 1つのDokerfileに1つしか記載できない

ENTRYPOINT + CMD

  • Dockerイメージpushを上手に使うことで、ENTRYPOINTのみのDockerイメージとCMDのみの実行コンテナとに分けることができる
    1. 実行コンテナ作成の際に、ENTRYPOINTのみのDockerイメージをpullする
    2. ENTRYPOINTのみのDockerイメージで指定したコマンドが実行コンテナで実行される
      • 作成されたコンテナの用途を限定できる ― pullされるDockerイメージ側で指定したコマンドしか実行できないため

pullされるDockerイメージ

  • ENTRYPOINTでコマンドを指定する

実行コンテナ

  • CMDENTRYPOINTで指定したコマンドの補完となるよう指定する

下記のdockerfileを基にしたDockerイメージをDockerHubに上げます。

FROM alpine:latest
EXPOSE 80
RUN apk add --no-cache net-tools
RUN apk add --no-cache nmap-nping
ENTRYPOINT ["nping", "-c", "3", "--tcp", "-p", "80"]

ここでは{DockerID}/ping:latestとして上げています。DockerHubに上げる手順は以前の記事を参照してください。

実際に動かすコンテナのdocerfileは以下になります。

FROM {DockerID}/ping:latest
CMD ["www.google.co.jp"]

コンテナを構築し、実行します。

docker image build -t sample/ping:latest .
docker container run -p 80:80 --name ping sample/ping:latest

コンテナ実行結果:

まとめ

Dockerfileの命令は深く踏み込むと少々複雑です。効果的に使い分けてください。

参考

Dockerfile リファレンス

Docker/Kubernetes 実践コンテナ開発入門

[docker] CMD とENTRYPOINT の違いを試してみた

DockerfileのCMDとENTRYPOINTを改めて解説する