仮想化通信

日本仮想化技術株式会社の公式エンジニアブログ

Juju/MAASでKubernetes 1.16 + Kata Containerを使ってみた

しばらくJuju/MAASは触っていなかったのですが、先日次のリリースノートの「Kata Containers support」というところを見て、早速ためしてみようと思いました。

ubuntu.com

ちなみにKata Containerについては、次のドキュメントを見ればすぐわかると思うのでここでは述べません。ざっくり説明すると仮想マシンの中でコンテナーを動かすソリューションで、コンテナーに仮想マシンのセキュリティーと利便性をプラスするためのものと考えていただければOKだと思います。

katacontainers.io katacontainers.io

前提要件

動かすために必要な最低限のものは次のとおりです。MAAS 2.4.2はUbuntu 18.04.xの標準パッケージにふくまれるMAASのStable版です。

  • QEMUとかKVMが動くようなサーバー
  • Juju CLIが使えるOSセットアップ済みのPC
  • MAAS 2.4.2以降のバージョン

インストールの流れ

インストールの流れをざっと説明すると、次のとおりです。

  1. Jujuをインストール
  2. JujuでCloudと関連付ける
  3. CharmsやBundleを使って、Kubernetesをインストール
  4. Kata ContainerをKubernetesに追加

Juju Cloudとしては今回MAASを使いました。セットアップ方法については MAAS Cloudのページに書かれています。

MAASのインストールがまだであれば、MAASの公式インストール手順に従ってインストールをまず行います。

Jujuを使ったKubernetesのセットアップについては「Kubernetes Core」Bundleを使いました。LBが必要であれば「CDK」が最適だと思います。

今回は3と4について解説します。

Bundleを使ったKubernetesのデプロイ

Jujuでアプリケーションをデプロイするには、まずmodelを作成します。 modelを作成したら、juju switchコマンドを使って切り替えます。

$ juju add-model k8s-kata
$ juju switch k8s-kata

これでJujuを使ったKubernetesのデプロイの準備は完了しましたので、CharmsやBundleを使ってKubernetesをデプロイします。 いくつかBundleが用意されています。今回はKubernetes Coreを使いました。

jaas.ai

このBundleは2つのマシンが必要になります。 このBundleを一部修正します。

Jujuでアプリケーションをデプロイするにはまず、Juju machineを定義します。利用するJuju Cloudによって指定できるリソースは異なりますが、MAASの場合はMAAS tagを使うことで、ノードを指定できます。MAASにmaster、workerタグを設定したノードを1台ずつ用意します。

f:id:virtualtech:20191029154840p:plain
masterタグを指定したノードの例

あとはデプロイ用のYAMLにそのタグを指定するだけです。各アプリケーションはtoでデプロイ先のJuju Machineを指定しています。kubernetes-workerをJuju Machine 1、それ以外をJuju Machine 0にすると良いと思います。

description: A minimal two-machine Kubernetes cluster, appropriate for development.
series: bionic
machines:
  '0':
    constraints: tags=master
    series: bionic
  '1':
    constraints: tags=worker
    series: bionic

編集が終わったら、あとはjuju deployコマンドで実行するだけです。おおよそ1時間くらいで環境ができあがります。

$ juju deploy k8s-bundle.yaml

Kata ContainerをKubernetesに追加

JujuによるKubernetes環境が構築できたら、次のコマンドを実行し、Kata ContainerをKubernetesに追加します。 kata charmsと各Charmsのリレーションを張ります。これだけです。

% juju deploy cs:~containers/kata
% juju add-relation kata kubernetes-master
% juju add-relation kata kubernetes-worker
% juju add-relation kata:untrusted containerd:untrusted

少々待ったらjuju statusコマンドを実行して、アプリケーションやユニットにエラーが無いことを確認します。

Kata ContainerをKubernetesでつかってみる

次のようなYAMLファイルを用意します。

$ cat kata-pod.yml
---
apiVersion: v1
kind: Pod
metadata:
  name: nginx
  annotations:
    io.kubernetes.cri.untrusted-workload: "true"
spec:
  containers:
  - name: nginx
    image: nginx
    ports:
      - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: nginx-nodeport
  labels:
    app: nginx
spec:
  type: NodePort
  ports:
  - port: 80
    targetPort: 80
    nodePort: 30080
  selector:
    app: nginx

Podを作ってみます。

$ kubectl apply -f katapod.yml

問題なく、Podが作られ、NGINXアプリケーションとNodePortサービスがデプロイされました。

$ kubectl get -f katapod.yml
NAME        READY   STATUS    RESTARTS   AGE
pod/nginx   1/1     Running   0          21s

NAME                         TYPE       CLUSTER-IP       EXTERNAL-IP   PORT(S)        AGE
service/nginxapp1-nodeport   NodePort   10.152.183.155   <none>        80:30080/TCP   21s

Podはどのノードに作られたのでしょうか。確認します。 本例の場合はJuju Machine 1番のbay15という名前のホストで実行されたのが確認できます。

$ kubectl get po -o wide
NAME    READY   STATUS    RESTARTS   AGE   IP           NODE    NOMINATED NODE   READINESS GATES
nginx   1/1     Running   0          41s   10.1.96.11   bay15   <none>           <none>

$ juju machines
Machine  State    DNS           Inst id  Series  AZ       Message
0        started  172.17.28.63  bay13    bionic  default  Deployed
1        started  172.17.28.64  bay15    bionic  default  Deployed

Juju Machine 1番のノードにアクセスしてみます。

$ juju ssh 1
$ sudo kata-runtime list
ID                                                                 PID         STATUS      BUNDLE                                                                                                                  CREATED                          OWNER
99ba00a981842c747a789fa11b7247da99fa883fff95bdfb184b51fabc220f9b   -1          running     /run/containerd/io.containerd.runtime.v2.task/k8s.io/99ba00a981842c747a789fa11b7247da99fa883fff95bdfb184b51fabc220f9b   2019-10-29T04:47:12.572752789Z   #0
0c422b93810e32554ec3c8ef89a4fd48bd2a24dafd754090361724cca4427174   -1          running     /run/containerd/io.containerd.runtime.v2.task/k8s.io/0c422b93810e32554ec3c8ef89a4fd48bd2a24dafd754090361724cca4427174   2019-10-29T04:47:20.095326259Z   #0

$ ps aux|grep qemu
ubuntu    6867  0.0  0.0  14856  1028 pts/0    S+   07:10   0:00 grep --color=auto qemu
root     56868  0.4  0.1 2710444 175724 ?      Sl   04:47   0:35 /usr/bin/qemu-vanilla-system-x86_64 -name sandbox-99ba00a981842c747a789fa11b7247da99fa883fff95bdfb184b51fabc220f9b -uuid 4c1e33ab-3d99-4587-981b-8f8658c940ca -machine pc,accel=kvm,kernel_irqchip,nvdimm -cpu host -qmp unix:/run/vc/vm/99ba00a981842c747a789fa11b7247da99fa883fff95bdfb184b51fabc220f9b/qmp.sock,server,nowait -m 2048M,slots=10,maxmem=129813M -device pci-bridge,bus=pci.0,id=pci-bridge-0
...

以上で、KubernetesでKata Containerを使えるようになったのが確認できます。

参考にした情報

jaas.ai ubuntu.com ubuntu.com katacontainers.io