Slide 1

Slide 1 text

©2024 CyberAgent Inc. Distribution prohibited Container Onboarding20240514 Masaaki Suzuki@sZma5a / AI Shift

Slide 2

Slide 2 text

©2024 CyberAgent Inc. Distribution prohibited Today’s Goal

Slide 3

Slide 3 text

©2024 CyberAgent Inc. Distribution prohibited コンテナを構成している要素を知り 良さげなイメージを作る

Slide 4

Slide 4 text

©2024 CyberAgent Inc. Distribution prohibited Masaaki Suzuki AI Shift Development Team (Backend) sZma5a

Slide 5

Slide 5 text

©2024 CyberAgent Inc. Distribution prohibited ● Containerについて ● ローカルでのContainer実行 ● イメージ作成のtips ● 運用を考慮したtips Agenda

Slide 6

Slide 6 text

©2024 CyberAgent Inc. Distribution prohibited Containerについて

Slide 7

Slide 7 text

©2024 CyberAgent Inc. Distribution prohibited 仮想化技術の一つであり、プログラムを実行 環境ごとパッケージ化することができる。 そのため、コンテナランタイムがあれば容易 に展開することができる。 Containerとは?

Slide 8

Slide 8 text

©2024 CyberAgent Inc. Distribution prohibited 仮想化の変遷 物理環境に直接デプロイする形から、様々な抽象化を施し可用性や密度 を高めるため、仮想化技術が用いられてきた。 Server Hypervisor Container

Slide 9

Slide 9 text

©2024 CyberAgent Inc. Distribution prohibited Hypervisor: ハードウェアが抽象化されているため、OSレベ ルで分離することができる。そのため、自由に OS(Linux, Windows, macOS)を選択するこ とができるが、起動までに時間がかかる。 ex) VirtualBox, KVM HypervisorとContainerの違い https://kubernetes.io/docs/concepts/overview/what-is-kubernetes/

Slide 10

Slide 10 text

©2024 CyberAgent Inc. Distribution prohibited Container: プロセス単位で仮想化されるため、カーネル はホストOSと共有される。 そのため、Hypervisorと比較し自由度は限ら れるが、起動がすごく早い。 ex) docker, podman HypervisorとContainerの違い https://kubernetes.io/docs/concepts/overview/what-is-kubernetes/

Slide 11

Slide 11 text

©2024 CyberAgent Inc. Distribution prohibited https://www.docker.com/ja-jp/blog/containers-and-vms-together/ HypervisorとContainerの違い

Slide 12

Slide 12 text

©2024 CyberAgent Inc. Distribution prohibited ContainerはLinuxのカーネル機能であるNamespaceとcgroupを用いて実行環 境を分離している。 ● Namespace プロセスやユーザグループを論理的に分割するために用いる ex) マウント名前空間, PID名前空間, ネットワーク名前空間, IPC名前空間... ● cgroup プロセスに対しリソースの制限をかけるための仕組み Container Structure

Slide 13

Slide 13 text

©2024 CyberAgent Inc. Distribution prohibited 以下の3つの仕様からなるコンテナ形式とランタイムに関するオープンな 標準仕様であり、Linux Foundation のプロジェクトの1つである。 ● ランタイム仕様 (runtime-spec) ● イメージ仕様 (image-spec) ● 配布仕様 (distribution-spec) OCI (Open Container Initiative)

Slide 14

Slide 14 text

©2024 CyberAgent Inc. Distribution prohibited Dockerとは? Docker社が開発したContainer Engineであり、コ ンテナ間のネットワーク通信やオーケストレーショ ンなど様々な機能が含まれている。 また、標準化のために様々な機能がコンポーネント 化されている。

Slide 15

Slide 15 text

©2024 CyberAgent Inc. Distribution prohibited https://www.docker.com/ja-jp/blog/containerd-vs-docker/ Architecture DockerはCLIを通しdockerdでイメー ジのpullやコンテナの起動を行う。 dockerdはコンテナを管理する永続的 なプロセスであり、クライアントとは 異なるバイナリで動作している。

