您当前的位置:首页 > 电脑百科 > 程序开发 > 编程百科

Kubernetes 多区域扩展轻松搞定:远不像你想象的那么难!

时间:2023-07-28 19:40:20  来源:51CTO  作者:

对 Kube.NETes 来说,跨越多个地域(Region)部署工作负载,这是个有趣的挑战。虽然从技术上来说,我们可以用分布在多个地域的节点创建集群,但因为会造成额外的延迟,通常并不建议这样做。

一种比较流行的替代方法是在每个地域部署一个集群,然后设法对多个集群进行必要的编排。

本文将介绍如何:

  1. 分别在北美、欧洲和东南亚各自创建一个集群。
  2. 创建第四个集群,将其作为上述三个集群的编排器。
  3. 设置一个将三个集群连接在一起的网络,从而实现跨集群的无缝通信。

本文涉及的操作均可通过脚本实现,只需最少量人工介入即可适用于 Terraform。相关代码请访问 LearnK8s Github

 

创建集群管理器

首先创建用于管理其余集群的集群。我们可以通过下列命令创建该集群并保存 Kubeconfig 文件。

bash
$ linode-cli lke cluster-create 
 --label cluster-manager 
 --region eu-west 
 --k8s_version 1.23
$ linode-cli lke kubeconfig-view "insert cluster id here" --text | tAIl +2 | base64 -d > kubeconfig-cluster-manager

随后可通过下列命令验证安装过程已成功完成:

bash
$ kubectl get pods -A --kubecnotallow=kubeconfig-cluster-manager

我们还需要在集群管理器中安装 Karmada,这个管理系统可以帮助我们跨越多个 Kubernetes 集群或多个云平台运行自己的云原生应用程序。Karmada 是一种安装在集群管理器中的控制平面,其他集群中需要安装代理程序。

该控制平面包含三个组件:

  1. 一个 API 服务器(API Server)
  2. 一个控制器管理器(Controller Manager)
  3. 一个调度器(Scheduler)

 

是否看起来觉得很熟悉?这是因为它与 Kubernetes 控制平面功能其实是相同组件,只不过 Karmada 能适用于多种集群。

理论部分说的差不多了,接下来开始看看具体要用的代码。我们可以使用 Helm 安装 Karmada API 服务器。为此可使用下列命令添加 Helm 仓库:

bash
$ helm repo add karmada-charts https://raw.githubusercontent.com/karmada-io/karmada/master/charts
$ helm repo list
NAME URL
karmada-charts https://raw.githubusercontent.com/karmada-io/karmada/master/charts

由于 Karmada API 服务器必须能被所有其他集群访问,因此我们必须:

  1. 从节点上将其暴露出来;并且
  2. 确保连接是可信任的。

因此首先需要通过下列命令获取承载了控制平面的节点的 IP 地址:

bash
kubectl get nodes -o jsnotallow='{.items[0].status.addresses[?(@.type=="ExternalIP")].address}' 
 --kubecnotallow=kubeconfig-cluster-manager

随后即可用下列命令安装 Karmada 控制平面:

bash
$ helm install karmada karmada-charts/karmada 
 --kubecnotallow=kubeconfig-cluster-manager 
 --create-namespace --namespace karmada-system 
 --versinotallow=1.2.0 
 --set apiServer.hostNetwork=false 
 --set apiServer.serviceType=NodePort 
 --set apiServer.nodePort=32443 
 --set certs.auto.hosts[0]="kubernetes.default.svc" 
 --set certs.auto.hosts[1]="*.etcd.karmada-system.svc.cluster.local" 
 --set certs.auto.hosts[2]="*.karmada-system.svc.cluster.local" 
 --set certs.auto.hosts[3]="*.karmada-system.svc" 
 --set certs.auto.hosts[4]="localhost" 
 --set certs.auto.hosts[5]="127.0.0.1" 
 --set certs.auto.hosts[6]="<insert the IP address of the node>"

安装完成后,即可通过下列命令获得 Kubeconfig 并连接到 Karmada API:

bash
kubectl get secret karmada-kubeconfig 
 --kubecnotallow=kubeconfig-cluster-manager 
 -n karmada-system 
 -o jsnotallow={.data.kubeconfig} | base64 -d > karmada-config

不过为什么这里要用另一个 Kubeconfig 文件?

按照设计,Karmada API 是为了取代标准的 Kubernetes API,同时依然提供了用户需要的全部功能。换句话说,我们可以借助 kubectl 创建横跨多个集群的部署。

