Share
Embed
コンテナ・K8s研修 コンテナ編【MIXI 25新卒技術研修】
本スライドは、MIXIの2025年度新卒向け技術研修で使用された資料です。
MIXI 2025新卒技術研修
『コンテナ・K8s研修 コンテナ編』
▼リポジトリ
https://github.com/mixigroup/2025BeginnerTrainingContainer
▼動画
https://youtu.be/Znp31343ScI
───────────────────────────────
※皆様へのお願い※ 資料・動画・リポジトリのご利用について
───────────────────────────────
公開している資料や動画は、是非、勉強会や社内の研修などにご自由にお使いいただければと思いますが、以下のような場でのご利用はご遠慮ください。
- 受講者から参加費や授業料など金銭を集めるような場での利用
(会場費や飲食費など勉強会の運営に必要な実費を集める場合は問題ありません)
- 出典を削除または改変しての利用
MIXI ENGINEERS PRO
April 17, 2025
Video
Transcript
55 slides
-
自己紹介 • 宗形 翼 ◦ 22 新卒 • デジタルエンターテインメントパブリッシング本部 ◦ グローバルモンスト室
> グローバルモンストエンジニアグループ • Ruby on Rails でサーバーを書いたりしています -
自己紹介 • 岩崎 将典 ◦ 2020年中途入社 • デジタルエンターテインメントパブリッシング本部 ◦ グローバルモンスト室
> グローバルモンストエンジニアグループ • モンパニ、STAR SMASH、タワーオブスカイ等のサーバを担当 -
Docker 等インストール確認 • gcloud auth list ◦ 会社のメールアドレスが出てくるか確認 •
docker version ◦ Server: Docker Desktop 4.40.0 がでてくる • GitHub リポジトリにアクセスできる ◦ https://github.com/mixigroup/2025BeginnerTrainingContainer • gcloud auth configure-docker asia-northeast1-docker.pkg.dev • docker pull asia-northeast1-docker.pkg.dev/hr-mixi/container-training-2024/test-example -
なぜコンテナ技術を学ぶのか • 弊社のプロジェクトに広く利用されているため • 弊社以外でも多くの企業で利用されている技術だから • コンテナ技術を雰囲気ではなく少し踏み込んで知って欲しいから 利用例 •
開発環境に必要なバックエンドサーバーや DB 等をコマンド一つで用意 • 本番環境へコンテナとしてデプロイ -
コンテナの概要: 軽量で移植性の高いアプリケーション実行環境 • コンテナとはアプリケーションとその依存関係を一つのパッケージにまとめ独立して実行でき る環境。 • メリット ◦ 複数環境で同じコンテナを動作させることができるので移植性が高い
◦ VM に比べて軽量でインフラリソースを効率的に利用できる • 代表的なコンテナ技術 ◦ Docker ◦ Kubernetes ◦ クラウド (ECS, Cloud Run…) -
VM とコンテナの違い • 同じマシンで動作する他の VM とリソース隔離 • VM ごとに独立して
OS が動作 • 起動に時間がかかる • 他のコンテナとリソース隔離 ◦ 独立したファイルシステム・ネットワーク • 通常の Linux プロセスが動作するので軽量 • プロセスと同程度の起動時間 -
Docker architecture (一部省略) Client Host Registry Host を操作するプログラム コンテナの実行・管理を行う
コンテナイメージの保存・管理 $ docker run $ docker pull $ docker build Docker Desktop アプリ等 Docker deamon (dockerd) • ubuntu • python • golang • my-image1 docker cli イメージ 実行中 • ubuntu-1 • my-app-1 停止中 • my-app-2 コンテナ • 様々な公開イメージ • プライベートイメージ Docker Hub Amazon ECR Docker 社以外のレジストリの例 Google Container Registry 管理 -
Docker Desktop for Mac では Linux VM が動作 Client
Host Registry Host を操作するプログラム コンテナの実行・管理を行う コンテナイメージの保存・管理 $ docker run $ docker pull $ docker build Docker Desktop アプリ等 Docker deamon (dockerd) • ubuntu • python • golang • my-image1 docker cli イメージ 実行中 • ubuntu-1 • my-app-1 停止中 • my-app-2 コンテナ • 様々な公開イメージ • プライベートイメージ Docker Hub Amazon ECR Docker 社以外のレジストリの例 Google Container Registry 管理 Linux VM -
containerd • 2016年12月14日 Docker 社が Docker Engine のコアコンポーネントであるcontainerd をスピ
ンアウト • Dockerd は内部で containerd を利用 • container image の pull, push、コンテナの実行と監視等が利用できる • lazy pulling や IPFS のような先進的な機能を利用可能 • コンテナの隔離環境の構築や起動には低レベルランタイムを使う • Docker Desktop では低レベルランタイムにデフォルトでは runc を利用 Docker deamon (dockerd) containerd runc コンテナ コンテナごとに起動されるプロセス docker cli HTTP gRPC -
runc • OCI(Open Container Initiative)によるリファレンス実装 • Linux namespace, cgroups 等を利用してコンテナの隔離環境を作成・管理
◦ macOSには上記に相当するものが無いのでコンテナを利用したい場合は Linux を動かす必要がある ◦ Windows には HCS(Host Compute Service)といった上記に相当するものが実装されていてWindows container を起動する際に利用される • containerd は runc 以外の OCI 互換の低レベルランタイムも利用可能 ◦ Kata Containers は軽量 VM を用いて隔離コンテナ環境を用意 ◦ runwasi は WebAssembly をコンテナとして実行できる -
Docker architecture (一部省略) Client Host Registry Host を操作するプログラム コンテナの実行・管理を行う
コンテナイメージの保存・管理 $ docker run $ docker pull $ docker build docker compose Docker Desktop アプリ等 Docker deamon (dockerd) • ubuntu • python • golang • my-image1 docker cli イメージ 実行中 • ubuntu-1 停止中 • my-app-1 コンテナ • 様々な公開イメージ • プライベートイメージ Docker Hub Amazon ECR Docker 社以外のレジストリの例 Google Container Registry Buildkit containerd storage network runc イメージを作成 コンテナの実行 -
なぜ containerd を直接使わずに Docker Desktop を使うのか? • コンテナを利用するためには Linux
を動かす必要がある ◦ macOS 上で Linux を動かす VM を用意する必要がある ◦ Docker Desktop ではそのあたりが利用者に気にしなくても使える仕組みになっている ▪ macOS 上で Docker Desktop を起動する Hypervisor Framework を利用しLinuxを起動してくれる ▪ kernel patches, security fixes は良い感じにdockerが適用している ▪ Git のようにインストールするだけで便利に使えるのが普及した理由だと個人的には思っている -
結局 Docker 以外のコンテナって何選べば良いのよ? • 本番環境では containerd を利用するのが無難です ◦ Docker
から移行とかになったとき、そもそも Docker は containerd を利用しているので 動作に差異が生じない ◦ Docker cli によせた cli が存在する https://github.com/containerd/nerdctl ◦ K8s や AWS Fargate はすでに Docker を使わず直接 containerd を利用している • macOS では Docker Desktop が便利 ◦ 無料で使いたい場合や containerd を直接触りたいなら lima が便利 ◦ lima は macOS 上で Linux VM を動作 + mac, Linux 間のファイルやポートを自動で共有 ◦ lima 上で nerdctl + containerd を使える -
結局 docker 以外のコンテナって何選べば良いのよ? • ローカル開発 ◦ 基本Docker Desktop ◦
macOSで無料で使うなら lima + nerdctl + containerd などが便利 ▪ lima は macOS 上で Linux VM を動作 + mac, Linux 間のファイルやポートを自動で共有 ▪ nerdctl は Docker cli と同じようなコマンドで containerd を利用可能な cli • 本番環境 ◦ containerd を利用するのが無難です ▪ Dockerから移行とかになったとき、そもそもDockerはcotainerdを利用しているので 動作に差異が生じない ▪ Docker cliによせたcliが存在する https://github.com/containerd/nerdctl ▪ K8s や Fargate はすでに Docker を使わず直接 containerd を利用している -
Docker Hub からコンテナを選んで実行する 実行するコマンド (step1) $ docker run hello-world
Hello from Docker! と出力するプ ログラムを実行する。 -
実行結果 コマンドの実行結果 $ docker run hello-world Unable to find image
'hello-world:latest' locally latest: Pulling from library/hello-world 7050e35b49f5: Pull complete Digest: sha256:ffb13da98453e0f04d33a6eee5bb8e46ee50d08e be17735fc0779d0349e889e9 Status: Downloaded newer image for hello-world:latest Hello from Docker! This message shows that your installation appears to be working correctly. (以下略) ローカルにないイメージは 自動的に pull してくる ここからコンテナで実行 しているプログラムの出力 -
Docker architecture (一部省略) Client Host Registory Host を操作するプログラム コンテナの実行・管理を行う
コンテナイメージの保存・管理 $ docker run Docker Desktop アプリ等 Docker deamon (dockerd) • hello-world docker cli イメージ 実行中 • xxx コンテナ • hello-world Docker Hub Amazon ECR Docker 社以外のレジストリの例 Google Container Registry 管理 ① ②pull ③起動 ④出力を転送 -
コンテナと HTTP 通信する Python を実行して簡易 web サーバーを起動し、ブラウザからアクセスする。
step 1 ディレクトリで python -m http.server コマンドを実行すると localhost:8000/index.html にブラウザでアクセスできる これをコンテナで行う。 -
コンテナと HTTP 通信する 実行するコマンド (step1) $ docker run -p
8000:8000 -v $PWD:/app python \ python -m http.server オプション -p 8000:8000 コンテナのポート(右)をホストのポート(左)へ公開 -v $PWD:/app ホストの $PWD をコンテナの /app にマウント イメージ python Python イメージ コマンド python Python コマンドを実行する 引数... -m http.server コマンド引数、Python 標準のサーバーを起動 Python を実行して簡易 web サーバーを起動し、ブラウザからアクセスする。 http://localhost:8000/app へアクセスしてみよう -
実行結果 出力 172.17.0.1 - - [07/Apr/2023 04:17:00] "GET /app/HTTP/1.1" 200
- • コンテナとファイルを共有できる • コンテナのポートに通信できる -
コンテナの終了方法 コマンド $ docker ps CONTAINER ID IMAGE COMMAND
(略) NAMES 888036ffe01a python "python -m http.serv…" (略) charming_hoover $ docker stop 888036ffe01a 1. Ctrl-C などでプロセスを終了する。 2. docker stop コマンドを使う。 Ctrl+p Ctrl+q を順番に押すとコンテナは実行したままターミナルに戻れる -
Step 2: イメージを作成してアップロードする Dockerfile コンテナイメージ レジストリ build push BuildKit
• コンテナイメージを作るた めの手順書 • ビルドに必要なファイル ファイル -
Dockerfile の命令が順番に実行される Dockerfile FROM python:3.12 WORKDIR /app RUN pip
install flask COPY . /app CMD ["python", "main.py"] ベースイメージの指定 このイメージをもとにして新しいイメージを作成する -
イメージ名の指定の仕方 registry-1.docker.io/library/hello-world:latest レジストリのドメイン イメージの名前 イメージのタグ イメージのタグを指定することでバージョン等を指定可能 イメージ名を省略可能
• レジストリを省略すると registry-1.docker.io になる • library/ の場合は library/ を省略可能 • タグを省略すると :latest になる registry-1.docker.io/library/python:latest を省略すると python -
ベースイメージの選び方 Docker Hub から検索しよう。 Docker Hub へは誰でもアップロードできるので Docker Official
Image を選ぶのが安心 \ Docker Hub 以外もあるよ / -
Dockerfile の命令が順番に実行される Dockerfile FROM python:3.12 WORKDIR /app RUN pip
install flask COPY . /app CMD ["python", "main.py"] ワーキングディレクトリの設定 -
Dockerfile の命令が順番に実行される Dockerfile FROM python:3.12 WORKDIR /app RUN pip
install flask COPY . /app CMD ["python", "main.py"] コマンドの実行 ライブラリのインストールなど -
Dockerfile の命令が順番に実行される Dockerfile FROM python:3.12 WORKDIR /app RUN pip
install flask COPY . /app CMD ["python", "main.py"] ホストのディレクトリからファイルをコピー -
Dockerfile の命令が順番に実行される Dockerfile FROM python:3.12 WORKDIR /app RUN pip
install flask COPY . /app CMD ["python", "main.py"] デフォルトのコマンドを指定 docker run でコマンドを指定しない場合、 このコマンドが実行される -
docker build によってイメージを作成し起動してみる • docker build コマンドでコンテキストと Dockerfile から
コンテナイメージを作成 • 引数でビルド対象のディレクトリを指定 • -t オプションでイメージ名を指定できる。 実行するコマンド (step2) $ docker build -t myimage . $ docker run myimage • カレントディレクトリのファイルと Dockerfile でイメージを作成し、 myimage と名前をつけるコマンド -
docker build によってイメージを作成し起動してみる 実行結果 [+] Building 3.0s (9/9) FINISHED
=> [internal] load build definition from Doc 0.0s => => transferring dockerfile: 37B 0.0s => [internal] load .dockerignore 0.0s => => transferring context: 2B 0.0s => [internal] load metadata for docker.io/li 0.9s => [1/4] FROM docker.io/library/python:3.11. 0.0s => [internal] load build context 0.0s => => transferring context: 59B 0.0s => CACHED [2/4] WORKDIR /app 0.0s => [3/4] RUN pip install flask 1.9s => [4/4] COPY . /app 0.0s => exporting to image 0.1s => => exporting layers 0.1s => => writing image sha256:9144792bebcfff27c 0.0s => => naming to docker.io/library/myapp 0.0s docker が BuildKit を起動してコンテナをビルド ローカルのファイルを転送 Dockerfile の命令を一つずつ実行 -
Dockerfile の命令ごとに差分を増やして新しいイメージを作る 変更差分 変更差分 変更差分 変更差分 ベースイメージ (python:3.11.2) 変更差分
変更差分 変更差分 変更差分 WORKDIR の差分 RUN の差分 COPY の差分 CMD の差分 新イメージ Dockerfile 変更差分 ベースイメージの ベースイメージ 一部省略. docker history [IMAGE] コマンドで履歴が見れる -
Dockerfile を書き換えて本番環境用のイメージを作る Flask で本番環境用のサーバーを実行する一例 1. まず pip install waitress
で本番環境用のサーバーをインストールする 2. waitress-serve 'main:app' でサーバーを 8080 ポートに起動する Dockerfile に必要な処理を書き加えてイメージのビルド・実行してみよう。 INFO:waitress:Serving on http://0.0.0.0:8080 と出力されて同じページが見れる ヒント: いきなり Dockerfile を書くのは大変なので先ほど作ったイメージ上で bash を起動して、 コマンドが合っているかどうか一つずつ実行しながら試すと良いです。 $ docker run -it python bash または $ docker run -it python <先ほど作ったイメージ名> -
Dockerfile のベストプラクティス (余裕がある人向け) • イメージサイズを小さくすることで起動に必要な pull の時間を短縮できる ◦ サイズが小さいベースイメージを使う
(python:3.12-slim, 3.12-alpine など) ◦ パッケージマネージャー等のキャッシュを削除する (rm -rf $(pip cache dir) など) ◦ RUN 命令はまとめて書く • Dockerfile はキャッシュが有効になるように書くとビルド時間を短縮できる ◦ RUN 命令で使わないファイルは、あとで COPY 命令で追加する ◦ main.py を変更しても pip install は実行されずにキャッシュが使えるようになる -
書き換えた Dockerfile の例 Dockerfile FROM python:3.12 WORKDIR /app RUN
pip install flask waitress && pip cache purge COPY . /app CMD ["waitress-serve", "main:app"] -
コンテナを Google Cloud に push する 実行するコマンド (step2) $
docker tag myimage \ asia-northeast1-docker.pkg.dev/hr-mixi/container-training-2024/好きな名 前:latest $ docker push asia-northeast1-docker.pkg.dev/hr-mixi/container-training-2024/好きな名 前:latest https://console.cloud.google.com/artifacts/docker/hr-mixi/asia-northeast1/container-training-2024 -
Docker Compose を利用して開発環境に複数のコンテナを起動する • アプリケーションは複数のサービスが協調して動作する ◦ アプリケーションサーバー, データベースサーバーなど •
複数のコンテナを起動する方法を学ぶ • Docker Compose は開発環境で複数のコンテナを動かすためのツール • 本番環境は複数のサーバーで構成されるので使えない App サーバー DB サーバー -
Docker Compose が管理するもの docker-compose .yaml サービス: コンテナと環境変数などの設定 docker compose
up ボリューム : コンテナ間で共有できる永続的なストレージ ネットワーク : サービス間の通信を管理する仮想的なネット ワーク -
Docker Compose の主なコマンド • docker compose … の形式、昔は docker-compose
コマンドだった。 • docker compose up コンテナの起動 • docker compose up -d デタッチモードでコンテナの起動 • docker compose down コンテナの削除 • docker compose build サービスのビルド -
docker-compose.yaml にサービス等の定義を書く step3/docke-compose.yaml (一部省略) services: app: # API サーバー
build: context: python dockerfile: Dockerfile environment: ... ports: - "5000:5000" web: # React image: node:18 working_dir: '/app' volumes: - ./web/:/app ports: - "3000:3000" environment: REACT_APP_API_URL: 'http://localhost:5… entrypoint: /bin/bash command: - /app/entrypoint.sh db: # データベース image: mysql:8.0 ... yaml に3 つのコンテナが起動するように定義されている。 • app (API サーバー) ◦ python ディレクトリの Dockerfile でビルドしたコンテナ起 動 • web (React の Web アプリ) ◦ node イメージにソースコードのディレクトリをマウントして 開発サーバーを起動 • db (データベースサーバー) ◦ データベースファイルを永続化できるようにマウント -
Docker Compose を利用して複数のコンテナを起動する 実行するコマンド (step3) $ docker compose build
$ docker compose up 1 分弱で localhost:3000 にアクセスできる。 • Todo App が動くか確認しよう。 • docker ps コマンドで起動したコンテナを確認しよう。 docker compose up はコンテナがない場合は自動で build してく れる。すでにコンテナがある場合はファイルを更新しても自動で build されないので注意。 -
docker compose exec を利用して mysql に接続する 実行するコマンド (step3) $
docker compose exec db -it mysql -uroot -ppassword docker compose exec は実行中のコンテナの中でプログラムを実行でき る。 • db はサービスの名前 • -it は対話型のプログラムを動かすときに使うオプション。 • mysql 以降は実行するコマンド MySQL に接続してクエリを入力できる画面が表示されるので、 クエリを実行して DB の内容を確認してみよう。 クエリ実行例 mysql> SELECT * FROM app.todos; +----+-------+-----------+ | id | task | completed | +----+-------+-----------+ | 31 | test1 | 0 | | 32 | test2 | 0 | +----+-------+-----------+ 2 rows in set (0.01 sec)