下载本书所使用的示例代码之后,切换到目录traffic-policy/sidecar下可以查看所有相关的代码文件。
启动httpbin服务示例应用,这个应用将会作为本任务的后端服务。切换到下载文件的根目录之后,运行以下命令:
kubectl create namespace sidecar kubectl label namespace sidecar istio-injection=enabled kubectl apply -n sidecar -f sidecar/app.yaml kubectl apply -n sidecar -f sidecar/sleep.yaml
上述命令执行成功之后,会在命名空间sidecar下创建相应的服务,接着运行以下命令在命名空间nosidecar下创建相应的服务:
kubectl create namespace nosidecar kubectl label namespace nosidecar istio-injection=enabled kubectl apply -n nosidecar -f sidecar/app.yaml kubectl apply -n nosidecar -f sidecar/sleep.yaml
至此,示例中所需要的服务和pod都已经创建完毕,等待启动成功之后,通过如下命令可以查看到命名空间sidecar下的sleep容器组对应的代理配置中的信息,里面包含了2个httpbin服务,分别来自于本命名空间sidecar和另外一个命名空间nosidecar,具体如下:
export SLEEP_POD_SIDECAR=$(kubectl get pod -l app=sleep -o jsonpath={.items..metadata.name} -n sidecar)
istioctl proxy-config clusters $SLEEP_POD_SIDECAR -n sidecar |grep httpbin
httpbin.nosidecar.svc.cluster.local 5678 - outbound EDS
httpbin.sidecar.svc.cluster.local 5678 - outbound EDS
同样,通过如下命令也可以查看到命名空间nosidecar下的sleep容器组对应的代理配置中的信息,里面包含了2个httpbin服务,分别来自于本命名空间nosidecar和另外一个命名空间sidecar,具体如下:
export SLEEP_POD_NOSIDECAR=$(kubectl get pod -l app=sleep -o jsonpath={.items..metadata.name} -n nosidecar)
istioctl proxy-config clusters $SLEEP_POD_NOSIDECAR -n nosidecar |grep httpbin
httpbin.nosidecar.svc.cluster.local 5678 - outbound EDS
httpbin.sidecar.svc.cluster.local 5678 - outbound EDS
可以看到,在命名空间sidecar或者nosidecar中的pod,保存了其他非本命名空间中的路由信息。如果这些非本命名空间中的资源比较多,不管是对内存消耗还是对路由控制来说,都会造成一定的资源消耗。为此,可以定义一个Sidecar资源,以此来限制这些服务只访问同一命名空间的其他服务,而不去保持其他非本命名空间中的路由信息。
创建一个Sidecar资源的定义非常简单,如下所示:
apiVersion: networking.istio.io/v1alpha3
kind: Sidecar
metadata:
name: sleep
spec:
workloadSelector:
labels:
app: sleep
egress:
- hosts:
- "sidecar/*"
将上述yaml内容保存为sidecar.yaml文件,或者切换到下载文件的根目录,并执行如下kubectl命令:
kubectl apply -n sidecar -f sidecar/sidecar.yaml
运行成功之后,可以看到,命令空间sidecar下的httpbin的路由只剩下了本命名空间之内的服务,如下所示:
export SLEEP_POD_SIDECAR=$(kubectl get pod -l app=sleep -o jsonpath={.items..metadata.name} -n sidecar)
istioctl proxy-config clusters $SLEEP_POD_SIDECAR -n sidecar |grep httpbin
httpbin.sidecar.svc.cluster.local 5678 - outbound EDS
而因为Sidecar资源只是针对命名空间sidecar定义的,所以命名空间nosidecar下的httpbin的路由仍然包含了非本命名空间之内的服务,如下所示:
export SLEEP_POD_NOSIDECAR=$(kubectl get pod -l app=sleep -o jsonpath={.items..metadata.name} -n nosidecar)
istioctl proxy-config clusters $SLEEP_POD_NOSIDECAR -n nosidecar |grep httpbin
httpbin.nosidecar.svc.cluster.local 5678 - outbound EDS
httpbin.sidecar.svc.cluster.local 5678 - outbound EDS
在命名空间sidecar下,通过sleep_POD尝试分别访问命名空间sidecar和nosidecar下的httpbin服务,执行结果如下:
export SLEEP_POD_SIDECAR=$(kubectl get pod -l app=sleep -o jsonpath={.items..metadata.name} -n sidecar)
export SLEEP_POD_NOSIDECAR=$(kubectl get pod -l app=sleep -o jsonpath={.items..
metadata.name} -n nosidecar)
kubectl exec -c sleep -it $SLEEP_POD_SIDECAR -n sidecar -- curl -v http://httpbin.
sidecar:5678/ip
* Trying 172.25.3.169...
* TCP_NODELAY set
* Connected to httpbin.sidecar (172.25.3.169) port 5678 (#0)
> GET /ip HTTP/1.1
> Host: httpbin.sidecar:5678
> User-Agent: curl/7.60.0
> Accept: */*
>
< HTTP/1.1 200 OK
< x-application-context: sample-service:5678
< content-type: application/json;charset=UTF-8
< date: Mon, 19 Aug 2019 08:30:02 GMT
< x-envoy-upstream-service-time: 22
< server: envoy
< transfer-encoding: chunked
<
* Connection #0 to host httpbin.sidecar left intact
{"ipAddress":"172.24.0.126","hostname":"httpbin-v1-5f698657b5-8b98w"}%
可以看到,命名空间sidecar下的sleep服务是可以成功访问同命名空间下的httpbin服务的。但是,如果试图去访问非本命名空间下的服务,就会遇到问题。命名空间sidecar下的sleep服务调用命名空间nosidecar下的httpbin服务,会返回502错误信息:
kubectl exec -c sleep -it $SLEEP_POD_SIDECAR -n sidecar -- curl -v http://httpbin. nosidecar:5678/ip * Trying 172.25.3.25... * TCP_NODELAY set * Connected to httpbin.nosidecar (172.25.3.25) port 5678 (#0) > GET /ip HTTP/1.1 > Host: httpbin.nosidecar:5678 > User-Agent: curl/7.60.0 > Accept: */* > < HTTP/1.1 502 Bad Gateway < location: http://httpbin.nosidecar:5678/ip < date: Mon, 19 Aug 2019 08:46:23 GMT < server: envoy < content-length: 0 < * Connection #0 to host httpbin.nosidecar left intact
由此可见,Sidecar资源对象为流量拦截转发提供了一定的控制能力,对于跨命名空间之间的服务无需访问的场景特别有用,可以对这种场景带来很好的效率提升和资源节省。