11、Kubernetes核心技术 - Service

news2024/11/27 9:43:58

目录

一、概述

二、Endpoint

三、Service资源清单

四、Service 类型

4.1、ClusterIP

4.2、NodePort

4.3、LoadBalancer

4.4、ExternalName

五、Service使用

5.1、ClusterIP

5.1.1、定义Pod资源清单

5.1.2、创建Pod

5.1.3、定义Service资源清单

5.1.4、创建Service

5.2、NodePort

5.2.1、集群内通过ClusterIP+虚端口访问

5.2.2、集群外通过NodeIP+nodePort端口访问

5.2.3、集群内通过Pod IP + 虚端口访问

5.3、ExternalName

六、Service代理模式

6.1、userspace 代理模式

6.2、iptables 代理模式

6.3、IPVS 代理模式

6.3.1、加载ipvs相关内核模块 

6.3.2、编辑配置文件

6.3.3、删除原有的kube-proxy代理 

6.3.4、查看IPVS

七、HeadLiness services

7.1、创建Pod

7.2、创建Service

7.3、进入容器,查看服务域名 


一、概述

在k8s中,Pod是应用程序的载体,我们可以通过Pod的IP地址来访问应用程序,但是当Pod宕机后重建后,其IP地址等状态信息可能会变动,也就是说Pod的IP地址不是固定的,这也就意味着不方便直接采用Pod的IP地址对服务进行访问。

为了解决这个问题,k8s提供了Service资源,Service会对提供同一个服务的多个Pod进行聚合,并且提供一个统一的入口地址,通过访问Service的入口地址就能访问到后面的Pod服务 ,并且将请求负载分发到后端的各个容器应用上 。

Service引入主要是解决Pod的动态变化,提供统一的访问入口

  • 1、防止Pod失联,准备找到提供同一服务的Pod(服务发现)
  • 2、定义一组Pod的访问策略(负载均衡)

Service通常是通过Label Selector访问一组Pod,如下图:

其实 Service 只是一个概念,真正起到转发数据的是 kube-proxy 服务进程,kube-proxy 是集群中每个节点上运行的网络代理,每个节点之上都运行一个 kube-proxy 服务进程。当创建 Service 的时候,首先API Server向 etcd 写入 Service 的信息,然后kube-proxy会监听API Server,监听到etcd中 Service 的信息,然后根据Service的信息生成对应的访问规则。

二、Endpoint

Endpoint是kubernetes中的一个资源对象,存储在etcd中,用来记录一个Service对应的所有Pod的访问地址,它是根据Service配置文件中的label selector(标签选择器)生成的。

一个Service由一组Pod组成,这些Pod通过Endpoints暴露出来,Endpoints是实现实际服务的端点集合。换言之,Service和Pod之间的联系是通过Endpoints实现的。

当我们创建Service的时候,如果Service有指定Label Selector(标签选择器)的话,Endpoints控制器会自动创建一个名称跟Service名称一致的Endpoint对象。可简单理解为,Endpoint是一个中间对象,用来存放Service与Pod的映射关系,在Endpoint中,可以看到,当前能正常提供服务的Pod以及不能正常提供的Pod。

例如:

$ kubectl get pod -o wide --show-labels
NAME                     READY   STATUS    RESTARTS   AGE   IP            NODE           NOMINATED NODE   READINESS GATES   LABELS
nginx-7f456874f4-c7224   1/1     Running   0          20m   192.168.1.3   node01         <none>           <none>            app=nginx,pod-template-hash=7f456874f4
nginx-7f456874f4-v8pnz   1/1     Running   0          20m   192.168.0.6   controlplane   <none>           <none>            app=nginx,pod-template-hash=7f456874f4

$ kubectl get svc -o wide              
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE   SELECTOR
kubernetes   ClusterIP   10.96.0.1       <none>        443/TCP   14d   <none>
nginx        ClusterIP   10.109.113.53   <none>        80/TCP    12m   app=nginx

$ kubectl get ep
NAME         ENDPOINTS                       AGE
kubernetes   172.30.1.2:6443                 14d
nginx        192.168.0.6:80,192.168.1.3:80   12m