Slide 16

Slide 16 text

©2024 CyberAgent Inc. Distribution prohibited Architecture DockerのContainer Runtimeは、 containerdとruncから構成される。 runcがコンテナの作成・実行を行なっ ており、containerdではイメージやコ ンテナの状態管理などを行なっている。

Slide 17

Slide 17 text

©2024 CyberAgent Inc. Distribution prohibited containerd コンテナランタイムを標準化する過程でDocker からCNCFに寄贈されたプロジェクト。 KubernetesやAWS Fargateでも使用されている。 https://www.docker.com/ja-jp/blog/introducing-containerd/

Slide 18

Slide 18 text

©2024 CyberAgent Inc. Distribution prohibited containerd https://containerd.io/

Slide 19

Slide 19 text

©2024 CyberAgent Inc. Distribution prohibited ローカルでのコンテナ実行

Slide 20

Slide 20 text

©2024 CyberAgent Inc. Distribution prohibited Container実行手順

Slide 21

Slide 21 text

©2024 CyberAgent Inc. Distribution prohibited コンテナ実行までの流れ

Slide 22

Slide 22 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 Dockerfileとはイメージを作成するため の命令が書かれたドキュメントファイル のことである。 Dockerfileでは既存のイメージをベース トしたカスタムイメージを作成すること ができる。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 23

Slide 23 text

©2024 CyberAgent Inc. Distribution prohibited $ docker history golang:latest IMAGE CREATED CREATED BY SIZE COMMENT 295f95becd4e 3 weeks ago WORKDIR /go 0B buildkit.dockerfile.v0 3 weeks ago RUN /bin/sh -c mkdir -p "$GOPATH/src" "$GOPA… 0B buildkit.dockerfile.v0 3 weeks ago COPY /usr/local/go/ /usr/local/go/ # buildkit 220MB buildkit.dockerfile.v0 3 weeks ago ENV PATH=/go/bin:/usr/local/go/bin:/usr/loca… 0B buildkit.dockerfile.v0 3 weeks ago ENV GOPATH=/go 0B buildkit.dockerfile.v0 3 weeks ago ENV GOTOOLCHAIN=local 0B buildkit.dockerfile.v0 3 weeks ago ENV GOLANG_VERSION=1.22.2 0B buildkit.dockerfile.v0 3 weeks ago RUN /bin/sh -c set -eux; apt-get update; a… 240MB buildkit.dockerfile.v0 4 days ago /bin/sh -c set -eux; apt-get update; apt-g… 183MB 4 days ago /bin/sh -c set -eux; apt-get update; apt-g… 48.5MB 4 days ago /bin/sh -c #(nop) CMD ["bash"] 0B 4 days ago /bin/sh -c #(nop) ADD file:07ae70ad05f39a240… 139MB コンテナイメージはレイヤー構造で管理されており、docker historyでイメー ジの構造を見ることができる。 イメージの作成

Slide 24

Slide 24 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 各レイヤはDockerfileに書かれた命令 (FROM, RUNなど)と対応している。 また、レイヤごとにキャッシュが作成さ れており、ビルドの効率化やレジストリ へのアップロードなどで使われる。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 25

Slide 25 text

©2024 CyberAgent Inc. Distribution prohibited ベースイメージの指定 FROM: ベースとなるイメージを指定している。 golang: Debianベースのイメージ golang:-alpine 軽量なAlpineを使用したイメージ golang:-windowsservercore Windows coreをベースとしたイメージ FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 26

Slide 26 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 WORKDIR イメージ内での作業ディレクトリを指定 している。 WORKDIRが指定されている場合、後続 の命令は全て該当のディレクトリで実行 される。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 27

Slide 27 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"] COPY ファイルをイメージ内にコピーするため の命令。 オプションを使うことによって、様々な 方法でファイルを持って来れる。

Slide 28

