kubernetes中部署DNS


声明:本文转载自https://my.oschina.net/blueyuquan/blog/1587301,转载目的在于传递更多信息,仅供学习交流之用。如有侵权行为,请联系我,我会及时删除。

  • 先吐槽一下,最近研究k8s的dns,看了很多相关博客,发现很多都是一样的内容,大部分都是转载或者copy,也不验证一下就发出来,给我无形中挖了很多坑。再次先谴责一下这些人!

  • 开始正题!

  • 使用场景:ubuntu16.04, kubernetes1.4及以上, 集群没有搭建CA等认证!其他场景仅作参考!

1.为什么要部署DNS

kubernetes 提供了 service 的概念可以通过 VIP(Service IP 是 virtual IP(VIP)) 访问 pod 提供的服务,但是在使用的时候还有一个问题:怎么知道某个应用的 VIP?比如我们有两个应用,一个 app,一个 是 db,每个应用使用 rc或deployment进行管理,并通过 service 暴露出端口提供服务。app 需要连接到 db 应用,我们只知道 db 应用的名称,但是并不知道它的 VIP 地址。这就涉及到了==服务发现==的问题了。

  • 针对以上问题,k8s提供了三种==服务发现==的方法:

方法1.通过kubernetes 提供的 API 查询

该方法较为简单,但问题较多。首先每个应用都要在启动的时候编写查询依赖服务的逻辑,这本身就是重复和增加应用的复杂度;其次这也导致应用需要依赖 kubernetes,不能够单独部署和运行(当然如果通过增加配置选项也是可以做到的,但这又是增加复杂度)。

方法2.环境变量

K8S默认支持,这一方法是参照docker的。每个 pod 启动时候,k8s会将之前存在的所有服务的 IP 和 port 信息通过环境变量的形式写入到新启动的pod中,这样 pod中的应用可以通过读取环境变量来获取依赖服务的地址信息。但是有个很大的问题:依赖的服务必须在 pod 启动之前就存在,不然就不会出现在环境变量中。

方法3.DNS(最理想的方案)

应用只需要知道服务的具体名字,不需要关心服务的实际的 ip 地址,中间的==服务名--IP==转换由DNS自动完成。名字和 ip 之间的转换就是 DNS 系统的功能。

2.DNS 版本介绍

DNS 服务不是独立的系统服务,而是一种 ==addon== ,作为==插件==来安装的,不是 kubernetes 集群必须的(==但是非常推荐安装==)。可以把它看做运行在集群上的应用,只不过这个应用比较特殊而已。 目前常用的DNS配置方式有两种,在 1.3 之前使用 etcd + kube2sky + skydns + exechealthz的方式,在 1.3 之后可以使用 kubedns + dnsmasq +sidecar 的方式。

下面对这些组件功能进行介绍

  • 1.3版本前
  1. etcd: DNS存储
  2. kube2sky: 通过K8S API监视Service资源的变化,将service注册到etcd
  3. skydns: 提供DNS域名解析服务,为集群中的Pod提供DNS查询服务
  4. exechealthz: 提供对skydns服务的健康检查功能

架构图

输入图片说明

  • 1.3版本后
  1. kubedns: 通过K8S API监视Service资源的变化,并使用树形结构在内存中保存DNS记录
  2. dnsmasq: 提供DNS域名解析服务,为集群中的Pod提供DNS查询服务
  3. exechealthz: 提供对kubedns和dnsmasq两个服务的健康检查功能,更加完善

架构图

输入图片说明

从中可以看出kubedns替代了 etcd和 kube2sky这两个功能,为dnsmasq提供查询服务,使用树形结构在内存中保存DNS记录

dnsmasq在kube-dns插件中的作用: 通过kubedns容器获取DNS规则,在集群中提供DNS查询服务 提供DNS缓存,提高查询性能 降低kubedns容器的压力、提高稳定性

3.搭建DNS

网上有很多搭建的教程,本人一一尝试!发现都没成功!很尴尬!可能是因为k8s版本不同或k8s集群搭建方式不同,又或者是引入了ServiceAccount 、token和认证等模块。此处就不详细介绍。 通过本人不懈努力(请允许我装个B..),终于实现了一个精简版DNS方案:kubedns + dnsmasq + exechealthz,具体的yaml文件可点击这里查看。

废话不多说,直接上内容!

dns-rc.yaml

