티스토리 뷰

etc

[Docker] Dockerfile - ENTRYPOINT vs CMD

tbMaster 2022. 1. 24. 15:17
반응형

https://www.ctl.io/developers/blog/post/dockerfile-entrypoint-vs-cmd/

 

Dockerfile: ENTRYPOINT vs CMD - CenturyLink Cloud Developer Center

When looking at the instructions that are available for use in a Dockerfile there are a few that may initially appear to be redundant (or, at least, have significant overlap). We've already covered ADD and COPY and now we're going to look at ENTRYPOINT and

www.ctl.io

 

 

Dockerfile을 작성하고 실행하는데, 동작 방식이 자기 맘대로다...

이참에 CMD, ENTRYPOINT  사용법을 제대로 확인하고 정리해본다. 

본 글은 위 내용을 정리한 것이다. 더 자세한 내용이 궁금하다면, 위 링크를 확인하자.

 

 


 

 

ENTRYPOINT, CMD 모두 궁극적으로 Docker 이미지로부터 container를 생성하여 run 을 통해, 실행할 수 있도록 하는 명령어다. 

따라서, docker run 을  통해 argument를 가지지 않는 파일을 실행할 때는, ENTRYPOINT 나 CMD 를 이용할 수 있다. 

특히, Docker Hub 에서 받은 linux 기반의 이미지를 보면,  CMD를 활용할 경우, /bin/sh 또는 /bin/bash 와 같은 shell을 사용했다는 것을 알 수 있다. 이를 통해, 기본적으로 shell script가 동작되지 않는다는 것을 알 수 있다.

 

 

 

CMD와 ENTRYPOINT를 이용한 Override 

CMD 와 ENTRYPOINT 모두 Dockerfile에서 작성한 내용을 실행한다.  더 나아가, docker run 시 image 뒤에 argument를 넣어 Dockerfile에 작성된 내용을 오버라이드 할 수 있다.

- CMD 

 

- ENTRYPOINT

반드시 --entrypoint 플래그를 넣는다.

 

Override를 통해 알 수 있는 것은 결과적으로 CMD, ENTRYPOINT 모두 Override 가능하나, ENTRYPOINT의 사용은 플래그(--entrypoint)를 추가해야 하므로써, argument가 Dockerfile에 작성된 내용에 더 의존적임을 확인할 수 있다. 

ENTRYPOINT는 CMD와 같이 사용되면서, 그 의미를 더 명확하게 알 수 있다.

 

 

 

Shell vs. Exec

ENTRYPOINT 와 CMD 명령은 shell form,  exec form 두 가지를 지원한다.

CMD 로 shell form을 지원하면, /bin/sh -c 를 이용한 shell 이 실행되면서, 특정 binary가 실행된다. docker ps를 통해 명확하게 container가 어떤 form에서 실행됐는지 확인할 수 있다.

COMMAND : "/bin/sh -c 'ping localhost'"

보기에는 잘 동작하는 것처럼 보인다. 그러나 ENTRYPOINT 나 CMD 명령에서 shell form을 이용하여 실행하면, 감지하기 어려운 이슈가 발생한다.

아래는 실행중인 컨테이너 내부에서 동작하고 있는 프로세스들을 나열한 것이다. 

나열된 프로세스에서 PID 1은 사용자가 실행시킨 명령이 아니다. 이는 문제가 될 수 있는데,  container 에 특정 POSIX 시그널을 전달해야 할 필요가 있는 경우, PID1 에 전달되며, 사용자가 실행한 script 에는 전달되지 않는다.

(https://www.ctl.io/developers/blog/post/gracefully-stopping-docker-containers/)

PID 1 에 대한 문제 외에도, shell binary도 포함하지 않는 최소한의 image를 build할 경우 shell form 형식은 실행하는데 문제가 된다. 

Docker는 Dockerfile에 작성된 shell 명령들이 실제 container에서 정상동작하는지는 확인하지 않는다. 따라서 실행할 image에 /bin/sh 가 없으면, 해당 이미지는 run 에 실패한다.

 

 

그래서 더 좋은 방법으로 ENTRYPONT/CMD를 exec form 을 이용하여 실행하는 것이다. 

 exec form 은 ENTRYPOINT/CMD 명령 뒤에  JSONArray 형식으로 내용을 포함한다. exec form은 shell 없이 명령을 실행시킬 수 있다. shell 없이 exec form 을 이용하여 실행한 container 의 process를 확인하면, 아래와 같이 우리가 실행시킨 프로세스 외에 다른 프로세스는 실행되지 않았음을 확인할 수 있다.

 

ENTRYPOINT나 CMD를 이용할 때는 항상 exec form을 이용하여, 정확하게 container 안에 PID1으로 command를 실행하게 한다. 

지금까지 ENTRYPOINT나 CMD를 이용할 때, 어떤 form 으로 사용해야 하는지에 대해 알아봤다. 

 

 

 

ENTRYPOINT and CMD

ENTRYPOINT 와 CMD를 같이 적절하게 사용해야 하는 경우도 있다. 

ENTRYPOINT와 CMD 를 조합하여 사용하는 경우는 사용자에 의해 argument를 받아서 image를 실행시켜야 하는 경우다.

ENTRYPOINT와 CMD를 같이 사용할 경우, CMD는 ENTRYPOINT에 의존하게 되며, docker run 시에 CMD 에 입력한 문자열이 argument가 되어 동작하게 된다.

[ Dockerfile ]
[ Dockerfile에 작성된 default value 기준으로 run ]
[ 사용자에게 "google.com"을 입력받아 run ]

 

 

 

Conclusion

위에 내용을 종합해보면... 

 

1. CMD/ENTRYPOINT 명령어는 image를 실행시켜 원하는 동작을 수행하게 한다.

 

2. CMD/ENTRYPOINT 각각 사용할 경우 override가 가능하다.

단, ENTRYPOINT를 override 할 경우, --entrypoint 옵션을 추가해야 한다. 

그렇기 때문에 override가 필요한 명령문은 CMD, 그렇지 않을 경우 ENTRYPOINT를 사용한다. 

 

3. CMD/ENTRYPOINT 는 shell / exec form 이 있으나, exec form으로 작성하여, 사용자가 원하는 동작을 바로 실행할 수 있도록 한다.

shell form 의 경우, container 내부에서 사용자가 실행하지 않은 process가 PID1 로 실행된다. 이는 원치 않은 결과가 발생시킬 수 있다. 

 

4. 사용자에게 입력을 받아 image를 run해야할 경우, CMD와 ENTRYPOINT를 조합하여 작성한다. 

ENTRYPOINT 는 변하지 않는 명령문, default value를 작성하는데 사용한다. 

CMD는 사용자에게 입력받아야 하는 변경가능한 value를 작성하는데 사용한다.

 

반응형
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
TAG
more
«   2024/07   »
1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30 31
글 보관함