在测试 Karmada API 和 kubectl 之前,还需要调整 Kubeconfig 文件。默认情况下生成的 Kubeconfig 只能在集群网络的内部使用。不过我们只需调整这几行内容就可以消除这一限制:

yaml
apiVersion: v1
kind: Config
clusters:
 - cluster:
 certificate-authority-data: LS0tLS1CRUdJTi…
 insecure-skip-tls-verify: false
 server: https://karmada-apiserver.karmada-system.svc.cluster.local:5443 # <- this works only in the cluster
 name: karmada-apiserver
# truncated

请将之前获取的节点 IP 地址替换进去:

yaml
apiVersion: v1
kind: Config
clusters:
 - cluster:
 certificate-authority-data: LS0tLS1CRUdJTi…
 insecure-skip-tls-verify: false
 server: https://<node's IP address>:32443 # <- this works from the public internet
 name: karmada-apiserver
# truncated

接下来就可以开始测试 Karmada 了。

安装 Karmada 代理程序

运行下列命令检索所有部署和所有集群:

bash
$ kubectl get clusters,deployments --kubecnotallow=karmada-config
No resources found

可想而知,目前没有任何部署,也没有任何额外的集群。我们可以添加几个集群并将其连接到 Karmada 控制平面。

请重复执行下列命令三次:

bash
linode-cli lke cluster-create 
 --label <insert-cluster-name> 
 --region <insert-region> 
 --k8s_version 1.23
linode-cli lke kubeconfig-view "insert cluster id here" --text | tail +2 | base64 -d > kubeconfig-<insert-cluster-name>

执行时请分别使用如下的值:

  1. Cluster name eu, region eu-west 以及 kubeconfig file kubeconfig-eu
  2. Cluster name ap, region ap-south 以及 kubeconfig file kubeconfig-ap
  3. Cluster name us, region us-west 以及 kubeconfig file kubeconfig-us

随后通过下列命令确认集群已经成功创建:

bash
$ kubectl get pods -A --kubecnotallow=kubeconfig-eu
$ kubectl get pods -A --kubecnotallow=kubeconfig-ap
$ kubectl get pods -A --kubecnotallow=kubeconfig-us

接下来要将这些集群加入 Karmada 集群。Karmada 需要在其他每个集群中使用代理程序来协调控制平面的部署。

我们可以使用 Helm 安装 Karmada 代理程序并将其链接至集群管理器:

bash
$ helm install karmada karmada-charts/karmada 
 --kubecnotallow=kubeconfig-<insert-cluster-name> 
 --create-namespace --namespace karmada-system 
 --versinotallow=1.2.0 
 --set installMode=agent 
 --set agent.clusterName=<insert-cluster-name> 
 --set agent.kubeconfig.caCrt=<karmada kubeconfig certificate authority> 
 --set agent.kubeconfig.crt=<karmada kubeconfig client certificate data> 
 --set agent.kubeconfig.key=<karmada kubeconfig client key data> 
 --set agent.kubeconfig.server=https://<insert node's IP address>:32443 

上述命令同样需要重复三次,每次分别插入下列变量:

  1. 集群名称:分别为 eu、ap 和 us。
  2. 集群管理器的证书授权机构。我们可以在 karmada-config 文件的 clusters [0].cluster ['certificate-authority-data'] 中找到该值,这些值可以通过 base64 进行解码。
  3. 用户的客户端证书数据。我们可以在 karmada-config 文件的 users [0].user ['client-certificate-data'] 中找到该值,这些值可以通过 base64 进行解码。
  4. 用户的客户端密钥数据。我们可以在 karmada-config 文件的 users [0].user ['client-key-data'] 中找到该值,这些值可以通过 base64 进行解码。
  5. 承载 Karmada 控制平面的节点的 IP 地址。

随后可以运行下列命令来验证安装是否成功完成:

bash
$ kubectl get clusters --kubecnotallow=karmada-config
NAME VERSION MODE READY
eu v1.23.8 Pull True
ap v1.23.8 Pull True
us v1.23.8 Pull True

借助 Karmada Policies 编排多集群部署

只要配置正确无误,我们即可将工作负载提交给 Karmada,由它将任务分发给其他集群。

为了进行测试,我们首先需要创建一个部署:

yaml
apiVersion: Apps/v1
kind: Deployment
metadata:
 name: hello
spec:
 replicas: 3
 selector:
 matchLabels:
 app: hello
 template:
 metadata:
 labels:
 app: hello
 spec:
 containers:
 - image: stefanprodan/podinfo
 name: hello
---
apiVersion: v1
kind: Service
metadata:
 name: hello
