我们已经把应用进行了拆分,并按照微服务的模式开发并部署到了 istio。
如何实现那些微服务治理的高级功能?现在就是见证奇迹的时候了。
弹性伸缩
isito 的弹性功能是由 K8S 实现的。此部分和 K8S 一样。
1、修改 yaml 的 Deployment 的 replicas 参数。
kind: Deployment
...
spec:
replicas: 1 # 实例数量
...
2、伸缩到指定数量:
kubectl scale --replicas=3 rs/foo1234
kubectl scale --replicas=3 deployment foo
3、自动伸缩
首先在 deploy 中指定部署的资源:
...
resources:
limits:
cpu: 500m
memory: 1Gi
requests:
cpu: 250m
memory: 256Mi
...
通过如下命令行,可以指定当 CPU 利用率达到阈值 60% 时便自动伸缩。
kubectl autoscale deployment foo --cpu-percent=60 --min=2 --max=10
也可以通过 yaml 指定更详细的水平自动伸缩策略。
apiVersion: autoscaling/v2beta2
kind: HorizontalPodAutoscaler
metadata:
name: php-apache
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: php-apache
minReplicas: 1
maxReplicas: 10
metrics:
- type: Resource
resource:
name: cpu
target:
type: Utilization
averageUtilization: 60
status:
observedGeneration: 1
lastScaleTime: <some-time>
currentReplicas: 1
desiredReplicas: 10
currentMetrics:
- type: Resource
resource:
name: cpu
current:
averageUtilization: 0
averageValue: 0
- type: Object
object:
metric:
name: requests-per-second
describedObject:
apiVersion: networking.k8s.io/v1beta1
kind: Ingress
name: main-route
current:
value: 10k
负载均衡
服务间的负载均衡策略在 DestinationRule 中指定。
一个简单的LB配置:
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
name: passport
spec:
host: passport
trafficPolicy:
loadBalancer:
simple: ROUND_ROBIN
负载均衡策略可选项:
ROUND_ROBIN,LEAST_CONN,RANDOM,PASSTHROUGH
灰度
下面的例子将 30% 的流量转发到了新开发上线的版本为 v2 的应用。
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: passport
namespace: xyz
spec:
hosts:
- passport
http:
- route:
- destination:
host: passport
subset: v1
weight: 70
- destination:
host: passport
subset: v2
weight: 30
下面的例子将 header 中 area=north 的流量进行了重新定义。
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: xyzdemo-product-service-route
namespace: xyz
spec:
hosts:
- xyzdemo-product-service
http:
- match:
- headers:
area:
exact: north
route:
- destination:
host: xyzdemo-product-service
subset: v1
weight: 70
- destination:
host: xyzdemo-product-service
subset: v2
weight: 30
限流熔断
熔断限流是微服务必须面对的问题。
在 istio 中,通过 connectionPool 节点来定义限流指标。
使用 outlierDetection 来定义熔断策略。
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
name: httpbin
spec:
host: httpbin
trafficPolicy:
connectionPool:
tcp:
maxConnections: 1
http:
http1MaxPendingRequests: 1
maxRequestsPerConnection: 1
outlierDetection:
consecutiveErrors: 1
interval: 1s
baseEjectionTime: 3m
maxEjectionPercent: 100
connectionPool 可以指定如下指标
HTTP
配置名 |
解释 |
---|---|
http1MaxPendingRequests |
http1.1的最大挂起数量,即请求的堆积数量。 |
http2MaxRequests |
http2 后台的最大请求数量 |
maxRequestsPerConnection |
每个连接的最大请求数 |
maxRetries |
最大重试数量 |
idleTimeout |
闲置超时时间,如果没有访问,连接关闭,默认是1小时 |
h2UpgradePolicy |
http1.1 升到 http2 的策略,可以指定升级还是不升 |
TCP
配置名 |
解释 |
---|---|
maxConnections |
最大连接数 |
connectTimeout |
TCP 超时时间 |
tcpKeepalive |
tcp 活跃指标,包含检查次数(probes),检查时间间隔(interval),活动时间间隔(time) |
tcpKeepalive 意思是,每隔 time 时间会发起一次检查,这次检查一共会发起 probes 次,每次间隔 interval时间。
outlierDetection 策略
配置名 |
解释 |
---|---|
consecutiveErrors |
连续错误次数,达到指标剔除此节点 |
interval |
错误扫描时间间隔,在这段时间内出粗的次数如果达到 consecutiveErrors ,则剔除 |
baseEjectionTime |
最短的剔除时长,被剔除的pod在此时间内不允许服务。 |
maxEjectionPercent |
最大的剔除数量百分比。 |
minHealthPercent |
最小健康阈值,当健康pod百分比低于此值,则会把所有的pod重新加回来。 |
故障注入
为了测试我们的应用,可以通过istio 来模拟一些故障,以此来测试整个微服务体系的健壮度。
下面的配置:header 里 end-user=jason 的请求一律延迟 7 秒。
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: passport
...
spec:
hosts:
- ratings
http:
- fault:
delay:
fixedDelay: 7s
percentage:
value: 100
match:
- headers:
end-user:
exact: jason
route:
- destination:
host: passport
subset: v1
- route:
- destination:
host: passport
subset: v1
可供注册的错误类型有:
delay:指定一定的延时时间
abort:可以指定 http status 的错误响应
总结:
以上的所有脚本,都和具体的业务无关。我们再也不用在我们的业务项目中引用那些服务治理相关,让人头大的 Java SDK 了。