# 查看endpoint资源清单
$ kubectl get ep nginx -o yaml
apiVersion: v1
kind: Endpoints
metadata:
  annotations:
    endpoints.kubernetes.io/last-change-trigger-time: "2023-01-06T06:33:26Z"
  creationTimestamp: "2023-01-06T06:33:27Z"
  name: nginx		# Endpoint名称,跟service的名称一样
  namespace: default
  resourceVersion: "2212"
  uid: 5c1d6639-c27a-4ab5-8832-64c9d618a209
subsets:
- addresses:		# Ready addresses表示能正常提供服务的Pod, 还有一个NotReadyAddress表示不能提供正常服务的Pod
  - ip: 192.168.0.6			# Pod的IP地址
    nodeName: controlplane		# Pod被调度到的节点
    targetRef:
      kind: Pod
      name: nginx-7f456874f4-v8pnz
      namespace: default
      uid: b248209d-a854-48e8-8162-1abd4e1b498f
  - ip: 192.168.1.3			# Pod的IP地址
    nodeName: node01			# Pod被调度到的节点
    targetRef:
      kind: Pod
      name: nginx-7f456874f4-c7224
      namespace: default
      uid: f45e4aa2-ddfd-48cd-a7d1-5bfb28d0f31f
  ports:
  - port: 80
    protocol: TCP

Service与Endpoints、Pod的关系大体如下:

三、Service资源清单

yaml 格式的 Service 定义文件 :kubectl get svc nginx -o yaml

apiVersion: v1  	 # 版本号
kind: Service  		# 资源类型,固定值Service
metadata: 	# 元数据
  creationTimestamp: "2022-12-29T08:46:28Z"
  labels:			# 自定义标签属性列表
    app: nginx  		#  标签:app=nginx
  name: nginx			# Service名称
  namespace: default			# Service所在的命名空间,默认值为default
  resourceVersion: "2527"
  uid: 1770ab42-bd33-4455-a190-5753e8eac460
spec:	
  clusterIP: 10.102.82.102		# 虚拟服务的IP地址,当spec.type=ClusterIP时,如果不指定,则系统进行自动分配,也可以手工指定。当spec.type=LoadBalancer时,则需要指定
  clusterIPs:
  - 10.102.82.102
  externalTrafficPolicy: Cluster
  internalTrafficPolicy: Cluster
  ipFamilies:
  - IPv4
  ipFamilyPolicy: SingleStack
  ports:		# Service需要暴露的端口列表
  - nodePort: 30314				# 当spec.type=NodePort时,指定映射到物理机的端口号
    port: 80			# 服务监听的端口号
    protocol: TCP			# 端口协议,支持TCP和UDP,默认值为TCP
    targetPort: 80		# 需要转发到后端Pod的端口号
  selector:			# label selector配置,将选择具有指定label标签的pod作为管理范围
    app: nginx   	#  选择具有app=nginx的pod进行管理
  sessionAffinity: None		# session亲和性,可选值为ClientIP,表示将同一个源IP地址的客户端访问请求都转发到同一个后端Pod。默认值为空【None】
  type: NodePort		#  Service的类型,指定service的访问方式,默认值为ClusterIP。取值范围:[ClusterIP、NodePort、LoadBalancer]
status:
  loadBalancer: {} 	# 当spec.type=LoadBalancer时,设置外部负载均衡器的地址,用于公有云环境

四、Service 类型

Service在k8s中有以下三种常用类型:

4.1、ClusterIP

只能在集群内部访问,默认类型,自动分配一个仅Cluster内部可以访问的虚拟IP(即VIP)。

4.2、NodePort

在每个主机节点上启用一个端口来暴露服务,可以在集群外部访问,也会分配一个稳定内部集群IP地址。

访问地址:<任意Node节点的IP地址>: NodePort端口

默认NodePort端口范围:30000-32767

4.3、LoadBalancer

与NodePort类似,在每个节点上启用一个端口来暴露服务。除此之外,Kubernetes会请求底层云平台(例如阿里云、腾讯云、AWS等)上的负载均衡器,将每个Node ([NodeIP]:[NodePort])作为后端添加进去,此模式需要外部云环境的支持,适用于公有云。

4.4、ExternalName

ExternalName Service用于引入集群外部的服务,它通过externalName属性指定一个服务的地址,然后在集群内部访问此Service就可以访问到外部的服务了。