spec:
 ports:
 - port: 5000
 targetPort: 9898
 selector:
 app: hello

随后通过下列命令将该部署提交至 Karmada API 服务器:

bash
$ kubectl apply -f deployment.yaml --kubecnotallow=karmada-config

该部署包含三个副本,那么是否可以平均分发给这三个集群?一起来验证一下:

bash
$ kubectl get deployments --kubecnotallow=karmada-config
NAME READY UP-TO-DATE AVAILABLE
hello 0/3 0 0

Karmada 为何没有创建 Pod?先来看看这个部署:

bash
$ kubectl describe deployment hello --kubecnotallow=karmada-config
Name: hello
Namespace: default
Selector: app=hello
Replicas: 3 desired | 0 updated | 0 total | 0 available | 0 unavailable
StrategyType: RollingUpdate
MinReadySeconds: 0
RollingUpdateStrategy: 25% max unavailable, 25% max surge
Events:
 Type Reason From Message
 ---- ------ ---- -------
 Warning ApplyPolicyFailed resource-detector No policy match for resource

Karmada 并不知道该如何处理这个部署,因为我们尚未指定策略。

Karmada 调度器会使用策略将工作负载分配给集群。那么我们就定义一个简单的策略,为每个集群分配一个副本:

yaml
apiVersion: policy.karmada.io/v1alpha1
kind: PropagationPolicy
metadata:
 name: hello-propagation
spec:
 resourceSelectors:
 - apiVersion: apps/v1
 kind: Deployment
 name: hello
 - apiVersion: v1
 kind: Service
 name: hello
 placement:
 clusterAffinity:
 clusterNames:
 - eu
 - ap
 - us
 replicaScheduling:
 replicaDivisionPreference: Weighted
 replicaSchedulingType: Divided
 weightPreference:
 staticWeightList:
 - targetCluster:
 clusterNames:
 - us
 weight: 1
 - targetCluster:
 clusterNames:
 - ap
 weight: 1
 - targetCluster:
 clusterNames:
 - eu
 weight: 1

并用下列命令将该策略提交给集群:

 
bash
$ kubectl apply -f policy.yaml --kubecnotallow=karmada-config

然后再来看看部署和 Pod:

bash
$ kubectl get deployments --kubecnotallow=karmada-config
NAME READY UP-TO-DATE AVAILABLE
hello 3/3 3 3
$ kubectl get pods --kubecnotallow=kubeconfig-eu
NAME READY STATUS RESTARTS
hello-5d857996f-hjfqq 1/1 Running 0
$ kubectl get pods --kubecnotallow=kubeconfig-ap
NAME READY STATUS RESTARTS
hello-5d857996f-xr6hr 1/1 Running 0
$ kubectl get pods --kubecnotallow=kubeconfig-us
NAME READY STATUS RESTARTS
hello-5d857996f-nbz48 1/1 Running 0

Karmada 会为每个集群分配一个 Pod,因为策略中为每个集群定义了相等的权重。

我们用下列命令将该部署扩展为 10 个副本:

bash
$ kubectl scale deployment/hello --replicas=10 --kubecnotallow=karmada-config

随后查看 Pod 会看到如下的结果:

bash
$ kubectl get deployments --kubecnotallow=karmada-config
NAME READY UP-TO-DATE AVAILABLE
hello 10/10 10 10
$ kubectl get pods --kubecnotallow=kubeconfig-eu
NAME READY STATUS RESTARTS
hello-5d857996f-dzfzm 1/1 Running 0
hello-5d857996f-hjfqq 1/1 Running 0
hello-5d857996f-kw2rt 1/1 Running 0
hello-5d857996f-nz7qz 1/1 Running 0
$ kubectl get pods --kubecnotallow=kubeconfig-ap
NAME READY STATUS RESTARTS
hello-5d857996f-pd9t6 1/1 Running 0
hello-5d857996f-r7bmp 1/1 Running 0
hello-5d857996f-xr6hr 1/1 Running 0
$ kubectl get pods --kubecnotallow=kubeconfig-us
NAME READY STATUS RESTARTS
hello-5d857996f-nbz48 1/1 Running 0
hello-5d857996f-nzgpn 1/1 Running 0
hello-5d857996f-rsp7k 1/1 Running 0

随后修改策略,让 EU 和 US 集群各承载 40% 的 Pod,让 AP 集群只承载 20%。

yaml
apiVersion: policy.karmada.io/v1alpha1
kind: PropagationPolicy
metadata:
 name: hello-propagation
