はじめに
記念すべき初投稿です。個人的な興味でkubernetes(Minikube)をさわり始めました。
kubernetesの知識が少ないため、はまりっぱなしで、はまったところを備忘録として残していきたいと思います。
今回のはまりどころ
- minikubeを実行しているサーバ以外からアクセスする場合はiptablesでポリシー設定が必要
検証環境
- Minikube実行サーバ
- Ubuntu 24.04
- minikube version: v1.36.0 (kubernetes version: v1.33.1)
- IPアドレス:192.168.11.20
- アクセス端末
- IPアドレス:192.168.11.50
NGINX Ingress Controllerの準備
公式のドキュメントを参考にingressコントローラーを有効化する
まずは有効化
$ minikube start
$ minikube addons enable ingress
Hello Worldアプリは以下の内容でdeployment,service,ingressを定義してデプロイします
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: hello-deployment
spec:
replicas: 1
selector:
matchLabels:
app: hello
template:
metadata:
labels:
app: hello
spec:
containers:
- name: hello-world
image: "gcr.io/google-samples/hello-app:1.0"
ports:
- containerPort: 8080
---
apiVersion: v1
kind: Service
metadata:
name: sample-web
spec:
# typeは公式ではNodePortになっているが、ClusterIP(default)でも問題ない
selector:
app: hello # deploymentのlabelと名前を合わせる
ports:
- protocol: TCP
port: 80
targetPort: 8080
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: sample-ingress
spec:
ingressClassName: nginx
rules:
- host: hello-world.info
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: sample-web
port:
number: 80
内容を反映する
$ kubectl apply -f sample.yaml
$ kubectl get deployment,pod,svc,ingress
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/hello-deployment 1/1 1 1 25h
NAME READY STATUS RESTARTS AGE
pod/hello-deployment-545875f79c-v8wzp 1/1 Running 0 25h
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 28h
service/sample-web ClusterIP 10.102.172.70 <none> 80/TCP 25h
NAME CLASS HOSTS ADDRESS PORTS AGE
ingress.networking.k8s.io/sample-ingress nginx hello-world.info 192.168.49.2 80 27h
minikube ipを確認します。作成したingressのADDRESSに出てくるIPアドレスと同じものが表示されそうです。
$ minikube ip
192.168.49.2
Minikube実行サーバで、表示されたIPを/etc/hostsに記載し、curlでingressを経由してPodにアクセスし、Podアクセスが正常にできることを確認します。
$ echo $(minikube ip) hello-world.info | sudo tee -a /etc/hosts
192.168.49.2 hello-world.info
$ curl http://hello-world.info
Hello, world!
Version: 1.0.0
Hostname: hello-deployment-545875f79c-v8wzp
アクセス端末からのクラスタアクセス確認
まず、アクセス端末に192.168.49.2へのルートがMinikubeサーバに向くようにルートを追加します。反映させるネットマスクや恒久的に反映させる場合は環境に合わせていい感じに調整してください。
Minikubeサーバと同様にアクセス端末のhostsにも名前解決を追加し、curlでアクセスしますが、疎通がうまくいかずタイムアウトします。
$ sudo ip route add 192.168.49.0/24 via 192.168.11.20
$ echo $(minikube ip) hello-world.info | sudo tee -a /etc/hosts
192.168.49.2 hello-world.info
$ curl http://hello-world.info
※ここで応答なし
原因調査
Minikube実行サーバやアクセス端末でpingやtracerouteを実行し、アクセス端末から192.168.49.1(Minikube実行サーバ)までは疎通確認できるものの、minikube ip(192.168.49.2)には到達できない。Minikube実行サーバ上から192.168.49.2に到達できるため、iptablesのFORWARDチェインでDROPされているんじゃないかという仮説を立てました。(ここにたどり着く前の試行錯誤も長かったんですが、、、)
FORWARDチェインの一番最初にminikube ip(192.168.49.2)へのアクセス許可を追加し、無事にアクセス端末からPodにアクセスできることを確認しました。
$ sudo iptables -I FORWARD -s 192.168.11.0/24 -d 192.168.49.2 -j ACCEPT
$ sudo iptables -nL FORWARD
Chain FORWARD (policy ACCEPT)
target prot opt source destination
ACCEPT 0 -- 192.168.11.0/24 192.168.49.2 ★これが追加されている
DOCKER-USER 0 -- 0.0.0.0/0 0.0.0.0/0
DOCKER-FORWARD 0 -- 0.0.0.0/0 0.0.0.0/0
LIBVIRT_FWX 0 -- 0.0.0.0/0 0.0.0.0/0
LIBVIRT_FWI 0 -- 0.0.0.0/0 0.0.0.0/0
LIBVIRT_FWO 0 -- 0.0.0.0/0 0.0.0.0/0
まとめ
- Minikube実行サーバ外からNGINX Ingress Controllerにアクセスする場合はFORWARDチェインのポリシーに許可設定を追加する
- このあたりは、Ingressの設定もしくはIngress Controllerのvalues等でうまく反映できないものだろうか。
- 追加するポリシーは短絡的に入れずに、もっと適切なものを入れるように考慮した方がいい可能性も非常に高い
- もちろんNW的な考慮として、minikube ip(192.168.49.2)へのルーティング設定の考慮は必要
- 別途、恒久的に反映させる設定は必要