Opensourcetechブログ

OpensourcetechによるNGINX/Kubernetes/Zabbix/Neo4j/Linuxなどオープンソース技術に関するブログです。

NGINX Ingress Controller + Ingressによるサービス公開(kubernetes v1.26)


LinuCエヴァンジェリストの鯨井貴博@opensourcetechです。


はじめに
今回は、こちらの記事で作成したkubernetesクラスター v1.26.00で、
NGINX Ingress ControllerとIngressを使って外部クライアントへのサービス公開をやってみます。
なお、サービス公開はIPv4のみ(Single Stack)とIPv4&IPv6(Dual Stack)で行います。


Ingressとは
Ingressとは、クラスター内のServiceに対する外部からのアクセス(主にHTTP)を管理するAPIオブジェクトです。

https://kubernetes.io/ja/docs/concepts/services-networking/ingress/


Ingress Controllerとは
その名の通り、Ingressを制御する機能です。
https://kubernetes.io/ja/docs/concepts/services-networking/ingress-controllers/

様々なIngress Controllerがありますが、
今回はその中からNGINX Ingress Controllerを使います。



前提条件
Ingressに公開用のIPアドレスを付与してくれるロードバランサが必要となるので、
MetalLBなどで予め用意します。
※MetalLBの用意は、MetalLBとService(type:LoadBalancer)による外部クライアントへのサービス公開(kubernetes v1.26.00 on ubuntu22.04)を参照ください。


NGINX Ingress Controllerのインストール
インストール方法は、こちらを参照しました。

kubeuser@master01:~$ kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.6.4/deploy/static/provider/cloud/deploy.yaml
namespace/ingress-nginx created
serviceaccount/ingress-nginx created
serviceaccount/ingress-nginx-admission created
role.rbac.authorization.k8s.io/ingress-nginx created
role.rbac.authorization.k8s.io/ingress-nginx-admission created
clusterrole.rbac.authorization.k8s.io/ingress-nginx created
clusterrole.rbac.authorization.k8s.io/ingress-nginx-admission created
rolebinding.rbac.authorization.k8s.io/ingress-nginx created
rolebinding.rbac.authorization.k8s.io/ingress-nginx-admission created
clusterrolebinding.rbac.authorization.k8s.io/ingress-nginx created
clusterrolebinding.rbac.authorization.k8s.io/ingress-nginx-admission created
configmap/ingress-nginx-controller created
service/ingress-nginx-controller created
service/ingress-nginx-controller-admission created
deployment.apps/ingress-nginx-controller created
job.batch/ingress-nginx-admission-create created
job.batch/ingress-nginx-admission-patch created
ingressclass.networking.k8s.io/nginx created
validatingwebhookconfiguration.admissionregistration.k8s.io/ingress-nginx-admission created


インストール完了。

kubeuser@master01:~$ kubectl get pods --namespace=ingress-nginx 
NAME                                       READY   STATUS      RESTARTS   AGE
ingress-nginx-admission-create-cpvv2       0/1     Completed   0          88s
ingress-nginx-admission-patch-d8r6t        0/1     Completed   2          88s
ingress-nginx-controller-c69664497-5bgqv   1/1     Running     0          88s


なお、上記手順でNGINX Ingress Controllerをインストールした場合は、
IPv4 Single Stackとなります(デフォルト設定)。
そのためDual Stackにする場合、deploy.yamlを一部修正する必要があります。

kubeuser@master01:~$ wget https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.6.4/deploy/static/provider/cloud/deploy.yaml
--2023-03-16 23:42:14--  https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.6.4/deploy/static/provider/cloud/deploy.yaml
Resolving raw.githubusercontent.com (raw.githubusercontent.com)... 2606:50c0:8003::154, 2606:50c0:8000::154, 2606:50c0:8001::154, ...
Connecting to raw.githubusercontent.com (raw.githubusercontent.com)|2606:50c0:8003::154|:443... connected.
HTTP request sent, awaiting response... 200 OK
Length: 15574 (15K) [text/plain]
Saving to: ‘deploy.yaml’

deploy.yaml                           100%[=========================================================================>]  15.21K  --.-KB/s    in 0.001s  

