如何监控Kubernetes API服务器


【编者的话】本文讨论了Kubernetes API服务器监控的重要性和相关方法。

在生产环境中运行Kubernetes时,学习如何监控Kubernetes API服务器是至关重要的。监视kube-apiserver能使你检测和排除延迟、错误,并验证服务是否按预期执行。继续阅读可以了解如何从kube-apiserver收集最重要的指标,并用它们来监视该服务。

Kubernetes API服务器是Kubernetes控制面板的基础组件。集群中运行的所有服务都使用这个接口进行通信。整个用户交互也通过API处理:kubectl是一个向API发送请求的包装工具。kubectl使用HTTP连接API服务器,而其余的控制面板组件使用gRPC通信。我们应该准备好监控这两个渠道。
1.png

与其他微服务一样,我们将采用黄金指标方法来监视Kubernetes API服务器的健康状况和性能:
  • 延迟
  • 通讯量
  • 错误
  • 饱和度


但在深入研究每个指标的含义之前,让我们先看看如何获取这些指标。

获取用于监视kube-apiserver的指标

API服务器已经被测量过,默认情况下它展示在Prometheus指标中,提供诸如延迟、请求、错误和etcd缓存状态等监控指标。这些信息节点可以轻松地获取到,从而获得有用的信息,而不需要额外的脚本或导出程序。

API服务器需要身份验证才能向/metrics节点发出请求,因此你需要为此获得具有特权的凭据。如果你在集群中运行Prometheus,我们可以使用绑定到ClusterRole的服务帐户进行身份验证,允许GET请求查询/metrics节点。

这可以使用Prometheus向ClusterRole添加一条规则来实现:
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
labels:
app: monitor
component: server
name: monitor
rules:
- nonResourceURLs:
- /metrics
verbs:
- get

通过这种方式,我们可以使用服务帐户中的不记名的令牌访问/metrics节点,该令牌位于/var/run/secrets/kubernet.io/serviceaccount中的Pod中。

我们可以在Prometheus Pod中执行这个shell命令来测试身份验证:
#curl  https://kubernetes.default.svc/metrics -H "Authorization: Bearer $(cat /var/run/secrets/kubernetes.io/serviceaccount/token)"
--cacert /var/run/secrets/kubernetes.io/serviceaccount/ca.crt

它将返回一长串Prometheus指标(这里有截断):
# TYPE APIServiceOpenAPIAggregationControllerQueue1_adds counter
APIServiceOpenAPIAggregationControllerQueue1_adds 108089
# HELP APIServiceOpenAPIAggregationControllerQueue1_depth Current depth of workqueue: APIServiceOpenAPIAggregationControllerQueue1
# TYPE APIServiceOpenAPIAggregationControllerQueue1_depth gauge
APIServiceOpenAPIAggregationControllerQueue1_depth 0
# HELP APIServiceOpenAPIAggregationControllerQueue1_queue_latency How long an item stays in workqueueAPIServiceOpenAPIAggregationControllerQueue1 before being requested.
# TYPE APIServiceOpenAPIAggregationControllerQueue1_queue_latency summary
APIServiceOpenAPIAggregationControllerQueue1_queue_latency{quantile="0.5"} 15
...

通过添加一个job到你的targets,配置Prometheus就可以抓取Kubernetes API服务器节点信息:
- job_name: 'kubernetes-apiservers'
kubernetes_sd_configs:
  - role: endpoints
scheme: https 
tls_config:
  ca_file: /var/run/secrets/kubernetes.io/serviceaccount/ca.crt
bearer_token_file: /var/run/secrets/kubernetes.io/serviceaccount/token
relabel_configs:
  - source_labels: [__meta_kubernetes_namespace, __meta_kubernetes_service_name, __meta_kubernetes_endpoint_port_name]
    action: keep
    regex: default;kubernetes;https

监视Kubernetes API服务器:要找什么?

我们可以使用黄金指标来监视Kubernetes API服务器。Golden Signals是一种技术,用于通过一些指标来监视服务,可以洞察服务如何为消费者执行(这里是kubectl用户和内部集群组件)。这些指标是延迟、通信量、错误和饱和度(服务器使用当前资源时达到最大容量的繁忙程度)。


免责声明:不同Kubernetes版本的API服务器指标可能不同。这里我们使用的是Kubernetes 1.15。你可以在Kubernetes repo(1.15.3版本的链接)中查看您的版本的可用指标。
延迟:可以从apiserver_request_duration_seconds直方图中提取延迟:
# TYPE apiserver_request_latencies histogram apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="125000"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="250000"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="500000"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="1e+06"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="2e+06"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="4e+06"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="8e+06"} 2 apiserver_request_duration_seconds{resource="adapters",scope="cluster",subresource="",verb="LIST",le="+Inf"} 2 apiserver_request_duration_seconds_sum{resource="adapters",scope="cluster",subresource="",verb="LIST"} 50270 apiserver_request_duration_seconds_count{resource="adapters",scope="cluster",subresource="",verb="LIST"} 2

使用百分位数来理解延迟传播是个好主意:
histogram_quantile(0.99, sum(rate(apiserver_request_latencies_count{job="kubernetes-apiservers"}[5m])) by (verb, le))