spec:
 resourceSelectors:
 - apiVersion: apps/v1
 kind: Deployment
 name: hello
 - apiVersion: v1
 kind: Service
 name: hello
 placement:
 clusterAffinity:
 clusterNames:
 - eu
 - ap
 - us
 replicaScheduling:
 replicaDivisionPreference: Weighted
 replicaSchedulingType: Divided
 weightPreference:
 staticWeightList:
 - targetCluster:
 clusterNames:
 - us
 weight: 2
 - targetCluster:
 clusterNames:
 - ap
 weight: 1
 - targetCluster:
 clusterNames:
 - eu
 weight: 2

并通过下列命令提交策略:

bash
$ kubectl apply -f policy.yaml --kubecnotallow=karmada-config

接着可以看到,Pod 的分配情况也酌情产生了变化:

bash
$ kubectl get pods --kubecnotallow=kubeconfig-eu
NAME READY STATUS RESTARTS AGE
hello-5d857996f-hjfqq 1/1 Running 0 6m5s
hello-5d857996f-kw2rt 1/1 Running 0 2m27s
$ kubectl get pods --kubecnotallow=kubeconfig-ap
hello-5d857996f-k9hsm 1/1 Running 0 51s
hello-5d857996f-pd9t6 1/1 Running 0 2m41s
hello-5d857996f-r7bmp 1/1 Running 0 2m41s
hello-5d857996f-xr6hr 1/1 Running 0 6m19s
$ kubectl get pods --kubecnotallow=kubeconfig-us
hello-5d857996f-nbz48 1/1 Running 0 6m29s
hello-5d857996f-nzgpn 1/1 Running 0 2m51s
hello-5d857996f-rgj9t 1/1 Running 0 61s
hello-5d857996f-rsp7k 1/1 Running 0 2m51s

Karmada 支持通过多种策略分配工作负载,更多高级用例可以参考文档。

Pod 在三个集群中运行,但我们该如何访问?

先来看看 Karmada 中的服务:

bash
$ kubectl describe service hello --kubecnotallow=karmada-config
Name: hello
Namespace: default
Labels: propagationpolicy.karmada.io/name=hello-propagation
 propagationpolicy.karmada.io/namespace=default
Selector: app=hello
Type: ClusterIP
IP Family Policy: SingleStack
IP Families: IPv4
IP: 10.105.24.193
IPs: 10.105.24.193
Port: <unset> 5000/TCP
TargetPort: 9898/TCP
Events:
 Type Reason Message
 ---- ------ -------
 Normal SyncSucceed Successfully applied resource(default/hello) to cluster ap
 Normal SyncSucceed Successfully applied resource(default/hello) to cluster us
 Normal SyncSucceed Successfully applied resource(default/hello) to cluster eu
 Normal AggregateStatusSucceed Update resourceBinding(default/hello-service) with AggregatedStatus successfully.
 Normal ScheduleBindingSucceed Binding has been scheduled
 Normal SyncWorkSucceed Sync work of resourceBinding(default/hello-service) successful.

这些服务被部署在全部的三个集群中,但彼此之间并未连接。

尽管 Karmada 可以管理多个集群,但它并未提供任何网络机制将这三个集群连接在一起。换句话说,Karmada 是一种跨越多个集群编排部署的好工具,但我们需要通过其他机制让这些集群相互通信。

使用 Istio 连接多个集群

Istio 通常被用于控制同一个集群中应用程序之间的网络流量,它可以检查所有传入和传出的请求,并通过 Envoy 以代理的方式发送这些请求。

Istio 控制平面负责更新并收集来自这些代理的指标,还可以发出指令借此转移流量。

 

因此我们可以用 Istio 拦截到特定服务的所有流量,并将其重定向至三个集群之一。这就是所谓的 Istio 多集群配置。

理论知识这就够了,接下来亲自试试吧。首先需要在三个集群中安装 Istio。虽然安装方法很多,但 Helm 最方便:

bash
$ helm repo add istio https://istio-release.storage.googleapis.com/charts
$ helm repo list
NAME URL
istio https://istio-release.storage.googleapis.com/charts

我们可以用下列命令将 Istio 安装给三个集群:

bash
$ helm install istio-base istio/base 
 --kubecnotallow=kubeconfig-<insert-cluster-name> 
 --create-namespace --namespace istio-system 
 --versinotallow=1.14.1

请将 cluster-name 分别替换为 ap、eu 和 us,并将该命令同样执行三遍。

Base chart 将只安装通用资源,例如 Roles 和 RoleBindings。实际的安装会被打包到 istiod chart 中。但在执行该操作前,我们首先需要配置 Istio Certificate Authority (CA),以确保这些集群可以相互连接和信任。