Slide 28 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 --fromで指定することで、他のビルド ステージやイメージからファイルをコ ピーすることができる。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"] FROM golang:1.19 as bulder … RUN go build -o /docker-gs-ping —----------------------------------------- FROM golang:1.19 COPY --from=builder /docker-gs-ping / CMD ["/docker-gs-ping"] 1つのDockerfile

Slide 29

Slide 29 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 他にも... --exclude: 除外指定 (labs) --chown --chmod: 権限周りを指定 etc... 様々なオプションが存在する。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 30

Slide 30 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 RUN イメージビルド時にコマンドを実行するた めの命令。 ※ コマンドの文字列からキャッシュを行う FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 31

Slide 31 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"] EXPOSE コンテナを実行時にリッスンするポートを 示す命令。 実際にポートが公開されるわけではない が、使用するポートを実行環境に示すため に用いられる。

Slide 32

Slide 32 text

©2024 CyberAgent Inc. Distribution prohibited イメージの作成 CMD コンテナが起動時に実行されるコマンド を指定する命令。 似たような命令としてENTRYPOINTも あり、docker run時にコマンドを指定 した時の挙動が異なる。 CMDの場合はそのコマンドで上書きさ れるが、ENTRYPOINTの場合はオプ ションとして実行される。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 33

Slide 33 text

©2024 CyberAgent Inc. Distribution prohibited イメージのビルド $ docker build . -t mlops-handson/mecab:v1 コンテキストの指定. Dockerに見てほしいpath. COPY句でどこを起点にするか. 基本的にDockerfileのある場所でOK イメージ名. お作法的にはowner/image_name イメージタグ. イメージは更新されゆくのでいわゆるversioning イメージのビルド時はdocker buildコマンドを使用する。

Slide 34

Slide 34 text

©2024 CyberAgent Inc. Distribution prohibited コンテナの起動 $ docker run -p 8080:80 mlops-handson/mecab:v1 外部公開するポートを指定することで、ホストマシンからコンテナ内のアプリ ケーションにアクセスすることができる ビルドしたイメージを指定 必要に応じて外部公開するポートを指定しdocker runでコンテナを実行する。

Slide 35

Slide 35 text

©2024 CyberAgent Inc. Distribution prohibited Dockerでは6種類のネットワークドライバが存在 し、それらを元にコンテナ間ネットワークの構築や 外部との接続を行う。 Dockerネットワーク bridge (Default) コンテナ間の通信をブリッジすることでお互いに通信することができる host ホストのネットワークに直接参加する overlay 複数のDockerデーモンを接続することができる ipvlan L2またはL3からコンテナネットワークを構築することができる macvlan コンテナにMACアドレスを割り当てることができる none ネットワークを割り当てない(接続しない)

Slide 36

Slide 36 text

©2024 CyberAgent Inc. Distribution prohibited イメージ作成のtips

Slide 37

Slide 37 text

©2024 CyberAgent Inc. Distribution prohibited イメージサイズの軽量化 サイズが大きいとネットワーク内の運搬コストが高くなるため、スケールが遅く なったり、無駄に課金されたりする。 研修の時、FargateをPrivate Subnetにおいていたため、ECRか らイメージを読み込む際、NAT Gatewayを通る関係で一晩で5千 円くらい課金された...

Slide 38

Slide 38 text