五、Service使用

5.1、ClusterIP

5.1.1、定义Pod资源清单

vim clusterip-pod.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx
spec:
  replicas: 2
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
        - name: nginx
          image: nginx
          ports:
            - containerPort: 80
              protocol: TCP

5.1.2、创建Pod

$ kubectl apply -f clusterip-pod.yaml 
deployment.apps/nginx created

$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE   IP            NODE           NOMINATED NODE   READINESS GATES
nginx-7f456874f4-c7224   1/1     Running   0          13s   192.168.1.3   node01         <none>           <none>
nginx-7f456874f4-v8pnz   1/1     Running   0          13s   192.168.0.6   controlplane   <none>           <none>

# 任意节点发起请求
$ curl 192.168.1.3
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

# 任意节点发起请求
$ curl 192.168.0.6
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

由于pod节点都是nginx默认界面都是一样的,为了方便测试,我们进入Pod修改默认界面:

$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE     IP            NODE           NOMINATED NODE   READINESS GATES
nginx-7f456874f4-c7224   1/1     Running   0          2m39s   192.168.1.3   node01         <none>           <none>
nginx-7f456874f4-v8pnz   1/1     Running   0          2m39s   192.168.0.6   controlplane   <none>           <none>

$ kubectl exec -it nginx-7f456874f4-c7224 /bin/sh
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
# echo "hello, this request is from 192.168.1.3" > /usr/share/nginx/html/index.html
# 
# cat /usr/share/nginx/html/index.html
hello, this request is from 192.168.1.3
# exit

$ kubectl exec -it nginx-7f456874f4-v8pnz /bin/sh
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
# echo "hello, this request is from 192.168.0.6" > /usr/share/nginx/html/index.html
# cat /usr/share/nginx/html/index.html
hello, this request is from 192.168.0.6
# exit

# 发起请求
$ curl 192.168.1.3
hello, this request is from 192.168.1.3
$ curl 192.168.0.6
hello, this request is from 192.168.0.6

5.1.3、定义Service资源清单

vim clusterip-svc.yaml

apiVersion: v1
kind: Service
metadata:
  name: nginx
spec:
  selector:
    app: nginx
  type: ClusterIP
  # clusterIP: 10.109.113.53   # service IP地址 如果不写默认会生成一个
  ports:
    - port: 80		# service端口
      targetPort: 80		# 目标pod端口

5.1.4、创建Service

$ kubectl apply -f clusterip-svc.yaml 
service/nginx created

$ kubectl get svc -o wide
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE   SELECTOR
kubernetes   ClusterIP   10.96.0.1       <none>        443/TCP   14d   <none>
nginx        ClusterIP   10.109.113.53   <none>        80/TCP    15s   app=nginx

$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE   IP            NODE           NOMINATED NODE   READINESS GATES
nginx-7f456874f4-c7224   1/1     Running   0          11m   192.168.1.3   node01         <none>           <none>
nginx-7f456874f4-v8pnz   1/1     Running   0          11m   192.168.0.6   controlplane   <none>           <none>

# 查看svc的详细描述信息,注意Endpoints表示的就是后端真实的Pod服务节点
$ kubectl describe svc nginx
Name:              nginx
Namespace:         default
Labels:            <none>
Annotations:       <none>
Selector:          app=nginx
Type:              ClusterIP
IP Family Policy:  SingleStack
IP Families:       IPv4
IP:                10.109.113.53
IPs:               10.109.113.53
Port:              <unset>  80/TCP
TargetPort:        80/TCP
Endpoints:         192.168.0.6:80,192.168.1.3:80		# 后端真实的Pod服务节点【Pod的IP地址+虚端口】
Session Affinity:  None
Events:            <none>

如上,我们可以看到,分配的ClusterIP为10.109.113.53,我们可以通过ClusterIP访问:

$ curl 10.109.113.53:80
hello, this request is from 192.168.0.6

$ curl 10.109.113.53:80
hello, this request is from 192.168.1.3

可以看到,发起两次请求,请求会被负载均衡到两个不同的Pod,这就是Service提供的负载均衡功能。

5.2、NodePort

$ kubectl create deployment nginx --image=nginx