请在一个新目录中使用下列命令克隆 Istio 代码库:

bash
$ git clone https://github.com/istio/istio

创建一个 certs 文件夹并进入该目录:

bash
$ mkdir certs
$ cd certs

使用下列命令创建根证书:

bash
$ make -f ../istio/tools/certs/Makefile.selfsigned.mk root-ca

该命令将生成下列文件:

  1. root-cert.pem:生成的根证书
  2. root-key.pem:生成的根密钥
  3. root-ca.conf:供 OpenSSL 生成根证书的配置
  4. root-cert.csr:为根证书生成的 CSR

对于每个集群,还需要为 Istio Certificate Authority 生成一个中间证书和密钥:

bash
$ make -f ../istio/tools/certs/Makefile.selfsigned.mk cluster1-cacerts
$ make -f ../istio/tools/certs/Makefile.selfsigned.mk cluster2-cacerts
$ make -f ../istio/tools/certs/Makefile.selfsigned.mk cluster3-cacerts

上述命令会在名为 cluster1、cluster2 和 cluster3 的目录下生成下列文件:

bash
$ kubectl create secret generic cacerts -n istio-system 
 --kubecnotallow=kubeconfig-<cluster-name>
 --from-file=<cluster-folder>/ca-cert.pem 
 --from-file=<cluster-folder>/ca-key.pem 
 --from-file=<cluster-folder>/root-cert.pem 
 --from-file=<cluster-folder>/cert-chain.pem

我们需要使用下列变量执行这些命令:

| cluster name | folder name |
| :----------: | :---------: |
| ap | cluster1 |
| us | cluster2 |
| eu | cluster3 |

上述操作完成后,可以安装 istiod 了:

bash
$ helm install istiod istio/istiod 
 --kubecnotallow=kubeconfig-<insert-cluster-name> 
 --namespace istio-system 
 --versinotallow=1.14.1 
 --set global.meshID=mesh1 
 --set global.multiCluster.clusterName=<insert-cluster-name> 
 --set global.network=<insert-network-name>

请使用下列变量将上述命令重复执行三遍:

| cluster name | network name |
| :----------: | :----------: |
| ap | network1 |
| us | network2 |
| eu | network3 |

我们还可以使用拓扑注释来标记 Istio 的命名空间:

bash
$ kubectl label namespace istio-system topology.istio.io/network=network1 --kubecnotallow=kubeconfig-ap
$ kubectl label namespace istio-system topology.istio.io/network=network2 --kubecnotallow=kubeconfig-us
$ kubectl label namespace istio-system topology.istio.io/network=network3 --kubecnotallow=kubeconfig-eu

至此几乎就快完成了。

通过东西网关为流量创建隧道

接下来我们还需要:

  1. 一个网关,借此通过隧道将流量从一个集群发送到另一个
  2. 一种机制,借此发现其他集群中的 IP 地址

我们可以使用 Helm 安装网关:

bash
$ helm install eastwest-gateway istio/gateway 
 --kubecnotallow=kubeconfig-<insert-cluster-name> 
 --namespace istio-system 
 --versinotallow=1.14.1 
 --set labels.istio=eastwestgateway 
 --set labels.app=istio-eastwestgateway 
 --set labels.topology.istio.io/network=istio-eastwestgateway 
 --set labels.topology.istio.io/network=istio-eastwestgateway 
 --set networkGateway=<insert-network-name> 
 --set service.ports[0].name=status-port 
 --set service.ports[0].port=15021 
 --set service.ports[0].targetPort=15021 
 --set service.ports[1].name=tls 
 --set service.ports[1].port=15443 
 --set service.ports[1].targetPort=15443 
 --set service.ports[2].name=tls-istiod 
 --set service.ports[2].port=15012 
 --set service.ports[2].targetPort=15012 
 --set service.ports[3].name=tls-webhook 
 --set service.ports[3].port=15017 
 --set service.ports[3].targetPort=15017 

请使用下列变量将上述命令执行三遍:

| cluster name | network name |
| :----------: | :----------: |
| ap | network1 |
| us | network2 |
| eu | network3 |

随后对于每个集群,请使用下列资源暴露一个网关:

yaml
apiVersion: networking.istio.io/v1alpha3
kind: Gateway
metadata:
 name: cross-network-gateway
spec:
 selector:
 istio: eastwestgateway
 servers:
 - port:
 number: 15443
 name: tls
 protocol: TLS
 tls:
 mode: AUTO_PASSTHROUGH
 hosts:
 - "*.local"

