Ciliumサービスメッシュのセキュリティ
最終更新: September 11, 2026 · Cilium/chart 1.20.1 · 同梱SPIRE 1.15.2。テスト済みKubernetes/EKS版とプラットフォーム要件は概要を参照してください。
概要
ワークロード認可、ピア認証、アプリデータ暗号化という3つの別制御を評価します。Ciliumの帯域外相互認証、WireGuard/IPsec転送暗号化、別のztunnel mTLSベータは要件と制限が異なります。
以下のポリシー例は通常のCiliumポリシー/帯域外認証経路です。ztunnel暗号化を有効にしたときも同じL4適用が維持されると想定しないでください。ベータの制限は後述します。
セキュリティアーキテクチャ
ボックスは責務をまとめ、全組み合わせが全ポリシーを保持すると認定するものではありません。特にztunnelベータは別のID/データ経路を使い、デフォルトCAは帯域外認証で示すSPIRE統合を必要としません。
相互認証とデータ暗号化
従来のCilium相互認証
帯域外方式はCilium 1.20.1でもベータ/未完成と文書化されています。CiliumエージェントはSPIRE提供SVIDでCiliumセキュリティIDを認証します。ネットワークポリシールールが認証を要求しても、アプリ接続自体がTLSになるわけではありません。
認証記録はID関係についてキャッシュされます。図はHTTP要求ごと、あるいは必ずアプリ接続ごとに新証明書/ハンドシェイクを作る意味ではありません。認証要件に加え明示的な認可ルールも適用します。
ztunnelによるネイティブmTLS(2026年更新)
Cilium 1.20.1には Ztunnel Transparent Encryption(ベータ) があります。必要なブートストラップ/CA素材を準備してから、次のモード断片で選択します。
encryption:
enabled: true
type: ztunnel
ztunnel:
ca:
type: internalリリースのデフォルトはCilium内部CAオプションです。cilium-ztunnel-secrets Secretがbootstrap-private.key、bootstrap-root.crt、ca-private.key、ca-root.crtを提供します。公式生成スクリプトは例で、完全な本番PKI/ローテーション設計ではありません。チャートのbootstrapRootCert単体は公開証明書だけを提供し、内部CAに必要な秘密鍵は生成しません。
Ciliumエージェントは参加Podのネットワーク名前空間にiptablesリダイレクトを設定し、ノードのztunnelへワークロード状態を送り、制御/証明書インターフェースを提供します。チャートはztunnel-cilium DaemonSetを作成します。名前空間参加にはio.cilium/mtls-enabled=trueを使い、モードをインストールするだけでは全名前空間は参加しません。
リリースガイドは次の境界を定めています。
- 送信元と宛先の両ワークロードが参加する必要があり、参加済みと未参加間の通信は非対応。
- 参加は名前空間単位で、Podごとの参加は非対応。ホストネットワークPodは参加不可。
- mTLSへリダイレクトするのはTCPだけで、UDPや他プロトコルはこの暗号化経路外。
- ClusterMeshは非対応で、カーネルは必要なiptables操作に対応している必要がある。
- 暗号化はパケットがPodを出る前に行われる。そのためHBONEポート15008を直接対象とする場合を除き、通常L4ポリシーはこの経路で動作しない。
この統合は名前空間/サービスアカウントのワークロードIDモデルを使います。帯域外認証の数値/identity/<id> SPIFFEパスとは異なります。
準備したテストインストールの読み取り専用確認例:
kubectl -n kube-system get daemonset ztunnel-cilium
kubectl get namespaces -l io.cilium/mtls-enabled=true
kubectl -n kube-system get configmap cilium-config -o yaml名前空間ラベル、正常プロキシ、15008上のパケットだけでは期待する全通信の暗号化/認可は証明されません。参加成功、選択経路の両端、証明書ID/信頼、非対応通信を確認します。
mTLSにCiliumとIstioのどちらを選ぶか
必要なID、認可、通信範囲で選択します。既存CiliumではIDポリシーとWireGuard/IPsecを使うか、制限内で別のztunnelベータを評価できます。実際に有効にする追加プロキシ、CA、運用依存関係を考慮します。
Istioはサイドカー/ambientでワークロードプロキシmTLSを提供し、それぞれ機能/プラットフォーム境界があります。PeerAuthenticationのSTRICTは受信mTLS要件で、単体ではID発行、プロキシ導入、全呼び出し元認可をしません。比較を暗号化スイッチ1つに還元しないでください。サイドカー/ambientの章は実測版とシナリオを保持しています。
SPIREベース相互認証の設定
帯域外認証には、レビュー済みインストールvaluesへこのオーバーレイをマージします。
authentication:
enabled: true
mutual:
spire:
enabled: true
trustDomain: spiffe.cilium
agentSocketPath: /run/spire/sockets/agent/agent.sock
install:
enabled: true
server:
dataStorage:
enabled: true
size: 1GiSPIRE StatefulSetに適切なStorageClass/PVを準備します。gp3クラスが全EKSに自動存在するわけではありません。authentication.enabledは必須です。trust domainとagent socket設定はinstall.serverやinstall.agent下でなくauthentication.mutual.spire下です。同梱チャートは旧server.replicas、server.nodeAttestor、agent.workloadAttestor、server.ca.ttl例を実装しません。
SPIRE Serverはエージェントを検証しSVIDに署名します。エージェントはワークロードを検証します。Cilium統合はさらに取得を委任し、CiliumセキュリティIDのエントリを登録します。SPIREを有効にするだけでは全通信への認証適用もWireGuard/IPsec有効化もしません。
相互認証ポリシーの適用
authenticationはIngress/Egress許可ルール内のオブジェクトです。配列でも最上位spec.authenticationスイッチでもありません。このクラスター範囲ポリシーは意図的に1アプリ/名前空間を選びます。
apiVersion: cilium.io/v2
kind: CiliumClusterwideNetworkPolicy
metadata:
name: production-backend-auth
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: backend
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: frontend
toPorts:
- ports:
- port: '8080'
protocol: TCP
authentication:
mode: required名前空間ごとの相互認証
この名前空間単位の例はproductionのワークロードを選び、その名前空間の認証済みピアをTCP 8080で許可します。
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: namespace-auth
namespace: production
spec:
endpointSelector: {}
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: production
toPorts:
- ports:
- port: '8080'
protocol: TCP
authentication:
mode: required同一名前空間許可の例で、全アプリの最小権限ではありません。他ポート、クライアント、プローブ、既存ポリシー許可は別評価です。Ingressに影響し、完全なEgress依存ポリシーを暗黙に設定しません。
サービスごとの相互認証
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: service-auth
namespace: default
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: backend
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: frontend
toPorts:
- ports:
- port: '8080'
protocol: TCP
authentication:
mode: required送信元/宛先ラベルはワークロードを記述し、エンドユーザーのログインではありません。ワークロード作成、ラベル変更、サービスアカウント使用を誰ができるか、Kubernetes権限で制御する必要があります。
CiliumNetworkPolicyのL7ルール
HTTP L7セキュリティポリシー
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: http-security-policy
namespace: default
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: api-server
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:role: reader
toPorts:
- ports:
- port: '8080'
protocol: TCP
rules:
http:
- method: ^GET$
path: ^/api/.*$
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:role: admin
toPorts:
- ports:
- port: '8080'
protocol: TCP
rules:
http:
- method: ^(GET|POST|PUT|PATCH|DELETE)$
path: ^/api/.*$
headers:
- Authorization
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: monitoring
toPorts:
- ports:
- port: '8080'
protocol: TCP
rules:
http:
- method: ^GET$
path: ^/health$
- method: ^GET$
path: ^/metrics$ルール内のHTTPルールは選択肢です。headers: [Authorization]は存在だけを要求し、bearer token、署名、期限、権限は検証しません。旧Authorization: Bearer .*文字列はJWT検証器でも汎用正規表現の値一致でもありません。アプリ認証/認可を独立して行います。
HTTPパスポリシーには対応する検査可能L7経路が必要です。アプリTLS、プローブ、他依存通信には関連設定が必要で、ポート番号だけではTLSは有効になりません。
Kafka L7セキュリティポリシー
旧rules.kafkaオブジェクトはCilium 1.20.1 L7スキーマで拒否されます。以下の置換はネットワーク到達性だけを制限します。
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: kafka-network-boundary
namespace: kafka
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: kafka
k8s:app: kafka
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kafka
k8s:role: producer
toPorts:
- ports:
- port: '9092'
protocol: TCP
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kafka
k8s:role: consumer
toPorts:
- ports:
- port: '9092'
protocol: TCPproduce/fetch、トピック、コンシューマーグループ用に、実KafkaリスナーのTLS/SASLとブローカーACLを設定します。古いL7ルール削除後にはL4アクセスが残り、トピック単位認可は維持されません。
DNS L7セキュリティポリシー
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: dns-security
namespace: default
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: web-application
egress:
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kube-system
k8s:k8s-app: kube-dns
toPorts:
- ports:
- port: '53'
protocol: UDP
- port: '53'
protocol: TCP
rules:
dns:
- matchPattern: '*.*.svc.cluster.local'
- matchName: api.stripe.com
- matchName: sts.us-east-1.amazonaws.com
- toFQDNs:
- matchName: api.stripe.com
- matchName: sts.us-east-1.amazonaws.com
toPorts:
- ports:
- port: '443'
protocol: TCP例はkube-systemのk8s-app=kube-dnsラベル付きCoreDNSと通常のcluster.local DNSサフィックスを前提とします。UDP/TCP両方のDNSを許可します。Service FQDNはserviceとnamespace両ラベルを含むため、*.*.svc.cluster.localは旧*.svc.cluster.localと異なります。
外部HTTPS許可はDNSクエリ許可と別です。sts.us-east-1.amazonaws.comは特定リージョンのAWSエンドポイントです。AWSは旧api.aws.amazon.comを汎用APIエンドポイントとして使いません。該当IPv6/デュアルスタック/プライベート版も含め、実SDKのリージョン/サービスエンドポイントを選びます。内部DNS応答は全内部Serviceへの接続を自動許可しません。
リゾルバー検索リストと、有効ならNodeLocal DNS動作を確認します。広いS3ワイルドカードは意図した1バケット以外も許し得ます。DNS/IPポリシーは許可先経由の持ち出し防止を保証しません。
相互認証
認証モード
| モード | 帯域外ポリシーAPIでの意味 |
|---|---|
required | 一致する許可通信に認証成功を要求 |
disabled | 一致ルールに対する明示的認証免除 |
test-always-fail | 意図的に認証失敗させるテストモード |
リリーススキーマにoptionalはありません。他ルールが重なる場合、明示要件がないことと慎重に範囲を限定した免除は異なります。認証ルールが通常の独立Allowと同じと想定せず、結果ポリシーを確認します。
相互認証ポリシー例
免除は明示的かつ狭い範囲とし、理由を示すべきです。
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: authentication-exception
namespace: production
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: secure-service
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: trusted-client
toPorts:
- ports:
- port: '443'
protocol: TCP
authentication:
mode: required
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: monitoring
k8s:app: prometheus
toPorts:
- ports:
- port: '9090'
protocol: TCP
authentication:
mode: disabledPrometheusルールは「可能なら認証」でなく認証無効です。指定監視ワークロードとポートだけを許可します。どちらかのアプリ待ち受けポートのTLSは別アプリ設定です。
SPIFFE IDベースの認証
デフォルトの帯域外SPIRE trust domainでは、CiliumセキュリティIDは次の形式です。
spiffe://spiffe.cilium/identity/<numeric-security-identity>許可ピアはエンドポイント/IDポリシーで選択します。authenticationに任意SPIFFE-ID許可リストフィールドはありません。コメントをIstio型/ns/.../sa/... URIに変えてもアクセスは制限されません。上述のztunnelベータは別のワークロードIDモデルです。
暗号化
WireGuard透過暗号化
encryption:
enabled: true
type: wireguardCiliumはノード鍵ペアを作り、CiliumNode情報で公開鍵を配布します。異なるノードのCilium管理Pod間の対応通信は暗号化されますが、同一ノード通信はされません。カーネルのWireGuard対応が必要です。チャートにencryption.wireguard.userspaceFallbackはありません。
必要なノード間UDP 51871経路を許可し、MTU/カプセル化を考慮します。AWS VPC CNIチェイニングには、文書化されたcni.enableRouteMTUForCNIChainingを含む追加MTU要件があります。無条件に適用せず、選択インストールモードに従います。
WireGuardアーキテクチャ
Agentボックスは管理/鍵配布を表し、各パケットのユーザー空間中継ホップではありません。WireGuardインターフェース上のキャプチャでは平文の内側パケットが見える場合があります。暗号化評価では正しい外側ネットワーク経路を確認します。
ノード間の対象拡張は別のベータオプションです。
encryption:
enabled: true
type: wireguard
nodeEncryption: true鍵更新のブートストラップ失敗を避けるため、デフォルトではコントロールプレーンノードをノード暗号化から除外します。リリースの通信表はXDPアクセラレーション、非Geneve DSR、Egress Gateway応答の除外も示します。外部要求のクライアント→クラスター区間はノードWireGuardでは暗号化されません。
IPsec暗号化
encryption:
enabled: true
type: ipsec
ipsec:
secretName: cilium-ipsec-keys
keyFile: keys
keyWatcher: true
keyRotationDuration: 5mSecretはCiliumの名前空間に存在する必要があります。文書化されたAES-GCM例のkeysエントリは次の形式です。
3+ rfc4106(gcm(aes)) <fresh-20-byte-random-value-in-hex> 128+はトンネルごとに導出した鍵を選びます。+なしの旧グローバル鍵形式はセキュリティ上の理由で非推奨です。現行ガイダンスとしてコピーしないでください。サンプル鍵を再利用せず、文書化されたCLI/Secret手順で新しい鍵素材を生成・保護します。
keyRotationDuration: 5mは鍵変更後の移行/旧鍵削除猶予で、5分ごとに新鍵を生成するスケジューラーではありません。対応ローテーション手順で鍵IDと素材を更新し、ClusterMesh使用時は全クラスターを調整します。更新中にノード版が混在している間はローテーションしないでください。
ESP/ファイアウォール対応、実暗号化インターフェース、ネイティブルーティングCIDRを確認します。現IPsecはL7で文書化された透過DNSプロキシ動作を要求し、CNIチェイニングとホストポリシーは非対応で、同一ノード通信は暗号化しません。
暗号化の比較
| 項目 | WireGuard | IPsec | ztunnelベータ |
|---|---|---|---|
| 鍵/ID | ノード生成の鍵ペア | トンネル別導出を使う配布鍵素材 | ワークロードmTLS証明書とブートストラップ/CA素材 |
| データ経路 | カーネルWireGuardインターフェース | カーネルIPsec/XFRM | ノードごとのTLSプロキシとPod名前空間リダイレクト |
| 同一ノード/範囲 | 同一ノード通信は非暗号化。リリース通信表を使用 | 同一ノード通信は非暗号化。モード制限あり | 両端参加、TCPのみ、ポリシー制限あり |
| 暗号設定 | WireGuardのChaCha20-Poly1305スイート | AES-GCMなどカーネル対応の設定アルゴリズム | 対応プロキシがネゴシエートするTLS |
| 性能 | 実CPU、MTU、通信構成を測定 | アルゴリズム/ハードウェア、トンネル、単一トンネル復号制約を測定 | プロキシ、TLS、ワークロード負荷を測定。以前の比較ベンチマーク対象外 |
透過暗号化にも、許可された未知宛先を外部として扱うエンドポイント検出の期間があり得ます。Ciliumは緩和策として制限Egressと暗号化strictモードを文書化しますが、制限があります。strict EgressはIPv4/CIDR依存、strict IngressはWireGuardと管理インターフェースが必要でCNIチェイニング非対応です。「暗号化有効」を全経路のfail-closed保護の証明と解釈しないでください。
IDベースのセキュリティ
Cilium ID
CiliumはIDに関係するラベル集合に数値IDを割り当て、複数Podが共有できます。ユーザー計算のハッシュでも永久Pod識別子でもありません。
IDの構成要素
kubectl -n kube-system get pods -l k8s-app=cilium -o wide
CILIUM_POD='<agent-on-the-workload-node>'
kubectl -n default get ciliumendpoints
kubectl get ciliumidentities
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg identity list
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg status --verbose
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg encrypt status名前空間、サービスアカウント、選択ワークロードラベルが寄与し得ます。ID 1–6はhost、world、unmanaged、health、init、remote-nodeに対応し、割り当てワークロードIDはインストールに依存します。関連ノードのエージェントを調べ、コマンド失敗/状態を完全に保持します。
IDベースのポリシー
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: identity-based-policy
namespace: default
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: backend
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: default
k8s:app: frontend
k8s:environment: production
toPorts:
- ports:
- port: '8080'
protocol: TCP
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: monitoring
k8s:app: prometheus
toPorts:
- ports:
- port: '9090'
protocol: TCPIPとIDの比較
IP変更をまたいでポリシーセレクターは安定したままにできます。Ciliumはエンドポイント/IPキャッシュ状態を更新する必要があり、IDはGCで回収・再割り当てされ得ます。図は再起動ごとに数値IDが不変と約束しません。
外部PKI統合
cert-manager統合
以下は上流CA Secret生成の例であり、それだけでSecretをSPIREへ接続しません。
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
name: cilium-ca-issuer
spec:
ca:
secretName: cilium-ca-secret
---
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
name: cilium-spire-ca
namespace: cilium-spire
spec:
secretName: spire-ca-secret
duration: 8760h
renewBefore: 720h
isCA: true
privateKey:
algorithm: ECDSA
size: 256
rotationPolicy: Always
usages:
- cert sign
- crl sign
subject:
organizations:
- Cilium
commonName: SPIRE upstream CA
issuerRef:
name: cilium-ca-issuer
kind: ClusterIssuer
group: cert-manager.iocert-manager設定のクラスターリソース名前空間にあるcilium-ca-secretへ、十分な残存有効期間を持つ有効署名CA/キーを準備します。CA制約、署名用途、信頼チェーンを検証します。1年は下位CA寿命の例で、普遍的推奨ではありません。
外部管理SPIREサーバーは対応UpstreamAuthorityを使い、必要マウント素材またはissuer APIへアクセスする必要があります。既存PKIへ参加するdisk authorityでは、SPIREはcert_file_path、key_file_path、信頼ルートのbundle_file_pathを要求します。再読み込み/ローテーションと信頼の重複期間を計画します。Kubernetes Secret更新だけでは全利用者が新CAを採用した証明にはなりません。
同梱SPIRE ConfigMapを部分的な無関係ファイルで置き換えないでください。外部運用SPIREでは、Ciliumの外部サーバーアドレス、trust domain、委任ID登録、認証前提を別々に確認します。
Vault統合
以下は独立設定したSPIRE 1.15.2サーバーのプラグイン断片のみで、完全なサーバー設定やKubernetes Deploymentではありません。
plugins {
UpstreamAuthority "vault" {
plugin_data {
vault_addr = "https://vault.vault.svc:8200"
pki_mount_point = "pki"
ca_cert_path = "/vault/ca/ca.crt"
k8s_auth {
k8s_auth_mount_point = "kubernetes"
k8s_auth_role_name = "spire-upstream"
token_path = "/var/run/secrets/vault/token"
}
}
}
}プラグインはserver内でなく最上位pluginsに置きます。フィールドはpki_mount_point、ここでtoken_pathはk8s_auth内です。トークンは設定Vault認証ロール用の投影Kubernetesサービスアカウントトークンで、汎用Vaultトークンファイルではありません。
トークン投影/audienceとVault Kubernetes認証を準備し、ロールを対象SPIREワークロードに結び付け、Vault検証用TLS CAをマウントして、必要なPKI sign-intermediate操作を許可します。SPIREのca_ttl、Vault PKI TTL、ワークロード信頼、ローテーションを調整します。このガイドは外部依存をデプロイ/テスト済みと主張しません。
ゼロトラストネットワーキング
デフォルト拒否ポリシー
このクラスター範囲リソースは、隔離したpolicy-lab名前空間を意図的に対象とします。
apiVersion: cilium.io/v2
kind: CiliumClusterwideNetworkPolicy
metadata:
name: policy-lab-default-deny
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: policy-lab
enableDefaultDeny:
ingress: true
egress: true
ingress: []
egress: []enableDefaultDenyを明示します。空のCilium ingress/egress配列だけではデフォルト拒否を有効にするルールは提供されません。Kubernetes NetworkPolicy例からその前提を持ち込まないでください。
DNSなど具体的な依存先を別Allowルールとして追加します。
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: policy-lab-dns
namespace: policy-lab
spec:
endpointSelector: {}
egress:
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kube-system
k8s:k8s-app: kube-dns
toPorts:
- ports:
- port: '53'
protocol: UDP
- port: '53'
protocol: TCPすべてのホストネットワーク通信を許す普遍的要件はありません。実kubelet/プローブ、リゾルバー、ホストポリシー動作を評価します。例はCiliumのホスト処理を変えず、侵害された特権ノードを防御しません。
最小権限アクセス
例はedgeのapp=ingress-gatewayラベル付きCilium管理ゲートウェイ、productionのfrontend/database、動作するSPIRE統合を前提とします。
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: production-security
namespace: production
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: api
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: frontend
toPorts:
- ports:
- port: '8080'
protocol: TCP
authentication:
mode: required
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: edge
k8s:app: ingress-gateway
toPorts:
- ports:
- port: '8080'
protocol: TCP
egress:
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kube-system
k8s:k8s-app: kube-dns
toPorts:
- ports:
- port: '53'
protocol: UDP
- port: '53'
protocol: TCP
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: production
k8s:app: database
toPorts:
- ports:
- port: '5432'
protocol: TCP
authentication:
mode: required選択Gateway実装で実際に観測したラベルとIDを使います。Cilium自身のノードEnvoy Ingress/Gateway経路や外部LBは異なるIDを示す場合があります。任意Podラベルはreserved:ingressや外部クライアントアドレスと交換可能ではありません。終了した旧ingress-nginx例は必須依存ではありません。
マイクロセグメンテーション
このアプリ階層ポリシーは、Service検索を開始する階層に明示DNSアクセスを残します。同じGatewayモデルと指定待ち受けポートを前提とします。
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: frontend-policy
namespace: app
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: frontend
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: edge
k8s:app: ingress-gateway
toPorts:
- ports:
- port: '443'
protocol: TCP
egress:
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kube-system
k8s:k8s-app: kube-dns
toPorts:
- ports:
- port: '53'
protocol: UDP
- port: '53'
protocol: TCP
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: backend
toPorts:
- ports:
- port: '8080'
protocol: TCP
authentication:
mode: required
---
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: backend-policy
namespace: app
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: backend
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: frontend
toPorts:
- ports:
- port: '8080'
protocol: TCP
authentication:
mode: required
egress:
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: kube-system
k8s:k8s-app: kube-dns
toPorts:
- ports:
- port: '53'
protocol: UDP
- port: '53'
protocol: TCP
- toEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: database
toPorts:
- ports:
- port: '5432'
protocol: TCP
authentication:
mode: required
---
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: database-policy
namespace: app
spec:
endpointSelector:
matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: database
enableDefaultDeny:
egress: true
ingress:
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: app
k8s:tier: backend
toPorts:
- ports:
- port: '5432'
protocol: TCP
authentication:
mode: required
egress: []DBはEgress Allowなしで明示的にEgressデフォルト拒否を有効にします。許可接続へのステートフル応答は引き続き許可されます。実バックアップ、レプリケーション、認証などの依存を意図的に追加します。ネットワーク経路制限は、認可されたDB/アプリ要求を通じたデータ取得を完全防止しません。
セキュリティ監査と監視
ポリシー監査モード
cilium.io/audit-mode: "true"は対応するポリシーごとの監査スイッチではありません。その任意アノテーションを持つポリシーも通常どおり適用され得ます。
隔離エンドポイントテストでは、実際の変更可能オプションはPolicyAuditModeです。ローカルエンドポイントを確認し、一時有効化して管理された観察後に適用を戻します。
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg endpoint list
ENDPOINT_ID='<local-endpoint-id-in-the-isolated-test>'
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg endpoint config "$ENDPOINT_ID"
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg endpoint config "$ENDPOINT_ID" PolicyAuditMode=true
# Observe the controlled test, then restore enforcement.
kubectl -n kube-system exec "$CILIUM_POD" -c cilium-agent -- cilium-dbg endpoint config "$ENDPOINT_ID" PolicyAuditMode=false1ポリシーオブジェクトへ監査動作を付けるのでなく、そのエンドポイントの適用を変えます。全L7拒否や全セキュリティ失敗が許可監査イベントになると推測しないでください。具体的データパス/プロキシ動作を確認します。enableDefaultDeny: falseも同等のL7監査モードではありません。
ポリシー違反の監視
# Terminal 1
cilium hubble port-forward --port-forward 4245
# Terminal 2
hubble observe --server localhost:4245 --namespace production --verdict DROPPED --last 100
hubble observe --server localhost:4245 --namespace production --verdict DROPPED --drop-reason-desc POLICY_DENIED --last 100
hubble observe --server localhost:4245 --namespace policy-lab --verdict AUDIT --last 100DROPPEDにはポリシー拒否以外の原因も含まれます。理由で絞ったクエリは報告されたpolicy-denied破棄に注目します。L7/アプリ認可失敗には独自観測が必要です。AUDITはDROPPEDと別です。--last 100は制限付き履歴で、Relayは接続Hubbleインスタンスごとにその数を返す場合があります。完全なクラスター通信カウンターではありません。ストリーミング観測が意図した場合だけ--followを追加します。
Prometheusメトリクス
prometheus:
enabled: true
hubble:
enabled: true
metrics:
enabled:
- dns
- drop
- flow
- httpV2
- icmp
- port-distribution
- tcpエージェントとHubbleエクスポーターには、有効化フラグに加えてPrometheus検出/スクレイプが必要です。httpV2は非推奨httpを置き換えるため両方有効にしないでください。HTTPメトリクスには対応L7可視性が必要です。
cilium_drop_count_totalは理由/方向別の破棄パケットを数え、ポリシー違反だけではありません。cilium_forward_count_totalは転送パケットを数え、成功アプリ要求ではありません。- Hubbleの
dropエクスポーターはhubble_drop_totalでフロー破棄情報を公開し、エージェントのパケットカウンターとは計数単位が違います。 - 旧
cilium_policy_verdictは文書化されたメトリクス名ではありません。実ポリシー判定イベントか選択エクスポーターが公開するメトリクスを使います。
次のステップ
参考資料
- Cilium1.20.1相互認証
- 認証例/API構造
- Cilium1.20.1 CNPスキーマ
- Cilium1.20.1 ztunnelベータ
- Ztunnel CA実装
- Ztunnelブートストラップ例
- 暗号化範囲/strictモード
- WireGuard
- IPsecと鍵ローテーション
- Helm values
- HTTP/DNSポリシー
- デフォルト拒否動作
- 明示的デフォルト拒否API
- 変更可能エンドポイント監査オプション
- エンドポイント設定CLI
- メトリクス
- SPIRE1.15.2サーバー設定
- SPIRE Vault authority
- SPIRE disk authority
- Kafka ACL
- AWS STSエンドポイント
- WireGuardプロトコル
- NISTゼロトラストアーキテクチャ — 追加資料



