一.系统环境
本文主要基于Kubernetes1.21.9和Linux操作系统CentOS7.4。
服务器版本 | docker软件版本 | Kubernetes(k8s)集群版本 | CPU架构 |
---|---|---|---|
CentOS Linux release 7.4.1708 (Core) | Docker version 20.10.12 | v1.21.9 | x86_64 |
Kubernetes集群架构:k8scloude1作为master节点,k8scloude2,k8scloude3作为worker节点。
服务器 | 操作系统版本 | CPU架构 | 进程 | 功能描述 |
---|---|---|---|---|
k8scloude1/192.168.110.130 | CentOS Linux release 7.4.1708 (Core) | x86_64 | docker,kube-apiserver,etcd,kube-scheduler,kube-controller-manager,kubelet,kube-proxy,coredns,calico | k8s master节点 |
k8scloude2/192.168.110.129 | CentOS Linux release 7.4.1708 (Core) | x86_64 | docker,kubelet,kube-proxy,calico | k8s worker节点 |
k8scloude3/192.168.110.128 | CentOS Linux release 7.4.1708 (Core) | x86_64 | docker,kubelet,kube-proxy,calico | k8s worker节点 |
二.前言
Kubernetes是目前最流行的容器编排平台之一,它可以自动化地部署、扩展和管理容器化应用程序。但是,在部署一个大规模的容器集群时面临一个问题就是如何保护网络安全。这时候,我们就需要使用网络策略(NetworkPolicy)。
本文将介绍Kubernetes中的网络策略(NetworkPolicy)。我们将深入了解什么是网络策略,并如何在Kubernetes集群中使用网络策略来保护网络安全。
使用网络策略NetworkPolicy的前提是已经有一套可以正常运行的Kubernetes集群,关于Kubernetes(k8s)集群的安装部署,可以查看博客《Centos7 安装部署Kubernetes(k8s)集群》https://www.cnblogs.com/renshengdezheli/p/16686769.html。
三.网络策略(NetworkPolicy)简介
Kubernetes网络策略(NetworkPolicy)是一个资源对象,主要用于定义Pod之间的流量控制,其实现了一个基于标签的选择器模型,允许管理员通过网络策略规则限制对Pod的流量访问。
网络策略(NetworkPolicy)是以Pod为单位进行授权的,因此,只有当所有的Pod都通过了网络策略时,才能够接收到其他Pod发送的流量。这种方式极大提高了网络的安全性。
四.创建pod和svc
创建存放网络策略的目录
<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># mkdir network</span><span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># mkdir network</span>[root@k8scloude1 ~]# mkdir network
创建namespace
<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># kubectl create ns network</span>namespace/network created<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># kubectl create ns network</span> namespace/network created[root@k8scloude1 ~]# kubectl create ns network namespace/network created
切换namespace
<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># kubens network</span>Context <span class="token string">"kubernetes-admin@kubernetes"</span> modified.Active namespace is <span class="token string">"network"</span><span class="token builtin class-name">.</span><span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># kubens network</span> Context <span class="token string">"kubernetes-admin@kubernetes"</span> modified. Active namespace is <span class="token string">"network"</span><span class="token builtin class-name">.</span>[root@k8scloude1 ~]# kubens network Context "kubernetes-admin@kubernetes" modified. Active namespace is "network".
为了方便进行curl测试网络,所有节点下载busybox-curl 镜像(内置curl命令)
<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># docker pull yauritux/busybox-curl </span><span class="token punctuation">[</span>root@k8scloude2 ~<span class="token punctuation">]</span><span class="token comment"># docker pull yauritux/busybox-curl</span><span class="token punctuation">[</span>root@k8scloude3 ~<span class="token punctuation">]</span><span class="token comment"># docker pull yauritux/busybox-curl</span><span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># docker pull yauritux/busybox-curl </span> <span class="token punctuation">[</span>root@k8scloude2 ~<span class="token punctuation">]</span><span class="token comment"># docker pull yauritux/busybox-curl</span> <span class="token punctuation">[</span>root@k8scloude3 ~<span class="token punctuation">]</span><span class="token comment"># docker pull yauritux/busybox-curl</span>[root@k8scloude1 ~]# docker pull yauritux/busybox-curl [root@k8scloude2 ~]# docker pull yauritux/busybox-curl [root@k8scloude3 ~]# docker pull yauritux/busybox-curl
pod的yaml文件如下,功能是使用Nginx镜像创建pod。
<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># cd network/</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim pod.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat pod.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> Pod<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">labels</span><span class="token punctuation">:</span><span class="token key atrule">test</span><span class="token punctuation">:</span> podtest<span class="token key atrule">name</span><span class="token punctuation">:</span> podtest<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#当需要关闭容器时,立即杀死容器而不等待默认的30秒优雅停机时长。</span><span class="token key atrule">terminationGracePeriodSeconds</span><span class="token punctuation">:</span> <span class="token number">0</span><span class="token key atrule">containers</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> nginx<span class="token key atrule">image</span><span class="token punctuation">:</span> nginx<span class="token comment">#imagePullPolicy: IfNotPresent:表示如果本地已经存在该镜像,则不重新下载;否则从远程 Docker Hub 下载该镜像</span><span class="token key atrule">imagePullPolicy</span><span class="token punctuation">:</span> IfNotPresent<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># cd network/</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim pod.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat pod.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> Pod <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">labels</span><span class="token punctuation">:</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> podtest <span class="token key atrule">name</span><span class="token punctuation">:</span> podtest <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#当需要关闭容器时,立即杀死容器而不等待默认的30秒优雅停机时长。</span> <span class="token key atrule">terminationGracePeriodSeconds</span><span class="token punctuation">:</span> <span class="token number">0</span> <span class="token key atrule">containers</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> nginx <span class="token key atrule">image</span><span class="token punctuation">:</span> nginx <span class="token comment">#imagePullPolicy: IfNotPresent:表示如果本地已经存在该镜像,则不重新下载;否则从远程 Docker Hub 下载该镜像</span> <span class="token key atrule">imagePullPolicy</span><span class="token punctuation">:</span> IfNotPresent[root@k8scloude1 ~]# cd network/ [root@k8scloude1 network]# vim pod.yaml [root@k8scloude1 network]# cat pod.yaml apiVersion: v1 kind: Pod metadata: labels: test: podtest name: podtest spec: #当需要关闭容器时,立即杀死容器而不等待默认的30秒优雅停机时长。 terminationGracePeriodSeconds: 0 containers: - name: nginx image: nginx #imagePullPolicy: IfNotPresent:表示如果本地已经存在该镜像,则不重新下载;否则从远程 Docker Hub 下载该镜像 imagePullPolicy: IfNotPresent
创建两个nginx pod用于测试使用。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># sed 's/podtest/pod1/' pod.yaml | kubectl apply -f -</span>pod/pod1 created<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># sed 's/podtest/pod2/' pod.yaml | kubectl apply -f -</span>pod/pod2 created<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATESpod1 <span class="token number">1</span>/1 Running <span class="token number">0</span> 12s <span class="token number">10.244</span>.112.129 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>pod2 <span class="token number">1</span>/1 Running <span class="token number">0</span> 8s <span class="token number">10.244</span>.251.203 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># sed 's/podtest/pod1/' pod.yaml | kubectl apply -f -</span> pod/pod1 created <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># sed 's/podtest/pod2/' pod.yaml | kubectl apply -f -</span> pod/pod2 created <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 <span class="token number">1</span>/1 Running <span class="token number">0</span> 12s <span class="token number">10.244</span>.112.129 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> pod2 <span class="token number">1</span>/1 Running <span class="token number">0</span> 8s <span class="token number">10.244</span>.251.203 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>[root@k8scloude1 network]# sed 's/podtest/pod1/' pod.yaml | kubectl apply -f - pod/pod1 created [root@k8scloude1 network]# sed 's/podtest/pod2/' pod.yaml | kubectl apply -f - pod/pod2 created [root@k8scloude1 network]# kubectl get pod -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 1/1 Running 0 12s 10.244.112.129 k8scloude2 <none> <none> pod2 1/1 Running 0 8s 10.244.251.203 k8scloude3 <none> <none>
修改nginx的首页文件index.html,用于区分两个pod。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh -c "echo 111 >/usr/share/nginx/html/index.html"</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod2 -- sh -c "echo 222 >/usr/share/nginx/html/index.html"</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh -c "echo 111 >/usr/share/nginx/html/index.html"</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod2 -- sh -c "echo 222 >/usr/share/nginx/html/index.html"</span>[root@k8scloude1 network]# kubectl exec -it pod1 -- sh -c "echo 111 >/usr/share/nginx/html/index.html" [root@k8scloude1 network]# kubectl exec -it pod2 -- sh -c "echo 222 >/usr/share/nginx/html/index.html"
访问pod,首页文件已经改变。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># curl 10.244.112.129</span><span class="token number">111</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># curl 10.244.251.203</span><span class="token number">222</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># curl 10.244.112.129</span> <span class="token number">111</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># curl 10.244.251.203</span> <span class="token number">222</span>[root@k8scloude1 network]# curl 10.244.112.129 111 [root@k8scloude1 network]# curl 10.244.251.203 222
给pod创建svc服务。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod1svc pod pod1 --port=80</span>service/pod1svc exposed<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod2svc pod pod2 --port=80</span>service/pod2svc exposed<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span>NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTORpod1svc ClusterIP <span class="token number">10.104</span>.66.174 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">80</span>/TCP 36s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1pod2svc ClusterIP <span class="token number">10.108</span>.254.110 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">80</span>/TCP 17s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod1svc pod pod1 --port=80</span> service/pod1svc exposed <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod2svc pod pod2 --port=80</span> service/pod2svc exposed <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span> NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTOR pod1svc ClusterIP <span class="token number">10.104</span>.66.174 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">80</span>/TCP 36s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 pod2svc ClusterIP <span class="token number">10.108</span>.254.110 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">80</span>/TCP 17s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2[root@k8scloude1 network]# kubectl expose --name=pod1svc pod pod1 --port=80 service/pod1svc exposed [root@k8scloude1 network]# kubectl expose --name=pod2svc pod pod2 --port=80 service/pod2svc exposed [root@k8scloude1 network]# kubectl get svc -o wide NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR pod1svc ClusterIP 10.104.66.174 <none> 80/TCP 36s test=pod1 pod2svc ClusterIP 10.108.254.110 <none> 80/TCP 17s test=pod2
五.没有网络策略的条件下访问pod
查看网络策略,现在没有任何的网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span>No resources found <span class="token keyword">in</span> network namespace.<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span> No resources found <span class="token keyword">in</span> network namespace.[root@k8scloude1 network]# kubectl get networkpolicy No resources found in network namespace.
建立一个临时pod作为客户端,用于访问pod1和pod2,在没有任何网络策略的条件下,可以访问pod1svc和pod2svc。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest -it --rm --image-pull-policy=IfNotPresent -- sh </span>If you don<span class="token string">'t see a command prompt, try pressing enter./home # curl pod1svc111/home # curl pod2svc222/home # exitSession ended, resume using '</span>kubectl attach podclient <span class="token parameter variable">-c</span> podclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is runningpod <span class="token string">"podclient"</span> deleted<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest -it --rm --image-pull-policy=IfNotPresent -- sh </span> If you don<span class="token string">'t see a command prompt, try pressing enter. /home # curl pod1svc 111 /home # curl pod2svc 222 /home # exit Session ended, resume using '</span>kubectl attach podclient <span class="token parameter variable">-c</span> podclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is running pod <span class="token string">"podclient"</span> deleted[root@k8scloude1 network]# kubectl run podclient --image=yauritux/busybox-curl:latest -it --rm --image-pull-policy=IfNotPresent -- sh If you don't see a command prompt, try pressing enter. /home # curl pod1svc 111 /home # curl pod2svc 222 /home # exit Session ended, resume using 'kubectl attach podclient -c podclient -i -t' command when the pod is running pod "podclient" deleted
建立一个临时pod作为客户端,-n default:进入容器并切换到default命名空间。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest -n default -it --rm --image-pull-policy=IfNotPresent -- sh </span>If you don<span class="token string">'t see a command prompt, try pressing enter./home # curl pod1svccurl: (6) Couldn'</span>t resolve <span class="token function">host</span> <span class="token string">'pod1svc'</span><span class="token comment">#跨命名空间访问需要指定namespace</span>/home <span class="token comment"># curl pod1svc.network</span><span class="token number">111</span>/home <span class="token comment"># curl pod2svc.network</span><span class="token number">222</span>/home <span class="token comment"># exit</span>Session ended, resume using <span class="token string">'kubectl attach podclient -c podclient -i -t'</span> <span class="token builtin class-name">command</span> when the pod is runningpod <span class="token string">"podclient"</span> deleted<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest -n default -it --rm --image-pull-policy=IfNotPresent -- sh </span> If you don<span class="token string">'t see a command prompt, try pressing enter. /home # curl pod1svc curl: (6) Couldn'</span>t resolve <span class="token function">host</span> <span class="token string">'pod1svc'</span> <span class="token comment">#跨命名空间访问需要指定namespace</span> /home <span class="token comment"># curl pod1svc.network</span> <span class="token number">111</span> /home <span class="token comment"># curl pod2svc.network</span> <span class="token number">222</span> /home <span class="token comment"># exit</span> Session ended, resume using <span class="token string">'kubectl attach podclient -c podclient -i -t'</span> <span class="token builtin class-name">command</span> when the pod is running pod <span class="token string">"podclient"</span> deleted[root@k8scloude1 network]# kubectl run podclient --image=yauritux/busybox-curl:latest -n default -it --rm --image-pull-policy=IfNotPresent -- sh If you don't see a command prompt, try pressing enter. /home # curl pod1svc curl: (6) Couldn't resolve host 'pod1svc' #跨命名空间访问需要指定namespace /home # curl pod1svc.network 111 /home # curl pod2svc.network 222 /home # exit Session ended, resume using 'kubectl attach podclient -c podclient -i -t' command when the pod is running pod "podclient" deleted
删除svc。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl delete svc pod1svc</span><span class="token function">service</span> <span class="token string">"pod1svc"</span> deleted<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl delete svc pod2svc</span><span class="token function">service</span> <span class="token string">"pod2svc"</span> deleted<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl delete svc pod1svc</span> <span class="token function">service</span> <span class="token string">"pod1svc"</span> deleted <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl delete svc pod2svc</span> <span class="token function">service</span> <span class="token string">"pod2svc"</span> deleted[root@k8scloude1 network]# kubectl delete svc pod1svc service "pod1svc" deleted [root@k8scloude1 network]# kubectl delete svc pod2svc service "pod2svc" deleted
给pod创建svc,为了让集群外的机器能访问svc服务,我们指定svc的发布方式为Loadbalancer,注意使用LoadBalancer的svc发布方式需要用到METALLB创建地址池,详情请查看博客《Kubernetes(k8s)服务service:service的发现和service的发布》。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod1svc pod pod1 --port=80 --type=LoadBalancer</span>service/pod1svc exposed<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod2svc pod pod2 --port=80 --type=LoadBalancer</span>service/pod2svc exposed<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span>NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTORpod1svc LoadBalancer <span class="token number">10.103</span>.187.15 <span class="token number">192.168</span>.110.188 <span class="token number">80</span>:31116/TCP 49s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1pod2svc LoadBalancer <span class="token number">10.110</span>.132.42 <span class="token number">192.168</span>.110.189 <span class="token number">80</span>:32118/TCP 9s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod1svc pod pod1 --port=80 --type=LoadBalancer</span> service/pod1svc exposed <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod2svc pod pod2 --port=80 --type=LoadBalancer</span> service/pod2svc exposed <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span> NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTOR pod1svc LoadBalancer <span class="token number">10.103</span>.187.15 <span class="token number">192.168</span>.110.188 <span class="token number">80</span>:31116/TCP 49s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 pod2svc LoadBalancer <span class="token number">10.110</span>.132.42 <span class="token number">192.168</span>.110.189 <span class="token number">80</span>:32118/TCP 9s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2[root@k8scloude1 network]# kubectl expose --name=pod1svc pod pod1 --port=80 --type=LoadBalancer service/pod1svc exposed [root@k8scloude1 network]# kubectl expose --name=pod2svc pod pod2 --port=80 --type=LoadBalancer service/pod2svc exposed [root@k8scloude1 network]# kubectl get svc -o wide NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR pod1svc LoadBalancer 10.103.187.15 192.168.110.188 80:31116/TCP 49s test=pod1 pod2svc LoadBalancer 10.110.132.42 192.168.110.189 80:32118/TCP 9s test=pod2
现在在Windows里访问svc:192.168.110.188 和192.168.110.189。
也可以通过物理机IP+PORT端口访问svc。
可以看到,没有网络策略的条件下,外界可以随意访问pod,这是不安全的,下面给pod添加网络策略。
六.给pod添加网络策略
网络策略NetworkPolicy 是一种以应用为中心的结构,允许你设置如何允许 Pod 与网络上的各类网络“实体” 通信。 说白了,网络策略本质上就是建立一个防火墙,控制入站和出站流量。
网络策略通过CNI(Containernetworking Interface)网络插件来实现。 要使用网络策略,你必须使用支持 NetworkPolicy 的网络解决方案。 创建一个 NetworkPolicy 资源对象而没有控制器来使它生效的话,是没有任何作用的。此kubernetes集群使用的网络插件是Calico,Calico支持网络策略,大家熟知的Flannel是不支持网络策略的,关于网络插件的详情,请查看博客《使用CNI网络插件(calico)实现docker容器跨主机互联》。
Pod 有两种隔离: 出口的隔离和入口的隔离,即出站(Egress)和入站(Ingress)。
为了允许两个 Pods 之间的网络数据流,源端 Pod 上的出站(Egress)规则和 目标端 Pod 上的入站(Ingress)规则都需要允许该流量。 如果源端的出站(Egress)规则或目标端的入站(Ingress)规则拒绝该流量, 则流量将被拒绝。
下面先介绍入站(Ingress)网络策略,即谁能访问我和谁不能访问我。
6.1 入站网络策略
下面的yaml文件是一个标准的网络策略:
- PodSelector: 指定被此 NetworkPolicy 影响的 Pod。此处匹配 Label 为 “role=db” 的 Pod。
- PolicyTypes: 规定所需的网络策略类型。此处包括 Ingress 和 Egress。
- Ingress: 定义允许从指定来源(IP 地址范围、命名空间或 Pod)和端口接收流量的规则。此处仅允许 TCP 流量访问端口 6379。
- Egress: 定义允许发送到指定目标(IP 地址范围)和端口的流量的规则。此处仅允许 TCP 流量发送到端口 5978 的目标 IP 地址范围为 10.0.0.0/24。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">role</span><span class="token punctuation">:</span> db<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token punctuation">-</span> Egress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span><span class="token key atrule">cidr</span><span class="token punctuation">:</span> 172.17.0.0/16<span class="token key atrule">except</span><span class="token punctuation">:</span><span class="token punctuation">-</span> 172.17.1.0/24<span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">project</span><span class="token punctuation">:</span> myproject<span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">role</span><span class="token punctuation">:</span> frontend<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">6379</span><span class="token comment">#出站规则</span><span class="token key atrule">egress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span><span class="token key atrule">cidr</span><span class="token punctuation">:</span> 10.0.0.0/24<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">5978</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">role</span><span class="token punctuation">:</span> db <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token punctuation">-</span> Egress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span> <span class="token key atrule">cidr</span><span class="token punctuation">:</span> 172.17.0.0/16 <span class="token key atrule">except</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> 172.17.1.0/24 <span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">project</span><span class="token punctuation">:</span> myproject <span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">role</span><span class="token punctuation">:</span> frontend <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">6379</span> <span class="token comment">#出站规则</span> <span class="token key atrule">egress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span> <span class="token key atrule">cidr</span><span class="token punctuation">:</span> 10.0.0.0/24 <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">5978</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: matchLabels: role: db #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Ingress - Egress #ingress:入站规则 ingress: - from: - ipBlock: cidr: 172.17.0.0/16 except: - 172.17.1.0/24 - namespaceSelector: matchLabels: project: myproject - podSelector: matchLabels: role: frontend ports: - protocol: TCP port: 6379 #出站规则 egress: - to: - ipBlock: cidr: 10.0.0.0/24 ports: - protocol: TCP port: 5978
我们先讲解使用pod标签选择器定义的入站网络策略。
6.1.1 入站网络策略-pod标签选择器
查看pod的标签。
<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide --show-labels</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELSpod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 16h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 16h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2<span class="token punctuation">[</span>root@k8scloude1 ~<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide --show-labels</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS pod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 16h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 16h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2[root@k8scloude1 ~]# kubectl get pod -o wide --show-labels NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS pod1 1/1 Running 1 16h 10.244.112.136 k8scloude2 <none> <none> test=pod1 pod2 1/1 Running 1 16h 10.244.251.227 k8scloude3 <none> <none> test=pod2
编写网络策略规则,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,仅仅允许当前命名空间内标签为role=podclient的pod可以访问pod1的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token comment">#先通过pod标签选择器控制</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则,只有Ingress表示定义的是入站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token comment">#允许哪些客户端可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token comment">#标签为role: podclient的pod可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">role</span><span class="token punctuation">:</span> podclient<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token comment">#先通过pod标签选择器控制</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则,只有Ingress表示定义的是入站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token comment">#允许哪些客户端可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token comment">#标签为role: podclient的pod可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">role</span><span class="token punctuation">:</span> podclient <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml #先通过pod标签选择器控制 [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则,只有Ingress表示定义的是入站规则 policyTypes: - Ingress #ingress:入站规则 ingress: #允许哪些客户端可以访问 - from: #标签为role: podclient的pod可以访问 - podSelector: matchLabels: role: podclient ports: - protocol: TCP port: 80
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy -o wide</span>NAME POD-SELECTOR AGEmy-network-policy <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 85s<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy -o wide</span> NAME POD-SELECTOR AGE my-network-policy <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 85s[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured [root@k8scloude1 network]# kubectl get networkpolicy -o wide NAME POD-SELECTOR AGE my-network-policy test=pod1 85s
查看svc。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span>NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTORpod1svc LoadBalancer <span class="token number">10.103</span>.187.15 <span class="token number">192.168</span>.110.188 <span class="token number">80</span>:31116/TCP 19h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1pod2svc LoadBalancer <span class="token number">10.110</span>.132.42 <span class="token number">192.168</span>.110.189 <span class="token number">80</span>:32118/TCP 19h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span> NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTOR pod1svc LoadBalancer <span class="token number">10.103</span>.187.15 <span class="token number">192.168</span>.110.188 <span class="token number">80</span>:31116/TCP 19h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 pod2svc LoadBalancer <span class="token number">10.110</span>.132.42 <span class="token number">192.168</span>.110.189 <span class="token number">80</span>:32118/TCP 19h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2[root@k8scloude1 network]# kubectl get svc -o wide NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR pod1svc LoadBalancer 10.103.187.15 192.168.110.188 80:31116/TCP 19h test=pod1 pod2svc LoadBalancer 10.110.132.42 192.168.110.189 80:32118/TCP 19h test=pod2
使用Windows客户端访问svc,因为Windows客户端没有pod标签,所以Windows客户端访问不了pod1svc服务了。
使用临时pod podclient客户端访问svc,临时pod podclient没有标签role: podclient,所以访问不了pod1svc服务,pod2没有网络策略保护,可以随意被访问。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest -it --rm --image-pull-policy=IfNotPresent -- sh</span>If you don<span class="token string">'t see a command prompt, try pressing enter./home # curl pod1svc^C/home # curl pod2svc222/home # exitSession ended, resume using '</span>kubectl attach podclient <span class="token parameter variable">-c</span> podclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is runningpod <span class="token string">"podclient"</span> deleted<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest -it --rm --image-pull-policy=IfNotPresent -- sh</span> If you don<span class="token string">'t see a command prompt, try pressing enter. /home # curl pod1svc ^C /home # curl pod2svc 222 /home # exit Session ended, resume using '</span>kubectl attach podclient <span class="token parameter variable">-c</span> podclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is running pod <span class="token string">"podclient"</span> deleted[root@k8scloude1 network]# kubectl run podclient --image=yauritux/busybox-curl:latest -it --rm --image-pull-policy=IfNotPresent -- sh If you don't see a command prompt, try pressing enter. /home # curl pod1svc ^C /home # curl pod2svc 222 /home # exit Session ended, resume using 'kubectl attach podclient -c podclient -i -t' command when the pod is running pod "podclient" deleted
创建podclient。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest --image-pull-policy=IfNotPresent -it</span>If you don<span class="token string">'t see a command prompt, try pressing enter./home # exitSession ended, resume using '</span>kubectl attach podclient <span class="token parameter variable">-c</span> podclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is running<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podclient --image=yauritux/busybox-curl:latest --image-pull-policy=IfNotPresent -it</span> If you don<span class="token string">'t see a command prompt, try pressing enter. /home # exit Session ended, resume using '</span>kubectl attach podclient <span class="token parameter variable">-c</span> podclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is running[root@k8scloude1 network]# kubectl run podclient --image=yauritux/busybox-curl:latest --image-pull-policy=IfNotPresent -it If you don't see a command prompt, try pressing enter. /home # exit Session ended, resume using 'kubectl attach podclient -c podclient -i -t' command when the pod is running
给pod podclient打标签。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label pod podclient role=podclient</span>pod/podclient labeled<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label pod podclient role=podclient</span> pod/podclient labeled[root@k8scloude1 network]# kubectl label pod podclient role=podclient pod/podclient labeled
查看pod标签,此时podclient具有了role=podclient的标签。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide --show-labels</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELSpod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 39s <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide --show-labels</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS pod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2 podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 39s <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient[root@k8scloude1 network]# kubectl get pod -o wide --show-labels NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS pod1 1/1 Running 1 20h 10.244.112.136 k8scloude2 <none> <none> test=pod1 pod2 1/1 Running 1 20h 10.244.251.227 k8scloude3 <none> <none> test=pod2 podclient 1/1 Running 1 39s 10.244.112.140 k8scloude2 <none> <none> role=podclient,run=podclient
在podclient里访问svc,因为podclient具有标签 role=podclient,所以可以访问pod1svc,pod2没有网络策略保护,可以随意被访问。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podclient -- sh</span>/home <span class="token comment"># curl pod1svc</span><span class="token number">111</span>/home <span class="token comment"># curl pod2svc</span><span class="token number">222</span>/home <span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podclient -- sh</span> /home <span class="token comment"># curl pod1svc</span> <span class="token number">111</span> /home <span class="token comment"># curl pod2svc</span> <span class="token number">222</span> /home <span class="token comment"># exit</span>[root@k8scloude1 network]# kubectl exec -it podclient -- sh /home # curl pod1svc 111 /home # curl pod2svc 222 /home # exit
创建podnsclient,-n default表示在default命名空间创建podnsclient。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podnsclient --image=yauritux/busybox-curl:latest --image-pull-policy=IfNotPresent -n default -it</span>If you don<span class="token string">'t see a command prompt, try pressing enter./home # exitSession ended, resume using '</span>kubectl attach podnsclient <span class="token parameter variable">-c</span> podnsclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is running<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl run podnsclient --image=yauritux/busybox-curl:latest --image-pull-policy=IfNotPresent -n default -it</span> If you don<span class="token string">'t see a command prompt, try pressing enter. /home # exit Session ended, resume using '</span>kubectl attach podnsclient <span class="token parameter variable">-c</span> podnsclient <span class="token parameter variable">-i</span> -t' <span class="token builtin class-name">command</span> when the pod is running[root@k8scloude1 network]# kubectl run podnsclient --image=yauritux/busybox-curl:latest --image-pull-policy=IfNotPresent -n default -it If you don't see a command prompt, try pressing enter. /home # exit Session ended, resume using 'kubectl attach podnsclient -c podnsclient -i -t' command when the pod is running
在podnsclient里访问svc,podnsclient不具备role=podclient标签,所以访问不了pod1svc
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span>/home <span class="token comment"># curl pod1svc.network</span>^C/home <span class="token comment"># exit</span><span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span> /home <span class="token comment"># curl pod1svc.network</span> ^C /home <span class="token comment"># exit</span> <span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span>[root@k8scloude1 network]# kubectl exec -it podnsclient -n default -- sh /home # curl pod1svc.network ^C /home # exit command terminated with exit code 130
给podnsclient添加role=podclient标签,–overwrite强制覆盖。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label pod podnsclient role=podclient -n default --overwrite</span>pod/podnsclient labeled<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide --show-labels -n default</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELSpodnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 7m22s <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label pod podnsclient role=podclient -n default --overwrite</span> pod/podnsclient labeled <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide --show-labels -n default</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 7m22s <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient[root@k8scloude1 network]# kubectl label pod podnsclient role=podclient -n default --overwrite pod/podnsclient labeled [root@k8scloude1 network]# kubectl get pod -o wide --show-labels -n default NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS podnsclient 1/1 Running 1 7m22s 10.244.251.230 k8scloude3 <none> <none> role=podclient
在podnsclient里访问svc,访问pod1svc失败,这表示网络策略podSelector:matchLabels:role: podclient,只允许在当前namespace里标签为role: podclient的pod可以访问,其他命名空间的pod就算有这个标签也不行。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span><span class="token comment">#访问不了</span>/home <span class="token comment"># curl pod1svc.network</span>^C/home <span class="token comment"># exit</span><span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span> <span class="token comment">#访问不了</span> /home <span class="token comment"># curl pod1svc.network</span> ^C /home <span class="token comment"># exit</span> <span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span>[root@k8scloude1 network]# kubectl exec -it podnsclient -n default -- sh #访问不了 /home # curl pod1svc.network ^C /home # exit command terminated with exit code 130
6.1.2 入站网络策略-namespaceSelector命名空间选择器
查看命名空间的标签。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get ns --show-labels</span>NAME STATUS AGE LABELSdaemonset Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>daemonsetdefault Active 38d kubernetes.io/metadata.name<span class="token operator">=</span>defaultdeployment Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>deploymentingress-nginx Active 2d13h app.kubernetes.io/instance<span class="token operator">=</span>ingress-nginx,app.kubernetes.io/name<span class="token operator">=</span>ingress-nginx,kubernetes.io/metadata.name<span class="token operator">=</span>ingress-nginx<span class="token punctuation">..</span><span class="token punctuation">..</span><span class="token punctuation">..</span>volume Active 30d kubernetes.io/metadata.name<span class="token operator">=</span>volume<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get ns --show-labels</span> NAME STATUS AGE LABELS daemonset Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>daemonset default Active 38d kubernetes.io/metadata.name<span class="token operator">=</span>default deployment Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>deployment ingress-nginx Active 2d13h app.kubernetes.io/instance<span class="token operator">=</span>ingress-nginx,app.kubernetes.io/name<span class="token operator">=</span>ingress-nginx,kubernetes.io/metadata.name<span class="token operator">=</span>ingress-nginx <span class="token punctuation">..</span><span class="token punctuation">..</span><span class="token punctuation">..</span> volume Active 30d kubernetes.io/metadata.name<span class="token operator">=</span>volume[root@k8scloude1 network]# kubectl get ns --show-labels NAME STATUS AGE LABELS daemonset Active 22d kubernetes.io/metadata.name=daemonset default Active 38d kubernetes.io/metadata.name=default deployment Active 22d kubernetes.io/metadata.name=deployment ingress-nginx Active 2d13h app.kubernetes.io/instance=ingress-nginx,app.kubernetes.io/name=ingress-nginx,kubernetes.io/metadata.name=ingress-nginx ...... volume Active 30d kubernetes.io/metadata.name=volume
给default命名空间打name=default标签。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label ns default name=default</span>namespace/default labeled<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get ns --show-labels</span>NAME STATUS AGE LABELSdaemonset Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>daemonsetdefault Active 38d kubernetes.io/metadata.name<span class="token operator">=</span>default,name<span class="token operator">=</span>defaultdeployment Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>deployment<span class="token punctuation">..</span><span class="token punctuation">..</span><span class="token punctuation">..</span>volume Active 30d kubernetes.io/metadata.name<span class="token operator">=</span>volume<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label ns default name=default</span> namespace/default labeled <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get ns --show-labels</span> NAME STATUS AGE LABELS daemonset Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>daemonset default Active 38d kubernetes.io/metadata.name<span class="token operator">=</span>default,name<span class="token operator">=</span>default deployment Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>deployment <span class="token punctuation">..</span><span class="token punctuation">..</span><span class="token punctuation">..</span> volume Active 30d kubernetes.io/metadata.name<span class="token operator">=</span>volume[root@k8scloude1 network]# kubectl label ns default name=default namespace/default labeled [root@k8scloude1 network]# kubectl get ns --show-labels NAME STATUS AGE LABELS daemonset Active 22d kubernetes.io/metadata.name=daemonset default Active 38d kubernetes.io/metadata.name=default,name=default deployment Active 22d kubernetes.io/metadata.name=deployment ...... volume Active 30d kubernetes.io/metadata.name=volume
下面定义通过namespaceSelector命名空间来控制的入站网络策略,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,允许标签为name: default的namespace下的所有pod可以访问pod1的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token comment">#允许哪些客户端可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#允许标签为name: default的namespace下的pod访问</span><span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token comment">#允许哪些客户端可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#允许标签为name: default的namespace下的pod访问</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> default <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Ingress #ingress:入站规则 ingress: #允许哪些客户端可以访问 - from: - namespaceSelector: matchLabels: #允许标签为name: default的namespace下的pod访问 name: default ports: - protocol: TCP port: 80
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy -o wide</span>NAME POD-SELECTOR AGEmy-network-policy <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 3h1m<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy -o wide</span> NAME POD-SELECTOR AGE my-network-policy <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 3h1m[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured [root@k8scloude1 network]# kubectl get networkpolicy -o wide NAME POD-SELECTOR AGE my-network-policy test=pod1 3h1m
在podnsclient里访问svc, 访问成功,default命名空间下的任何pod都能访问pod1svc。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide -n default</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATESpodnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 21m <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span>/home <span class="token comment"># curl pod1svc.network</span><span class="token number">111</span>/home <span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide -n default</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 21m <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span> /home <span class="token comment"># curl pod1svc.network</span> <span class="token number">111</span> /home <span class="token comment"># exit</span>[root@k8scloude1 network]# kubectl get pod -o wide -n default NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES podnsclient 1/1 Running 1 21m 10.244.251.230 k8scloude3 <none> <none> [root@k8scloude1 network]# kubectl exec -it podnsclient -n default -- sh /home # curl pod1svc.network 111 /home # exit
在podclient里访问svc,访问失败,可以看到当前namespace下的pod都不能访问pod1svc,default命名空间下的pod能访问pod1svc。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATESpod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 25m <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podclient -- sh</span>/home <span class="token comment"># curl pod1svc</span>^C/home <span class="token comment"># exit</span><span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 20h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 25m <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podclient -- sh</span> /home <span class="token comment"># curl pod1svc</span> ^C /home <span class="token comment"># exit</span> <span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span>[root@k8scloude1 network]# kubectl get pod -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 1/1 Running 1 20h 10.244.112.136 k8scloude2 <none> <none> pod2 1/1 Running 1 20h 10.244.251.227 k8scloude3 <none> <none> podclient 1/1 Running 1 25m 10.244.112.140 k8scloude2 <none> <none> [root@k8scloude1 network]# kubectl exec -it podclient -- sh /home # curl pod1svc ^C /home # exit command terminated with exit code 130
修改网络策略,设置只允许default命名空间里的特定pod能访问,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,允许标签为name: default的namespace下的标签为role: podclient的pod可以访问pod1的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token comment">#允许哪些客户端可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">role</span><span class="token punctuation">:</span> podclient<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token comment">#允许哪些客户端可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> default <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">role</span><span class="token punctuation">:</span> podclient <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Ingress #ingress:入站规则 ingress: #允许哪些客户端可以访问 - from: - namespaceSelector: matchLabels: name: default podSelector: matchLabels: role: podclient ports: - protocol: TCP port: 80
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured
在podnsclient里访问svc,访问失败,原因为:podnsclient虽然在default命名空间,但是pod的标签标签不是role: podclient。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span><span class="token comment">#访问不了</span>/home <span class="token comment"># curl pod1svc.network</span>^C/home <span class="token comment"># exit</span><span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide -n default --show-labels</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELSpodnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 31m <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">run</span><span class="token operator">=</span>podclient<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span> <span class="token comment">#访问不了</span> /home <span class="token comment"># curl pod1svc.network</span> ^C /home <span class="token comment"># exit</span> <span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide -n default --show-labels</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 31m <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">run</span><span class="token operator">=</span>podclient[root@k8scloude1 network]# kubectl exec -it podnsclient -n default -- sh #访问不了 /home # curl pod1svc.network ^C /home # exit command terminated with exit code 130 [root@k8scloude1 network]# kubectl get pod -o wide -n default --show-labels NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS podnsclient 1/1 Running 1 31m 10.244.251.230 k8scloude3 <none> <none> run=podclient
给podnsclient打role=podclient标签。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label pod podnsclient role=podclient -n default</span>pod/podnsclient labeled<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide -n default --show-labels</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELSpodnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 33m <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl label pod podnsclient role=podclient -n default</span> pod/podnsclient labeled <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide -n default --show-labels</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 33m <span class="token number">10.244</span>.251.230 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient[root@k8scloude1 network]# kubectl label pod podnsclient role=podclient -n default pod/podnsclient labeled [root@k8scloude1 network]# kubectl get pod -o wide -n default --show-labels NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES LABELS podnsclient 1/1 Running 1 33m 10.244.251.230 k8scloude3 <none> <none> role=podclient,run=podclient
设置标签之后,podnsclient就可以访问pod1svc了。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span>/home <span class="token comment"># curl pod1svc.network</span><span class="token number">111</span>/home <span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podnsclient -n default -- sh</span> /home <span class="token comment"># curl pod1svc.network</span> <span class="token number">111</span> /home <span class="token comment"># exit</span>[root@k8scloude1 network]# kubectl exec -it podnsclient -n default -- sh /home # curl pod1svc.network 111 /home # exit
修改网络策略,设置允许所有命名空间里标签为run=podclient的pod可以访问,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,允许所有命名空间下的标签为role: podclient的pod可以访问pod1的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token comment">#允许哪些客户端可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token comment">#允许所有命名空间里标签为role=podclient的pod可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">role</span><span class="token punctuation">:</span> podclient<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token comment">#允许哪些客户端可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token comment">#允许所有命名空间里标签为role=podclient的pod可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">role</span><span class="token punctuation">:</span> podclient <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Ingress #ingress:入站规则 ingress: #允许哪些客户端可以访问 - from: #允许所有命名空间里标签为role=podclient的pod可以访问 - namespaceSelector: matchLabels: podSelector: matchLabels: role: podclient ports: - protocol: TCP port: 80
查看标签为role=podclient的所有pod。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -A -l role=podclient</span>NAMESPACE NAME READY STATUS RESTARTS AGEdefault podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 39mnetwork podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 42m<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -A -l role=podclient --show-labels</span>NAMESPACE NAME READY STATUS RESTARTS AGE LABELSdefault podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 40m <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclientnetwork podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 43m <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -A -l role=podclient</span> NAMESPACE NAME READY STATUS RESTARTS AGE default podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 39m network podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 42m <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -A -l role=podclient --show-labels</span> NAMESPACE NAME READY STATUS RESTARTS AGE LABELS default podnsclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 40m <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient network podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 43m <span class="token assign-left variable">role</span><span class="token operator">=</span>podclient,run<span class="token operator">=</span>podclient[root@k8scloude1 network]# kubectl get pod -A -l role=podclient NAMESPACE NAME READY STATUS RESTARTS AGE default podnsclient 1/1 Running 1 39m network podclient 1/1 Running 1 42m [root@k8scloude1 network]# kubectl get pod -A -l role=podclient --show-labels NAMESPACE NAME READY STATUS RESTARTS AGE LABELS default podnsclient 1/1 Running 1 40m role=podclient,run=podclient network podclient 1/1 Running 1 43m role=podclient,run=podclient
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured
在podclient和podnsclient里访问svc,全都访问成功。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podclient -- sh</span>/home <span class="token comment"># curl pod1svc</span><span class="token number">111</span>/home <span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it -n default podnsclient -- sh</span>/home <span class="token comment"># curl pod1svc.network</span><span class="token number">111</span>/home <span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it podclient -- sh</span> /home <span class="token comment"># curl pod1svc</span> <span class="token number">111</span> /home <span class="token comment"># exit</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it -n default podnsclient -- sh</span> /home <span class="token comment"># curl pod1svc.network</span> <span class="token number">111</span> /home <span class="token comment"># exit</span>[root@k8scloude1 network]# kubectl exec -it podclient -- sh /home # curl pod1svc 111 /home # exit [root@k8scloude1 network]# kubectl exec -it -n default podnsclient -- sh /home # curl pod1svc.network 111 /home # exit
6.1.3 入站网络策略-IP地址控制
下面定义通过IP地址来控制的入站网络策略,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,只允许192.168.110.0/24这个网段的pod可以访问pod1的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token comment">#允许哪些客户端可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span><span class="token comment">#只允许192.168.110.0/24这个网段的进行访问</span><span class="token key atrule">cidr</span><span class="token punctuation">:</span> 192.168.110.0/24<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token comment">#允许哪些客户端可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span> <span class="token comment">#只允许192.168.110.0/24这个网段的进行访问</span> <span class="token key atrule">cidr</span><span class="token punctuation">:</span> 192.168.110.0/24 <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Ingress #ingress:入站规则 ingress: #允许哪些客户端可以访问 - from: - ipBlock: #只允许192.168.110.0/24这个网段的进行访问 cidr: 192.168.110.0/24 ports: - protocol: TCP port: 80
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured
修改网络策略,设置只允许192.168.110.0/24这个网段的进行访问,但是192.168.110.128不可以访问,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,只允许192.168.110.0/24这个网段的pod可以访问pod1的80端口(TCP),但是192.168.110.128这个IP的pod不可以访问pod1的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token comment">#ingress:入站规则</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token comment">#允许哪些客户端可以访问</span><span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span><span class="token key atrule">cidr</span><span class="token punctuation">:</span> 192.168.110.0/24<span class="token comment">#192.168.110.128不可以访问</span><span class="token key atrule">except</span><span class="token punctuation">:</span><span class="token punctuation">-</span> 192.168.110.128/24<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token comment">#ingress:入站规则</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token comment">#允许哪些客户端可以访问</span> <span class="token punctuation">-</span> <span class="token key atrule">from</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span> <span class="token key atrule">cidr</span><span class="token punctuation">:</span> 192.168.110.0/24 <span class="token comment">#192.168.110.128不可以访问</span> <span class="token key atrule">except</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> 192.168.110.128/24 <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Ingress #ingress:入站规则 ingress: #允许哪些客户端可以访问 - from: - ipBlock: cidr: 192.168.110.0/24 #192.168.110.128不可以访问 except: - 192.168.110.128/24 ports: - protocol: TCP port: 80
6.2 出站网络策略
6.2.1 出站网络策略-pod标签选择器
下面配置出站网络策略,就是pod1能访问谁?
现在有pod1,pod2。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATESpod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 153m <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 153m <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>[root@k8scloude1 network]# kubectl get pod -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 1/1 Running 1 22h 10.244.112.136 k8scloude2 <none> <none> pod2 1/1 Running 1 22h 10.244.251.227 k8scloude3 <none> <none> podclient 1/1 Running 1 153m 10.244.112.140 k8scloude2 <none> <none>
创建pod3。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># sed 's/podtest/pod3/' pod.yaml | kubectl apply -f -</span>pod/pod3 created<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span>NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATESpod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>pod3 <span class="token number">1</span>/1 Running <span class="token number">0</span> 5s <span class="token number">10.244</span>.112.141 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 155m <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># sed 's/podtest/pod3/' pod.yaml | kubectl apply -f -</span> pod/pod3 created <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get pod -o wide</span> NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.112.136 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> pod2 <span class="token number">1</span>/1 Running <span class="token number">1</span> 22h <span class="token number">10.244</span>.251.227 k8scloude3 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> pod3 <span class="token number">1</span>/1 Running <span class="token number">0</span> 5s <span class="token number">10.244</span>.112.141 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span> podclient <span class="token number">1</span>/1 Running <span class="token number">1</span> 155m <span class="token number">10.244</span>.112.140 k8scloude2 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token operator"><</span>none<span class="token operator">></span>[root@k8scloude1 network]# sed 's/podtest/pod3/' pod.yaml | kubectl apply -f - pod/pod3 created [root@k8scloude1 network]# kubectl get pod -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod1 1/1 Running 1 22h 10.244.112.136 k8scloude2 <none> <none> pod2 1/1 Running 1 22h 10.244.251.227 k8scloude3 <none> <none> pod3 1/1 Running 0 5s 10.244.112.141 k8scloude2 <none> <none> podclient 1/1 Running 1 155m 10.244.112.140 k8scloude2 <none> <none>
修改pod3的首页文件index.html。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod3 -- sh -c "echo 333 > /usr/share/nginx/html/index.html"</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod3 -- sh -c "echo 333 > /usr/share/nginx/html/index.html"</span>[root@k8scloude1 network]# kubectl exec -it pod3 -- sh -c "echo 333 > /usr/share/nginx/html/index.html"
访问pod3,首页文件已经改变。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># curl 10.244.112.141</span><span class="token number">333</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># curl 10.244.112.141</span> <span class="token number">333</span>[root@k8scloude1 network]# curl 10.244.112.141 333
给pod3创建svc,类型默认(ClusterIP)就行。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod3svc pod pod3 --port=80</span>service/pod3svc exposed<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span>NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTORpod1svc LoadBalancer <span class="token number">10.103</span>.187.15 <span class="token number">192.168</span>.110.188 <span class="token number">80</span>:31116/TCP 22h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1pod2svc LoadBalancer <span class="token number">10.110</span>.132.42 <span class="token number">192.168</span>.110.189 <span class="token number">80</span>:32118/TCP 22h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2pod3svc ClusterIP <span class="token number">10.103</span>.213.71 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">80</span>/TCP 11s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod3<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl expose --name=pod3svc pod pod3 --port=80</span> service/pod3svc exposed <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide</span> NAME TYPE CLUSTER-IP EXTERNAL-IP PORT<span class="token punctuation">(</span>S<span class="token punctuation">)</span> AGE SELECTOR pod1svc LoadBalancer <span class="token number">10.103</span>.187.15 <span class="token number">192.168</span>.110.188 <span class="token number">80</span>:31116/TCP 22h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 pod2svc LoadBalancer <span class="token number">10.110</span>.132.42 <span class="token number">192.168</span>.110.189 <span class="token number">80</span>:32118/TCP 22h <span class="token assign-left variable">test</span><span class="token operator">=</span>pod2 pod3svc ClusterIP <span class="token number">10.103</span>.213.71 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">80</span>/TCP 11s <span class="token assign-left variable">test</span><span class="token operator">=</span>pod3[root@k8scloude1 network]# kubectl expose --name=pod3svc pod pod3 --port=80 service/pod3svc exposed [root@k8scloude1 network]# kubectl get svc -o wide NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR pod1svc LoadBalancer 10.103.187.15 192.168.110.188 80:31116/TCP 22h test=pod1 pod2svc LoadBalancer 10.110.132.42 192.168.110.189 80:32118/TCP 22h test=pod2 pod3svc ClusterIP 10.103.213.71 <none> 80/TCP 11s test=pod3
下面定义通过pod标签选择器来控制的出站网络策略,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,pod1只能访问当前命名空间标签为 test: pod3的pod的80端口(TCP)。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Egress<span class="token key atrule">egress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span><span class="token comment">#只能访问标签为 test: pod3的pod</span><span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod3<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Egress <span class="token key atrule">egress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span> <span class="token comment">#只能访问标签为 test: pod3的pod</span> <span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod3 <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Egress egress: - to: #只能访问标签为 test: pod3的pod - podSelector: matchLabels: test: pod3 ports: - protocol: TCP port: 80
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span>No resources found <span class="token keyword">in</span> network namespace.<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy created<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span>NAME POD-SELECTOR AGEmy-network-policy <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 2s<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span> No resources found <span class="token keyword">in</span> network namespace. <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy created <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span> NAME POD-SELECTOR AGE my-network-policy <span class="token assign-left variable">test</span><span class="token operator">=</span>pod1 2s[root@k8scloude1 network]# kubectl get networkpolicy No resources found in network namespace. [root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy created [root@k8scloude1 network]# kubectl get networkpolicy NAME POD-SELECTOR AGE my-network-policy test=pod1 2s
进入pod1访问其他pod,可以看到在pod1中可以通过IP地址访问pod3,但是不能通过pod3svc访问pod3,原因为:如果想通过svc访问pod,pod需要去kube-dns那里查询svc的IP地址,但是现在pod1没有kube-dns的访问权限。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span><span class="token comment"># curl 10.244.251.227</span>^C<span class="token comment"># curl 10.244.112.141</span><span class="token number">333</span><span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span><span class="token comment"># curl 10.244.112.141</span><span class="token number">333</span><span class="token comment"># curl pod3svc</span>^C<span class="token comment"># exit </span><span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span> <span class="token comment"># curl 10.244.251.227</span> ^C <span class="token comment"># curl 10.244.112.141</span> <span class="token number">333</span> <span class="token comment"># exit</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span> <span class="token comment"># curl 10.244.112.141</span> <span class="token number">333</span> <span class="token comment"># curl pod3svc</span> ^C <span class="token comment"># exit </span> <span class="token builtin class-name">command</span> terminated with <span class="token builtin class-name">exit</span> code <span class="token number">130</span>[root@k8scloude1 network]# kubectl exec -it pod1 -- sh # curl 10.244.251.227 ^C # curl 10.244.112.141 333 # exit [root@k8scloude1 network]# kubectl exec -it pod1 -- sh # curl 10.244.112.141 333 # curl pod3svc ^C # exit command terminated with exit code 130
6.2.2 出站网络策略-pod标签选择器和namespaceSelector命名空间选择器
查看命名空间kube-system的标签。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get ns --show-labels</span>NAME STATUS AGE LABELSdaemonset Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>daemonsetdefault Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>default,name<span class="token operator">=</span>defaultdeployment Active 23d kubernetes.io/metadata.name<span class="token operator">=</span>deploymentingress-nginx Active 2d16h app.kubernetes.io/instance<span class="token operator">=</span>ingress-nginx,app.kubernetes.io/name<span class="token operator">=</span>ingress-nginx,kubernetes.io/metadata.name<span class="token operator">=</span>ingress-nginxjob Active 7d23h kubernetes.io/metadata.name<span class="token operator">=</span>jobkube-node-lease Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>kube-node-leasekube-public Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>kube-publickube-system Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>kube-system<span class="token punctuation">..</span><span class="token punctuation">..</span><span class="token punctuation">..</span>volume Active 30d kubernetes.io/metadata.name<span class="token operator">=</span>volume<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get ns --show-labels</span> NAME STATUS AGE LABELS daemonset Active 22d kubernetes.io/metadata.name<span class="token operator">=</span>daemonset default Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>default,name<span class="token operator">=</span>default deployment Active 23d kubernetes.io/metadata.name<span class="token operator">=</span>deployment ingress-nginx Active 2d16h app.kubernetes.io/instance<span class="token operator">=</span>ingress-nginx,app.kubernetes.io/name<span class="token operator">=</span>ingress-nginx,kubernetes.io/metadata.name<span class="token operator">=</span>ingress-nginx job Active 7d23h kubernetes.io/metadata.name<span class="token operator">=</span>job kube-node-lease Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>kube-node-lease kube-public Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>kube-public kube-system Active 39d kubernetes.io/metadata.name<span class="token operator">=</span>kube-system <span class="token punctuation">..</span><span class="token punctuation">..</span><span class="token punctuation">..</span> volume Active 30d kubernetes.io/metadata.name<span class="token operator">=</span>volume[root@k8scloude1 network]# kubectl get ns --show-labels NAME STATUS AGE LABELS daemonset Active 22d kubernetes.io/metadata.name=daemonset default Active 39d kubernetes.io/metadata.name=default,name=default deployment Active 23d kubernetes.io/metadata.name=deployment ingress-nginx Active 2d16h app.kubernetes.io/instance=ingress-nginx,app.kubernetes.io/name=ingress-nginx,kubernetes.io/metadata.name=ingress-nginx job Active 7d23h kubernetes.io/metadata.name=job kube-node-lease Active 39d kubernetes.io/metadata.name=kube-node-lease kube-public Active 39d kubernetes.io/metadata.name=kube-public kube-system Active 39d kubernetes.io/metadata.name=kube-system ...... volume Active 30d kubernetes.io/metadata.name=volume
查看kube-dns服务的端口。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide -n kube-system | grep dns</span>kube-dns ClusterIP <span class="token number">10.96</span>.0.10 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">53</span>/UDP,53/TCP,9153/TCP 39d k8s-app<span class="token operator">=</span>kube-dns<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get svc -o wide -n kube-system | grep dns</span> kube-dns ClusterIP <span class="token number">10.96</span>.0.10 <span class="token operator"><</span>none<span class="token operator">></span> <span class="token number">53</span>/UDP,53/TCP,9153/TCP 39d k8s-app<span class="token operator">=</span>kube-dns[root@k8scloude1 network]# kubectl get svc -o wide -n kube-system | grep dns kube-dns ClusterIP 10.96.0.10 <none> 53/UDP,53/TCP,9153/TCP 39d k8s-app=kube-dns
修改网络策略,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,pod1能访问kube-system命名空间下的所有pod和当前命名空间下标签为test: pod3的pod,访问端口为80和53。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Egress<span class="token key atrule">egress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">kubernetes.io/metadata.name</span><span class="token punctuation">:</span> kube<span class="token punctuation">-</span>system<span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">test</span><span class="token punctuation">:</span> pod3<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> UDP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">53</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> <span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>network<span class="token punctuation">-</span>policy <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Egress <span class="token key atrule">egress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">namespaceSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">kubernetes.io/metadata.name</span><span class="token punctuation">:</span> kube<span class="token punctuation">-</span>system <span class="token punctuation">-</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">test</span><span class="token punctuation">:</span> pod3 <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">80</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> UDP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">53</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Egress egress: - to: - namespaceSelector: matchLabels: kubernetes.io/metadata.name: kube-system - podSelector: matchLabels: test: pod3 ports: - protocol: TCP port: 80 - protocol: UDP port: 53
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured
进入pod1访问其他pod,可以看到在pod1中可以通过IP地址访问pod3,也可以通过pod3svc访问pod3了。
<span class="token comment">#这样就可以通过svc访问了</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span><span class="token comment"># curl 10.244.112.141</span><span class="token number">333</span><span class="token comment"># curl pod3svc</span><span class="token number">333</span><span class="token comment"># exit</span><span class="token comment">#这样就可以通过svc访问了</span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span> <span class="token comment"># curl 10.244.112.141</span> <span class="token number">333</span> <span class="token comment"># curl pod3svc</span> <span class="token number">333</span> <span class="token comment"># exit</span>#这样就可以通过svc访问了 [root@k8scloude1 network]# kubectl exec -it pod1 -- sh # curl 10.244.112.141 333 # curl pod3svc 333 # exit
6.2.3 优化出站网络策略
但是这样写有问题:pod1可以访问标签为test: pod3的pod的80端口和53端口。
修改网络策略,如下网络策略的功能为:把名为my-network-policy的网络策略应用到pod1,pod1能访问kube-system命名空间下的所有pod的53端口,pod1能访问当前命名空间下标签为test: pod3的pod的80端口。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span>apiVersion: networking.k8s.io/v1kind: NetworkPolicymetadata:name: my-network-policyspec:<span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span>podSelector:<span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span>matchLabels:<span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span>test: pod1<span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span>policyTypes:- Egressegress:- to:- namespaceSelector:matchLabels:kubernetes.io/metadata.name: kube-systemports:- protocol: UDPport: <span class="token number">53</span>- to:- podSelector:matchLabels:test: pod3ports:- protocol: TCPport: <span class="token number">80</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># vim networkpolicy.yaml </span> <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># cat networkpolicy.yaml </span> apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: <span class="token comment">#podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod</span> podSelector: <span class="token comment">#如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod</span> matchLabels: <span class="token comment">#test: pod1:把网络策略应用到标签为test: pod1的pod上</span> test: pod1 <span class="token comment">#policyTypes:启用的是入站规则还是出站规则</span> policyTypes: - Egress egress: - to: - namespaceSelector: matchLabels: kubernetes.io/metadata.name: kube-system ports: - protocol: UDP port: <span class="token number">53</span> - to: - podSelector: matchLabels: test: pod3 ports: - protocol: TCP port: <span class="token number">80</span>[root@k8scloude1 network]# vim networkpolicy.yaml [root@k8scloude1 network]# cat networkpolicy.yaml apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: my-network-policy spec: #podSelector网络策略要应用到哪个pod上,通过标签的方式来控制pod,只能应用到和网络策略相同namespace的pod podSelector: #如果matchLabels下面没写标签,则应用网络策略到当前namespace下的所有pod matchLabels: #test: pod1:把网络策略应用到标签为test: pod1的pod上 test: pod1 #policyTypes:启用的是入站规则还是出站规则 policyTypes: - Egress egress: - to: - namespaceSelector: matchLabels: kubernetes.io/metadata.name: kube-system ports: - protocol: UDP port: 53 - to: - podSelector: matchLabels: test: pod3 ports: - protocol: TCP port: 80
应用网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io/my-network-policy configured<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl apply -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io/my-network-policy configured[root@k8scloude1 network]# kubectl apply -f networkpolicy.yaml networkpolicy.networking.k8s.io/my-network-policy configured
进入pod1访问其他pod,可以看到在pod1中可以通过IP地址访问pod3,也可以通过pod3svc访问pod3了。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span><span class="token comment"># curl 10.244.112.141</span><span class="token number">333</span><span class="token comment"># curl pod3svc</span><span class="token number">333</span><span class="token comment"># exit</span><span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl exec -it pod1 -- sh</span> <span class="token comment"># curl 10.244.112.141</span> <span class="token number">333</span> <span class="token comment"># curl pod3svc</span> <span class="token number">333</span> <span class="token comment"># exit</span>[root@k8scloude1 network]# kubectl exec -it pod1 -- sh # curl 10.244.112.141 333 # curl pod3svc 333 # exit
删除网络策略。
<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl delete -f networkpolicy.yaml </span>networkpolicy.networking.k8s.io <span class="token string">"my-network-policy"</span> deleted<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span>No resources found <span class="token keyword">in</span> network namespace.<span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl delete -f networkpolicy.yaml </span> networkpolicy.networking.k8s.io <span class="token string">"my-network-policy"</span> deleted <span class="token punctuation">[</span>root@k8scloude1 network<span class="token punctuation">]</span><span class="token comment"># kubectl get networkpolicy</span> No resources found <span class="token keyword">in</span> network namespace.[root@k8scloude1 network]# kubectl delete -f networkpolicy.yaml networkpolicy.networking.k8s.io "my-network-policy" deleted [root@k8scloude1 network]# kubectl get networkpolicy No resources found in network namespace.
6.2.4 出站网络策略-指定端口范围
在Kubernetes v1.22版本,出了个新特性,在编写 NetworkPolicy 时,你可以针对一个端口范围而不是某个固定端口。这一目的可以通过使用 endPort 字段来实现,如下例所示:
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> multi<span class="token punctuation">-</span>port<span class="token punctuation">-</span>egress<span class="token key atrule">namespace</span><span class="token punctuation">:</span> default<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span><span class="token key atrule">matchLabels</span><span class="token punctuation">:</span><span class="token key atrule">role</span><span class="token punctuation">:</span> db<span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Egress<span class="token key atrule">egress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span><span class="token key atrule">cidr</span><span class="token punctuation">:</span> 10.0.0.0/24<span class="token key atrule">ports</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP<span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">32000</span><span class="token key atrule">endPort</span><span class="token punctuation">:</span> <span class="token number">32768</span><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> multi<span class="token punctuation">-</span>port<span class="token punctuation">-</span>egress <span class="token key atrule">namespace</span><span class="token punctuation">:</span> default <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token key atrule">matchLabels</span><span class="token punctuation">:</span> <span class="token key atrule">role</span><span class="token punctuation">:</span> db <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Egress <span class="token key atrule">egress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">to</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">ipBlock</span><span class="token punctuation">:</span> <span class="token key atrule">cidr</span><span class="token punctuation">:</span> 10.0.0.0/24 <span class="token key atrule">ports</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token key atrule">protocol</span><span class="token punctuation">:</span> TCP <span class="token key atrule">port</span><span class="token punctuation">:</span> <span class="token number">32000</span> <span class="token key atrule">endPort</span><span class="token punctuation">:</span> <span class="token number">32768</span>apiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: multi-port-egress namespace: default spec: podSelector: matchLabels: role: db policyTypes: - Egress egress: - to: - ipBlock: cidr: 10.0.0.0/24 ports: - protocol: TCP port: 32000 endPort: 32768
上面的规则允许名字空间 default 中所有带有标签 role: db 的 Pod 使用 TCP 协议 与 10.0.0.0/24 范围内的 IP 通信,只要目标端口介于 32000 和 32768 之间就可以。
使用此字段时存在以下限制:
- 作为一种 Beta 阶段的特性,端口范围设定默认是被启用的。要在整个集群 范围内禁止使用 endPort 字段,你需要为 API 服务器设置 -feature-gates=NetworkPolicyEndPort=false,… 以禁用 NetworkPolicyEndPort 特性。
- endPort 字段必须等于或者大于 port 字段的值。
- port,endPort 两个字段的设置值都只能是数字。
注意:你的集群所使用的 CNI 网络插件 必须支持在 NetworkPolicy 规约中使用 endPort 字段。 如果你的网络插件 不支持 endPort 字段,而你指定了一个包含 endPort 字段的 NetworkPolicy, 策略只对单个 port 字段生效。
6.3 默认网络策略
6.3.1 默认拒绝所有入站流量
可以通过创建选择所有容器但不允许任何进入这些容器的入站流量的 NetworkPolicy 来为命名空间创建 “default” 隔离策略。这样可以确保即使容器没有选择其他任何 NetworkPolicy,也仍然可以被隔离。 此策略不会更改默认的出口隔离行为。
默认拒绝所有入站流量,网络策略如下:
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token punctuation">-</span>deny<span class="token punctuation">-</span>ingress<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token punctuation">-</span>deny<span class="token punctuation">-</span>ingress <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> IngressapiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: default-deny-ingress spec: podSelector: {} policyTypes: - Ingress
6.3.2 默认允许所有入站流量
如果要允许所有流量进入某个命名空间中的所有 Pod(即使添加了导致某些 Pod 被视为 “隔离”的策略),则可以创建一个策略来明确允许该名字空间中的所有流量。
默认允许所有入站流量,网络策略如下:
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> allow<span class="token punctuation">-</span>all<span class="token punctuation">-</span>ingress<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">ingress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> allow<span class="token punctuation">-</span>all<span class="token punctuation">-</span>ingress <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">ingress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> IngressapiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: allow-all-ingress spec: podSelector: {} ingress: - {} policyTypes: - Ingress
6.3.3 默认拒绝所有出站流量
可以通过创建选择所有容器但不允许来自这些容器的任何出站流量的 NetworkPolicy 来为名字空间创建 “default” egress 隔离策略。
此策略可以确保即使没有被其他任何 NetworkPolicy 选择的 Pod 也不会被允许流出流量。 此策略不会更改默认的入站流量隔离行为。
默认拒绝所有出站流量,网络策略如下:
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token punctuation">-</span>deny<span class="token punctuation">-</span>egress<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Egress<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token punctuation">-</span>deny<span class="token punctuation">-</span>egress <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> EgressapiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: default-deny-egress spec: podSelector: {} policyTypes: - Egress
6.3.4 默认允许所有出站流量
如果要允许来自名字空间中所有 Pod 的所有流量(即使添加了导致某些 Pod 被视为“隔离”的策略), 则可以创建一个策略,该策略明确允许该名字空间中的所有出站流量。
默认允许所有出站流量,网络策略如下:
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> allow<span class="token punctuation">-</span>all<span class="token punctuation">-</span>egress<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">egress</span><span class="token punctuation">:</span><span class="token punctuation">-</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Egress<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> allow<span class="token punctuation">-</span>all<span class="token punctuation">-</span>egress <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">egress</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> EgressapiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: allow-all-egress spec: podSelector: {} egress: - {} policyTypes: - Egress
6.3.5 默认拒绝所有入口和所有出站流量
你可以为名字空间创建“默认”策略,以通过在该名字空间中创建以下 NetworkPolicy 来阻止所有入站和出站流量。
此策略可以确保即使没有被其他任何 NetworkPolicy 选择的 Pod 也不会被 允许入站或出站流量。
默认拒绝所有入口和所有出站流量,网络策略如下:
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1<span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy<span class="token key atrule">metadata</span><span class="token punctuation">:</span><span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token punctuation">-</span>deny<span class="token punctuation">-</span>all<span class="token key atrule">spec</span><span class="token punctuation">:</span><span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token key atrule">policyTypes</span><span class="token punctuation">:</span><span class="token punctuation">-</span> Ingress<span class="token punctuation">-</span> Egress<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> networking.k8s.io/v1 <span class="token key atrule">kind</span><span class="token punctuation">:</span> NetworkPolicy <span class="token key atrule">metadata</span><span class="token punctuation">:</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> default<span class="token punctuation">-</span>deny<span class="token punctuation">-</span>all <span class="token key atrule">spec</span><span class="token punctuation">:</span> <span class="token key atrule">podSelector</span><span class="token punctuation">:</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> <span class="token key atrule">policyTypes</span><span class="token punctuation">:</span> <span class="token punctuation">-</span> Ingress <span class="token punctuation">-</span> EgressapiVersion: networking.k8s.io/v1 kind: NetworkPolicy metadata: name: default-deny-all spec: podSelector: {} policyTypes: - Ingress - Egress
七.总结
网络策略(NetworkPolicy)是Kubernetes集群中一个非常重要的安全控制措施,可以帮助我们保护Kubernetes集群的网络安全。在本文中,我们已经学习了什么是网络策略(NetworkPolicy),以及如何在Kubernetes集群中使用网络策略(NetworkPolicy)来保护网络安全。
通过网络策略(NetworkPolicy)示例,我们展示了如何使用网络策略(NetworkPolicy)来限制Pod之间的流量访问。
在Kubernetes集群中使用网络策略(NetworkPolicy)可以提高网络的安全性,但也需要注意以下几点:
- 应该避免创建过于复杂的网络策略(NetworkPolicy),因为这可能会导致网络通信中断或延迟。
- 在创建网络策略(NetworkPolicy)前,需要确保已仔细检查其规则,并确认这些规则符合预期。
- 当修改或删除一个网络策略(NetworkPolicy)时,需要确保所有Pod都能够正常通信。
最后,希望本文可以帮助读者了解Kubernetes的网络策略(NetworkPolicy)并在实践中得到应用。