并使用下列命令将文件提交至集群:

bash
$ kubectl apply -f expose.yaml --kubecnotallow=kubeconfig-eu
$ kubectl apply -f expose.yaml --kubecnotallow=kubeconfig-ap
$ kubectl apply -f expose.yaml --kubecnotallow=kubeconfig-us

对于发现机制,我们需要共享每个集群的凭据。这是因为集群并不知道彼此的存在。

为了发现其他 IP 地址,集群必须能彼此访问,并将这些集群注册为流量的可能目的地。为此我们必须使用其他集群的 kubeconfig 文件创建一个 Kubernetes secret。Istio 可以借此连接其他集群,发现端点,并指示 Envoy 代理转发流量。

我们需要三个 Secret:

yaml
apiVersion: v1
kind: Secret
metadata:
 labels:
 istio/multiCluster: true
 annotations:
 networking.istio.io/cluster: <insert cluster name>
 name: "istio-remote-secret-<insert cluster name>"
type: Opaque
data:
 <insert cluster name>: <insert cluster kubeconfig as base64>

请使用下列变量创建这三个 Secret:

| cluster name | secret filename | kubeconfig |
| :----------: | :-------------: | :-----------: |
| ap | secret1.yaml | kubeconfig-ap |
| us | secret2.yaml | kubeconfig-us |
| eu | secret3.yaml | kubeconfig-eu |

接下来需要向集群提交 Secret,但是请注意,不要将 AP 的 Secret 提交给 AP 集群。

为此需要执行下列命令:

bash
$ kubectl apply -f secret2.yaml -n istio-system --kubecnotallow=kubeconfig-ap
$ kubectl apply -f secret3.yaml -n istio-system --kubecnotallow=kubeconfig-ap
$ kubectl apply -f secret1.yaml -n istio-system --kubecnotallow=kubeconfig-us
$ kubectl apply -f secret3.yaml -n istio-system --kubecnotallow=kubeconfig-us
$ kubectl apply -f secret1.yaml -n istio-system --kubecnotallow=kubeconfig-eu
$ kubectl apply -f secret2.yaml -n istio-system --kubecnotallow=kubeconfig-eu
 

至此,大部分操作已经完成,我们可以开始测试整个配置了。

测试多集群网络连接

首先为一个睡眠中的 Pod 创建一个部署。我们可以使用该 Pod 向刚才创建的 Hello 部署发出请求:

yaml
apiVersion: apps/v1
kind: Deployment
metadata:
 name: sleep
spec:
 selector:
 matchLabels:
 app: sleep
 template:
 metadata:
 labels:
 app: sleep
 spec:
 terminationGracePeriodSeconds: 0
 containers:
 - name: sleep
 image: curlimages/curl
 command: ["/bin/sleep", "3650d"]
 imagePullPolicy: IfNotPresent
 volumeMounts:
 - mountPath: /etc/sleep/tls
 name: secret-volume
 volumes:
 - name: secret-volume
 secret:
 secretName: sleep-secret
 optional: true

请用下列命令创建部署:

bash
$ kubectl apply -f sleep.yaml --kubecnotallow=karmada-config

因为该部署尚未指定策略,Karmada 将不处理该部署,使其处于 “未决” 状态。我们可以修改策略以包含该部署:

yaml
apiVersion: policy.karmada.io/v1alpha1
kind: PropagationPolicy
metadata:
 name: hello-propagation
spec:
 resourceSelectors:
 - apiVersion: apps/v1
 kind: Deployment
 name: hello
 - apiVersion: v1
 kind: Service
 name: hello
 - apiVersion: apps/v1
 kind: Deployment
 name: sleep
 placement:
 clusterAffinity:
 clusterNames:
 - eu
 - ap
 - us
 replicaScheduling:
 replicaDivisionPreference: Weighted
 replicaSchedulingType: Divided
 weightPreference:
 staticWeightList:
 - targetCluster:
 clusterNames:
 - us
 weight: 2
 - targetCluster:
 clusterNames:
 - ap
 weight: 2
 - targetCluster:
 clusterNames:
 - eu
 weight: 1

使用下列命令应用该策略:

bash
$ kubectl apply -f policy.yaml --kubecnotallow=karmada-config

要了解该 Pod 被部署到哪里,可以使用下列命令:

bash
$ kubectl get pods --kubecnotallow=kubeconfig-eu
$ kubectl get pods --kubecnotallow=kubeconfig-ap
$ kubectl get pods --kubecnotallow=kubeconfig-us

接下来,假设该 Pod 被部署到 US 集群,请执行下列命令:

