【问题标题】:How to avoid coredns resolving overhead in kubernetes如何避免 coredns 解决 kubernetes 中的开销
【发布时间】:2020-03-21 22:19:01
【问题描述】:

我认为标题几乎是不言自明的。我做了很多实验,可悲的是,coredns 确实为集群内的所有请求增加了20 ms 开销。起初我们认为也许通过添加更多复制,并在更多实例之间平衡解析请求,我们可以提高响应时间,但它根本没有帮助。 (我们从 2 个 pod 扩大到 4 个 pod)

在扩展到 4 个实例后,解决时间的波动得到了一些增强。但这不是我们所期望的,20 ms 开销仍然存在。

我们有一些 web 服务,它们的实际响应时间是 < 30 ms,而使用 coredns 我们将响应时间加倍,这并不酷!

在对此事得出结论后,我们做了一个实验来仔细检查这不是操作系统级别的开销。结果与我们的预期没有什么不同。

我们认为也许我们可以基于将每个 pod 所需的 hostname 映射列表放入该 pod 的 /etc/hosts 中来实施/部署一个解决方案。所以我最后的问题如下:

  • 有没有其他人经历过与coredns类似的事情?
  • 您能否建议coredns 在 k8s 环境中工作的替代解决方案?

感谢任何想法或见解。提前致谢。

【问题讨论】:

  • 您的工作负载需要集群 dns 还是只需要公共的?
  • 我们在集群内部有很多内部请求,所以我们需要有集群dns。图中显示的结果也是内部请求(在相同集群 pod 之间)@coderanger
  • 我对这个kep并不熟悉,但现在我将很快对其进行测试。感谢您的回复。

标签: kubernetes dns coredns


【解决方案1】:

在 kubernetes 集群中运行 coreDNS 时需要注意几件事

  • 内存
  • 自动路径
  • 副本数
  • 自动缩放器
  • 其他插件
  • 普罗米修斯指标
  • 单独的服务器块

内存

CoreDNS 推荐的副本内存量是

MB required (default settings) = (Pods + Services) / 1000 + 54

自动路径

Autopath 是 Coredns 中的一项功能,有助于增加外部查询的响应时间

通常会通过 DNS 查询

  1. ..svc.cluster.local
  2. .svc.cluster.local
  3. cluster.local
  4. 然后配置转发,一般是主机搜索路径(/etc/resolv.conf
Trying "example.com.default.svc.cluster.local"
Trying "example.com.svc.cluster.local"
Trying "example.com.cluster.local"
Trying "example.com"
Trying "example.com"
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 55265
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 0

;; QUESTION SECTION:
;example.com.           IN  A

;; ANSWER SECTION:
example.com.        30  IN  A   93.184.216.34

这需要更多内存,所以现在计算变成了

MB required (w/ autopath) = (Number of Pods + Services) / 250 + 56

副本数

默认为 2,但启用 Autoscaler 应该有助于解决负载问题。

自动缩放器

apiVersion: autoscaling/v1
kind: HorizontalPodAutoscaler
metadata:
  name: coredns
  namespace: default
spec:
  maxReplicas: 20
  minReplicas: 2
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: coredns
  targetCPUUtilizationPercentage: 50

节点本地缓存

Kubernetes 1.15 中的测试版

NodeLocal DNSCache 通过在集群节点上作为 DaemonSet 运行 dns 缓存代理来提高集群 DNS 性能。在当今的架构中,ClusterFirst DNS 模式下的 Pod 会访问 kube-dns serviceIP 进行 DNS 查询。这通过 kube-proxy 添加的 iptables 规则转换为 kube-dns/CoreDNS 端点。使用这种新架构,Pods 将接触到运行在同一节点上的 dns 缓存代理,从而避免 iptables DNAT 规则和连接跟踪。本地缓存代理将向 kube-dns 服务查询集群主机名的缓存未命中(默认为 cluster.local 后缀)。

https://kubernetes.io/docs/tasks/administer-cluster/nodelocaldns/

其他插件

这些也将有助于了解 CoreDNS 内部发生了什么

Error - 查询处理过程中遇到的任何错误都将打印到标准输出。

Trace - 启用请求如何通过 CoreDNS 流动的 OpenTracing

Log - 查询日志

health - CoreDNS 已启动并运行,这将返回 200 OK HTTP 状态代码

ready - 通过启用准备就绪,端口 8181 上的 HTTP 端点将在所有能够发出准备就绪信号的插件都这样做时返回 200 OK。

Ready 和 Health 应该在部署中使用

        livenessProbe:
          httpGet:
            path: /health
            port: 8080
            scheme: HTTP
          initialDelaySeconds: 60
          timeoutSeconds: 5
          successThreshold: 1
          failureThreshold: 5
        readinessProbe:
          httpGet:
            path: /ready
            port: 8181
            scheme: HTTP

普罗米修斯指标

Prometheus Plugin

coredns_health_request_duration_seconds{} - duration to process a HTTP query to the local /health endpoint. As this a local operation, it should be fast. A (large) increase in this duration indicates the CoreDNS process is having trouble keeping up with its query load.

https://github.com/coredns/deployment/blob/master/kubernetes/Scaling_CoreDNS.md

单独的服务器块

最后一点建议是将集群 DNS 服务器块与外部块分开

    CLUSTER_DOMAIN REVERSE_CIDRS {
        errors
        health
        kubernetes
        ready
        prometheus :9153
        loop
        reload
        loadbalance
    }

    . {
        errors
        autopath @kubernetes
        forward . UPSTREAMNAMESERVER
        cache
        loop
    }

更多关于 k8 插件和其他选项的信息在这里 https://github.com/coredns/coredns/blob/master/plugin/kubernetes/README.md

【讨论】:

  • 感谢您的回答@strongjz。我们将测试 NodeLocal DNSCache,看看它如何影响我们的响应时间。测试完您的建议后,我会尽快回复您。
猜你喜欢
  • 2020-11-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-01-09
  • 2012-11-19
  • 2018-04-20
  • 1970-01-01
  • 2019-06-25
相关资源
最近更新 更多