例: クラスタ上のNginxイングレス・コントローラの設定
Kubernetes Engine (OKE)を使用して作成したクラスタでNginxイングレス・コントローラの例を設定および使用する方法を確認します。
Kubernetesエンジンで作成したクラスタに様々なオープン・ソース・イングレス・コントローラを設定して、Kubernetesアプリケーション・トラフィックを管理できます。
このトピックでは、Nginxイングレス・コントローラの例を、既存のクラスタ上の対応するアクセス制御とともに設定する方法について説明します。このトピックでは、イングレス・コントローラを設定した後、サンプルのhello-worldバックエンドでイングレス・コントローラを使用する方法と、イングレス・コントローラが期待どおりに動作していることを確認する方法について説明します。イングレス・コントローラの例を引き続き使用する場合は、アップグレード手順に従います。また、サンプル・イングレス・コントローラにこれ以上使用しない場合、このトピックではそれを削除する方法を示します。
サンプル・コンポーネント
例には、イングレス・コントローラおよびhello-worldバックエンドが含まれています。
イングレス・コントローラ・コンポーネント
イングレス・コントローラは次で構成されています:
ingress-nginx-controller
というイングレス・コントローラ・デプロイメント。このデプロイメントでは、イングレス・コントローラおよびNginxのバイナリを含むイメージがデプロイされます。バイナリは、イングレスがKubernetesで作成されるときに、/etc/nginx/nginx.conf
構成ファイルを操作およびリロードします。Nginxアップストリームは、指定されたセレクタと一致するサービスを指します。ingress-nginx-controller
というイングレス・コントローラ・サービス。このサービスでは、LoadBalancerタイプのサービスとしてイングレス・コントローラ・デプロイメントが公開されます。Kubernetes EngineはOracle Cloud Infrastructure統合/クラウド・プロバイダを使用するため、ロード・バランサはバックエンド・セットとして構成された正しいノードを使用して動的に作成されます。
バックエンド・コンポーネント
hello-worldバックエンドは次で構成されています:
docker-hello-world
というバックエンド・デプロイメント。このデプロイメントでは、ヘルス・チェックと404レスポンスのデフォルト・ルートが処理されます。これは、デフォルトのバックエンドに最低限必要なルートを提供する標準hello-worldイメージを使用して行われます。docker-hello-world-svc
というバックエンド・サービス。このサービスは、イングレス・コントローラ・デプロイメントによる消費のバックエンド・デプロイメントを公開します。
サンプルのイングレス・コントローラの設定
この項では、イングレスのアクセス・ルールを作成します。次に、サンプルのイングレス・コントローラ・コンポーネントを作成し、それらが実行されていることを確認します。
イングレス・コントローラのアクセス・ルールの作成
-
まだ実行していない場合は、ステップに従って、クラスタのkubeconfig構成ファイルを設定し、(必要に応じて)そのファイルを指すようにKUBECONFIG環境変数を設定します。自分のkubeconfigファイルを設定する必要があります。別のユーザーが設定したkubeconfigファイルを使用してクラスタにアクセスすることはできません。クラスタ・アクセスの設定を参照してください。
- Oracle Cloud Infrastructureユーザーがテナンシ管理者の場合は、次のステップをスキップして、イングレス・コントローラおよび関連リソースのデプロイに進みます。
-
Oracle Cloud Infrastructureユーザーがテナンシ管理者でない場合は、ターミナル・ウィンドウで、次のように入力して、クラスタでKubernetes RBAC cluster-admin clusterroleをユーザーに付与します:
kubectl create clusterrolebinding <my-cluster-admin-binding> --clusterrole=cluster-admin --user=<user-OCID>
ここでは:
<my-cluster-admin-binding>
は、ユーザーとKubernetes RBAC cluster-admin clusterrole間のバインディングの名前として使用される選択した文字列です。たとえば、jdoe_clst_adm
です<user-OCID>
は、ユーザーのOCIDです(コンソールから取得)。たとえば、ocid1.user.oc1..aaaaa...zutq
(読みやすさのために省略)です。
例:
kubectl create clusterrolebinding jdoe_clst_adm --clusterrole=cluster-admin --user=ocid1.user.oc1..aaaaa...zutq
イングレス・コントローラと関連リソースのデプロイ
イングレス・コントローラおよび関連リソース(Kubernetes RBACロールおよびバインディング、およびタイプLoadBalancerのingress-nginx-controller
イングレス・コントローラ・サービスを含む)をデプロイする方法は、管理対象/自己管理ノードを持つクラスタにデプロイするか、仮想ノードを持つクラスタにデプロイするかによって異なります:
-
管理対象ノードおよび自己管理ノード
Nginxイングレス・コントローラをデプロイするには、次のコマンドを実行します:
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v<vnum>/deploy/static/provider/cloud/deploy.yaml
<vnum>
は、ingress-nginx-controller
イングレス・コントローラ・デプロイメント・スクリプトの最新バージョンのバージョン番号です。たとえば、スクリプトの作成時には、最新バージョンのスクリプトのバージョン番号は1.1.3であるため、実行するコマンドは次のとおりです。kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.1.3/deploy/static/provider/cloud/deploy.yaml
最新バージョンのスクリプトのバージョン番号を確認するには、kubernetes/ingress-nginxのドキュメント(GitHub)を参照してください。
-
仮想ノード
仮想ノードでは、イングレス・コントローラのデプロイメント・マニフェストを変更し、
fsgroup
、allowprivilegeEscalation
およびcapabilities
セキュリティ・コンテキストをコメント・アウトする必要があります。このような変更されたデプロイメント・マニフェストの例は、https://github.com/oracle-devrel/oci-oke-virtual-nodes/tree/main/ingress-nginxを参照してください。この変更されたマニフェストに基づいてNginxイングレス・コントローラをデプロイするには、次のコマンドを実行します:
kubectl apply -f https://raw.githubusercontent.com/oracle-devrel/oci-oke-virtual-nodes/main/ingress-nginx/deploy.yaml
ingress-nginx-controller
イングレス・コントローラ・サービスがLoad Balancerサービスとして実行されていることの確認
-
次のように入力して、実行中のサービスのリストを表示します:
kubectl get svc -n ingress-nginx
前述のコマンドの出力に、実行中のサービスが表示されます:
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE ingress-nginx-controller LoadBalancer 10.96.229.38 <pending> 80:30756/TCP,443:30118/TCP 1h
ingress-nginx-controller
イングレス・コントローラ・サービスのEXTERNAL-IPは、ロード・バランサがOracle Cloud Infrastructureで完全に作成されるまで、<pending>
として表示されます。 -
ingress-nginx-controller
イングレス・コントローラ・サービスのEXTERNAL-IPが表示されるまで、kubectl get svc
コマンドを繰り返します:kubectl get svc -n ingress-nginx
前述の出力に、
ingress-nginx-controller
イングレス・コントローラ・サービスのEXTERNAL-IPが表示されます:NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE ingress-nginx-controller LoadBalancer 10.96.229.38 129.146.214.219 80:30756/TCP,443:30118/TCP 1h
TLSシークレットの作成
TLSシークレットは、イングレス・コントローラでのSSL終了に使用されます。
-
新しいキーをファイルに出力します。たとえば、次のように入力します:
openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout tls.key -out tls.crt -subj "/CN=nginxsvc/O=nginxsvc"
この例のシークレットを生成するには、自己署名証明書が使用されます。これはテストでは問題ありませんが、本番環境では、認証局によって署名された証明書を使用してください。
ノート
Windowsでは、"/CN=nginxsvc/O=nginxsvc"
を"//CN=nginxsvc\O=nginxsvc"
に置き換えることが必要な場合があります。たとえば、これはGit Bashシェルからopenssl
コマンドを実行する場合に必要です。 -
次のように入力してTLSシークレットを作成します:
kubectl create secret tls tls-secret --key tls.key --cert tls.crt
サンプルのバックエンドの設定
この項では、hello-worldバックエンド・サービスおよびデプロイメントを定義します。
docker-hello-worldサービス定義の作成
-
次のコードを含むファイル
hello-world-ingress.yaml
を作成します。このコードは、Docker Hubから公開されているhello-worldイメージを使用しています。同様の方法で実行できる、選択した別のイメージに置き換えることができます。apiVersion: apps/v1 kind: Deployment metadata: name: docker-hello-world labels: app: docker-hello-world spec: selector: matchLabels: app: docker-hello-world replicas: 3 template: metadata: labels: app: docker-hello-world spec: containers: - name: docker-hello-world image: scottsbaldwin/docker-hello-world:latest ports: - containerPort: 80 --- apiVersion: v1 kind: Service metadata: name: docker-hello-world-svc spec: selector: app: docker-hello-world ports: - port: 8088 targetPort: 80 type: ClusterIP
docker-hello-worldサービスのタイプはLoadBalancerではなくClusterIPです。このサービスは
ingress-nginx-controller
イングレス・コントローラ・サービスによってプロキシ設定されるためです。docker-hello-worldサービスは、直接パブリック・アクセスを必要としません。かわりに、パブリック・アクセスはロード・バランサからイングレス・コントローラに、イングレス・コントローラからアップストリーム・サービスにルーティングされます。 -
次のコマンドを実行して、クラスタ内のノードで新しいhello-worldデプロイメントおよびサービスを作成します:
kubectl create -f hello-world-ingress.yaml
サンプル・イングレス・コントローラを使用したサンプル・バックエンドへのアクセス
この項では、イングレス・コントローラを使用してバックエンドにアクセスするイングレスを作成します。
イングレス・リソースの作成
-
ファイル
ingress.yaml
を作成し、次のコードを移入します:apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: hello-world-ing annotations: kubernetes.io/ingress.class: "nginx" spec: tls: - secretName: tls-secret rules: - http: paths: - path: / pathType: Prefix backend: service: name: docker-hello-world-svc port: number: 8088
前述の例のYAMLは、Kubernetesバージョン1.19.x以降を実行しているクラスタで動作することに注意してください。
-
次のように入力して、リソースを作成します:
kubectl create -f ingress.yaml
サンプル・コンポーネントが期待どおりに動作していることの確認
この項では、すべてのサンプル・コンポーネントが正常に作成され、期待どおりに動作していることを確認します。docker-hello-world-svc
サービスはClusterIPサービスとして実行され、ingress-nginx-controller
サービスはLoadBalancerサービスとして実行される必要があります。イングレス・コントローラに送信されたリクエストは、クラスタ内のノードにルーティングされる必要があります。
ロード・バランサの外部IPアドレスの取得
ingress-nginx-controller
サービスがLoadBalancerサービスとして実行されていることを確認します:
kubectl get svc --all-namespaces
前述のコマンドの出力に、実行中のサービスが表示されます:
NAMESPACE NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
default docker-hello-world-svc ClusterIP 10.96.83.247 <none> 8088/TCP 16s
default kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 1h
ingress-nginx ingress-nginx-controller LoadBalancer 10.96.229.38 129.146.214.219 80:30756/TCP,443:30118/TCP 5m
kube-system kube-dns ClusterIP 10.96.5.5 <none> 53/UDP,53/TCP 1h
cURLリクエストのロード・バランサへの送信
-
ingress-nginx-controller
サービスの外部IPアドレス(たとえば、129.146.214.219)を使用して、httpリクエストのcurlを実行します:curl -I http://129.146.214.219
前述のコマンドの出力例:
HTTP/1.1 301 Moved Permanently Via: 1.1 10.68.69.10 (McAfee Web Gateway 7.6.2.10.0.23236) Date: Thu, 07 Sep 2017 15:20:16 GMT Server: nginx/1.13.2 Location: https://129.146.214.219/ Content-Type: text/html Content-Length: 185 Proxy-Connection: Keep-Alive Strict-Transport-Security: max-age=15724800; includeSubDomains;
出力には、httpトラフィックがhttpsにリダイレクトされていることを示す301リダイレクトとLocationヘッダーが表示されます。
-
https urlに対してcURLを実行するか、Locationヘッダーに自動的に従うように
-L
オプションを追加します。-k
オプションは、SSL証明書を検証しないようにcURLに指示します。たとえば、次のように入力します:curl -ikL http://129.146.214.219
前述のコマンドの出力例:
HTTP/1.1 301 Moved Permanently Via: 1.1 10.68.69.10 (McAfee Web Gateway 7.6.2.10.0.23236) Date: Thu, 07 Sep 2017 15:22:29 GMT Server: nginx/1.13.2 Location: https://129.146.214.219/ Content-Type: text/html Content-Length: 185 Proxy-Connection: Keep-Alive Strict-Transport-Security: max-age=15724800; includeSubDomains; HTTP/1.0 200 Connection established HTTP/1.1 200 OK Server: nginx/1.13.2 Date: Thu, 07 Sep 2017 15:22:30 GMT Content-Type: text/html Content-Length: 71 Connection: keep-alive Last-Modified: Thu, 07 Sep 2017 15:17:24 GMT ETag: "59b16304-47" Accept-Ranges: bytes Strict-Transport-Security: max-age=15724800; includeSubDomains; <h1>Hello webhook world from: docker-hello-world-1732906117-0ztkm</h1>
出力の最後の行には、ホスト名が
docker-hello-world-1732906117-0ztkm
のポッドから返されるHTMLが表示されます。 -
cURLリクエストを複数回発行して、HTML出力の変更にホスト名を表示し、ロード・バランシングが発生していることを示します:
$ curl -k https://129.146.214.219 <h1>Hello webhook world from: docker-hello-world-1732906117-6115l</h1> $ curl -k https://129.146.214.219 <h1>Hello webhook world from: docker-hello-world-1732906117-7r89v</h1> $ curl -k https://129.146.214.219 <h1>Hello webhook world from: docker-hello-world-1732906117-0ztkm</h1>
nginx.confの調査
ingress-nginx-controller
イングレス・コントローラ・デプロイメントにより、実行中のポッドでnginx.conf
ファイルが操作されます。
-
次を入力して、
ingress-nginx-controller
イングレス・コントローラ・デプロイメントを実行しているポッドの名前を見つけます:kubectl get po -n ingress-nginx
前述の出力に、
ingress-nginx-controller
イングレス・コントローラ・デプロイメントを実行しているポッドの名前が表示されます:NAME READY STATUS RESTARTS AGE ingress-nginx-controller-110676328-h86xg 1/1 Running 0 1h
-
次の
kubectl exec
コマンドを入力して、ingress-nginx-controller
イングレス・コントローラ・デプロイメントを実行しているポッドの名前を使用し、nginx.conf
の内容を表示します:kubectl exec -n ingress-nginx -it ingress-nginx-controller-110676328-h86xg -- cat /etc/nginx/nginx.conf
-
出力で
proxy_pass
を探します。デフォルトのバックエンド用と、次に示すような別のものがあります:proxy_pass http://upstream_balancer;
これは、Nginxが
upstream_balancer
というアップストリームへのリクエストをプロキシ設定していることを示しています。 -
出力でアップストリーム定義を見つけます。次のように表示されます:
upstream upstream_balancer { server 0.0.0.1:1234; # placeholder balancer_by_lua_block { tcp_udp_balancer.balance() } }
アップストリームはLuaを介してプロキシ設定しています。
(オプション)サンプル・イングレス・コントローラのアップグレード
このオプション・セクションでは、Kubernetesアプリケーション・トラフィック管理用のサンプル・イングレス・コントローラを使用して、すぐに削除するのではなく、継続する方法を説明します。
必要に応じて、前に作成したサンプル・イングレス・コントローラを引き続き使用できます。ただし、新しいバージョンのNginxは定期的にリリースされることに注意してください。したがって、サンプル・イングレス・コントローラを引き続き使用する場合は、イングレス・コントローラが使用するNginxのバージョンを定期的にアップグレードする必要があります。通常、Nginxのアップグレード時にイングレス・コントローラの既存のEXTERNAL-IPアドレスを保持します。
既存のOracle Cloud Infrastructureロード・バランサを削除せずに既存のイングレス・コントローラをアップグレード(それによって既存のEXTERNAL-IPアドレスを保持)するには、NginxドキュメントのHelmを使用しないNginxのアップグレード手順に従います。
Nginxのアップグレード時に参照する Nginxイメージを確認するには、Nginxのドキュメントの Nginx Changelogを参照してください。
(オプション)例のイングレス・コントローラの削除
このオプション・セクションでは、前に作成した例のイングレス・コントローラを削除します。次に例を示します。
ingress-nginx-controller
イングレス・コントローラ・デプロイメント- Kubernetes RBACのロールとバインディング
- LoadBalancerタイプの
ingress-nginx-controller
イングレス・コントローラ・サービス
後でイングレス・コントローラのデプロイメント・スクリプトを2回適用してサンプル・イングレス・コントローラを再作成することにした場合、以前のサービスとは異なるEXTERNAL-IPアドレスを持つLoadBalancerタイプの新しいingress-nginx-controller
サービスが作成されます。
使用を続行する場合は、サンプル・イングレス・コントローラを削除する必要はありません。ただし、サンプル・イングレス・コントローラを引き続き使用する場合は、イングレス・コントローラが使用するNginxのバージョンを定期的にアップグレードする必要があります。(オプション)サンプル・イングレス・コントローラのアップグレードを参照してください。
イングレス・コントローラの例の削除
-
次のコマンドを実行して、前に作成したサンプル・イングレス・コントローラを削除します:
kubectl delete -f <deployment-script-location>
<deployment-script-location>
は、サンプル・イングレス・コントローラの作成に以前使用したデプロイメント・スクリプトの場所です。例:
kubectl delete -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.1.3/deploy/static/provider/cloud/deploy.yaml