CIS Istio Service Mesh Benchmark
Security configuration recommendations for Istio service mesh
v1.0.0 01-2025Overview
▶This benchmark provides prescriptive guidance for establishing a secure configuration posture for Istio service mesh deployments. It covers mutual TLS enforcement, authorization policies, JWT validation, certificate rotation, Gateway TLS hardening, access logging, distributed tracing, sidecar injection, control plane hardening, and resilience patterns like circuit breaking and retry policies.
| Section | Area | Focus |
|---|---|---|
| 1 | Mutual TLS & Authorization | STRICT mTLS enforcement and deny-all policies |
| 2 | Authentication & Certificates | JWT validation and certificate rotation |
| 3 | Gateway & Traffic Management | TLS Gateway hardening and rate limiting |
| 4 | Observability | Access logging and distributed tracing |
| 5 | Sidecar Management | Injection enforcement and resource limits |
| 6 | Control Plane Hardening | Version management and istiod autoscaling |
| 7 | Resilience & Reliability | Circuit breaking and retry policies |
Profile Definitions
▶| Profile | Description | Intended Use |
|---|---|---|
| L1 | Level 1 — Standard | Essential security for all Istio deployments; minimal performance impact. |
| L2 | Level 2 — Hardened | Advanced hardening for PCI-DSS, HIPAA, or high-security environments. |
1 — Mutual TLS & Authorization
▶1.1 mTLS & Policy
▶This recommendation ensures that STRICT mutual TLS is enforced mesh-wide on the Istio service mesh. Enforcing this requirement establishes a minimum security standard and prevents insecure configurations.
Without this enforcement, the Istio service mesh may accept insecure configurations that weaken overall security posture. Mandating this control ensures consistent protection against common attack vectors.
# Check mutual TLS mode: istioctl analyze --all-namespaces 2>&1 | grep -i mtls # Verify PeerAuthentication policies: kubectl get peerauthentication --all-namespaces -o yaml | grep -A2 'mtls' # Check mesh-wide default: kubectl get peerauthentication -n istio-system default -o yaml
# Enable STRICT mTLS mesh-wide:
kubectl apply -f - << 'EOF'
apiVersion: security.istio.io/v1beta1
kind: PeerAuthentication
metadata:
name: default
namespace: istio-system
spec:
mtls:
mode: STRICT
EOF
# Verify mesh-wide mTLS:
istioctl x describe pod <POD_NAME> -n <NS>This recommendation verifies that deny-all AuthorizationPolicy baseline is applied per namespace on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# List AuthorizationPolicies: kubectl get authorizationpolicy --all-namespaces # Check for overly permissive rules: kubectl get authorizationpolicy --all-namespaces -o yaml | grep -B5 -A10 'action: ALLOW'
# Create deny-all baseline:
kubectl apply -f - << 'EOF'
apiVersion: security.istio.io/v1beta1
kind: AuthorizationPolicy
metadata:
name: deny-all
namespace: production
spec:
{}
EOF
# Add specific allow policy:
kubectl apply -f - << 'EOF'
apiVersion: security.istio.io/v1beta1
kind: AuthorizationPolicy
metadata:
name: allow-frontend-to-api
namespace: production
spec:
selector:
matchLabels:
app: api
action: ALLOW
rules:
- from:
- source:
principals: ["cluster.local/ns/production/sa/frontend"]
to:
- operation:
methods: ["GET", "POST"]
paths: ["/api/*"]
EOF2 — Authentication & Certificates
▶2.1 JWT & Cert Rotation
▶This recommendation verifies that RequestAuthentication with JWT validation is configured at ingress on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check RequestAuthentication policies: kubectl get requestauthentication --all-namespaces # Verify JWT validation: kubectl get requestauthentication --all-namespaces -o yaml | grep -A10 'jwtRules'
# Configure JWT validation for ingress:
kubectl apply -f - << 'EOF'
apiVersion: security.istio.io/v1beta1
kind: RequestAuthentication
metadata:
name: jwt-auth
namespace: istio-system
spec:
selector:
matchLabels:
istio: ingressgateway
jwtRules:
- issuer: "https://auth.example.com"
jwksUri: "https://auth.example.com/.well-known/jwks.json"
forwardOriginalToken: true
EOF
# Require valid JWT:
kubectl apply -f - << 'EOF'
apiVersion: security.istio.io/v1beta1
kind: AuthorizationPolicy
metadata:
name: require-jwt
namespace: istio-system
spec:
selector:
matchLabels:
istio: ingressgateway
action: DENY
rules:
- from:
- source:
notRequestPrincipals: ["*"]
EOFThis recommendation verifies that workload certificate TTL and rotation are configured on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check certificate rotation settings: istioctl proxy-config secret <POD_NAME> -n <NS> | head # Verify cert TTL: kubectl get cm istio -n istio-system -o yaml | grep -i 'workload.*cert\|rotation\|ttl'
# Configure certificate rotation in mesh config:
kubectl apply -f - << 'EOF'
apiVersion: install.istio.io/v1alpha1
kind: IstioOperator
spec:
meshConfig:
defaultConfig:
proxyMetadata:
ISTIO_META_CERT_SIGNER: istio-ca
certificates:
- secretName: dns.example-service
dnsNames:
- example.com
EOF
# Set certificate TTL (default 24h, recommended: shorter):
# In istiod deployment env:
# - MAX_WORKLOAD_CERT_TTL=48h
# - WORKLOAD_CERT_TTL=12h3 — Gateway & Traffic Management
▶3.1 Ingress Security
▶This recommendation verifies that Gateway resources enforce TLS with strong cipher suites on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check Gateway configuration: kubectl get gateway --all-namespaces -o yaml # Verify TLS settings on Gateways: kubectl get gateway --all-namespaces -o yaml | grep -A10 'tls:'
# Configure secure Gateway with TLS:
kubectl apply -f - << 'EOF'
apiVersion: networking.istio.io/v1beta1
kind: Gateway
metadata:
name: secure-gateway
namespace: istio-system
spec:
selector:
istio: ingressgateway
servers:
- port:
number: 443
name: https
protocol: HTTPS
tls:
mode: SIMPLE
credentialName: tls-secret
minProtocolVersion: TLSV1_2
cipherSuites:
- ECDHE-RSA-AES256-GCM-SHA384
- ECDHE-RSA-AES128-GCM-SHA256
hosts:
- "*.example.com"
EOFThis recommendation verifies that rate limiting is configured at the ingress gateway on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check VirtualService configurations: kubectl get virtualservice --all-namespaces # Verify rate limiting: kubectl get envoyfilter --all-namespaces | grep -i rate
# Configure rate limiting with EnvoyFilter:
kubectl apply -f - << 'EOF'
apiVersion: networking.istio.io/v1alpha3
kind: EnvoyFilter
metadata:
name: rate-limit
namespace: istio-system
spec:
workloadSelector:
labels:
istio: ingressgateway
configPatches:
- applyTo: HTTP_FILTER
match:
context: GATEWAY
listener:
filterChain:
filter:
name: envoy.filters.network.http_connection_manager
patch:
operation: INSERT_BEFORE
value:
name: envoy.filters.http.local_ratelimit
typed_config:
"@type": type.googleapis.com/udpa.type.v1.TypedStruct
type_url: envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
value:
stat_prefix: http_local_rate_limiter
token_bucket:
max_tokens: 100
tokens_per_fill: 50
fill_interval: 60s
EOF4 — Observability
▶4.1 Logging & Tracing
▶This recommendation verifies that access logging is enabled for error detection on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check Istio access logging: kubectl get cm istio -n istio-system -o yaml | grep -i 'accessLog\|access_log' # Verify telemetry configuration: kubectl get telemetry --all-namespaces
# Enable access logging:
kubectl apply -f - << 'EOF'
apiVersion: telemetry.istio.io/v1alpha1
kind: Telemetry
metadata:
name: mesh-default
namespace: istio-system
spec:
accessLogging:
- providers:
- name: envoy
filter:
expression: "response.code >= 400"
EOF
# Or via mesh config:
# meshConfig:
# accessLogFile: /dev/stdout
# accessLogEncoding: JSON
# enableEnvoyAccessLogService: trueThis recommendation verifies that distributed tracing is configured for request visibility on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check Prometheus/tracing integration: kubectl get pods -n istio-system | grep -E 'prometheus|jaeger|zipkin' # Verify metrics collection: istioctl dashboard prometheus 2>/dev/null & curl -s localhost:9090/api/v1/targets | python3 -m json.tool | head -20
# Enable distributed tracing:
kubectl apply -f - << 'EOF'
apiVersion: install.istio.io/v1alpha1
kind: IstioOperator
spec:
meshConfig:
enableTracing: true
defaultConfig:
tracing:
sampling: 10.0
zipkin:
address: jaeger-collector.observability:9411
EOF
# Verify tracing:
istioctl proxy-config bootstrap <POD> -n <NS> | grep -i tracing5 — Sidecar Management
▶5.1 Injection & Resources
▶This recommendation verifies that sidecar injection is enabled on all application namespaces on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check sidecar injection:
kubectl get ns --show-labels | grep istio-injection
# Verify all pods have sidecars:
for ns in $(kubectl get ns -l istio-injection=enabled -o name); do
kubectl get pods -n ${ns##*/} -o jsonpath='{range .items[*]}{.metadata.name} {.spec.containers[*].name}{"\n"}{end}' | grep -v istio-proxy
done# Enable sidecar injection on namespaces: kubectl label namespace production istio-injection=enabled --overwrite # Verify injection: kubectl get namespace -L istio-injection # Restart deployments to inject sidecars: kubectl rollout restart deployment -n production
This recommendation verifies that sidecar egress scope and resource limits are configured on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check Sidecar resource limits: kubectl get cm istio-sidecar-injector -n istio-system -o yaml | grep -A20 'resources'
# Configure sidecar resource limits:
kubectl apply -f - << 'EOF'
apiVersion: networking.istio.io/v1beta1
kind: Sidecar
metadata:
name: default
namespace: production
spec:
egress:
- hosts:
- "./*"
- "istio-system/*"
EOF
# Set proxy resource limits in IstioOperator:
# meshConfig:
# defaultConfig:
# concurrency: 2
# resources:
# requests:
# cpu: 100m
# memory: 128Mi
# limits:
# cpu: 500m
# memory: 256Mi6 — Control Plane Hardening
▶6.1 Upgrades & Resources
▶This recommendation verifies that Istio is running a supported version with canary upgrades on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check Istio version: istioctl version # Check for available updates: istioctl manifest versions
# Upgrade Istio using canary upgrade: istioctl install --set revision=1-20-0 # Migrate workloads: kubectl label namespace production istio.io/rev=1-20-0 --overwrite kubectl rollout restart deployment -n production # Verify upgrade: istioctl proxy-status
This recommendation verifies that istiod has resource limits and horizontal pod autoscaling on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check istiod resource limits: kubectl get deploy istiod -n istio-system -o yaml | grep -A10 'resources' # Check HPA: kubectl get hpa -n istio-system
# Configure istiod resource limits and HPA:
kubectl apply -f - << 'EOF'
apiVersion: install.istio.io/v1alpha1
kind: IstioOperator
spec:
components:
pilot:
k8s:
resources:
requests:
cpu: 500m
memory: 2Gi
limits:
cpu: 1000m
memory: 4Gi
hpaSpec:
minReplicas: 2
maxReplicas: 5
targetAverageUtilization: 80
EOF7 — Resilience & Reliability
▶7.1 Circuit Breaking & Retries
▶This recommendation verifies that circuit breaking and outlier detection are configured on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check DestinationRule circuit breaking: kubectl get destinationrule --all-namespaces -o yaml | grep -A10 'connectionPool\|outlierDetection'
# Configure circuit breaking:
kubectl apply -f - << 'EOF'
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: api-circuit-breaker
namespace: production
spec:
host: api-service
trafficPolicy:
connectionPool:
tcp:
maxConnections: 100
http:
h2UpgradePolicy: DEFAULT
http1MaxPendingRequests: 100
http2MaxRequests: 1000
outlierDetection:
consecutive5xxErrors: 5
interval: 30s
baseEjectionTime: 30s
maxEjectionPercent: 50
EOFThis recommendation verifies that retry and timeout policies are defined for critical services on the Istio service mesh. Implementing this control strengthens the overall security configuration and reduces exposure to potential threats.
Failure to implement this control may leave the Istio service mesh vulnerable to attack or non-compliant with organizational security policies. This control helps establish a consistent, hardened configuration baseline.
# Check retry policies: kubectl get virtualservice --all-namespaces -o yaml | grep -A10 'retries'
# Configure retry and timeout policies:
kubectl apply -f - << 'EOF'
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: api-vs
namespace: production
spec:
hosts:
- api-service
http:
- route:
- destination:
host: api-service
timeout: 10s
retries:
attempts: 3
perTryTimeout: 3s
retryOn: gateway-error,connect-failure,refused-stream,5xx
EOF