Kubernetes Service

Posted by Vito on January 20, 2024

创建

  • 先创建 Pod
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
[root@k8s-master1 test]# vim deploy-vito-web.yaml 
apiVersion: apps/v1
kind: Deployment
metadata:
  name: deploy-vito-web
spec:
  replicas: 2
  selector:
    matchLabels:
      app: deploy-vito-nginx
  template:
    metadata:
      labels:
        app: deploy-vito-nginx
    spec:
      containers:
      - image: nginx:1.7.9
        imagePullPolicy: IfNotPresent
        name: deploy-vito-web-c-nginx

[root@k8s-master1 test]# kubectl create -f deploy-vito-web.yaml 
deployment.apps/deploy-vito-web created

[root@k8s-master1 test]# kubectl get po -o wide --show-labels
NAME                               READY   STATUS    RESTARTS   AGE     IP              NODE                 NOMINATED NODE   READINESS GATES   LABELS
deploy-vito-web-5f74dfcf97-nrx2k   1/1     Running   0          3m43s   10.244.37.250   k8s-node1.zhch.lan   <none>           <none>            app=deploy-vito-nginx,pod-template-hash=5f74dfcf97
deploy-vito-web-5f74dfcf97-pgjd9   1/1     Running   0          3m43s   10.244.8.195    k8s-node2.zhch.lan   <none>           <none>            app=deploy-vito-nginx,pod-template-hash=5f74dfcf97
  • 创建 Service
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
[root@k8s-master1 test]# vim svc-vito-web.yaml
apiVersion: v1
kind: Service # 创建 Service 类型的资源
metadata:
  name: svc-vito-web # Service 的名字
spec:
  selector: # 将服务流量路由到所有与此选择器匹配的 Pod 。若配置 spec.selector ,则创建 Service 的同时会自动创建 Endpoints ; 否则不会自动创建 Endpoints
    app: deploy-vito-nginx
  type: NodePort
  ports:
  - port: 80 # service 暴露在 cluster ip 上的端口,<clusterIP>:port 是提供给集群内部访问 service 的入口
    targetPort: 80 # pod 上的端口,本例对应 deploy-vito-web 中的 80 端口 
    #nodePort: 30080 # <nodeIP>:nodePort 是 Kubernetes 提供给集群外部客户访问 service 入口的一种方式(另一种方式是LoadBalancer)
    protocol: TCP
    # 总的来说,port 和 nodePort 都是 service 的端口,前者暴露给集群内客户访问服务,后者暴露给集群外客户访问服务。
    # 从这两个端口到来的数据都需要经过反向代理 kube-proxy 流入后端 Pod 的 targetPort ,从而到达 Pod 中的容器内
    # 默认情况下,出于方便考虑,targetPort 会被设置为与 port 字段相同的值(即 port 与 targetPort 相同时,可不配置 targetPort)
    # 注意:nodePort 的取值范围是 30000-32767,通常不手动指定该端口的值,而是让 Kubernetes 自动生成一个随机值

[root@k8s-master1 test]# kubectl create -f svc-vito-web.yaml 
service/svc-vito-web created
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
[root@k8s-master1 test]# kubectl get svc
NAME           TYPE        CLUSTER-IP    EXTERNAL-IP   PORT(S)        AGE
kubernetes     ClusterIP   10.96.0.1     <none>        443/TCP        6d15h
svc-vito-web   NodePort    10.100.0.48   <none>        80:30634/TCP   40s

# 自动创建的 Endpoints , Name 与 Service 的 Name 相同
[root@k8s-master1 test]# kubectl get endpoints
NAME           ENDPOINTS                          AGE
kubernetes     192.168.99.201:6443                6d15h
svc-vito-web   10.244.37.250:80,10.244.8.195:80   58s

[root@k8s-master1 test]# kubectl get ep
NAME           ENDPOINTS                          AGE
kubernetes     192.168.99.201:6443                6d15h
svc-vito-web   10.244.37.250:80,10.244.8.195:80   63s
  • 访问
    • 同 NameSpace : ServiceName:port
    • 跨 NameSapce : ServiceName.NameSpace:port