bash
for i in {1..10}
do
 kubectl exec --kubecnotallow=kubeconfig-us -c sleep 
 "$(kubectl get pod --kubecnotallow=kubeconfig-us -l 
 app=sleep -o jsnotallow='{.items[0].metadata.name}')" 
 -- curl -sS hello:5000 | grep REGION
done

我们将会发现,响应会来自不同地域的不同 Pod!搞定!

总结

该配置其实非常基础,缺乏真实环境中可能需要的其他很多功能:

  1. 我们可以从每个集群暴露出一个 Istio 入口以摄入流量
  2. 我们可以使用 Istio 进行流量塑型,这样就会优先进行本地处理
  3. 还可以使用 Istio 策略强制规则定义流量如何在不同集群之间流动


Tags:Kubernetes   点击:()  评论:()
声明:本站部分内容及图片来自互联网,转载是出于传递更多信息之目的,内容观点仅代表作者本人,不构成投资建议。投资者据此操作,风险自担。如有任何标注错误或版权侵犯请与我们联系,我们将及时更正、删除。
▌相关推荐
Kubernetes 究竟有没有 LTS?
从一个有趣的问题引出很多人都在关注的 Kubernetes LTS 的问题。有趣的问题2019 年,一个名为 apiserver LoopbackClient Server cert expired after 1 year[1] 的 issue 中提...【详细内容】
2024-03-15  Search: Kubernetes  点击:(6)  评论:(0)  加入收藏
Kubernetes 集群 CPU 使用率只有 13% :这下大家该知道如何省钱了
作者 | THE STACK译者 | 刘雅梦策划 | Tina根据 CAST AI 对 4000 个 Kubernetes 集群的分析,Kubernetes 集群通常只使用 13% 的 CPU 和平均 20% 的内存,这表明存在严重的过度...【详细内容】
2024-03-08  Search: Kubernetes  点击:(12)  评论:(0)  加入收藏
聊聊 Kubernetes 网络模型综合指南
这篇详细的博文探讨了 Kubernetes 网络的复杂性,提供了关于如何在容器化环境中确保高效和安全通信的见解。译自Navigating the Network: A Comprehensive Guide to Kubernete...【详细内容】
2024-02-19  Search: Kubernetes  点击:(37)  评论:(0)  加入收藏
Kubernetes是什么?主要特点是什么?
Kubernetes是什么?Kubernetes,也称为K8s,是一个开源的容器编排系统,由Google首次开发和维护。它允许容器化的应用程序在集群中自动部署、扩展和管理。Kubernetes提供了一种容器...【详细内容】
2024-02-01  Search: Kubernetes  点击:(154)  评论:(0)  加入收藏
开发者的Kubernetes懒人指南
你可以将本文作为开发者快速了解 Kubernetes 的指南。从基础知识到更高级的主题,如 Helm Chart,以及所有这些如何影响你作为开发者。译自Kubernetes for Lazy Developers。作...【详细内容】
2024-02-01  Search: Kubernetes  点击:(50)  评论:(0)  加入收藏
Kubernetes Informer基本原理,你明白了吗?
本文分析 k8s controller 中 informer 启动的基本流程不论是 k8s 自身组件,还是自己编写 controller,都需要通过 apiserver 监听 etcd 事件来完成自己的控制循环逻辑。如何高...【详细内容】
2024-01-30  Search: Kubernetes  点击:(37)  评论:(0)  加入收藏
Kubernetes 100个常用命令!
这篇文章是关于使用 Kubectl 进行 Kubernetes 诊断的指南。列出了 100 个 Kubectl 命令,这些命令对于诊断 Kubernetes 集群中的问题非常有用。这些问题包括但不限于:&bull; 集...【详细内容】
2024-01-03  Search: Kubernetes  点击:(76)  评论:(0)  加入收藏
一文读懂Kubernetes部署策略
在这篇文章中,我们将深入研究 Kubernetes 部署概念和一些常见策略,了解每种策略的优缺点。合适的部署策略使我们能够在发布应用程序时最大限度地减少停机时间、增强客户体验并...【详细内容】
2024-01-03  Search: Kubernetes  点击:(59)  评论:(0)  加入收藏
从Kubernetes的探针到DevOps
今天在群里又看有人问如何设置 Kubernetes 的探针,感觉要补充的话太多了,结合我们在一些 DevOps 项目中痛苦的体验,今天一劳永逸的全部说完,此外,也为大家展现一下为什么 DevOps...【详细内容】
2023-12-27  Search: Kubernetes  点击:(114)  评论:(0)  加入收藏
如何基于Kubernetes运行Nacos高可用集群
Nacos(Namings and Configuration Management)是阿里巴巴开源的一个易于构建云原生应用的动态服务发现、配置管理和服务管理平台。以下是Nacos的一些主要功能和特点: 服务发现...【详细内容】
2023-12-18  Search: Kubernetes  点击:(69)  评论:(0)  加入收藏
▌简易百科推荐
即将过时的 5 种软件开发技能!
作者 | Eran Yahav编译 | 言征出品 | 51CTO技术栈(微信号:blog51cto) 时至今日,AI编码工具已经进化到足够强大了吗?这未必好回答,但从2023 年 Stack Overflow 上的调查数据来看,44%...【详细内容】
2024-04-03    51CTO  Tags:软件开发   点击:(5)  评论:(0)  加入收藏
跳转链接代码怎么写?
在网页开发中,跳转链接是一项常见的功能。然而,对于非技术人员来说,编写跳转链接代码可能会显得有些困难。不用担心!我们可以借助外链平台来简化操作,即使没有编程经验,也能轻松实...【详细内容】
2024-03-27  蓝色天纪    Tags:跳转链接   点击:(12)  评论:(0)  加入收藏
中台亡了,问题到底出在哪里?
曾几何时,中台一度被当做“变革灵药”,嫁接在“前台作战单元”和“后台资源部门”之间,实现企业各业务线的“打通”和全域业务能力集成,提高开发和服务效率。但在中台如火如荼之...【详细内容】
2024-03-27  dbaplus社群    Tags:中台   点击:(8)  评论:(0)  加入收藏
员工写了个比删库更可怕的Bug!
想必大家都听说过删库跑路吧,我之前一直把它当一个段子来看。可万万没想到,就在昨天,我们公司的某位员工,竟然写了一个比删库更可怕的 Bug!给大家分享一下(不是公开处刑),希望朋友们...【详细内容】
2024-03-26  dbaplus社群    Tags:Bug   点击:(5)  评论:(0)  加入收藏
我们一起聊聊什么是正向代理和反向代理
从字面意思上看,代理就是代替处理的意思,一个对象有能力代替另一个对象处理某一件事。代理,这个词在我们的日常生活中也不陌生,比如在购物、旅游等场景中,我们经常会委托别人代替...【详细内容】
2024-03-26  萤火架构  微信公众号  Tags:正向代理   点击:(10)  评论:(0)  加入收藏
看一遍就理解:IO模型详解
前言大家好,我是程序员田螺。今天我们一起来学习IO模型。在本文开始前呢,先问问大家几个问题哈~什么是IO呢?什么是阻塞非阻塞IO?什么是同步异步IO?什么是IO多路复用?select/epoll...【详细内容】
2024-03-26  捡田螺的小男孩  微信公众号  Tags:IO模型   点击:(8)  评论:(0)  加入收藏
为什么都说 HashMap 是线程不安全的?
做Java开发的人,应该都用过 HashMap 这种集合。今天就和大家来聊聊,为什么 HashMap 是线程不安全的。1.HashMap 数据结构简单来说,HashMap 基于哈希表实现。它使用键的哈希码来...【详细内容】
2024-03-22  Java技术指北  微信公众号  Tags:HashMap   点击:(11)  评论:(0)  加入收藏
如何从头开始编写LoRA代码,这有一份教程
选自 lightning.ai作者:Sebastian Raschka机器之心编译编辑:陈萍作者表示:在各种有效的 LLM 微调方法中,LoRA 仍然是他的首选。LoRA(Low-Rank Adaptation)作为一种用于微调 LLM(大...【详细内容】
2024-03-21  机器之心Pro    Tags:LoRA   点击:(12)  评论:(0)  加入收藏
这样搭建日志中心,传统的ELK就扔了吧!
最近客户有个新需求,就是想查看网站的访问情况。由于网站没有做google的统计和百度的统计,所以访问情况,只能通过日志查看,通过脚本的形式给客户导出也不太实际,给客户写个简单的...【详细内容】
2024-03-20  dbaplus社群    Tags:日志   点击:(4)  评论:(0)  加入收藏
Kubernetes 究竟有没有 LTS?
从一个有趣的问题引出很多人都在关注的 Kubernetes LTS 的问题。有趣的问题2019 年,一个名为 apiserver LoopbackClient Server cert expired after 1 year[1] 的 issue 中提...【详细内容】
2024-03-15  云原生散修  微信公众号  Tags:Kubernetes   点击:(6)  评论:(0)  加入收藏
站内最新
站内热门
站内头条