K8s之Service学习
Service主要用于提供网络服务,通过Service的定义,能够为客户端应用提供稳定的访问地址(域名或IP地址)和负载均衡功能,以及屏蔽后端Endpoint的变化,是Kubernetes实现微服务的核心资源。1 Service基础1.1 案例一个提供Web服务的Pod集合,由三个Tomcat容器副本组成,每个容器提供的服务端口号都为8081:apiVersion: apps/v1kind: De
Service主要用于提供网络服务,通过Service的定义,能够为客户端应用提供稳定的访问地址(域名或IP地址)和负载均衡功能,以及屏蔽后端Endpoint的变化,是Kubernetes实现微服务的核心资源。
1 Service基础
1.1 从案例认识service
一个提供Web服务的Pod集合,由三个Tomcat容器副本组成,每个容器提供的服务端口号都为8081:
apiVersion: apps/v1
kind: Deployment
metadata:
name: webapp
spec:
selector :
matchLabels:
app: webapp
replicas: 3
template:
metadata:
labels:
app: webapp
spec:
containers:
- name: webapp
image: tomcat
ports:
- containerPort: 8081
kubectl apply -f tomcat.yaml -n [namespace]
客户端应用可以直接通过这些Pod的IP地址和端口号8081访问Web服务。
现在将service加进来,使用如下命令创建service
kubectl expose deployment webapp -n [namespace]
kubectl get service -n [namespace]
查看新创建的Service,可以看到系统为它分配了一个虚拟IP地址(ClusterIP地址),Service的端口号则从Pod中的containerPort复制而来。接下来就可以通过Service的IP地址和Service的端口号访问该Service,访问被自动负载分发到了后端三个Pod之一。
当然也可以使用过yaml文件创建service
apiVersion: v1
kind: Service
metadata:
name: webapp
spec:
selector :
app: webapp
ports:
- protocol: TCP
port: 8081
targetPort: 8081
一个Service对应的“后端”由Pod的IP和容器端口号组成,即一个完整的“IP:Port”访问地址,这在Kubernetes系统中叫作Endpoint。
1.2 负载均衡机制
从服务IP到后端Pod的负载均衡机制,则是由每个Node上的kube-proxy负责实现的。
1)kube-proxy的代理模式:
userspace模式:用户空间模式,由kube-proxy完成代理的实现,效率最低,不再推荐使用。
iptables模式:kube-proxy通过设置Linux Kernel的iptables规则,实现从Service到后端Endpoint列表的负载分发规则,效率很高。但是,如果某个后端Endpoint在转发时不可用,此次客户端请求就会得到失败的响应,相对于userspace模式来说更不可靠。此时应该通过
为Pod设置readinessprobe(服务可用性健康检查)来保证只有达到ready状态的Endpoint才会被设置为Service的后端Endpoint。
ipvs模式:kube-proxy通过设置Linux Kernel的netlink接口设置IPVS规则,转发效率和
支持的吞吐率都是最高的。详细介绍:
Kubernetes从1.8开始增加了IPVS支持,IPVS相对于iptables来说效率更高,使用ipvs需要在允许proxy节点上安装ipvsadm,ipset工具包加载ipvs内核。并且ipvs可以轻松处理每秒10万次转发请求。
当proxy启动的时候,proxy将验证节点是否安装ipvs模块,如果没有安装将退回iptables模式IPVS模式也是基于Netfilter,支持更复杂的复杂均衡算法(最小复杂、最少连接、加权等),支持Service的健康检查和连接重试功能。
IPVS依赖于iptables,使用iptables进行包过滤,SNAT,masuared。
IPVS将使用ipset来存储需要DROP或MASQUARED的流量源地址和目标地址,这样可以保证iptables规则数量固定,不需要关心集群中有多少Service。
2)会话保持机制
保证同一个外部IP一直访问同一个后端pod,同时,用户可以设置会话保持的最长时间
apiVersion: v1
kind: Service
metadata:
name: webapp
spec:
sessionAffinity:ClientIP
sessionAffinityConfig:
clientIP:
timeoutSeconds:1000s
selector:
app: webapp
ports:
- protocol: TCP
port: 8081
targetPort: 8081
1.3 多端口服务
Service可以设置多个端口号来分别提供不同的服务:
apiVersion: v1
kind: Service
metadata:
name: webapp
spec:
selector :
app: webapp
ports:
-port: 8081
targetPort: 8081
name:web
-port:8082
targetPort: 8082
name:management
或者同一个端口号使用的协议不同,如TCP和UDP,也可以为多个端口号来提供不同的服务
1.4 定义外部服务
普通的Service通过Label Selector对后端Endpoint列表进行了一次抽象,如果后端的Endpoint不是由Pod副本集提供的,则Service还可以抽象定义任意其他服务。
用户在创建Service资源对象时不设置Label Selector(后端Pod也不存在),同时再定义一个与Service关联的Endpoint资源对象,在Endpoint中设置外部服务的IP地址和端口号
1.5 将service暴露出去
Kubernetes为Service创建的ClusterIP地址是对后端Pod列表的一层抽象,对于集群外部来说并没有意义,但有许多Service是需要对集群外部提供服务的,Kubernetes提供了多种机制将Service暴露出去,供集群外部的客户端访问。可以通过Service资源对象的类型字段“type”进行设置:
ClusterIP:Kubernetes默认会自动设置Service的虚拟IP地址,仅可被集群内部的客户端应用访问。
NodePort:将Service的端口号映射到每个Node的一个端口号上,这样集群中的任意Node都可以作为Service的访问入口地址,即NodeIP:NodePort。
LoadBalancer:将Service映射到一个已存在的负载均衡器的IP地址上,通常在公有云环境中使用。
ExternalName:将Service映射为一个外部域名地址,通过externalName字段进行设置。
apiVersion: v1
kind: Service
metadata:
name: webapp
spec:
tyoe:NodePort
selector:
app: webapp
ports:
-port: 8081
targetPort: 8081
nodePort:8081
2 DNS服务
作为服务发现机制的基本功能,在集群内需要能够通过服务名对服务进行访问,这就需要一个集群范围内的DNS服务来完成从服务名到ClusterIP地址的解析。DNS服务在Kubernetes的发展过程中经历了3个阶段:
附录:
Service的YAML格式文件定义
各属性的说明如下表:
更多推荐
所有评论(0)