🎯 LESSON OBJECTIVE__HTMLTAG_68___
- ✅ VirtualService: routing rules, header-based routing__HTMLTAG_71___
- ✅ DestinationRule: subsets, load balancing, connection pool
- ✅ Canary deployment with traffic splitting
- ✅ Circuit breaking and outlier detection
- ✅ Retry, timeout, fault injection
- ✅ Rate limiting with EnvoyFilter
PART 1: VIRTUALSERVICE
Traffic Flow:
Client → Gateway → VirtualService → DestinationRule → Pod (subset)
VirtualService: "WHERE to route" (rules)
DestinationRule: "HOW to route" (policies, subsets)
1.1. Basic Routing
# virtualservice-order.yaml:
apiVersion: networking.istio.io/v1
kind: VirtualService
metadata:
name: order-service
namespace: default
spec:
hosts:
- order-service # K8s service name
http:
- match:
- headers:
x-api-version:
exact: "v2"
route:
- destination:
host: order-service
subset: v2
port:
number: 8080
- route: # Default route
- destination:
host: order-service
subset: v1
port:
number: 8080
timeout: 10s
retries:
attempts: 3
perTryTimeout: 3s
retryOn: 5xx,reset,connect-failure,refused-stream
1.2. Canary Deployment (Traffic Splitting)
# canary-rollout.yaml: apiVersion: networking.istio.io/v1 kind: VirtualService metadata: name: order-service namespace: default spec: hosts: - order-service http: - route: - destination: host: order-service subset: v1 weight: 90 # 90% → v1 (stable) - destination: host: order-service subset: v2 weight: 10 # 10% → v2 (canary)Gradual rollout:
Step 1: 90/10 → monitor errors
Step 2: 70/30 → monitor latency
Step 3: 50/50 → load test
Step 4: 0/100 → full rollout
1.3. A/B Testing (Header-Based)
# ab-testing.yaml:
apiVersion: networking.istio.io/v1
kind: VirtualService
metadata:
name: frontend
namespace: default
spec:
hosts:
- frontend
http:
# Users with beta cookie → v2:
- match:
- headers:
cookie:
regex: ".*beta=true.*"
route:
- destination:
host: frontend
subset: v2
# Internal team (user-agent header):
- match:
- headers:
x-team:
exact: "internal"
route:
- destination:
host: frontend
subset: v2
# Everyone else → v1:
- route:
- destination:
host: frontend
subset: v1
PART 2: DESTINATIONRULE
# destination-rule-order.yaml:
apiVersion: networking.istio.io/v1
kind: DestinationRule
metadata:
name: order-service
namespace: default
spec:
host: order-service
trafficPolicy:
# Load balancing:
loadBalancer:
simple: LEAST_REQUEST # ROUND_ROBIN | LEAST_REQUEST | RANDOM
# Connection pool:
connectionPool:
tcp:
maxConnections: 100
connectTimeout: 5s
http:
h2UpgradePolicy: DEFAULT
http1MaxPendingRequests: 100
http2MaxRequests: 1000
maxRequestsPerConnection: 10
maxRetries: 3
# Outlier detection (circuit breaking):
outlierDetection:
consecutive5xxErrors: 5
interval: 10s
baseEjectionTime: 30s
maxEjectionPercent: 50
minHealthPercent: 50
subsets:
- name: v1
labels:
version: v1
- name: v2
labels:
version: v2
PART 3: CIRCUIT BREAKING
Circuit Breaker States:
CLOSED ──────────► OPEN ──────────► HALF-OPEN
(normal) (reject all) (test few)
▲ │
│ success │
└──────────────────────────────────┘
(close again)
Istio Outlier Detection:
- consecutive5xxErrors: 5 → 5 errors → eject pod
- interval: 10s → check every 10s
- baseEjectionTime: 30s → eject for 30s minimum
- maxEjectionPercent: 50 → max 50% pods ejected
# Circuit breaker + connection limits:
apiVersion: networking.istio.io/v1
kind: DestinationRule
metadata:
name: payment-service
namespace: default
spec:
host: payment-service
trafficPolicy:
connectionPool:
tcp:
maxConnections: 50 # Max concurrent TCP connections
http:
http1MaxPendingRequests: 50 # Max queued requests
http2MaxRequests: 100 # Max concurrent requests
maxRequestsPerConnection: 5
outlierDetection:
consecutive5xxErrors: 3
interval: 5s
baseEjectionTime: 60s
maxEjectionPercent: 100 # Can eject all pods
PART 4: FAULT INJECTION (CHAOS TESTING)
# Inject delay + abort for testing:
apiVersion: networking.istio.io/v1
kind: VirtualService
metadata:
name: payment-service
namespace: default
spec:
hosts:
- payment-service
http:
- fault:
delay:
percentage:
value: 10.0 # 10% requests get 5s delay
fixedDelay: 5s
abort:
percentage:
value: 5.0 # 5% requests get HTTP 503
httpStatus: 503
route:
- destination:
host: payment-service
subset: v1
PART 5: TRAFFIC MIRRORING (SHADOW TESTING)
# Mirror production traffic to new version:
apiVersion: networking.istio.io/v1
kind: VirtualService
metadata:
name: order-service
namespace: default
spec:
hosts:
- order-service
http:
- route:
- destination:
host: order-service
subset: v1
weight: 100 # 100% traffic to v1
mirror:
host: order-service
subset: v2 # Mirror copy to v2
mirrorPercentage:
value: 100.0 # Mirror 100% traffic
# → v2 receives copy, responses are discarded
# → Test v2 with real traffic, zero risk!
PART 6: RATE LIMITING
# Rate limiting với Istio (EnvoyFilter):
apiVersion: networking.istio.io/v1alpha3
kind: EnvoyFilter
metadata:
name: rate-limit-filter
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: type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
value:
stat_prefix: http_local_rate_limiter
token_bucket:
max_tokens: 100
tokens_per_fill: 100
fill_interval: 60s # 100 requests/minute
filter_enabled:
runtime_key: local_rate_limit_enabled
default_value:
numerator: 100
denominator: HUNDRED
filter_enforced:
runtime_key: local_rate_limit_enforced
default_value:
numerator: 100
denominator: HUNDRED
response_headers_to_add:
- append_action: OVERWRITE_IF_EXISTS_OR_ADD
header:
key: x-local-rate-limit
value: "true"
💡 KEY TAKEAWAYS
- VirtualService: Routing rules — WHERE traffic goes
- DestinationRule: Policies — HOW traffic is handled (LB, circuit breaker)
- Canary: weight-based traffic splitting, gradual rollout
- Circuit breaker: outlierDetection ejects unhealthy pods
- Fault injection: Test resilience with delays and errors
- Traffic mirroring: Shadow test new versions with real traffic
🎯 EXERCISES__HTMLTAG_138___
Exercise 1: Canary Deployment
- Deploy v1 and v2 of a service__HTMLTAG_143___
- Configure 90/10 traffic split
- Monitor error rate in Kiali
- Gradually shift to 0/100
Exercise 2: Circuit Breaking__HTMLTAG_152___
- Configure outlier detection (3 errors → eject)
- Use Fortio to load test__HTMLTAG_157___
- Observe ejection/recovery in Envoy admin
📚 NEXT POST
In Lesson 26: Istio Gateway and Ingress for Production, we will configure external access, TLS termination, and multi-domain hosting.