apiVersion: v1 kind: ReplicationController metadata:   name: kube-dns-v15   namespace: kube-system   labels:     k8s-app: kube-dns     version: v15     kubernetes.io/cluster-service: "true" spec:   replicas: 1   selector:     k8s-app: kube-dns     version: v15   template:     metadata:       labels:         k8s-app: kube-dns         version: v15         kubernetes.io/cluster-service: "true"     spec:       containers:       - name: kubedns         image: registry.cn-hangzhou.aliyuncs.com/sjq-k8s/kubedns-amd64:1.5         resources:           # TODO: Set memory limits when we've profiled the container for large           # clusters, then set request = limit to keep this container in           # guaranteed class. Currently, this container falls into the           # "burstable" category so the kubelet doesn't backoff from restarting it.           limits:             cpu: 100m             memory: 200Mi           requests:             cpu: 100m             memory: 100Mi         livenessProbe:           httpGet:             path: /healthz             port: 8080             scheme: HTTP           initialDelaySeconds: 60           timeoutSeconds: 5           successThreshold: 1           failureThreshold: 5         readinessProbe:           httpGet:             path: /readiness             port: 8081             scheme: HTTP           # we poll on pod startup for the Kubernetes master service and           # only setup the /readiness HTTP server once that's available.           initialDelaySeconds: 30           timeoutSeconds: 5         args:         # command = "/kube-dns"         - --kube_master_url=http://192.168.122.10:8080         - --domain=cluster.local.         - --dns-port=10053         ports:         - containerPort: 10053           name: dns-local           protocol: UDP         - containerPort: 10053           name: dns-tcp-local           protocol: TCP       - name: dnsmasq         image: registry.cn-hangzhou.aliyuncs.com/sjq-k8s/dnsmasq:1.1         args:         - --cache-size=1000         - --no-resolv         - --server=127.0.0.1#10053         ports:         - containerPort: 53           name: dns           protocol: UDP         - containerPort: 53           name: dns-tcp           protocol: TCP       - name: healthz         image: registry.cn-hangzhou.aliyuncs.com/sjq-k8s/exechealthz-amd64:1.0         resources:           # keep request = limit to keep this container in guaranteed class           limits:             cpu: 10m             memory: 20Mi           requests:             cpu: 10m             memory: 20Mi         args:         - -cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1 >/dev/null         - -port=8080         ports:         - containerPort: 8080           protocol: TCP       dnsPolicy: Default  # Don't use cluster DNS. 

其中的镜像由于被墙,所以直接被我替换成了本人阿里云上的镜像,可以直接下载使用, 其中- --kube_master_url=http://192.168.122.10:8080 中的IP记得换成自己的master ip和port

dns-svc.yaml

apiVersion: v1 kind: Service metadata:   name: kube-dns   namespace: kube-system   labels:     k8s-app: kube-dns     kubernetes.io/cluster-service: "true"     kubernetes.io/name: "KubeDNS" spec:   selector:     k8s-app: kube-dns   clusterIP: 192.168.3.10    ports:   - name: dns     port: 53     protocol: UDP   - name: dns-tcp     port: 53     protocol: TCP 

其中将clusterIP: 192.168.3.10 中的ip换成你实际定义的dns集群ip。

创建rc和service

$ kubectl create -f skydns-rc.yaml  replicationcontroller "kube-dns-v15" created $ kubectl create -f skydns-svc.yaml  service "kube-dns" created 

查看是否running

$ kubectl get pod -n kube-system NAME                                   READY     STATUS    RESTARTS   AGE kube-dns-v15-32902                     3/3       Running   0          2m $ $ kubectl get svc -n kube-system NAME                   CLUSTER-IP      EXTERNAL-IP   PORT(S)         AGE kube-dns               192.168.3.10    <none>        53/UDP,53/TCP   7m 

4.验证dns是否有效

通过启动一个带有nslookup工具的busybox来验证DNS服务是否能够正常工作:

busybox.yaml

apiVersion: v1 kind: Pod metadata:   name: busybox   namespace: default spec:   containers:   - image: busybox     command:       - sleep       - "3600"     imagePullPolicy: IfNotPresent     name: busybox   restartPolicy: Always 

启动

$ kubectl create -f busybox.yaml  pod "busybox" created 

pod成功运行后,通过kubectl exec <容器Id> nslookup进行测试

kubectl exec busybox -- nslookup kubernetes Server:    192.168.3.10 Address 1: 192.168.3.10 kube-dns.kube-system.svc.cluster.local  Name:      kubernetes Address 1: 192.168.3.1 kubernetes.default.svc.cluster.local  

成功!

如果测试的服务的命名空间不是default,那么一定要加上命名空间,不然会报下面的错误

$ kubectl exec busybox -- nslookup kube-dns nslookup: can't resolve 'kube-dns' Server:    192.168.3.10 Address 1: 192.168.3.10 kube-dns.kube-system.svc.cluster.local 

加上命名空间后

$ kubectl exec busybox -- nslookup kube-dns.kube-system Server:    192.168.3.10 Address 1: 192.168.3.10 kube-dns.kube-system.svc.cluster.local  Name:      kube-dns.kube-system Address 1: 192.168.3.10 kube-dns.kube-system.svc.cluster.local 

5.实际搭建截图

创建成功图

创建成功图

验证成功图

验证成功图

可能的问题

可能的问题

声明!以上内容纯属个人原创!转载请标注出处,谢谢!

如果本文有帮助到你,希望能动动小手点个赞。 如有错误请多指正!如有雷同!纯属巧合!

本文发表于2017年12月10日 10:33
(c)注:本文转载自https://my.oschina.net/blueyuquan/blog/1587301,转载目的在于传递更多信息,并不代表本网赞同其观点和对其真实性负责。如有侵权行为,请联系我们,我们会及时删除.

阅读 1923 讨论 0 喜欢 0

抢先体验

扫码体验
趣味小程序
文字表情生成器

闪念胶囊

你要过得好哇,这样我才能恨你啊,你要是过得不好,我都不知道该恨你还是拥抱你啊。

直抵黄龙府,与诸君痛饮尔。

那时陪伴我的人啊,你们如今在何方。

不出意外的话,我们再也不会见了,祝你前程似锦。

这世界真好,吃野东西也要留出这条命来看看

快捷链接
网站地图
提交友链
Copyright © 2016 - 2021 Cion.
All Rights Reserved.
京ICP备2021004668号-1