# 暴露端口,让集群外部可以访问,Service类型为NodePort
$ kubectl expose deployment nginx --port=80 --type=NodePort
service/nginx exposed

$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE     IP            NODE     NOMINATED NODE   READINESS GATES
nginx-748c667d99-5mf49   1/1     Running   0          6m13s   192.168.1.6   node01   <none>           <none>

$ kubectl get svc -o wide
NAME         TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE     SELECTOR
kubernetes   ClusterIP   10.96.0.1      <none>        443/TCP        14d     <none>
nginx        NodePort    10.98.224.65   <none>        80:31853/TCP   6m13s   app=nginx

可以看到,nginx这个service分配了一个ClusterIP为10.98.224.65,该Service的虚端口为80,K8S随机分配一个nodePort端口为31853,此时要访问nginx这个服务的话,有两种方式:

5.2.1、集群内通过ClusterIP+虚端口访问

# ClusterIP: 10.98.224.65     虚端口: 80
$ curl 10.98.224.65:80
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

5.2.2、集群外通过NodeIP+nodePort端口访问

# Node IP地址: 192.168.1.33     nodePort端口: 31853
$ curl 192.168.1.33:31853
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

5.2.3、集群内通过Pod IP + 虚端口访问

$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE   IP            NODE     NOMINATED NODE   READINESS GATES
nginx-748c667d99-5mf49   1/1     Running   0          11m   192.168.1.6   node01   <none>           <none>

$ kubectl get svc -o wide
NAME         TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE   SELECTOR
kubernetes   ClusterIP   10.96.0.1      <none>        443/TCP        14d   <none>
nginx        NodePort    10.98.224.65   <none>        80:31853/TCP   11m   app=nginx

$ kubectl get ep
NAME         ENDPOINTS         AGE
kubernetes   172.30.1.2:6443   14d
nginx        192.168.1.6:80    11m

# Pod IP地址: 192.168.1.6    虚端口: 80
$ curl 192.168.1.6:80
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

5.3、ExternalName

创建ExternalName Service:

vim externalname-service.yaml:

apiVersion: v1
kind: Service
metadata:
  name: externalname-service
spec:
  type: ExternalName 			# Service类型为ExternalName
  externalName: www.baidu.com
$ kubectl apply -f externalname-service.yaml 
service/externalname-service created

$ kubectl get svc -o wide
NAME                   TYPE           CLUSTER-IP   EXTERNAL-IP     PORT(S)   AGE   SELECTOR
externalname-service   ExternalName   <none>       www.baidu.com   <none>    7s    <none>
kubernetes             ClusterIP      10.96.0.1    <none>          443/TCP   17d   <none>

$ kubectl describe svc externalname-service
Name:              externalname-service
Namespace:         default
Labels:            <none>
Annotations:       <none>
Selector:          <none>
Type:              ExternalName
IP Families:       <none>
IP:                
IPs:               <none>
External Name:     www.baidu.com
Session Affinity:  None
Events:            <none>

# 查看DNS域名解析
controlplane $ dig @10.96.0.10 externalname-service.default.svc.cluster.local

; <<>> DiG 9.16.1-Ubuntu <<>> @10.96.0.10 externalname-service.default.svc.cluster.local
; (1 server found)
;; global options: +cmd
;; Got answer:
;; WARNING: .local is reserved for Multicast DNS
;; You are currently testing what happens when an mDNS query is leaked to DNS
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 31598
;; flags: qr aa rd; QUERY: 1, ANSWER: 4, AUTHORITY: 0, ADDITIONAL: 1
;; WARNING: recursion requested but not available

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
; COOKIE: 085781a8a4291b6d (echoed)
;; QUESTION SECTION:
;externalname-service.default.svc.cluster.local.        IN A

;; ANSWER SECTION:
externalname-service.default.svc.cluster.local. 7 IN CNAME www.baidu.com.
www.baidu.com.          7       IN      CNAME   www.a.shifen.com.
www.a.shifen.com.       7       IN      CNAME   www.wshifen.com.
www.wshifen.com.        7       IN      A       103.235.46.40

;; Query time: 4 msec
;; SERVER: 10.96.0.10#53(10.96.0.10)
;; WHEN: Mon Jan 09 09:43:29 UTC 2023
;; MSG SIZE  rcvd: 279

