インストール#
- docker.io のインストール
他の cgroup driver で docker をインストールした場合は、docker と Kubernetes が同じ cgroup driver を使うように設定する必要があります。
1
2
3
4
5
| cat << EOF >> /etc/docker/daemon.json
{
"exec-opts": ["native.cgroupdriver=systemd"]
}
EOF
|
- apt キーとソースをシステムに追加
1
2
3
4
5
| root@kube-master:~# curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -
OK
root@kube-master:~# cat <<EOF >> /etc/apt/sources.list.d/kubernetes.list
> deb http://apt.kubernetes.io/ kubernetes-xenial main
> EOF
|
その後、kubernetes パッケージをインストールします。
1
2
| root@kube-master:~# apt update -y
root@kube-master:~# apt install -y kubelet kubeadm kubectl
|
- kubeadm でセットアップと設定
kubeadm init
を実行する際、CNI を選択する必要があります。ここでは flannel を選ぶので、--pod-network-cidr
オプションを追加します。
1
| root@k8sm:~# kubeadm init --pod-network-cidr=10.244.0.0/16
|
しばらく待つと、インストール完了を示す以下のメッセージが表示されます。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| Your Kubernetes master has initialized successfully!
To start using your cluster, you need to run the following as a regular user:
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
You should now deploy a pod network to the cluster.
Run "kubectl apply -f [podnetwork].yaml" with one of the options listed at:
https://kubernetes.io/docs/concepts/cluster-administration/addons/
You can now join any number of machines by running the following on each node
as root:
kubeadm join 192.168.122.75:6443 --token .....<snip>
|
指示に従い、通常ユーザーで以下のコマンドを実行します。
1
2
3
| mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
|
また、kubeadm join
で始まるコマンドをメモしておきましょう。ワーカーノードをクラスターに参加させる際に必要です。
Pod 間の通信のために、Pod ネットワークをインストールする必要があります。ここでは Flannel を使います。
1
| kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
|
次に、すべてが正常に起動しているか確認します。
1
| kubectl get pods --all-namespaces
|
coredns-xxxxxx Pod が Running になっていて、master ノードが Ready であれば、クラスターはワーカーノードの参加を受け付ける準備ができています。
1
2
3
4
5
6
7
8
9
10
11
12
13
| wshi@k8sm:~$ kubectl get pods --all-namespaces
NAMESPACE NAME READY STATUS RESTARTS AGE
kube-system coredns-78fcdf6894-ltgw2 1/1 Running 0 17m
kube-system coredns-78fcdf6894-n8hw2 1/1 Running 0 17m
kube-system etcd-k8sm 1/1 Running 0 16m
kube-system kube-apiserver-k8sm 1/1 Running 0 16m
kube-system kube-controller-manager-k8sm 1/1 Running 0 16m
kube-system kube-flannel-ds-amd64-ktcqm 1/1 Running 0 1m
kube-system kube-proxy-nczhf 1/1 Running 0 17m
kube-system kube-scheduler-k8sm 1/1 Running 0 16m
wshi@k8sm:~$ kubectl get node
NAME STATUS ROLES AGE VERSION
k8sm Ready master 17m v1.11.2
|
- 他のノードをセットアップし、クラスターに参加させる
残りのワーカーノードも、上記と同様に kubectl、kubeadm、kubelet、docker をインストールし、kubeadm join ...
コマンドを実行します。
しばらくすると、すべてのワーカーノードが Ready になります。
1
2
3
4
5
| wshi@k8sm:~$ kubectl get node
NAME STATUS ROLES AGE VERSION
k8sm Ready master 44m v1.11.2
k8sn1 Ready <none> 11m v1.11.2
k8sn2 Ready <none> 11m v1.11.2
|
ジョブの実行#
Pod 内で動作するアプリケーションは「ジョブ」と呼ばれます。
ほとんどの Kubernetes オブジェクトは yaml で作成されます。以下は、perl で円周率を2000桁計算して終了するジョブのサンプル yaml です。
1
2
3
4
5
6
7
8
9
10
11
12
13
| apiVersion: batch/v1
kind: Job
metadata:
name: pi
spec:
template:
spec:
containers:
- name: pi
image: perl
command: ["perl", "-Mbignum=bpi", "-wle", "print bpi(2000)"]
restartPolicy: Never
backoffLimit: 4
|
この yaml ファイルを master ノード上に “pi-job.yaml” という名前で作成し、以下のコマンドでジョブを実行します。
1
| kubectl create -f pi-job.yaml
|
ジョブの詳細情報は以下のコマンドで確認できます。
1
2
3
4
5
6
| $ kubectl get pod
...
pi-72c7r 0/1 Completed 0 3m
$ kubectl describe pod pi-72c7r
...
|
ログ(標準出力)は以下のコマンドで確認できます。
1
2
| $ kubectl logs pi-72c7r
3.1415926535897932384626433832795028841971693993751058209749445923078164062862089986280348253421170679821480865132823066470938446095505822317253594081284811174502841027019385211055596446229489549303819644288109756659334461284756482337867831652712019091456485669234603486104543266482133936072602491412737245870066063155881748815209209628292540917153643678925903600113305305488204665213841469519415116094330572703657595919530921861173819326117931051185480744623799627495673518857527248912279381830119491298336733624406566430860213949463952247371907021798609437027705392171762931767523846748184676694051320005681271452635608277857713427577896091736371787214684409012249534301465495853710507922796892589235420199561121290219608640344181598136297747713099605187072113499999983729780499510597317328160963185950244594553469083026425223082533446850352619311881710100031378387528865875332083814206171776691473035982534904287554687311595628638823537875937519577818577805321712268066130019278766111959092164201989380952572010654858632788659361533818279682303019520353018529689957736225994138912497217752834791315155748572424541506959508295331168617278558890750983817546374649393192550604009277016711390098488240128583616035637076601047101819429555961989467678374494482553797747268471040475346462080466842590694912933136770289891521047521620569660240580381501935112533824300355876402474964732639141992726042699227967823547816360093417216412199245863150302861829745557067498385054945885869269956909272107975093029553211653449872027559602364806654991198818347977535663698074265425278625518184175746728909777727938000816470600161452491921732172147723501414419735685481613611573525521334757418494684385233239073941433345477624168625189835694855620992192221842725502542568876717904946016534668049886272327917860857843838279679766814541009538837863609506800642251252051173929848960841284886269456042419652850222106611863067442786220391949450471237137869609563643719172874677646575739624138908658326459958133904780275898
|
ジョブの別例#
“busybox” イメージを使い、10秒間スリープするジョブのサンプル yaml:
1
2
3
4
5
6
7
8
9
10
11
12
13
| apiVersion: batch/v1
kind: Job
metadata:
name: busybox
spec:
template:
spec:
containers:
- name: busybox
image: busybox
command: ["sleep", "10"]
restartPolicy: Never
backoffLimit: 4
|
Pod のデプロイ#
Pod は通常、Kubernetes クラスター内で稼働するアプリケーションを表します。以下は Pod を定義する yaml の例です:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
| apiVersion: v1
kind: Pod
metadata:
name: alpine
namespace: default
spec:
containers:
- name: alpine
image: alpine
command:
- sleep
- "3600"
imagePullPolicy: IfNotPresent
restartPolicy: Always
|
Pod の起動#
1
| kubectl create -f alpine.yaml
|
Pod の削除#
1
| kubectl delete -f alpine.yaml
|
または
1
| kubectl delete pod alpine
|
1
| kubectl delete pod/alpine
|
現在の状態の確認#
1
2
3
| kubectl get nodes
kubectl describe node node-name
kubectl get pods --all-namespaces -o wide
|
-n
オプションで namespace を指定できます。
1
| kubectl get pods -n kube-system
|
Deployment#
nginx デプロイメント用の yaml ファイル例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| apiVersion: apps/v1beta2
kind: Deployment
metadata:
name: nginx-deployment
spec:
selector:
matchLabels:
app: nginx
replicas: 2
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.7.9
ports:
- containerPort: 80
|
デプロイメントと Pod の作成#
1
| kubectl create -f nginx-deployment.yaml
|
詳細情報の取得
1
| kubectl describe deployment nginx-deployment
|
Pod がどのノードで稼働しているか確認
1
2
3
| $ kubectl get pod nginx-deployment-7fc9b7bd96-c6wwh -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE
nginx-deployment-7fc9b7bd96-c6wwh 1/1 Running 0 21h 10.1.33.6 juju-cfb27c-2 <none>
|
イメージバージョンのロールアウト#
イメージバージョンを1.8に変更するには、以下のコマンドを実行
1
| kubectl set image deployment nginx-deployment nginx=nginx:1.8
|
または、yaml のイメージバージョンを1.8に書き換えて apply
1
| kubectl apply -f nginx-deployment.yaml
|
ロールアウトの状態確認
1
| kubectl rollout status deployment nginx-deployment
|
前回のロールアウトを元に戻す
1
| kubectl rollout undo deployment nginx-deployment
|
履歴の表示
1
| kubectl rollout history deployment nginx-deployment
|
特定のリビジョンに戻す
1
| kubectl rollout history deployment nginx-deployment --revision=x
|
コンテナ環境変数の設定#
環境変数を出力する Pod のデプロイ例
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
| apiVersion: v1
kind: Pod
metadata:
name: env-dump
spec:
containers:
- name: busybox
image: busybox
command:
- env
env:
- name: STUDENT_NAME
value: "Your Name"
- name: SCHOOL
value: "Linux Academy"
- name: KUBERNETES
value: "is awesome"
|
Pod 実行後、ログで環境変数を確認
1
2
3
4
5
6
| $ kubectl logs env-dump
....
STUDENT_NAME=Your Name
SCHOOL=Linux Academy
KUBERNETES=is awesome
....
|
Pod のスケーリング#
コマンドライン#
–replicas=X でデプロイメントをスケール
1
2
3
4
5
6
7
8
9
10
11
12
13
14
| $ kubectl get deployment
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE
nginx-deployment 2 2 2 2 21h
$ kubectl scale deployment nginx-deployment --replicas=3
deployment.extensions/nginx-deployment scaled
$ kubectl get deployment
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE
nginx-deployment 3 3 3 3 21h
$ kubectl get pod
NAME READY STATUS RESTARTS AGE
...
nginx-deployment-7fc9b7bd96-c6wwh 1/1 Running 0 21h
nginx-deployment-7fc9b7bd96-kddj5 1/1 Running 0 31s
nginx-deployment-7fc9b7bd96-s86gc 1/1 Running 0 21h
|
yaml ファイル#
yaml の replicas: x
を変更し、apply
1
| kubectl apply -f nginx-deployment.yml
|
Replication Controller, ReplicaSet, Deployment#
Deployment は古い ReplicationController の機能を置き換えましたが、知っておいて損はありません。
ReplicationController は、指定した数の Pod レプリカが常に稼働していることを保証します。
nginx コンテナを3つ維持する例:
Replication Controller#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| apiVersion: v1
kind: ReplicationController
metadata:
name: nginx
spec:
replicas: 3
selector:
app: nginx
template:
metadata:
name: nginx
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx
ports:
- containerPort: 80
|
ReplicaSet#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| apiVersion: apps/v1beta2
kind: ReplicaSet
metadata:
name: nginx
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx
ports:
- containerPort: 80
|
Deployment#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| apiVersion: apps/v1beta2 # 1.8.0以前は apps/v1beta1
kind: Deployment
metadata:
name: nginx-deployment
labels:
app: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx
ports:
- containerPort: 80
|
ラベル#
ノードに色ラベルを付与
1
2
3
4
| kubectl label node node1-name color=black
kubectl label node node2-name color=red
kubectl label node node3-name color=green
kubectl label node node4-name color=blue
|
default namespace の全 Pod にラベル付与
1
| kubectl label pods -n default color=white --all
|
特定ラベルの Pod/ノード取得
1
| kubectl get pods -l color=white -n default
|
複数ラベルで取得
1
| kubectl get pods -l color=white,app=nginx
|
DaemonSet#
全ノードに nginx Pod をデプロイ
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| apiVersion: apps/v1
kind: DaemonSet
metadata:
name: cthulu
labels:
daemon: "yup"
spec:
selector:
matchLabels:
daemon: "pod"
template:
metadata:
labels:
daemon: pod
spec:
tolerations:
- key: node-role.kubernetes.io/master
effect: NoSchedule
containers:
- name: cthulu-jr
image: nginx
|
各ノードで Pod が稼働しているか確認
1
2
3
4
5
| $ kubectl get pod -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE
cthulu-kvbk9 1/1 Running 0 2m 10.1.33.8 juju-cfb27c-2 <none>
cthulu-t7hfc 1/1 Running 0 2m 10.1.45.13 juju-cfb27c-1 <none>
cthulu-x8hdf 1/1 Running 0 2m 10.1.31.9 juju-cfb27c-3 <none>
|
ノードにラベルを付けて Pod をスケジューリング#
ノードにラベルを付与
1
| kubectl label node juju-cfb27c-3 deploy=here
|
yaml の nodeSelector
で特定ノードに Pod を配置
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| apiVersion: v1
kind: Pod
metadata:
name: busybox
namespace: default
spec:
containers:
- name: busybox
image: busybox
command:
- sleep
- "300"
imagePullPolicy: IfNotPresent
restartPolicy: Always
nodeSelector:
deploy: here
|
確認
1
2
3
| $ kubectl get pod busybox -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE
busybox 1/1 Running 0 10s 10.1.31.10 juju-cfb27c-3 <none>
|
特定スケジューラー#
通常は spec で schedulerName を指定しませんが、カスタムスケジューラーを使いたい場合は指定します。
1
2
3
4
5
6
7
8
9
10
11
12
13
| apiVersion: v1
kind: Pod
metadata:
name: annotation-default-scheduler
labels:
name: multischeduler
annotations:
scheduledBy: custom-scheduler
spec:
schedulerName: custom-scheduler
containers:
- name: pod-container
image: k8s.gcr.io/pause:2.0
|
Pod の現在のログを表示
インタラクティブにログを表示
1
| kubectl logs pod-name -f
|
最後の10行だけ表示
1
| kubectl logs pod-name --tail=10
|
マスター/ノードのログファイルは /var/log/containers
にあります。
ノードメンテナンス#
ノードをメンテナンスするには、スケジューラーが新しい Pod を配置しないようにし、既存の Pod を退避させます(DaemonSet は除外)。
例:juju-cfb27c-2 をクラスターから外す
1
2
3
| root@juju-cfb27c-0:~# kubectl drain juju-cfb27c-2 --ignore-daemonsets
node/juju-cfb27c-2 cordoned
WARNING: Ignoring DaemonSet-managed pods: cthulu-kvbk9, nginx-ingress-kubernetes-worker-controller-t6qh9
|
juju-cfb27c-2 は “SchedulingDisabled” になります
1
2
3
4
5
| $ kubectl get node
NAME STATUS ROLES AGE VERSION
juju-cfb27c-1 Ready <none> 4d v1.11.2
juju-cfb27c-2 Ready,SchedulingDisabled <none> 4d v1.11.2
juju-cfb27c-3 Ready <none> 4d v1.11.2
|
この状態で -2 ノードをシャットダウンしてメンテナンスできます。新しい Pod は他のノードにのみ配置されます。
メンテナンス後、ノードを復帰させるには
1
2
3
4
5
6
7
| $ kubectl uncordon juju-cfb27c-2
node/juju-cfb27c-2 uncordoned
$ kubectl get node
NAME STATUS ROLES AGE VERSION
juju-cfb27c-1 Ready <none> 4d v1.11.2
juju-cfb27c-2 Ready <none> 4d v1.11.2
juju-cfb27c-3 Ready <none> 4d v1.11.2
|
Kubernetes コンポーネントのアップグレード#
現在のバージョン確認
- master ノードで kubeadm をアップグレード
1
| sudo apt upgrade kubeadm
|
kubeadm のバージョン確認
- アップグレードプランの確認
1
| sudo kubeadm upgrade plan
|
- アップグレードプランの適用
1
| sudo kubeadm upgrade apply v1.x.x
|
- kubelet のアップグレード
アップグレード前に、対象ノードを drain
1
| kubectl drain NODENAME --ignore-daemonsets
|
kubelet を手動でアップデート
1
2
| sudo apt update
sudo apt upgrade kubelet
|
アップグレード後、ノードを復帰させるのを忘れずに
1
| kubectl uncordon NODENAME
|
ネットワーク#
インバウンド Node Port 要件#
- マスターノード
- TCP 6443 – Kubernetes API Server
- TCP 2379-2380 – etcd server client API
- TCP 10250 – Kubelet API
- TCP 10251 – Kube-scheduler
- TCP 10252 – kube-controller-manager
- TCP 10255 – Read-only Kubelet API
- ワーカーノード
- TCP 10250 – Kubelet API
- TCP 10255 – Read-only Kubelet API
- TCP 30000-32767 – Node Port Services
Pod をインターネットに公開#
1
| kubectl expost deployment NAME --type="NodePort" --port XX
|
ロードバランサーのデプロイ#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
| Kind:Service
apiVersion: v1
metadata:
name: la-lb-service
spec:
selector:
app: la-lb
ports:
- protocol: TCP
port: 80
targetPort:9376
clusterIP: 10.0.171.223
loadBalancerIP: 78.12.23.17
type: LoadBalancer
|