Dockerからcontainerdへの移行 (NTT Tech Conference 2022発表レポート)
NTTの須田と徳永 (共同執筆)です。NTT Tech Conference 2022 (2022/3/23)で発表した、「Dockerからcontainerdへの移行」の内容をまとめました。
背景: Kubernetes 1.24は組み込み機能としてのDocker対応を打ち切る
2014年に公開された初期のKubernetesはDockerにのみ対応していましたが、2016年のKubernetes 1.5では Container Runtime Interface (CRI) と呼ばれる共通インターフェースが導入され、 CRIに対応した任意のランタイムが利用可能になりました。以来、様々なランタイムが開発されてきましたが、2022年現在では containerd と CRI-O の 2つが主流です。
CRIが導入されてからも、Kubernetesに組み込まれているDocker対応機能(dockershim)が広く使われていましたが、2022年4月リリース予定のKubernetes 1.24では、dockershimがついに削除されます。
したがって、Kubernetesをdockershimで動かしてきたユーザは、containerdなどの他のランタイムへ乗り換えなければなりません。
なお、dockershim は Kubernetesの組み込み機能としては削除されますが、Mirantis 社によって cri-dockerd という外部プロジェクトとして fork され、開発が継続されています。
containerdとは
元々のcontainerd は、Dockerの下でコンテナの基本的な管理機能を提供するデーモンとして、2015年にDocker社により開発されました (2017年にCNCFに移管)。
containerdのスコープはその後拡大し、現在ではcontainerdだけで Docker (Docker Engine) の機能をほぼカバーしています。
containerdはCRIを通じてKubernetesのランタイムとして動作できるだけでなく、 docker
コマンドとほぼ同じ使い勝手の nerdctl
(contaiNERD CTL)コマンドもsubproject (non-core)として提供しています。 docker run
に相当する nerdctl run
、 docker build
に相当する nerdctl build
、 docker-compose up
に相当する nerdctl compose up
などの機能を取り揃えています。
containerdに移行すると新しくできること
containerd ・nerdctl は単に Docker の焼き直しではなく、多くの機能を追加しています (スライド23–29):
これらの機能は全てオプショナルです。例えば、IPFSによるP2Pイメージ共有機能は、IPFSデーモン ( /usr/local/bin/ipfs
)をインストールし、IPFSデーモンを起動するようにinitの設定を変更し、更に明示的に nerdctl push ipfs://...
コマンドを実行しなければ有効になりません。containerd・nerdctl をインストールするだけで勝手にホストがP2Pネットワークに接続されるわけではないので、「P2P」ソフトウェアのインストールが禁止されている環境でも心配には及びません。
containerdに移行するとできなくなること
Kubernetesノードのデバッグに docker
コマンドは使えなくなりますが、 nerdctl --namespace=k8s.io
コマンドで代替できます。下の図では、nerdctlでビルドしたイメージをローカルノードのPodとして実行しています。イメージをレジストリにpushし、他のノードに配布することももちろん可能です ( nerdctl push
)。
また、Docker REST APIに依存しているアプリケーションは動かなくなります。Docker REST API を直接呼び出さず、 docker
コマンドをexecするアプリケーションについては、 nerdctl
コマンドをexecするように書き換えれば動作します。
移行準備
イメージ
レジストリにpush済のDockerイメージは、containerdでもそのまま利用できます。
未pushのイメージも、docker save
コマンドでtarファイルとして保存しておけば、 nerdctl load
コマンドでcontainerdに移せます。
レジストリの認証情報
~/.docker/config.json
や Kubernetes の imagePullSecrets
はそのまま利用できます。
/etc/docker/daemon.json
や /etc/docker/certs.d
の設定は containerd には読み込まれないので、containerd のドキュメントを参考に設定しなおす必要があります。
ログ
/var/log/pods
のログ形式は異なるので、スクリプトで監視している場合はスクリプトの修正が必要です。
移行手順 (Kubernetesの場合)
マネージドKubernetesサービスの多くは、既にデフォルトのランタイムをcontainerdに変更しつつあります。ノードを作り直すだけで、簡単にDockerからcontainerdに移行できます。
非マネージド環境ではノードを作り直さなくてもkubeadm reset
すれば十分ではありますが、作り直すほうが簡単なことがあります。
Google Kubernetes Engine (GKE)
GKEでは、Linuxノードについては1.19、Windowsノードについては1.21からcontainerdが既にデフォルトとなっています。
Amazon Elastic Kubernetes Service (EKS)
Amazon EKSも、Bottlerocket AMIを使う場合はcontainerd が使われます。AWS FargateでAmazon EKSを動かす場合もcontainerdが使われます。
Amazon Linux AMIやWindows AMIを用いる場合は、現在最新のAMI (Kubernetes 1.21)ではまだDockerがデフォルトとなっています。ただし、ブートストラップスクリプトに --container-runtime containerd
オプションを渡すとcontainerdに切り替えることができます。
Kubernetes 1.23用のAMIからはDocker対応を打ち切り、containerdのみに対応する予定のようです。
Azure Kubernetes Service (AKS)
AKSでは、Linuxノードについては1.19からcontainerdが既にデフォルトとなっています。Windowsノードについても、1.23からcontainerdがデフォルトとなるようです。
kubeadm
Dockerとcontainerdの両方がノードにインストールされている場合、kubeadmは1.23現在ではDockerをデフォルトで選択します。
Dockerをアンインストールするか、kubeadmに明示的に --cri-socket=/run/containerd/containerd.sock
オプションを渡すとcontainerdが選択されます。ただし、Windowsでは --cri-socket
の値が異なります。
sudo kubeadm resetsudo kubeadm join 192.168.56.120:6443 \
--cri-socket=/run/containerd/containerd.sock \
--token <省略> --discovery-token-ca-cert-hash <省略>
前述の通り、1.24からはdockershimが削除されるので、Dockerとcontainerdの両方がインストールされている場合でもcontainerdがデフォルトで選択されるようになります。
移行手順 (nerdctlの場合)
Linux
バイナリアーカイブを https://github.com/containerd/nerdctl/releases からダウンロードし、 /usr/local
などのパスに展開します。
安全なRootlessモードで動かす場合は、 nerdctl
コマンドを実行する前に containerd-rootless-setuptool.sh install
コマンドを実行します。
containerd-rootless-setuptool.sh installnerdctl run -d --name nginx -p 8080:80 nginx:alpine
macOS
containerd・nerdctl は macOS 上では直に動作しませんが、Lima (Linux Machines)を用いると、containerd・nerdctl が入ったLinux仮想マシンを簡単に起動できます。
brew install limalimactl startlima nerdctl run -d --name nginx -p 80:80 nginx:alpine
Lima は元々は nerdctl 専用の仮想マシンを立ち上げる nerdctl machine
として企画していましたが、今のLimaはWindowsのWSL2に似た、汎用的なLinux仮想マシンとして利用できます。WSL2のように、ホストのファイルシステムを自動的にマウントしたり、ホストのlocalhostをゲストのlocalhostに自動的に繋げたりできます。
なお、containerd・nerdctl は Rancher Desktop にも付属しています。Rancher Desktop (macOS版)も内部的にはLimaを使っていますが、単体のLimaとは異なりGUIがついています。
Windows
WSL2を使えば、WindowsでもLinux版のcontainerd・nerdctlを実行できます。Rancher Desktop を使うと簡単です。
nerdctlにはWindowsネイティブ版もありますが、まだ experimental です。
まとめ
Kubernetes 1.24でのdockershim削除を背景に、Docker から containerd への移行が急速に進んでいます。ログの形式など細かい違いはありますが、移行は難しくありません。従来のDockerイメージもそのまま使えます。
NTT is hiring!
私たちNTTは、 nerdctl、Lima、Rootlessコンテナ、eStargz などの分野でcontainerdコミュニティに大きくコントリビュートしています。NTTでは containerd に限らず様々なオープンソースコミュニティで共に活動する仲間を募集しています。ぜひ弊社採用情報ページをご覧ください: https://www.rd.ntt/sic/recruit/