六、Service代理模式

6.1、userspace 代理模式

在该模式下 kube-proxy 会为每一个 Service 创建一个监听端口,发送给 Cluseter IP 请求会被 iptable 重定向给 kube-proxy 监听的端口上,其中 kube-proxy 会根据 LB 算法将请求转发到相应的pod之上。

该模式下,kube-proxy充当了一个四层负载均衡器的角色。由于kube-proxy运行在userspace中,在进行转发处理的时候会增加内核和用户空间之间的数据拷贝,虽然比较稳定,但是效率非常低下。

6.2、iptables 代理模式

iptables模式下 kube-proxy 为每一个pod创建相对应的 iptables 规则,发送给 ClusterIP 的请求会被直接发送给后端pod之上。

在该模式下 kube-proxy 不承担负载均衡器的角色,其只会负责创建相应的转发策略,该模式的优点在于较userspace模式效率更高,但是不能提供灵活的LB策略,当后端Pod不可用的时候无法进行重试。

6.3、IPVS 代理模式

IPVS模式与iptable模式类型,kube-proxy 会根据pod的变化创建相应的 IPVS转发规则,与iptalbes模式相比,IPVS模式工作在内核态,在同步代理规则时具有更好的性能,同时提高网络吞吐量为大型集群提供了更好的可扩展性,同时提供了大量的负责均衡算法。

注意:当 kube-proxy 以 IPVS 代理模式启动时,它将验证 IPVS 内核模块是否可用。 如果未检测到 IPVS 内核模块,则 kube-proxy 将退回到以 iptables 代理模式运行。

下面演示如何修改代理模式为IPVS代理模式。

6.3.1、加载ipvs相关内核模块 

modprobe ip_vs
modprobe ip_vs_rr
modprobe ip_vs_wrr
modprobe ip_vs_sh

6.3.2、编辑配置文件

实际上是修改kube-proxy对应的ConfingMap:

$ kubectl get cm -n kube-system | grep kube-proxy
NAME                                 DATA   AGE
kube-proxy                           2      14d

$ kubectl edit cm kube-proxy -n kube-system
configmap/kube-proxy edited

修改mode的值,将其修改为ipvs,如下图:

6.3.3、删除原有的kube-proxy代理 

$ kubectl get pod -A | grep kube-proxy   
NAMESPACE     NAME                                       READY   STATUS    RESTARTS   AGE
kube-system   kube-proxy-xnz4r                           1/1     Running   0          14d
kube-system   kube-proxy-zbxrb                           1/1     Running   0          14d

$ kubectl delete pod kube-proxy-xnz4r -n kube-system
pod "kube-proxy-xnz4r" deleted

$ kubectl delete pod kube-proxy-zbxrb -n kube-system
pod "kube-proxy-zbxrb" deleted

 删除完成后,k8s会自动重启kube-proxy的Pod:

$ kubectl get pod -A | grep kube-proxy     
kube-system   kube-proxy-hvnmt                           1/1     Running   0          6m35s
kube-system   kube-proxy-zp6z5                           1/1     Running   0          6m20s

6.3.4、查看IPVS

$ ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
  -> RemoteAddress:Port           Forward Weight ActiveConn InActConn
TCP  10.96.0.1:443 rr
  -> 172.30.1.2:6443              Masq    1      1          0         
TCP  10.96.0.10:53 rr
  -> 192.168.0.5:53               Masq    1      0          0         
  -> 192.168.1.2:53               Masq    1      0          0         
TCP  10.96.0.10:9153 rr
  -> 192.168.0.5:9153             Masq    1      0          0         
  -> 192.168.1.2:9153             Masq    1      0          0         
TCP  10.99.58.167:80 rr
  -> 192.168.0.6:80               Masq    1      0          0         
  -> 192.168.1.3:80               Masq    1      0          0         
UDP  10.96.0.10:53 rr
  -> 192.168.0.5:53               Masq    1      0          0         
  -> 192.168.1.2:53               Masq    1      0          0  

如上图,产生了一批转发规则。

七、HeadLiness services

在某些场景中,开发人员可能不想使用Service提供的负载均衡功能,而希望自己来控制负载均衡策略,针对这种情况,kubernetes提供了HeadLiness Service,这类Service不会分配Cluster IP,如果想要访问Service,只能通过Service的域名进行查询。