©2024 CyberAgent Inc. Distribution prohibited $ docker history golang:latest IMAGE CREATED CREATED BY SIZE COMMENT 295f95becd4e 3 weeks ago WORKDIR /go 0B buildkit.dockerfile.v0 3 weeks ago RUN /bin/sh -c mkdir -p "$GOPATH/src" "$GOPA… 0B buildkit.dockerfile.v0 3 weeks ago COPY /usr/local/go/ /usr/local/go/ # buildkit 220MB buildkit.dockerfile.v0 3 weeks ago ENV PATH=/go/bin:/usr/local/go/bin:/usr/loca… 0B buildkit.dockerfile.v0 3 weeks ago ENV GOPATH=/go 0B buildkit.dockerfile.v0 3 weeks ago ENV GOTOOLCHAIN=local 0B buildkit.dockerfile.v0 3 weeks ago ENV GOLANG_VERSION=1.22.2 0B buildkit.dockerfile.v0 3 weeks ago RUN /bin/sh -c set -eux; apt-get update; a… 240MB buildkit.dockerfile.v0 4 days ago /bin/sh -c set -eux; apt-get update; apt-g… 183MB 4 days ago /bin/sh -c set -eux; apt-get update; apt-g… 48.5MB 4 days ago /bin/sh -c #(nop) CMD ["bash"] 0B 4 days ago /bin/sh -c #(nop) ADD file:07ae70ad05f39a240… 139MB docker historyで各レイヤーの内容やサイズを見れるので、適宜確認しながら イメージを最適化していく。 レイヤーごとのサイズ確認方法

Slide 39

Slide 39 text

©2024 CyberAgent Inc. Distribution prohibited ● マルチステージビルド ● ベースイメージの選定 ● RUN使用時の注意 ● 依存関係周りのキャッシュ ● COPY使用時の注意 ● 静的ファイルの取り扱い 軽量化方法

Slide 40

Slide 40 text

©2024 CyberAgent Inc. Distribution prohibited 実行用とビルド用にステージを分けるこ とによって、最終的なイメージを軽量で セキュアなものにする方法。 実行に必要な物のみが含まれたイメージ を作ることができるため、余分なレイ ヤーやライブラリを省くことができる。 マルチステージビルド FROM golang:1.22 as builder RUN apt-get install -y hoge… COPY *.go ./ RUN go build -o /binary FROM distroless as runner COPY --from builder /binary /binary RUN go build -o /binary CMD ["/binary"] 1つのDockerfile

Slide 41

Slide 41 text

©2024 CyberAgent Inc. Distribution prohibited ベースイメージの選定 ビルドと実行で使用するものは同じでな くても良い。 debian-slim Debianベースのイメージではあるが、必要最低限 のパッケージしかはいっていない。 alpine Alpine Linuxを用いた軽量のイメージ。 distroless ランタイム用の軽量なイメージであり、シェルがない ため安全に実行することができる。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ RUN go build -o /docker-gs-ping EXPOSE 8080 CMD ["/docker-gs-ping"]

Slide 42

Slide 42 text

©2024 CyberAgent Inc. Distribution prohibited パッケージのキャッシュに関するTips RUNとは異なりCOPYはファイルの内容を 元にキャッシュが生成される。 そのため、パッケージリストのみをコピー しておくことで、変更があった時のみ更新 することができる。 FROM golang:1.22 WORKDIR /app COPY go.mod go.sum ./ RUN go mod download COPY *.go ./ … キャッシュ

Slide 43

Slide 43 text

©2024 CyberAgent Inc. Distribution prohibited RUN使用時の注意 ファイルの取り扱い パッケージリストの更新と削除が分かれて いるため、レイヤに残ってしまう。 パッケージのキャッシュ パッケージのアップデートのみをRUNに置 くと、キャッシュにより更新されない。 →レイヤーはなるべくまとめて減らす FROM ubuntu:latest # パッケージデータがレイヤに保管される RUN apt-get update RUN apt-get install -y nginx RUN rm -rf /var/lib/apt/lists/* … # 修正 RUN apt-get update \ && apt-get install nginx \ && rm -rf /var/lib/apt/lists/*

Slide 44

Slide 44 text

©2024 CyberAgent Inc. Distribution prohibited COPY使用時の注意 … # 不要なものもCOPYのレイヤは残る COPY . . RUN rm -r ./tmp … RUNと同様にファイル取得と削除のレイ ヤが別れるとサイズを小さくすることが できない。 そのため、COPYでは必要なものだけ持っ てくることや不必要なものを省く。

Slide 45