spce.type

  • ClusterIP :默认值,只能在集群内部使用,集群外部无法访问该 Service 。
  • NodePort :会在所有安装了 kube-proxy 的节点都绑定一个端口,此端口可以代理至对应的 Pod,集群外部可以使用<任意节点 IP>:<NodePort>访问到集群中对应 Pod 中的服务。通常,在集群外部访问集群内服务更推荐使用 Ingress 。
  • LoadBalancer :使用云平台(阿里云、腾讯云等)的负载均衡器向外部公开 Service。Kubernetes 不直接提供负载均衡组件; 你必须提供一个,或者将你的 Kubernetes 集群与某个云平台集成。
  • ExternalName :将服务映射到 externalName 字段的内容(例如,映射到主机名 api.foo.bar.example 或者域名 baidu.com)。

ExternalName

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
[root@k8s-master1 test]# vim svc-external-vitozh.top.yaml
apiVersion: v1
kind: Service 
metadata:
  name: svc-external-vitozh
spec:
  type: ExternalName
  externalName: www.vitozh.top

[root@k8s-master1 test]# kubectl create -f svc-external-vitozh.top.yaml
service/svc-external-vitozh created

[root@k8s-master1 test]# kubectl get svc
NAME                  TYPE           CLUSTER-IP   EXTERNAL-IP      PORT(S)   AGE
kubernetes            ClusterIP      10.96.0.1    <none>           443/TCP   6d17h
svc-external-vitozh   ExternalName   <none>       www.vitozh.top   <none>    11s
[root@k8s-master1 test]# kubectl get ep
NAME         ENDPOINTS             AGE
kubernetes   192.168.99.201:6443   6d17h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
[root@k8s-node2 ~]# kubectl run --image busybox:1.28.4 dns-test --restart=Never --rm -it /bin/sh
/ # wget svc-external-vitozh
Connecting to svc-external-vitozh (192.3.253.8:80)
index.html           100% |********************************************************************************|   615   0:00:00 ETA
/ # cat index.html 
<!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>
/ # 

手动创建 Endpoints

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
[root@k8s-master1 test]# vim svc-vitozh.top.yaml
apiVersion: v1
kind: Service 
metadata:
  labels:
    site: vitozh.top
  name: svc-vitozh
  namespace: default 
spec:
  type: ClusterIP
  ports:
  - name: http
    port: 88
    targetPort: 80
  - name: https
    port: 8443
    targetPort: 443

[root@k8s-master1 test]# kubectl create -f svc-vitozh.top.yaml 
service/svc-vitozh created
1
2
3
4
5
6
7
[root@k8s-master1 test]# nslookup vitozh.top
Server:		192.168.3.157
Address:	192.168.3.157#53

Non-authoritative answer:
Name:	vitozh.top
Address: 192.3.253.8
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
[root@k8s-master1 test]# vim np-vitozh.top.yaml
apiVersion: v1
kind: Endpoints 
metadata:
  name: svc-vitozh # 必须与 Service 的 Name 一致
  namespace: default # 必须与 Service 的 namespace 一致
subsets:
- addresses:
  - ip: 192.3.253.8
  ports:
  - name: http # 必须与 Service 的 prots.name 一致
    port: 80 # 必须与 Service 的 prots.targetPort 一致
  - name: https
    port: 443

[root@k8s-master1 test]# kubectl create -f np-vitozh.top.yaml 
endpoints/svc-vitozh created
1
2
3
4
5
6
7
8
[root@k8s-master1 test]# kubectl get svc
NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)           AGE
kubernetes   ClusterIP   10.96.0.1       <none>        443/TCP           6d17h
svc-vitozh   ClusterIP   10.105.53.198   <none>        88/TCP,8443/TCP   103s
[root@k8s-master1 test]# kubectl get ep
NAME         ENDPOINTS                        AGE
kubernetes   192.168.99.201:6443              6d17h
svc-vitozh   192.3.253.8:80,192.3.253.8:443   27s
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
[root@k8s-node2 ~]# kubectl run --image busybox:1.28.4 dns-test --restart=Never --rm -it /bin/sh
/ # wget svc-vitozh:88
Connecting to svc-vitozh:88 (10.105.53.198:88)
index.html           100% |********************************************************************************|   615   0:00:00 ETA
/ # cat index.html 
<!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>
/ #