コンテンツにスキップ

Nginx Ingress 可観測性のベストプラクティス


はじめに

Kubernetes は、Pod にデプロイされたアプリケーションにアクセスするためのレイヤ 4 プロキシを提供します。このレイヤ 4 プロキシを持つ Service には、Kubernetes は 4 種類のアクセス方法を提供しています。

  1. ClusterIP:クラスター内の他のアプリケーションからのアクセス用で、外部からはアクセスできません。
  2. NodePort:すべてのノードで指定されたポートを開放し、外部から IP+ポート 経由でサービスにアクセスできます。NodePort のポートを指定しない場合、デフォルトで 30000–32767 の範囲内からランダムに割り当てられます。
  3. LoadBalancer:NodePort をベースに、クラウドプロバイダーが提供するロードバランサーを使用してトラフィックをサービスに転送します。
  4. ExternalName:CNAME とその値を返すことで、サービスを externalName フィールドの内容にマッピングします。

上記の 4 つの方法では、ドメイン名を使ってクラスター内のアプリケーションにアクセスすることはできません。Kubernetes にデプロイされたアプリケーションにドメイン名でアクセスするには、最も簡単な方法としてクラスター内にレイヤ 7 プロキシの Nginx をデプロイし、ドメイン名で対応する Service に転送します。新しいデプロイがあるたびに Nginx の設定を更新する必要があります。この設定更新を他のアプリケーションに影響を与えずに行うために、Ingress が登場しました。

image

Ingress は、HTTP および HTTPS のリクエストを Kubernetes クラスター内部のサービスに転送し、最終的に Service のバックエンドにある Pod にアクセスします。Ingress を設定することで、Service に対して外部からアクセス可能な URL の提供、負荷分散トラフィック、ドメインベースの仮想ホストを実現できます。

image

Ingress は、Ingress Controller と Ingress の 2 つの主要コンポーネントで構成されます。よく使われる Ingress としては、traefik Ingress や Nginx Ingress があり、本記事では Nginx Ingress を例に説明します。Ingress Controller は Kubernetes の API とやり取りを行い、Kubernetes クラスター内の Ingress サービスルールの変更を動的に検知し、そのルールを読み取って、Ingress のルールに従って Kubernetes クラスター内の対応する Service に転送します。Ingress はこれらのルールを設定するもので、どのドメイン名が Kubernetes クラスター内のどの Service に対応するかを定義し、Ingress Controller 内の Nginx 設定テンプレートに基づいて対応する Nginx 設定を生成します。Ingress Controller はこれらの設定を動的にロードし、Ingress Controller の Pod 内で実行されている Nginx サービスに書き込み、その後 reload して設定を有効にします。

Ingress をデプロイした Kubernetes クラスターでは、Ingress Controller の CPU 使用率、メモリ使用量、設定ファイルのロード、転送成功率などのリソースを監視することが非常に重要です。

Ingress の動作原理:

  1. クライアントが http://myNginx.com リクエストを発行します。
  2. クライアントの DNS サーバーが Ingress コントローラーの IP を返します。
  3. クライアントは Ingress コントローラーに HTTP リクエストを送信し、Host ヘッダーに myNginx.com を指定します。
  4. コントローラーはリクエストを受信すると、ヘッダーからクライアントがアクセスしようとしているサービスを特定し、そのサービスに関連付けられた endpoint オブジェクトを通じて Pod の IP を確認します。
  5. クライアントのリクエストは特定の Pod に転送されて実行されます。

image

前提条件

Ingress のデプロイ

本番環境では、DaemonSet 方式で Ingress をデプロイし、hostNetworktrue に設定して Nginx が直接ホストのネットワークを使用するようにし、クラウドベンダーが提供するロードバランサーを介して Ingress にアクセスすることを推奨します。

1 deploy.yaml のダウンロード

wget https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.1.1/deploy/static/provider/baremetal/deploy.yaml

2 deploy.yaml の編集

2.1 イメージの置き換え

以下のイメージを使用して、deploy.yaml ファイル内で使用されているイメージを置き換えます。

registry.cn-hangzhou.aliyuncs.com/google_containers/nginx-ingress-controller:v1.1.1
registry.cn-hangzhou.aliyuncs.com/google_containers/kube-webhook-certgen:v1.1.1
2.2 Deployment リソースファイルの修正

kind: Deployment の部分を見つけ、以下のように修正します。

kind: DaemonSet # 修正

