AKS:连接到专用网络上不同 aks 集群上的外部服务
AKS: connect to external service on a different aks cluster on private network
我的目标是从 pod 调用 aks 集群 (aks1) 上的服务或第二个 aks 集群 (aks2) 上的服务。
这些集群将位于不同的区域,并且应该通过专用网络进行通信。
Azure CNI 插件。
因此,经过一些阅读和一些视频收听后,对我来说,最好的选择是在 AKS2 上使用 externalName 服务,调用在自定义私有 DNS 区域中定义的服务 (ecommerce.private.eu.dev), 是这两个 VNets 之前配对的。
This seems the vnet giving the address space to aks services:
dev-vnet 10.0.0.0/14
=======================================
dev-test1-aks v1.22.4 - 1 node
dev-test1-vnet 11.0.0.0/16
dev-test2-aks v1.22.4 - 1 node
dev-test2-vnet 11.1.0.0/16
经过大量试验,我所能得到的只是 pods 网络之间的连接,并且永远无法从其他集群到达服务网络。
- 我没有看到任何活动的防火墙
- 我查看了所有三个网络:dev-test1-vnet、dev-test2-vnet、dev-vnet(服务 CIDR)
- 我创建了一个私有 DNS 区域 private.eu.dev,我在其中放置了应由 externalName 服务解析的“电子商务”A 记录 (10.0.129.155)
dev-test1-aks(欧盟集群):
kubectl create deployment eu-ecommerce --image=k8s.gcr.io/echoserver:1.4 --port=8080 --replicas=1
kubectl expose deployment eu-ecommerce --type=ClusterIP --port=8080 --name=eu-ecommerce
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.1.1/deploy/static/provider/cloud/deploy.yaml
kubectl create ingress eu-ecommerce --class=nginx --rule=eu.ecommerce/*=eu-ecommerce:8080 -o yaml --dry-run=client
这是入口规则:
❯ kubectl --context=dev-test1-aks get ingress eu-ecommerce-2 -o yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: eu-ecommerce-2
namespace: default
spec:
ingressClassName: nginx
rules:
- host: lb.private.eu.dev
http:
paths:
- backend:
service:
name: eu-ecommerce
port:
number: 8080
path: /ecommerce
pathType: Prefix
status:
loadBalancer:
ingress:
- ip: 20.xxxxx
这是我在 dev-test2-aks 上尝试过的外部名称之一:
apiVersion: v1
kind: Service
metadata:
name: eu-services
namespace: default
spec:
type: ExternalName
externalName: ecommerce.private.eu.dev
ports:
- port: 8080
protocol: TCP
这些是我的一些测试:
# --- Test externalName
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://eu-services:8080
: '
wget: cant connect to remote host (10.0.129.155): Connection timed out
'
# --- Test connectivity AKS1 -> eu-ecommerce service
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://eu-ecommerce:8080
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://10.0.129.155:8080
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://eu-ecommerce.default.svc.cluster.local:8080
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://ecommerce.private.eu.dev:8080
# OK client_address=11.0.0.11
# --- Test connectivity AKS2 -> eu-ecommerce POD
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://11.0.0.103:8080
#> OK
# --- Test connectivity AKS2 -> eu-ecommerce service
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://ecommerce.private.eu.dev:8080
#> FAIL
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://10.0.129.155:8080
# --- Test connectivity - LB private IP
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget --no-cache -qO- http://lb.private.eu.dev/ecommerce
#> OK
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget --no-cache -qO- http://lb.private.eu.dev/ecommerce
#> KO wget: can't connect to remote host (10.0.11.164): Connection timed out
# --- Traceroute gives no informations
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- traceroute -n -m4 ecommerce.private.eu.dev
: '
* * *
3 * * *
4 * * *
'
# --- test2-aks can see the private dns zone and resolve the hostname
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- nslookup ecommerce.private.eu.dev
: ' Server: 10.0.0.10
Address 1: 10.0.0.10 kube-dns.kube-system.svc.cluster.local
Name: ecommerce.private.eu.dev
Address 1: 10.0.129.155
'
我还为 aks 网络创建了入站和出站 network policies:
- 在 dev-aks (10.0/16) 上允许所有来自 11.1/16 和 11.0/16 的传入
- 在 dev-test2-aks 上允许任何出站
已阅读 文档:
- https://docs.microsoft.com/en-us/azure/aks/private-clusters#virtual-network-peering
- https://kubernetes.io/docs/concepts/services-networking/service/#externalname
- https://docs.microsoft.com/en-us/azure/dns/private-dns-getstarted-portal#create-a-private-dns-zone
- https://docs.microsoft.com/en-us/azure/virtual-network/virtual-network-peering-overview
- https://www.youtube.com/watch?v=J4S6AxYNDtM
在 AKS 中,服务 CIDR 不是您 vnet 地址的一部分 space,因此它不会以任何方式由 Azure 路由,因此您将无法从 pod 直接连接到服务另一个集群。
您需要做的是:
- 使用入口公开您的服务(我认为您正在尝试这样做,但命令显示仅生成入口规则的 yaml 而不是入口规则的实际创建)
- A-record 在您的私有 DNS 区域中应该指向您的负载均衡器的私有 IP 地址而不是您的服务 IP 地址
有了这个,您的 high-level 通信方案将如下所示:(aks1)pod -> (aks2)lb -> (aks2)ingress -> (aks2)service -> (aks2)pods
在对等 VNet 上使用 internal load balancer 解决。
此地址可路由且可从对等网络访问。所以您仍然可以使用 externalName 或 externalIP 从其他集群服务访问它
我的目标是从 pod 调用 aks 集群 (aks1) 上的服务或第二个 aks 集群 (aks2) 上的服务。 这些集群将位于不同的区域,并且应该通过专用网络进行通信。
Azure CNI 插件。
因此,经过一些阅读和一些视频收听后,对我来说,最好的选择是在 AKS2 上使用 externalName 服务,调用在自定义私有 DNS 区域中定义的服务 (ecommerce.private.eu.dev), 是这两个 VNets 之前配对的。
This seems the vnet giving the address space to aks services:
dev-vnet 10.0.0.0/14
=======================================
dev-test1-aks v1.22.4 - 1 node
dev-test1-vnet 11.0.0.0/16
dev-test2-aks v1.22.4 - 1 node
dev-test2-vnet 11.1.0.0/16
经过大量试验,我所能得到的只是 pods 网络之间的连接,并且永远无法从其他集群到达服务网络。
- 我没有看到任何活动的防火墙
- 我查看了所有三个网络:dev-test1-vnet、dev-test2-vnet、dev-vnet(服务 CIDR)
- 我创建了一个私有 DNS 区域 private.eu.dev,我在其中放置了应由 externalName 服务解析的“电子商务”A 记录 (10.0.129.155)
dev-test1-aks(欧盟集群):
kubectl create deployment eu-ecommerce --image=k8s.gcr.io/echoserver:1.4 --port=8080 --replicas=1
kubectl expose deployment eu-ecommerce --type=ClusterIP --port=8080 --name=eu-ecommerce
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.1.1/deploy/static/provider/cloud/deploy.yaml
kubectl create ingress eu-ecommerce --class=nginx --rule=eu.ecommerce/*=eu-ecommerce:8080 -o yaml --dry-run=client
这是入口规则:
❯ kubectl --context=dev-test1-aks get ingress eu-ecommerce-2 -o yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: eu-ecommerce-2
namespace: default
spec:
ingressClassName: nginx
rules:
- host: lb.private.eu.dev
http:
paths:
- backend:
service:
name: eu-ecommerce
port:
number: 8080
path: /ecommerce
pathType: Prefix
status:
loadBalancer:
ingress:
- ip: 20.xxxxx
这是我在 dev-test2-aks 上尝试过的外部名称之一:
apiVersion: v1
kind: Service
metadata:
name: eu-services
namespace: default
spec:
type: ExternalName
externalName: ecommerce.private.eu.dev
ports:
- port: 8080
protocol: TCP
这些是我的一些测试:
# --- Test externalName
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://eu-services:8080
: '
wget: cant connect to remote host (10.0.129.155): Connection timed out
'
# --- Test connectivity AKS1 -> eu-ecommerce service
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://eu-ecommerce:8080
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://10.0.129.155:8080
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://eu-ecommerce.default.svc.cluster.local:8080
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://ecommerce.private.eu.dev:8080
# OK client_address=11.0.0.11
# --- Test connectivity AKS2 -> eu-ecommerce POD
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://11.0.0.103:8080
#> OK
# --- Test connectivity AKS2 -> eu-ecommerce service
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://ecommerce.private.eu.dev:8080
#> FAIL
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget -qO- http://10.0.129.155:8080
# --- Test connectivity - LB private IP
kubectl --context=dev-test1-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget --no-cache -qO- http://lb.private.eu.dev/ecommerce
#> OK
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- wget --no-cache -qO- http://lb.private.eu.dev/ecommerce
#> KO wget: can't connect to remote host (10.0.11.164): Connection timed out
# --- Traceroute gives no informations
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- traceroute -n -m4 ecommerce.private.eu.dev
: '
* * *
3 * * *
4 * * *
'
# --- test2-aks can see the private dns zone and resolve the hostname
kubectl --context=dev-test2-aks run -it --rm --restart=Never busybox --image=gcr.io/google-containers/busybox -- nslookup ecommerce.private.eu.dev
: ' Server: 10.0.0.10
Address 1: 10.0.0.10 kube-dns.kube-system.svc.cluster.local
Name: ecommerce.private.eu.dev
Address 1: 10.0.129.155
'
我还为 aks 网络创建了入站和出站 network policies:
- 在 dev-aks (10.0/16) 上允许所有来自 11.1/16 和 11.0/16 的传入
- 在 dev-test2-aks 上允许任何出站
已阅读 文档:
- https://docs.microsoft.com/en-us/azure/aks/private-clusters#virtual-network-peering
- https://kubernetes.io/docs/concepts/services-networking/service/#externalname
- https://docs.microsoft.com/en-us/azure/dns/private-dns-getstarted-portal#create-a-private-dns-zone
- https://docs.microsoft.com/en-us/azure/virtual-network/virtual-network-peering-overview
- https://www.youtube.com/watch?v=J4S6AxYNDtM
在 AKS 中,服务 CIDR 不是您 vnet 地址的一部分 space,因此它不会以任何方式由 Azure 路由,因此您将无法从 pod 直接连接到服务另一个集群。
您需要做的是:
- 使用入口公开您的服务(我认为您正在尝试这样做,但命令显示仅生成入口规则的 yaml 而不是入口规则的实际创建)
- A-record 在您的私有 DNS 区域中应该指向您的负载均衡器的私有 IP 地址而不是您的服务 IP 地址
有了这个,您的 high-level 通信方案将如下所示:(aks1)pod -> (aks2)lb -> (aks2)ingress -> (aks2)service -> (aks2)pods
在对等 VNet 上使用 internal load balancer 解决。
此地址可路由且可从对等网络访问。所以您仍然可以使用 externalName 或 externalIP 从其他集群服务访问它