Kubernetes をいじって Hardware LoadBalancer で "type LoadBalancer" を実現してみた...
-
Upload
masaya-aoyama -
Category
Engineering
-
view
1.388 -
download
0
Transcript of Kubernetes をいじって Hardware LoadBalancer で "type LoadBalancer" を実現してみた...
Hardware LoadBalancer で“type LoadBalancer”を
使ってみた
青山 真也 (Masaya Aoyama)
普段の主な仕事↓
← 結果待ち
adtech studio のプライベートクラウド環境
・OpenStack をベースとしたプライベートクラウド環境
・Network のレイテンシが許容されないアドテクシステム
そんな弊社にも
GKE ライクなコンテナ基盤がございます。
AKE (Adtech Container Engine)
This is a slide title
AKE の中でも、
LoadBalancer 周りの話をします。
AKE 1.0 の構成 (NodePort + Metal LB)
eth0: 10.0.0.1:34567
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External
apiVersion: v1kind: Servicemetadata: name: svc1spec: type: NodePort ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
52.0.0.1:80 > 10.0.0.1:34567 > 10.0.0.2:34567(cli で登録が必要)
eth0: 10.0.0.2:34567
AKE 1.0 の構成 (NodePort + Metal LB + (HAProxy))
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer(+ HAProxy)
External
52.0.0.1:80 > 10.0.0.1:34567 > 10.0.0.2:34567(cli で登録が必要)
apiVersion: v1kind: Servicemetadata: name: svc1spec: type: NodePort ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
eth0: 10.0.0.1:34567 eth0: 10.0.0.2:34567
SNAT, NAPT ができない場合
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External仮に Service が増えたことを考えると、こんな感じになります
52.0.0.1:80 > VM α:80 > VM β:8052.0.0.2:80 > VM α:80 > VM β:80
lo.0: 52.0.0.1:80lo.1: 52.0.0.2:80
lo.0: 52.0.0.1:80lo.1: 52.0.0.2:80
SNAT, NAPT ができない場合
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External
52.0.0.1:80 > VM α:80 > VM β:8052.0.0.2:80 > VM α:80 > VM β:80
NodePort は Interface 全てでBind されてしまうため利用出来ない
例: *:80
apiVersion: v1kind: Servicemetadata: name: svc2spec: type: NodePort ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
apiVersion: v1kind: Servicemetadata: name: svc1spec: type: NodePort ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
lo.0: 52.0.0.1:80lo.1: 52.0.0.2:80
lo.0: 52.0.0.1:80lo.1: 52.0.0.2:80
SNAT, NAPT ができない場合
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External
externalIPs 使えばいけないことも無いが…
利便性が著しく低い
…metadata: name: svc1spec: externalIPs: - 52.0.0.1 ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
52.0.0.1:80 > VM α:80 > VM β:8052.0.0.2:80 > VM α:80 > VM β:80
…metadata: name: svc2spec: externalIPs: - 52.0.0.2 ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
lo.0: 52.0.0.1:80lo.1: 52.0.0.2:80
lo.0: 52.0.0.1:80lo.1: 52.0.0.2:80
おいでおいで〜
…
This is a slide title① SNAT, NAPT が必須な構成
ボトルネック or リソースが必要
② 外部のコマンドでやってもらうの不便
やっぱりGKE がいいって言われる
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External
52.0.0.1:80 > VM α:80 > VM β:8052.0.0.2:80 > VM α:80 > VM β:80
apiVersion: v1kind: Servicemetadata: name: svc2spec: type: ClusterIP ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
apiVersion: v1kind: Servicemetadata: name: svc1spec: type: ClusterIP ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
AKE 2.0 の構成 (NodePort + Metal LB)
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External
52.0.0.1:80 > VM α:80 > VM β:8052.0.0.2:80 > VM α:80 > VM β:80
apiVersion: v1kind: Servicemetadata: name: svc2spec: type: ClusterIP ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
apiVersion: v1kind: Servicemetadata: name: svc1spec: type: ClusterIP ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
AKE 2.0 の構成 (NodePort + Metal LB)
自前で動的に iptables を書き換えて頑張る(listen しない、ClusterIP を利用)
52.0.0.1:80 宛にきたパケットを該当 Service の KUBE-SVC-* に転送
This is a slide title① SNAT, NAPT が必須な構成
ボトルネック or リソースが必要
② 外部のコマンドでやってもらうの不便
やっぱりGKE がいいって言われる
This is a slide title
① 外部 LoadBalancer の操作
② IP 払い出しの自動化
③ K8s Node の iptables 操作
This is a slide titleやっぱ諦められないよ
type LoadBalancer
type LoadBalancer のつくりかた
CloudProvider を自作しましょう。● LoadBalancer (今回はここの話 )● Routing● Host● Zone● BlockDevice
(参考)
インターフェースの一覧: pkg/cloudprovider/cloud.goOpenStack の場合、pkg/cloudprovider/providers/openstack/* 辺り
LoadBalancer 用の InterfaceGetLoadBalancer(clusterName string, service *v1.Service) ・あまり変える部分はない
EnsureLoadBalancer(clusterName string, service *v1.Service, nodes []*v1.Node) ・LoadBalancer を作成する、IP の指定がない場合は自動アサイン
UpdateLoadBalancer(clusterName string, service *v1.Service, nodes []*v1.Node) ・LoadBalancer を更新する
EnsureLoadBalancerDeleted(clusterName string, service *v1.Service) ・LoadBalancer を削除する
大まかには上記 3 種類の Interface を実装してあげる形
渡ってくる構造体に必要な情報は大体揃っている
service.Nameservice.Spec.LoadBalancerIPservice.Spec.Ports[].Portservice.Spec.Ports[].TargetPort
nodes.[].Name
This is a slide title
この 4 つの関数を作ると
VM αKubernets node
Internal
VM βKubernets node
52.0.0.1:80
LoadBalancer
External
52.0.0.1:80 > VM α:80 > VM β:8052.0.0.2:80 > VM α:80 > VM β:80
apiVersion: v1kind: Servicemetadata: name: svc2spec: type: LoadBalancer ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
apiVersion: v1kind: Servicemetadata: name: svc1spec: type: LoadBalancer ports: - name: "http-port" protocol: "TCP" port: 80 targetPort: 80
AKE 3.0 の構成 (LoadBalancer + Metal LB)
GKE などと全く同じ type LoadBalancer
今後オンプレにより求められるのは、パブリッククラウドとのシームレスな統合
コンテナ環境だとなおさら移行し易い
GKE > AKE & AKE > GKE
これでマルチクラウドでの展開も容易に