7.1、创建Pod

vim headliness-pod.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx
spec:
  replicas: 2
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
        - name: nginx
          image: nginx
          ports:
            - containerPort: 80
              protocol: TCP
$ vim headliness-pod.yaml
$ kubectl apply -f headliness-pod.yaml 
deployment.apps/nginx created

$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE   IP            NODE           NOMINATED NODE   READINESS GATES
nginx-7f456874f4-225j6   1/1     Running   0          16s   192.168.1.3   node01         <none>           <none>
nginx-7f456874f4-r7csn   1/1     Running   0          16s   192.168.0.6   controlplane   <none>           <none>

7.2、创建Service

vim headliness-service.yaml

apiVersion: v1
kind: Service
metadata:
  name: headliness-service
spec:
  selector:
    app: nginx
  clusterIP: None 	# 将clusterIP设置为None,即可创建headliness Service
  type: ClusterIP
  ports:
    - port: 80 		# Service的端口
      targetPort: 80 		# Pod的端口
$ vim headliness-service.yaml
$ kubectl get pod -o wide --show-labels
NAME                     READY   STATUS    RESTARTS   AGE    IP            NODE           NOMINATED NODE   READINESS GATES   LABELS
nginx-7f456874f4-225j6   1/1     Running   0          103s   192.168.1.3   node01         <none>           <none>            app=nginx,pod-template-hash=7f456874f4
nginx-7f456874f4-r7csn   1/1     Running   0          103s   192.168.0.6   controlplane   <none>           <none>            app=nginx,pod-template-hash=7f456874f4

controlplane $ kubectl apply -f headliness-service.yaml 
service/headliness-service created

controlplane $ kubectl get svc -o wide --show-labels
NAME                 TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)   AGE   SELECTOR    LABELS
headliness-service   ClusterIP   None         <none>        80/TCP    10s   app=nginx   <none>
kubernetes           ClusterIP   10.96.0.1    <none>        443/TCP   17d   <none>      component=apiserver,provider=kubernetes

# 查看详情
$ kubectl describe service headliness-service
Name:              headliness-service
Namespace:         default
Labels:            <none>
Annotations:       <none>
Selector:          app=nginx
Type:              ClusterIP
IP Family Policy:  SingleStack
IP Families:       IPv4
IP:                None
IPs:               None
Port:              <unset>  80/TCP
TargetPort:        80/TCP
Endpoints:         192.168.0.6:80,192.168.1.3:80			# 能提供服务的Pod
Session Affinity:  None
Events:            <none>

7.3、进入容器,查看服务域名 

# 查看Pod
$ kubectl get pod -o wide
NAME                     READY   STATUS    RESTARTS   AGE     IP            NODE           NOMINATED NODE   READINESS GATES
nginx-7f456874f4-225j6   1/1     Running   0          4m37s   192.168.1.3   node01         <none>           <none>
nginx-7f456874f4-r7csn   1/1     Running   0          4m37s   192.168.0.6   controlplane   <none>           <none>

# 进入Pod
$ kubectl exec nginx-7f456874f4-r7csn -it -- bin/bash

# 查看域名
root@nginx-7f456874f4-r7csn:/# cat /etc/resolv.conf
search default.svc.cluster.local svc.cluster.local cluster.local
nameserver 10.96.0.10
options ndots:5

# 通过Service的域名进行查询:默认访问规则service名称.名称空间.svc.cluster.local
# 在Pod内通过curl可以访问
root@nginx-7f456874f4-r7csn:/# curl headliness-service.default.svc.cluster.local
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>
root@nginx-7f456874f4-r7csn:/# exit
exit

# 查看DNS
$ apt install  bind9-utils

$ dig @10.96.0.10 headliness-service.default.svc.cluster.local

; <<>> DiG 9.16.1-Ubuntu <<>> @10.96.0.10 headliness-service.default.svc.cluster.local
; (1 server found)
;; global options: +cmd
;; Got answer:
;; WARNING: .local is reserved for Multicast DNS
;; You are currently testing what happens when an mDNS query is leaked to DNS
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 59994
;; flags: qr aa rd; QUERY: 1, ANSWER: 2, AUTHORITY: 0, ADDITIONAL: 1
;; WARNING: recursion requested but not available

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 4096
; COOKIE: b633b51a4ca3a653 (echoed)
;; QUESTION SECTION:
;headliness-service.default.svc.cluster.local. IN A

