Contents
前提条件と環境構築
このセクションでは、Envoy を Kubernetes 上にデプロイするための最低限の前提条件を整理します。ツールバージョンやクラスタへの接続設定が不完全だと、以降のマニフェスト適用で致命的なエラーになる可能性があります。まずはローカル環境とクラスター双方で要件を満たしていることを確認してください。
必要ツールのバージョン
以下のバージョンは 2026 年 3 月時点の公式リリース を基準にしています。実際に使用する前に、各ツールの --version 出力で現在のバージョンを確認し、必要に応じてアップデートしてください。
- kubectl: v1.28 以上
- Helm: v3.14 以降
- Docker Engine: 24.0 以上
バージョン確認コマンド例:
kubectl version --client,helm version,docker version【^1】
Kubernetes クラスタの準備とアクセス権
- クラスタバージョン – v1.28 以上を推奨(Envoy の最新機能が利用可能)。
- kubeconfig 設定 –
export KUBECONFIG=$HOME/.kube/config後、kubectl get nodesが正常に返ることを確認。 - RBAC 権限 – デプロイ用 ServiceAccount に
cluster-adminもしくは少なくともapps.deploy,core.services,core.configmapsの権限が付与されているかチェック。
詳細は「KubernetesでEnvoy Proxyを初期設定する手順」でも同様に記載されています【^2】
Envoy のデプロイパターン比較(サイドカー vs スタンドアロン)
この章では、サイドカー方式とスタンドアロン方式の選択基準 を明確にし、それぞれのメリット・デメリットを表形式で整理します。設計段階でどちらが自組織に適しているか判断できるようにすることが目的です。
サイドカー vs スタンドアロン の選択基準
サイドカーは Pod 単位で細かいトラフィック制御を実現しやすく、マイクロサービス間の独立性が高まります。一方、スタンドアロン(DaemonSet)はノード単位で一括管理できるため運用コストが抑えられます。以下の観点で比較してください。
- 制御粒度 – Pod 細分化かノード統合か
- リソース消費 – Envoy コンテナ数と CPU/メモリ要求
- 運用複雑性 – デプロイ・アップグレードの頻度と手順
サイドカー方式の実装例
サイドカーは各 Pod に Envoy コンテナを同梱し、アプリケーションからの直接外部アクセスを遮断します。以下は最小構成の Deployment マニフェストです(app-container が対象サービス)。ConfigMap で設定ファイルを共有し、--service-node に Pod 名を渡すことで xDS の Node ID が一意になります。
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 |
apiVersion: apps/v1 kind: Deployment metadata: name: sample-app spec: replicas: 3 selector: matchLabels: app: sample template: metadata: labels: app: sample spec: containers: - name: app-container image: ghcr.io/example/sample-app:v1.0 ports: - containerPort: 8080 - name: envoy-sidecar image: envoyproxy/envoy:v1.28.2 args: - /usr/local/bin/envoy - -c /etc/envoy/config.yaml - --service-node $(HOSTNAME) - --service-cluster sample-app volumeMounts: - name: envoy-config mountPath: /etc/envoy volumes: - name: envoy-config configMap: name: sample-app-envoy-config |
ポイント
ConfigMap 名とvolumeMountsのキーが一致しているか必ず確認。
--service-node $(HOSTNAME)により、各 Envoy がユニークな Node ID を持つようになる。
スタンドアロン方式(DaemonSet)の実装例
スタンドアロンはノード単位で Envoy を展開し、全トラフィックを集約します。以下は基本的な DaemonSet 定義です。
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
apiVersion: apps/v1 kind: DaemonSet metadata: name: envoy-daemonset spec: selector: matchLabels: app: envoy template: metadata: labels: app: envoy spec: containers: - name: envoy image: envoyproxy/envoy:v1.28.2 args: - /usr/local/bin/envoy - -c /etc/envoy/config.yaml - --service-node $(HOSTNAME) - --service-cluster kube-envoy volumeMounts: - name: envoy-config mountPath: /etc/envoy volumes: - name: envoy-config configMap: name: envoy-global-config |
ポイント
DaemonSet によりノード増減に自動追随し、単一リソースで管理できる。
hostPortを使用しない設計とすればポート競合のリスクが低減する。
メリット・デメリット比較表
| 項目 | サイドカー | スタンドアロン |
|---|---|---|
| トラフィック制御粒度 | Pod 単位で細かく設定可能 | ノード単位で統一的に管理 |
| リソース消費 | 各 Pod に Envoy が付随 → 増加 | DaemonSet 1 コンテナ/ノードで抑えられる |
| デプロイ・アップグレード | アプリと同時にロールアウトが必要 | 単一リソース更新で済む |
| 可観測性 | Pod ごとのメトリクス取得が容易 | ノード単位の集計になる |
ConfigMap に記述する Listener / Cluster の基本設定(2026 年版)
この章では、Envoy v1.28 系における Listener と Cluster の主要フィールドを解説し、実際に使用できる最小構成の ConfigMap を提示します。なお、socket_address.protocol や transport_socket が必須かどうかはリリースノートで確認が必要です(2026 年 3 月時点では オプション とされています)【^3】。
推奨構成例と重要ポイント
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
apiVersion: v1 kind: ConfigMap metadata: name: sample-app-envoy-config data: config.yaml: | static_resources: listeners: - name: listener_http address: socket_address: address: 0.0.0.0 port_value: 10000 # protocol フィールドはオプション。明示したい場合は TCP/UDP を指定 filter_chains: - filters: - name: envoy.filters.network.http_connection_manager typed_config: "@type": type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager stat_prefix: ingress_http codec_type: AUTO route_config: name: local_route virtual_hosts: - name: backend domains: ["*"] routes: - match: { prefix: "/" } route: { cluster: service_backend } http_filters: - name: envoy.filters.http.router clusters: - name: service_backend connect_timeout: 0.25s type: STRICT_DNS lb_policy: ROUND_ROBIN load_assignment: cluster_name: service_backend endpoints: - lb_endpoints: - endpoint: address: socket_address: address: backend-svc.default.svc.cluster.local port_value: 8080 |
設定の要点
stat_prefixはメトリクス名に使用され、Prometheus の集計を簡素化します。connect_timeoutを短めに設定すると、障害時のフェイルオーバーが速くなります。type: STRICT_DNSにより K8s Service 名で直接バックエンドを解決でき、Service 発見が自動化されます。
ConfigMap の適用手順(箇条書き)
- 上記内容を
envoy-config.yamlとして保存。 kubectl apply -f envoy-config.yamlでクラスタに登録。- Deployment/DaemonSet の
volumeMountsに/etc/envoy/config.yamlをマウント。 - 設定変更時は ConfigMap を更新し、
kubectl rollout restart deployment/<name>または DaemonSet のロールアウトを実行。
この手順は「Envoy Proxy と xDS API の概要とKubernetesでの活用」でも同様に推奨されています【^4】
サイドカー vs スタンドアロン の選択基準(詳細解説)
ここでは、導入時に検討すべき具体的なシナリオ を 3 パターン提示し、どちらのパターンが適合するかを判断できるチェックリストを作成します。
- マイクロサービスが多数、かつ独自トラフィックポリシーが必要
-
サイドカーが推奨。Pod ごとに個別の Listener/Cluster を持たせられるため、認可やレート制限を細分化できる。
-
同一クラスタ内で統一的な L7 フィルタリングだけが目的
-
スタンドアロン(DaemonSet)で十分。ノード単位の Envoy が全トラフィックを集約し、設定変更は 1 カ所で完結する。
-
既存インフラに Service Mesh を段階的に導入したい
- 初期はスタンドアロンで全体のプロキシ基盤を構築し、後からサイドカーへ移行するハイブリッド戦略が有効。
| シナリオ | 推奨パターン | 主な理由 |
|---|---|---|
| 多数サービス・細かいポリシー | サイドカー | Pod 単位で独立した設定が可能 |
| 統一的 L7 フィルタリング | スタンドアロン | 管理対象がノードだけになる |
| 段階的 Service Mesh 移行 | ハイブリッド(スタンド→サイド) | 初期コスト低減と後方互換性 |
xDS API と動的構成管理の実装例
静的 ConfigMap に加えて、xDS 系列 API を利用すると設定変更がリアルタイムに反映されます。ここでは主要 4 種類(ADS・LDS・CDS・EDS)の役割を簡潔にまとめ、サンプルコントロールプレーンのデプロイ手順を示します。
ADS/EDS/CDS/LDS の概要とフロー
- ADS (Aggregated Discovery Service) – 1 本の gRPC 接続で全種別情報を取得。接続数削減が主な利点。
- LDS (Listener Discovery Service) – Listener 定義(ポート・フィルタチェーン)を配布し、TLS 設定変更などに即応。
- CDS (Cluster Discovery Service) – 上流サービス情報とロードバランシング方式を提供。バックエンドスケール時に自動更新。
- EDS (Endpoint Discovery Service) – 各 Cluster の実際の IP/Port を返し、K8s Endpoints と連携して Pod 増減へ即座に追随。
典型的なフロー
- Envoy 起動 →
--service-node・--service-clusterで自己情報送信。 - ADS エンドポイント(例:
grpc://controlplane.default.svc.cluster.local:18000)へ接続。 - Control Plane が LDS → CDS を順次プッシュし、必要に応じて EDS が更新。
- Envoy は受領した設定を即座に適用し、Admin UI で確認可能。
この流れは「Envoy Proxy と xDS API の概要」でも同様に解説されています【^5】
サンプルコントロールプレーンのデプロイ手順
1. Go 実装 envoycontrolplane を使う場合
|
1 2 3 4 5 6 7 |
# リポジトリ取得 & ビルド git clone https://github.com/example/envoycontrolplane.git cd envoycontrolplane docker build -t example/envoycontrolplane:v1.0 . # Kubernetes へデプロイ(マニフェストは省略) kubectl apply -f k8s/controlplane-deployment.yaml |
controlplane-deployment.yaml の要点
- replicas: 2 で冗長化
- 環境変数
NODE_IDに Pod 名を自動設定し、Envoy 側の--service-nodeと一致させる
2. Istio Pilot(軽量モード)を利用する場合
|
1 2 3 4 5 6 |
helm repo add istio https://istio-release.storage.googleapis.com/charts helm install pilot istio/pilot \ --namespace istio-system \ --set meshConfig.enableAutoMtls=true \ --set pilot.traceSampling=100 |
enableAutoMtlsにより TLS 終端が自動で有効化。traceSampling: 100はデバッグ時に全リクエストのトレース情報を取得できる設定です。
小規模なら Go 製コントロールプレーンが導入ハードル低く、拡張性や可視化が必要な場合は Istio Pilot が有力です【^6】
Helm Chart / EnvoyOperator を使った簡易デプロイ手順
Helm と Operator はマニフェスト管理の自動化に大きく貢献します。ここでは 公式 Helm Chart のカスタマイズ例 と EnvoyOperator の CRD 作成手順 をそれぞれ箇条書きで示し、選択肢ごとのメリットを比較します。
公式 Helm Chart のインストールとカスタマイズ
- リポジトリ追加 & 更新
bash
helm repo add envoyproxy https://envoyproxy.github.io/helm-charts
helm repo update values.yamlを取得し、必要項目を編集(例: イメージタグ、リソース上限、xDS 有効化)- カスタム values を適用してデプロイ
|
1 2 |
helm install my-envoy envoyproxy/envoy -f custom-values.yaml --namespace ingress |
主なカスタマイズポイント
| 項目 | 説明 |
|---|---|
image.tag |
Envoy のバージョン(例: v1.28.2) |
resources.limits / requests |
CPU・メモリの上限と要求値 |
xds.enabled |
ADS エンドポイント有効化フラグ |
xds.address/port |
コントロールプレーンの Service 名とポート |
EnvoyOperator の導入ステップ
- CRD と Operator 本体をインストール
bash
kubectl apply -f https://github.com/envoyproxy/operator/releases/download/v0.4.0/crd.yaml
kubectl apply -f https://github.com/envyproxy/operator/releases/download/v0.4.0/operator.yaml EnvoyProxyカスタムリソースを作成
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
apiVersion: operator.envoyproxy.io/v1alpha1 kind: EnvoyProxy metadata: name: sample-proxy spec: serviceAccountName: envoy-sa image: repository: envoyproxy/envoy tag: v1.28.2 listeners: - name: http address: socketAddress: address: 0.0.0.0 portValue: 10000 clusters: - name: backend type: STRICT_DNS loadAssignment: clusterName: backend endpoints: - lbEndpoints: - endpoint: address: socketAddress: address: backend-svc.default.svc.cluster.local portValue: 8080 |
kubectl apply -f envoyproxy.yaml→ Operator が自動で Deployment と Service、ConfigMap を生成。
比較表
| 手段 | 初期導入コスト | カスタマイズ性 | 運用自動化 |
|---|---|---|---|
| Helm Chart | 低(Chart ダウンロードだけ) | 中程度(values.yaml の編集) | upgrade --reuse-values で簡易更新可能 |
| EnvoyOperator | やや高(CRD と Operator の導入必要) | 高(CRD に全設定を宣言) | 完全宣言的管理、複数環境間の一貫性確保 |
トラフィックテスト・メトリクス確認・代表的エラーと対処法
デプロイ完了後は 実際にリクエストを流して動作検証 し、問題があれば速やかに切り分けられるようチェックリストを用意します。
curl / httpbin を使った基本テスト手順
- テスト用 Service(httpbin)をデプロイ
bash
kubectl run httpbin --image=kennethreitz/httpbin --port=80
kubectl expose pod httpbin --type=ClusterIP --name=httpbin-svc - Envoy の Listener ポートへリクエスト送信(例: 10000)
bash
curl -s http://<node-ip>:10000/get | jq .url
# 正常なら "http://httpbin-svc.default.svc.cluster.local/get" が返る - ヘッダー確認:
x-envoy-upstream-service-timeが付与されていれば、Envoy が正しくプロキシしている証拠です。
Admin UI と Prometheus Exporter の活用ポイント
| 機能 | アクセス方法 | 主な利用ケース |
|---|---|---|
| Admin UI | http://<pod-ip>:9901 → /config_dump で現在設定を JSON 表示 |
設定反映の検証、デバッグ |
| Prometheus Exporter | Chart の metrics.enabled: true または手動で stats_sinks に Prometheus を追加 |
メトリクス収集・Grafana 可視化 |
Grafana 用ダッシュボード例は公式リポジトリの
examples/monitoring/grafana-dashboard.jsonから取得可能です【^7】
よくあるエラーと対策チェックリスト
| エラーシナリオ | 主な原因 | 推奨対処 |
|---|---|---|
| ConfigMap 読み込み失敗 | volumeMounts と ConfigMap 名が不一致、キー名ミス |
kubectl describe pod <name> でマウント情報確認後、正しい名前・キーで再適用 |
| Listener ポート競合 | 同一ノード上の別 Pod が hostPort: 10000 を使用 |
hostPort を削除し Service に委譲、またはポート番号を変更 |
| xDS 接続エラー | Control Plane の Service 未公開、TLS 設定不整合 | Service 定義 (ClusterIP/Headless) と Envoy の --service-node が一致するか確認。ログで connection_error を検索 |
デプロイ完了チェックリスト
- [ ] ConfigMap 名・キーが正しくマウントされている
- [ ] Listener のポート競合が解消されている
- [ ] xDS 用 Service が期待通りに公開され、Envoy から接続できるか
kubectl logsで確認
まとめ
- 前提条件 – kubectl v1.28+, Helm v3.14+, Docker 24+ と Kubernetes v1.28 以上のクラスタが必須です。
- デプロイパターン – サイドカーは細粒度制御、DaemonSet は運用コスト削減という軸で選択し、シナリオ別チェックリストを活用してください。
- ConfigMap 設定 – v1.28 系では
protocolやtransport_socketがオプションである点に注意しつつ、TLS/HTTP2 を簡潔に記述できます(実装前に公式リリースノートで再確認)。 - xDS API の活用 – ADS・LDS・CDS・EDS を組み合わせることで、バックエンドスケールや設定変更をリアルタイム反映可能です。サンプルコントロールプレーンとして
envoycontrolplaneまたは Istio Pilot が選択肢になります。 - 自動化ツール – Helm Chart はシンプル導入、EnvoyOperator は宣言的管理と高いカスタマイズ性を提供します。組織の成熟度に合わせて選択してください。
- テスト・監視 –
curl/httpbinで基本検証し、Admin UI と Prometheus Exporter で可観測性を確保。典型的なエラーはチェックリストで即時対応できます。
以上の手順とポイントを抑えておけば、Envoy Proxy を Kubernetes 上に安全かつスケーラブルに導入できる はずです。ぜひ実環境で試し、必要に応じて各項目をチューニングしてください。
参考文献
[^1]: 「kubectl, Helm, Docker の公式リリースノート」(2026/03)
[^2]: 「KubernetesでEnvoy Proxyを初期設定する手順」 – app-tatsujin.com
[^3]: Envoy v1.28 リリースノート – https://www.envoyproxy.io/docs/envoy/v1.28.0/version_history/v1.28/
[^4]: 「Envoy Proxy と xDS API の概要とKubernetesでの活用」 – app-tatsujin.com
[^5]: 同上、xDS 系列解説ページ
[^6]: 「Istio Pilot 軽量モード導入ガイド」 – Istio公式ドキュメント (2026)
[^7]: Envoy 公式リポジトリ examples/monitoring/grafana-dashboard.json