도커는 하나의 어플리케이션을 이미지로 만들기 위해 컨테이너 상태를 그대로 이미지로 저장한다.
즉, 이미지로 만들 어플리케이션을 리눅스만 설치된 컨테이너에 설치하고 그걸 그상태 그대로 이미지로 저장한다. 가상머신의 스냅샷과 비스므리한 방식이다.
복잡한 과정이지만 좋은 샘플이 많이 공개되어 있어서 다행이다.
또한 컨테이너의 가벼운 특성과 레이어 개념을 이용하여 생성과 테스트를 빠르게 수행할 수 있다.
샘플은 Ruby로 만들어진 간단한 웹 어플리케이션을 이용할 것이다.
Sinatra라는 가벼운 웹 프레임워크를 사용할 것이다.
들어가기에 앞서 다음 과정은 간단히 요약하면
그렇게 웹 어플리케이션을 총 3번 실행시켜 볼것이다.
새로운 프로젝트를 생성하기 위해서 새 폴더를 만들고 Gemfile과 app.rb를 만든다.
패키지를 관리하는 파일이다.
Gemfile 에 작성하고 저장하자.
source 'https://rubygems.org'
gem 'sinatra'
호스트 명을 출력하는 웹서버이다.
app.rb 파일에 작성하고 저장하자
require 'sinatra'
require 'socket'
get '/' do
Socket.gethostname
end
이제 패키지를 설치하고 서버를 실행해보자 .
Gemfile 이 있는 패키지에서 아래 명령어를 수행하자
gem install bundler # bundler 설치
bundle install # 패키지 install
bundle exec ruby app.rb # app.rb 어플리케이션 실행
추가적으로
내가 참고한 블로그는 우분투 .. 나는 센토스 .. (우분투로 하다가 중간부터 바뀜)
그 과정에서 ruby 버전이 맞지않아 bundler를 설치할 수 없는 이슈가 생겼었다.
ruby 버전이 3.0 이상이여아 한다는점..
그래서 rvm을 설치해서 해결하려 하였으나
rvm도 설치가 안됫 ㅓ이래저래 gpt 한테 물어보고 해결하였으나..
중요한 사항은 아닌거 같아서 적진 않겠다 휴
정상작동까지 길고도 험난했다.. 중간에 서버도 가상환경에서 다른 서버로 바꾸면서 다시 하고 있는데 가상환경 우분투로 했을때 잘 돌아갔던 사진도 첨부한다.
localhost:4567 에 접속했을 때 정상적으로 호스트 명을 출력하고 있음을 볼 수 있다.
또는 ruby를 설치하지 않고 루비가 설치된 컨테이너에 호스트의 디렉토리를 마운트 한 다음
번들을 설치하고 app.rb 어플리케이션을 실행하라는 명령어를 실행하면
로컬에 개발 환경을 구축하지 않고 도커 컨테이너를 개발환경으로 사용할 수 있다.
docker run --rm \
-p 4567:4567 \
-v $PWD:/usr/src/app \
-w /usr/src/app \
ruby \
bash -c "bundle install && bundle exec ruby app.rb -o 0.0.0.0"
이제 컨테이너에 설치된 어플리케이션을 그대~~~로 이미지로 만들어보자!
이미지를 만들기 위해서는 Dockerfile
이라는 이미지 빌드용 DSL(Domain Specific Language)
파일을 사용하는데 이 파일은 단순 텍스트 파일로 일반적으로는 소스 파일과 함께 관리된다.
아래 사진은 실제로 내가 참여했던 프로젝트인데 docker를 사용해 배포했어서 dockerfile이 존재함을 확인할 수 있었다.
Ruby 웹 어플리케이션을 이미지로 만들기 위해 작성해야 하는 빌드 파일, Dockerfile의 내용은 아래와 같다.
그렇다면 Dockerfile을 바로 작성하기 전에
리눅스 서버만 설치 되어있는 우분투 컨테이너에서
쉘 스크립트로 테스트 설치해보고
그 쉘 스크립트를 Dockerfile로 작성해보자. (실수를 방지하기 위함이다)
즉 이미지를 만들어보기 전에 위에서 말했던 것처럼 우선 우분투 컨테이너에서 제대로 작동되는지 확인후 도커파일을 생성해 볼 것이다. 이제 두번째로 웹어플리케이션을 실행한다는 의미이다.
우분투 컨테이너를 우선 생성하고 접속하자
docker run -it --name ubuntu ubuntu /bin/bash
# 1. ubuntu 설치 (패키지 업데이트)
apt-get update
# 2. ruby 설치
apt-get install ruby
gem install bundler
# 3. 소스 복사
# 참고블로그는 scp를 사용하는데 나는 자꾸 거기서 에러가 나서 gpt한테 물어봐 echo로 바꿨다.
mkdir -p /usr/src/app
# /usr/src/app 로 이동
cd /usr/src/app
# 원래는 소스를 복사하는게 맞는데 복사해오지를 못해서 echo를 통해 빈 파일 생성만 하였다.
# 도커파일 생성할때 COPY 명령어는 잘 싱행되니 여기는 그냥 넘어가자
echo "source 'https://rubygems.org'" > Gemfile
echo "gem 'sinatra'" >> Gemfile
echo "require 'sinatra'" > app.rb
# 4. Gem 패키지 설치
bundle install
bundle add rackup
# 5. Sinatra 서버 실행
bundle exec ruby app.rb
위 명령어들을 그대로 실행하면 웹 서버를 실행할 수 있다.
쉘에서 잘 작동 되는 것을 봤으니 똑같은 과정을 Dockerfile로 작성하면 된다.
이제 도커를 실행한 환경에서 도커 파일을 생성하자.
내용은 거의 ~~ 비슷하다.
#Dockerfile 이라는 파일 생성 하고 읽기
vi Dockerfile
# 1. ubuntu 설치 (패키지 업데이트 + 만든사람 표시)
FROM ubuntu
MAINTAINER anna@anna.com
RUN apt-get -y update
# 2. ruby 설치
RUN apt-get -y install ruby
RUN gem install bundler
# 3. 소스 복사
COPY . /usr/src/app
# Gem 패키지 설치
WORKDIR /usr/src/app
RUN bundle install
RUN bundle add rackup
# 5. Sinatra 서버 실행 (Listen 포트 정의)
EXPOSE 4567
CMD bundle exec ruby app.rb -o 0.0.0.0
쉘과 차이점은 도커 빌드 중엔 키보드를 입력할 수 없기 때문에 (y/n)
을 물어보는 걸 방지하기 위해 -y
옵션을 추가한 것 정도이다.
빌드 파일을 작성했으니 빌드하고 실제로 이미지를 생성해보자
Dockerfile 이 있는 디렉토리에서 실행해야만 한다. ⇒ Dockerfile을 찾지 못해서 빌드 실패
Gemfile이 있는 디렉토리에서 실행해야하만 한다! ⇒ RUN bundle install 실패 (Gem 패키지를 설치못함)
COPY . /usr/src/app 명령어가 명령어를 실행시는 디렉토리를 /usr/src/app으로 복사하기 때문에 실행파일도 같이 있어야 한다.
docker build -t app .
도커파일까지 빌드해서 이미지까지 생성해보았다.
도커를 빌드후 이미지 목록을 보여주는 명령문을 하게 되면 생성된 도커 이미지를 확인 할 수 있다.
docker images
docker run -d -p 8080:4567 app
하게 되면 만들어둔 이미지로 컨테이너를 생성할 수 있다.
차란 ~
Sinatra 프레임워크에서 만들어주는 기본 페이지 인가보다.
이미지를 만들고 컨테이너를 생성해보았다.
컨테이너 3개를 각기 다른 포트를 가지도록 하여 띄우보았다. 접속도 잘된다
다음에는 도커파일의 명령어들과 도커파일 빌드 과정, 최적화에 대해 알아보고 도커허브에 대해 알아보겠다!!!
다음게시글 -> [Docker] Dockerfile 기본 명령어와 최적화
📎 참고 링크
https://subicura.com/2017/02/10/docker-guide-for-beginners-create-image-and-deploy.html