2023-03-16 23:42:15 (19.9 MB/s) - ‘deploy.yaml’ saved [15574/15574]

kubeuser@master01:~$ cp -p deploy.yaml deploy_original.yaml 
kubeuser@master01:~$ vi deploy.yaml 
kubeuser@master01:~$ diff deploy.yaml deploy_original.yaml 
350,351c350
<   - IPv6
<   ipFamilyPolicy: PreferDualStack
---
>   ipFamilyPolicy: SingleStack


変更箇所。

   348    ipFamilies:
   349    - IPv4
   350    ipFamilyPolicy: SingleStack



Ingressの作成
公開対象となるサービス(Service)は、以下となります。

kubeuser@master01:~$ kubectl create deployment nginx --image=nginx:1.23.0 --replicas=3
deployment.apps/nginx created

kubeuser@master01:~$ kubectl get deployments,replicasets,pods
NAME                    READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/nginx   3/3     3            3           68s

NAME                               DESIRED   CURRENT   READY   AGE
replicaset.apps/nginx-56b47c4dcc   3         3         3       68s

NAME                         READY   STATUS    RESTARTS   AGE
pod/nginx-56b47c4dcc-q46s5   1/1     Running   0          67s
pod/nginx-56b47c4dcc-qdrrm   1/1     Running   0          67s
pod/nginx-56b47c4dcc-xbjrp   1/1     Running   0          67s

kubeuser@master01:~$ kubectl expose deployments nginx --port=80

kubeuser@master01:~$ kubectl get svc nginx
NAME    TYPE        CLUSTER-IP    EXTERNAL-IP   PORT(S)   AGE
nginx   ClusterIP   10.1.62.254   <none>        80/TCP    18h


Ingressのyamlを作成します。
"http://公開されるIPアドレス:PORT番号/red"で外部クライアントからアクセスできるようになります。

kubeuser@master01:~$ vi ingress.yaml

kubeuser@master01:~$ cat ingress.yaml 
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nginx-localhost
  namespace: default
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  ingressClassName: nginx
  rules:
  - http:
      paths:
      - backend:
          service:
            name: nginx
            port:
              number: 80
        path: /red
        pathType: Prefix


Ingressをデプロイします。
なお、ロードバランサ(MetalLB)からアドレスが付与されるのに1分程度かかるので、少し待つ必要があります。

kubeuser@master01:~$ kubectl apply -f ingress.yaml
ingress.networking.k8s.io/nginx-localhost created

kubeuser@master01:~$ kubectl get ingress 
NAME              CLASS   HOSTS   ADDRESS        PORTS   AGE
nginx-localhost   nginx   *       192.168.1.50   80      18s


Dual Stack構成のNGINX Ingress Controllerにした場合は、
以下のようにIPv6のアドレスも付与されます。

kubeuser@master01:~$ kubectl get ingress
NAME              CLASS   HOSTS   ADDRESS                            PORTS   AGE
nginx-localhost   nginx   *       192.168.1.50,240f:32:57b8:1::1:0   80      18h



外部クライアントからのアクセス
"http://Ingressに付与されたIPアドレス/red"でアクセスします。

アクセス成功です!


おわりに
やってることはシンプルなのですが、
Ingressを使う上では以下の点に気を付ける必要があると思いました。
・いずれかのIngress Controllerのインストールが必要
・IPアドレスを付与してくれるロードバランサ(今回だとMetalLB)を用意が必要
・Dual StackのIngressを使いたい場合、Ingress Controllerの設定変更が必要

今回はIngressでService一つを公開しましたが、
ingressのyamlに複数Service用の設定を記載することで
/redというパスの場合はService1、
/blueというパスの場合はService2というように出来ます。

kubeuser@master01:~$ cat ingress.yaml 
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nginx-localhost
  namespace: default
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  ingressClassName: nginx
  rules:
  - http:
      paths:
      - backend:
          service:
            name: service1
            port:
              number: 80
        path: /red
        pathType: Prefix
  - http:
      paths:
      - backend:
          service:
            name: servicre2
            port:
              number: 80
        path: /blue
        pathType: Prefix

Opensourcetech by Takahiro Kujirai