---
hostNetwork: true # 追加
dnsPolicy: ClusterFirstWithHostNet # 修正
kubectl apply -f deploy.yaml

メトリクス収集

Input の有効化

Guance で Ingress メトリクスデータを収集するには、DataKit で prom プラグインを有効にし、prom プラグインの設定で exporter の URL を指定します。Kubernetes クラスター内で Ingress Controller のメトリクスを収集するには、annotations を使用してアノテーションを追加する方法を推奨します。Ingress をデプロイした deploy.yaml ファイルを開き、前の手順で修正した DaemonSet の部分を見つけて、annotations を追加します。

annotations:
  datakit/prom.instances: |
    [[inputs.prom]]
      url = "http://$IP:10254/metrics"
      source = "prom-ingress"
      metric_types = ["counter", "gauge", "histogram"]
      # metric_name_filter = ["cpu"]
      # measurement_prefix = ""
      measurement_name = "prom_ingress"
      interval = "60s"
      tags_ignore = ["build","le","path","method","release","repository"]
      metric_name_filter = ["nginx_process_cpu_seconds_total","nginx_process_resident_memory_bytes","request_size","response_size","requests","success","config_last_reload_successful"]
      [[inputs.prom.measurements]]
        prefix = "nginx_ingress_controller_"
        name = "prom_ingress"
      [inputs.prom.tags]
      namespace = "$NAMESPACE"

image

パラメーター説明

  • url: Exporter URLs。複数の URL はカンマで区切ります。例:"[http://127.0.0.1:9100/metrics",](http://127.0.0.1:9100/metrics",) "[http://127.0.0.1:9200/metrics"]
  • source: コレクターのエイリアス。
  • metric_types: メトリクスタイプ。指定可能な値は counter、gauge、histogram、summary。
  • measurement_name: メジャーメント名。
  • interval: 収集間隔。
  • inputs.prom.measurements: プレフィックスが一致するメトリクスを、指定された name のメジャーメントに分類します。
  • tags_ignore: 無視するタグ。
  • metric_name_filter: メトリクスフィルター。必要なメトリクス項目のみを収集します。

annotations では以下のワイルドカードがサポートされています。

  • $NAMESPACE:Pod の Namespace

Ingress Controller の再起動

kubectl delete -f deploy.yaml
kubectl apply -f deploy.yaml

デモンストレーション例

Nginx のデプロイファイル nginx-deployment.yaml を作成します。

nginx-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
spec:
  selector:
    matchLabels:
      app: backend
  replicas: 1
  template:
    metadata:
      labels:
        app: backend
    spec:
      # nodeName: df-k8s-node2
      containers:
        - name: nginx
          image: nginx:latest
          resources:
            limits:
              memory: "128Mi"
              cpu: "128m"
          ports:
            - containerPort: 80

---
apiVersion: v1
kind: Service
metadata:
  name: nginx-service
spec:
  selector:
    app: backend
  ports:
    - port: 80
      targetPort: 80

対応する nginx-ingress.yaml を作成します。このルールに従い、ドメイン名が mynginx.com の場合は、Nginx - Service という Service に転送されます。

nginx-ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nodeport-ingress
  namespace: default
spec:
  rules:
    - host: mynginx.com
      http:
        paths:
          - pathType: Prefix
            path: /
            backend:
              service:
                name: nginx-service
                port:
                  number: 80

デプロイ例

kubectl apply -f  nginx-deployment.yaml
kubectl apply -f  nginx-ingress.yaml

テストリクエスト。ここで

  • 8.136.204.98 は Kubernetes クラスター内で Ingress がデプロイされているノードの IP
  • mynginx.comnginx-ingress.yaml で指定された host
curl -v http://8.136.204.98 -H 'host: mynginx.com'

メトリクスデータの確認

Guance にログインし、「メトリクス」で prom_ingress メトリクスを確認します。prom_ingress は annotations 内の measurement_name パラメーターの値です。

image

Ingress の監視

Ingress モニタリングビュー

Guance にログインし、「シナリオ」→「新しいダッシュボードを作成」を選択し、テンプレートライブラリで「Ingress Nginx モニタリングビュー」を検索して「確定」をクリックします。

Ingress のパフォーマンス指標が表示されます。これには、Ingress Controller の平均 CPU 使用率、平均メモリ使用量、ネットワークリクエスト/レスポンスの合計、Ingress Config のロード回数、Ingress Config の前回ロード結果、Ingress の転送成功率などが含まれます。

image

フィードバック

このページは役に立ちましたか?