请求率:可以使用apiserver_request_total指标来监视对服务的请求、来自何处、到哪个服务、哪个操作以及是否成功:
# TYPE apiserver_request_count counter apiserver_request_total{client="Go-http-client/1.1",code="0",contentType="",resource="pods",scope="namespace",subresource="portforward",verb="CONNECT"} 4 apiserver_request_total{client="Go-http-client/2.0",code="200",contentType="application/json",resource="alertmanagers",scope="cluster",subresource="",verb="LIST"} 1 apiserver_request_total{client="Go-http-client/2.0",code="200",contentType="application/json",resource="alertmanagers",scope="cluster",subresource="",verb="WATCH"} 72082 apiserver_request_total{client="Go-http-client/2.0",code="200",contentType="appli

例如,你可以像这样获得所有成功的请求:
sum(rate(apiserver_request_total{job="kubernetes-apiservers",code=~"2.."}[5m]))

错误:你可以使用相同的查询请求率,并过滤400和500错误代码:
sum(rate(apiserver_request_total{job="kubernetes-apiservers",code=~"[45].."}[5m]))

饱和度:我们可以通过CPU、内存和网络I/O等系统资源消耗指标来监测饱和度。

除了API服务器相关指标外,我们还可以获得其他相关指标。API服务器提供:

  • controller-manager:
    • 工作队列添加率:我们通过控制器调度新操作执行的速度。这些操作可以包括集群中任何资源的添加、删除和修改(工作负载、配置映射表、服务……)。
    • 工作队列延迟:控制器-管理器执行这些操作有多快?
    • 工作队列深度:有多少动作等待执行?

  • etcd:
    • etcd缓存项:缓存了多少查询结果?
    • etcd缓存命中率/失误率:缓存有用吗?
    • etcd缓存持续时间:缓存结果存储多长时间?


问题示例

检测到对API的请求的延迟有增加

这通常是API服务器过载的标志。可能你的集群有很多负载,需要扩展API服务器。

你可以根据请求类型、资源或动词来划分指标。通过这种方式,您可以检测问题在哪里。也许你在etcd的读写上有问题,需要解决。

检测到工作队列的深度和延迟的增加

在调度操作时遇到问题。你应该检查调度程序是否工作。可能你的一些节点超载了,需要扩展集群。可能有一个节点有问题,需要替换它。

在Sysdig Monitor中监视Kubernetes API服务器指标

如果你想使用Sysdig monitor来监控Kubernetes API服务器,你只需要向Sysdig代理yaml配置文件中添加几个部分:
#Enable prometheus metrics
metrics_filter:
# beginning of kube-apiserver
- include: "apiserver_request_total"
- include: "apiserver_request_duration_seconds*"
- include: "workqueue_adds_total"
- include: "workqueue_depth"
- include: "workqueue_queue_duration_seconds*"
- include: "etcd_helper_cache_entry_total"
- include: "etcd_helper_cache_hit_total"
- include: "etcd_helper_cache_miss_total"
- include: "etcd_request_cache_get_duration_seconds*"
- include: "etcd_request_cache_add_duration_seconds*"
- include: "go_goroutines"
# end of kube-apiserver
prometheus:
enabled: true
histograms: true
max_metrics: 3000
max_metrics_per_process: 3000
process_filter:
  - include:
      kubernetes.pod.label.k8s-app: kube-apiserver
      port: 8080
      conf:
        tags:
          kubernetes.component.name: kube-apiserver
        host: 127.0.0.1
        port: 8080
        use_https: false
        auth_token_path: "/var/run/secrets/kubernetes.io/serviceaccount/token"

使用metrics_filter部分,可以确保在达到指标限制时不会丢弃这些指标。你可以添加API服务器提供的任何不在这个列表中的其他指标,如下所示:
metrics_filter:
- include: "apiserver_request_total"
...
- include: "go_goroutines"

然后,配置Sysdig代理将如何收集指标,搜索带有kube-apiserver标签的Kubernetes Pod,并通过端口8080在本地主机中收集数据。由于Sysdig代理能够切换网络上下文并像在本地主机上那样连接到Pod,所以我们不需要使用https。还必须指定代理使用的身份验证令牌来访问metrics节点:
prometheus:
enabled: true
...
process_filter:
  - include:
      kubernetes.pod.label.k8s-app: kube-apiserver
      port: 8080
      conf:
        tags:
          kubernetes.component.name: kube-apiserver
        host: 127.0.0.1
        port: 8080
        use_https: false
        auth_token_path: "/var/run/secrets/kubernetes.io/serviceaccount/token"

然后可以使用这些指标构建自定义仪表面板。我们有一些预置的仪表面板,如果你有兴趣,我们可以与你分享。
2.png

结论

监视Kubernetes API服务器是基础,因为它是集群操作中的关键部分。请记住,集群组件之间的所有通信都是通过kube-apiserver完成的。

检测API服务器中的问题可能是修复Kubernetes集群中的问题的关键因素。你应该了解控制面板中服务组件正在发生的事情,并学会以后出现这个问题后怎么处理对自己有利。

对所有Kubernetes组件进行完善的监视与监视在集群中运行的工作负载和应用程序同样重要。不要忘记监控你的控制面板!

原文链接:How to Monitor Kubernetes API Server(译者:姜俊厚)

0 个评论

要回复文章请先登录注册