概要
次回記事で各Podの処理内容や進捗状況を管理するため全ノードにetcdサーバーを配置しました。
Kubernetesの全ノード上でetcdサーバーを動かすサンプルです。
KubernetesのDaemon setを利用し各ノード上で1ポッド動かします。
なお、Kubernetesの構築(記事はこちら)が完了していることが前提となります。
Daemon setについて
Kubernetesの全ノード上で同じPodを動かすことができます。
その為ノードのポートをバインドしてサービスを動かしたりhostPathをマウントして利用するのもやりやすいと思います。
各ノード上でモニタリングツールを動かしたりログ収集ツールを動かすなどが公式の例として上がっています。
動作環境
Kubernetesの構築が完了している状態とほとんど同じです。
なお、今回は複数ノードで動かすため2ノード動かします。
masterサーバー | nodeサーバー1 | nodeサーバー2 | |
---|---|---|---|
ホスト名 | master | node1 | node2 |
IPアドレス | 192.168.137.20 | 192.168.137.21 | 192.168.137.22 |
動作しているサービス | etcd kube-apiserver kube-controller-manager kube-scheduler |
kubelet kube-proxy |
kubelet kube-proxy |
構成
今回はディスカバリー用のetcdとしてmasterサーバーで動いているetcdを利用しました。
Deamonsetを利用して各ノード上で立ち上がるetcdポッドは最初にディスカバリー用のetcdに問い合わせを行いクラスターを構築します。
各Podはetcdのデータを保存するためノード上の/data/etcdフォルダーをマウントします。
また、各ノードの2379/2380番ポートをPodの2379/2380番ポートをバインドします。
これにより各ノードの2379/2380番ポートにアクセスすることでetcdサーバーに接続できます。
ディスカバリーサーバーの準備
ここからはmasterサーバーのetcdがhttp://192.168.137.20:2379 で動いているとし、ディスカバリー用に/discovery/test以下を利用するとします。
まず、クラスターのサイズを登録します。
指定数のetcdが接続しないと起動しないのでノード数と同じ値にします。(適当な値にしてしまい動かないというトラブルが起きました。)
クラスターのサイズはディスカバリー用のパス/_config/sizeに登録します。
etcdctl --endpoints http://192.168.137.20:2379 set /discovery/test/_config/size 2
サンプルコード
Dockerfile及び起動用のスクリプトはGithub( https://github.com/mmitti/kube-etcd )にあります。
podのipアドレスを求めるためpythonのスクリプト経由でetcdを動かしています。
Deamonsetの環境変数として以下2つを指定してください。
DISCOVERY:etcdのディスカバリーのアドレス 例http://192.168.137.20:2379/v2/keys/discovery/test
DATADIR:etcdのデータの保存先 hostPathをマウントするパスと同じにしてください。
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
labels:
name: etcd
name: etcd
spec:
template:
metadata:
labels:
app: etcd
spec:
containers:
- name: etcd
image: mmitti/etcd
imagePullPolicy: Always
ports:
- containerPort: 2379
hostPort: 2379
name: p1
- containerPort: 2380
hostPort: 2380
name: p2
env:
- name: DISCOVERY
value: http://192.168.137.20:2379/v2/keys/discovery/test
- name: DATADIR
value: /data
volumeMounts:
- name: etcd-data
mountPath: /data
volumes:
- name: etcd-data
hostPath:
path: /data/etcd
---
apiVersion: v1
kind: Service
metadata:
name: etcd
labels:
app: etcd
spec:
ports:
- port: 2379
name: p1
- port: 2380
name: p2
clusterIP: None
selector:
app: etcd
こちらのyamlをKubernetesに登録します。
$ kubectl create -f etcd.yaml
動作確認
Podが起動しているか確認します。
$ kubectl get po -l app=etcd
NAME READY STATUS RESTARTS AGE
etcd-9w1sw 1/1 Running 1 21h
etcd-zrn62 1/1 Running 1 21h
また、各Podが動いているノードを確認します。
$ kubectl describe po -l app=etcd
Name: etcd-9w1sw
Namespace: default
Node: node1/192.168.137.21
--省略--
Name: etcd-zrn62
Namespace: default
Node: node2/192.168.137.22
--省略--
最後にetcdサーバーに値を書き込んで読み出してみます。
$ etcdctl --endpoints http://192.168.137.21:2379 set /hoge testtest
testtest
$ etcdctl --endpoints http://192.168.137.21:2379 get /hoge
testtest
$ etcdctl --endpoints http://192.168.137.22:2379 get /hoge
testtest
書き込んだ値を読み出せれば成功です。
追記
ノード再起動後PodのIPアドレスが変わる恐れがあり通信できなくなる場合があります。
ディスカバリーに登録するIPアドレスはポッドのものでなくノードのもののほうが良さそうです。