;; ANSWER SECTION:
headliness-service.default.svc.cluster.local. 30 IN A 192.168.1.3
headliness-service.default.svc.cluster.local. 30 IN A 192.168.0.6

;; Query time: 0 msec
;; SERVER: 10.96.0.10#53(10.96.0.10)
;; WHEN: Mon Jan 09 09:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1023398.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

面试官:请说说flex布局_番茄出品.md

面试官&#xff1a;请说说flex布局_番茄出品.md start 依然记得当初学习 flex 布局时&#xff0c;用 flex 布局&#xff1a;画麻将。一筒到九筒&#xff0c;应有尽有。但是光和面试官说&#xff0c;我用 flex 布局画过麻将&#xff0c;并没有什么用。面试官问你一个语法&…

Hadoop:YARN、MapReduce、Hive操作

目录 分布式计算概述 YARN概述 YARN架构 核心架构 辅助架构 MapReduce 概述 配置相关文件 提交MapReduce到YARN Hive Hive架构 Hive在VMware部署 Hive的启动 数据库操作 数据表操作 内部表操作 外部表操作 数据加载和导出 数据加载LOAD 数据加载 - INSERT SEL…

生物的神经系统与机器的人工神经网络

生物的神经系统与机器的人工神经网络 文章目录 前言一、人工神经网络二、生物的神经系统三、关系四、相似与区别4.1. 相似&#xff1a;4.2. 区别: 总结 前言 因为本人是学生物的&#xff0c;并且深度学习的核心——人工神经网络与生物的神经系统息息相关&#xff0c;故想要在本…

单片机测量任务运行时间

前言 1.之前是直接看定时器的计数值来粗略估计&#xff0c;可能会存在一些差错&#xff0c;也不够方便&#xff1b;所以做一个比较通用的计算任务运行时间的小Demo。 2.用定时器的计数值查看开始的Tick和结束的Tick&#xff0c;然后定时器每隔1毫秒溢出一次&#xff0c;通过简…

QML 碰到的奇怪问题

