Kubernetes におけるカーネルパラメータ
Kubernetesにアプリをデプロイして、すべてがうまくいったら、あとはスケーリングするだけです。
スケールするにはどうすればいいのでしょうか?
簡単に思いつくのは、Podを追加することですね。
ところが、ポッドはすぐにカーネルの限界に達します。
例えば、net.core.somaxconn
や kernel.msgmni
というカーネルパラメーターです。
前者は、受け入れのためにキューに入れることができる接続の最大数を表します。
後者は、システム全体におけるメッセージキューの最大数です。
こういったあたいは、システムのスケールとともに、より大きな値を設定することで効率的になると思います。
少なくとも、接続数のためにリソースにゆとりがあるのに、新しいPodを作成する必要はないとおもいます。
root@x:/# sysctl -a | grep "net.core.somaxconn"
net.core.somaxconn = 128
net.core.somaxconnはこのようにデフォルトで非常に小さい値に設定されています。
通常の Linux VM で sysctl パラメータを更新するには、以下のコマンドを実行します。
root@x:/# sysctl -w net.core.somaxconn=10000
しかし、ポッドで試してみるとこんな感じになります。
root@x:/# sysctl -w net.core.somaxconn=10000
sysctl: setting key "net.core.somaxconn": Read-only file system
これで、標準的なVMとは状況が異なるということはわかったと思います。
Kubernetes側でのの対処法
sysctlに関しては、Node側の責任を追っているものであり、Podから変更することはできないのです。
つまり、sysctlの変更によって、Node上の他のPodに影響を与えてしまうので、危険なsysctlはkubeletによって、カーネルへ貫通しないような設計にKubernetes側でしているということです。
しかし、ハイパフォーマンスやリアルタイムアプリケーションのチューニングのような非常に特殊な状況では、特定の安全でないsysctlsを許可することができます。安全ではないsysctlsはノードごとにkubeletのフラグで有効になります。
kubelet --allowed-unsafe-sysctls \
'kernel.msg*,net.core.somaxconn' ...
このコマンドによって、Unsafeなsysctlを許可することができます。
あとは、initContainerにパラメータを設定させることで、パラメータを変更できます。
initContainers:
- name: init-sysctl
image: busybox
command:
- /bin/sh
- -c
- |
sysctl -w net.core.somaxconn=10000
sysctl -w net.ipv4.ip_local_port_range='1024 65535'
securityContext:
privileged: true
参考
https://kubernetes.io/docs/tasks/administer-cluster/sysctl-cluster/
http://bogdan-albei.blogspot.com/2017/09/kernel-tuning-in-kubernetes.html