Slide 45 text

©2024 CyberAgent Inc. Distribution prohibited イメージに含めないファイルやディレクトリを定義することができ、 COPYを行う際、該当のファイルを省くことができる。 .gitignoreと形式や機能は似ているが、指定の仕方や動作に違いがあ るため注意する必要がある。 Ex) .dockerignoreの場合 ● 指定は相対パスで行う必要がある ● .dockerignoreはコンテキストと同じ階層に置く必要がある etc... .dockerignore

Slide 46

Slide 46 text

©2024 CyberAgent Inc. Distribution prohibited プログラム実行時に使用する静的ファイルのサイズによっては、イメージに含め ずマウントする方が適切な場合がある。 ・ライフサイクル  ファイルの更新と合わせイメージを最新化する必要があるか ・ネットワーク  イメージのアップデートやデプロイの際のトラフィック量や経路 ・スケール  イメージ起動までの時間はスケール時に許容できるか →学習モデルや学習データはイメージに含めずマウントすることも考える 静的ファイルの取り扱い

Slide 47

Slide 47 text

©2024 CyberAgent Inc. Distribution prohibited 運用を考慮したtips セキュリティ, タグ管理, プロセス管理

Slide 48

Slide 48 text

©2024 CyberAgent Inc. Distribution prohibited ホストマシンでContainer Runtimeを実行す る際、rootで実行しない。 Dockerではホストマシンのディレクトリをコ ンテナ内にbindすることができるため、マシ ン全体が攻撃される恐れがある。 セキュリティ rootlessでの実行(ホスト) https://kubernetes.io/docs/concepts/overview/what-is-kubernetes/

Slide 49

Slide 49 text

©2024 CyberAgent Inc. Distribution prohibited アプリケーションのバグなどで任意のコマ ンドを実行できる場合、ホストマシンに侵 入される恐れがある。 そのため、コンテナ実行時にあらかじめ不 要な権限を与えない。 セキュリティ アプリケーションをrootで実行しない FROM golang:1.22 … USER noroot … CMD ["/docker-gs-ping"]

Slide 50

Slide 50 text

©2024 CyberAgent Inc. Distribution prohibited Dockerでは、イメージに脆弱性が含まれていないかの検査を行うことができる。 発見された場合は、修正されたバージョンや該当CVEの情報が表示される。 セキュリティ 脆弱性のチェック https://docs.docker.com/reference/cli/docker/scout/cves/ $ docker scout cves ${IMAGE}:${TAG} … The image contains 46 packages with one or more vulnerability for a total of 181 vulnerabilities UNSPECIFIED | 4 LOW | 168 MEDIUM | 6 HIGH | 3 CRITICAL | 0

Slide 51

Slide 51 text

©2024 CyberAgent Inc. Distribution prohibited イメージを最新化するためにlatest運用が見 受けられるが、動いているイメージが区別で きないため、事故が起きやすくなる。 そのため、コミットハッシュや、バージョン タグを付ける。 タグ管理 イメージタグ運用

Slide 52

Slide 52 text

©2024 CyberAgent Inc. Distribution prohibited コンテナでは新たにプロセス名前空間が作られ るため、最初にアプリケーションを実行すると PID1が振られる。 そのため、SIGTERM(終了させるためのシグ ナル)がうまく伝わらずに強制終了したり、ソ ンビプロセス化したりする問題。 Ex) Node.js プロセス管理 PID1問題

Slide 53

Slide 53 text

©2024 CyberAgent Inc. Distribution prohibited Docker実行時に--initオプションを指定するこ とで実行時にtini(軽量のプロセス管理ツール) が起動される。これにより、適切にシグナルやプ ロセス管理を行うことができる。 Kubernetesの場合はPause Containerがその役 割も担っている。 プロセス管理 PID1問題

Slide 54

Slide 54 text

©2024 CyberAgent Inc. Distribution prohibited Thank you! リソースの削除忘れずに! 質問などあれば 🙌