text elied属性失效 elied属性就是当Text的文本文字超过Text的宽度时。文字会出现省略的效果。 import QtQuick 2.9 import QtQuick.Window 2.3Window {visible: truewidth: 640height: 480title: qsTr("Hello World")Rectangle{anchors.centerIn: parentwidth: pa…

颜色扩散类dp及其优化:0919T2

http://cplusoj.com/d/senior/p/330 此题前半部分是AGC058B 这是一个颜色扩散类dp&#xff0c;对于这类dp&#xff0c;存在一个性质。 假如一个区间被 i i i 染&#xff0c;一个被 j j j 染&#xff0c;则必然满足 i < j i<j i<j&#xff08;这是下标&#xff09…

基于SSM的智慧城市实验室主页系统的设计与实现

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;采用Vue技术开发 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#x…

e签宝,再「进化」

基于ePaaS&#xff0c;e签宝不仅打造了电子签领域的生态圈&#xff0c;也正在赋能整个SaaS行业奔向生态化的良性业态&#xff0c;这将使得SaaS厂商的边界愈发清晰&#xff0c;逐渐实现“量产”&#xff0c;奔向规模化。 作者|斗斗 出品|产业家 1957年11月&#xff0c;江苏…

文件字符输出流(FileWriter)(基础流)

1、不追加的情况 package com.csdn.d4_char_stream; import java.io.FileWriter; import java.io.IOException; import java.io.Writer; public class FileWriterDemo01 {public static void main(String[] args) throws IOException {//1、创建一个字符输出流管道与目标文件接…

Android进阶之路 - 盈利、亏损金额格式化

在金融类型的app中&#xff0c;关于金额、数字都相对敏感和常见一些&#xff0c;在此仅记录我在金融行业期间学到的皮毛&#xff0c;如后续遇到新的场景也会加入该篇 该篇大多采用 Kotlin 扩展函数的方式进行记录&#xff0c;尽可能熟悉 Kotlin 基础知识 兄弟 Blog StringUti…

Kafka为什么是高性能高并发高可用架构

目录 1 前言2 顺序写入3 页缓存4 零拷贝5 Broker 性能6 流数据并行7 总结 1 前言 我们都知道 Kafka 是基于磁盘进行存储的&#xff0c;但 Kafka 官方又称其具有高性能、高吞吐、低延时的特点&#xff0c;其吞吐量动辄几十上百万。小伙伴们是不是有点困惑了&#xff0c;一般认为…

Linux——IO

✅<1>主页&#xff1a;&#xff1a;我的代码爱吃辣 &#x1f4c3;<2>知识讲解&#xff1a;Linux——文件系统 ☂️<3>开发环境&#xff1a;Centos7 &#x1f4ac;<4>前言&#xff1a;是不是只有C/C有文件操作呢&#xff1f;python&#xff0c;java&…

Code Ocean :一个用于数据科学和科学研究的在线平台【源码+文章解析】

Code Ocean&#xff08;https://codeocean.com/&#xff09;是一个用于数据科学和科学研究的在线平台&#xff0c;旨在帮助研究人员更轻松地管理、共享和复制研究代码和数据。以下是Code Ocean的主要用途和功能&#xff1a; 代码和数据的管理&#xff1a;Code Ocean允许研究人…

辨析目录表、文件打开表、文件分配表、索引表、FCB、inode、fd等文件系统常见名词

文章目录 1 解释2 形象配图 以下内容仅供简单的辨析这些文件系统最基本的名词&#xff0c;如果需要更深入的了解&#xff0c;请查阅相关转移书籍&#xff0c;如《现代操作系统》、《操作系统概念》 、《操作系统精髓与设计原理》等书籍。 1 解释 2 形象配图 文件打开表 文件分…

工控机连接Profinet转Modbus RTU网关与水泵变频器Modbus通讯

Profinet转Modbus RTU网关是一个具有高性能的通信设备&#xff0c;它能够将工控机上的Profinet协议转换成水泵变频器可识别的Modbus RTU协议&#xff0c;实现二者之间的通信。通过这种方式&#xff0c;工控机可以直接控制水泵变频器的运行状态&#xff0c;改变其工作频率&#…

Windows10下的GTSAM因子图安装与使用

Windows10下的GTSAM因子图安装与使用 一、windows系统预安装1. windows 10安装gcc2.windows 10 安装 boost3.CMake 安装与查看4.CMake 配置boost 二、GTSAM安装与使用三、CMAKE 创建立 使用GTSAM的Visual Studio项目参考文献 一、windows系统预安装 1. windows 10安装gcc htt…

【深度学习框架格式转化】【CPU】Pytorch模型转ONNX模型格式流程详解【入门】

【深度学习框架格式转化】【GPU】Pytorch模型转ONNX模型格式流程详解【入门】 提示:博主取舍了很多大佬的博文并亲测有效,分享笔记邀大家共同学习讨论 文章目录 【深度学习框架格式转化】【GPU】Pytorch模型转ONNX模型格式流程详解【入门】前言PyTorch模型环境搭建(CPU)安装onn…

LCP 50. 宝石补给(每日一题)

欢迎各位勇者来到力扣新手村&#xff0c;在开始试炼之前&#xff0c;请各位勇者先进行「宝石补给」。 每位勇者初始都拥有一些能量宝石&#xff0c; gem[i] 表示第 i 位勇者的宝石数量。现在这些勇者们进行了一系列的赠送&#xff0c;operations[j] [x, y] 表示在第 j 次的赠送…

解决VS Code安装远程服务器插件慢的问题

解决VS Code安装远程服务器插件慢的问题 最近想在服务器上做juypter notebook的代码运行&#xff0c;发现要给服务器安装Jupyter插件&#xff0c;但是安装速度奇慢无比&#xff08;因为服务器不连外网&#xff09;&#xff0c;一开始查看从VS Code插件市场下载插件的博客&…

网络编程day02(socket套接字)

今日任务&#xff1a; TCP\UDP服务端客户端通信 TCP&#xff1a;代码 服务端&#xff1a; #include <stdio.h> #include <string.h> #include <stdlib.h> #include <sys/types.h> #include <sys/socket.h> #include <arpa/inet.h> #in…