第五课:Kubernetes 的 Pod 放置放置策略以及应用案例
优质
小牛编辑
126浏览
2023-12-01
Kubernetes 的 Pod 放置放置策略以及应用案例
王渊命 @jolestar
Agenda
- Kubernetes 的 Pod 放置策略
- 如何放置 Pod 到 Node
- Affinity 以及 anti-affinity
- Taints 和 Tolerations 机制
- Kubernetes 应用开发
- Java Spring Cloud 案例
- PHP Wordpress
如何放置 Pod 到 Node — 从手动编排过度到 Kubernets
Pod 的 nodeName 和 nodeSelector 属性
kubectl label nodes <nodename> disktype=ssd
apiVersion: v1kind: Podmetadata:name: dbspec:containers:- name: dbimage: mysqlnodeSelector: disktype: ssd
内置的 node labels
kubectl get nodes --show-labels
#cloud-providerkubernetes.io/hostnamefailure-domain.beta.kubernetes.io/zonefailure-domain.beta.kubernetes.io/regionbeta.kubernetes.io/instance-type#kubeletbeta.kubernetes.io/osbeta.kubernetes.io/arch#kubeadmnode-role.kubernetes.io/master
Affinity 以及 anti-affinity
为什么需要 Affinity 机制
- nodeSelector 选择表达式不够强大
- nodeSelector 不能区分强制要求和优先配置
- 无法避免同一个应用的多个 pod 调度到同一个 node 上
Affinity
- nodeAffinity
- podAffinity
- podAntiAffinity
为什么没有 nodeAntiAffinity?
nodeAffinity
- preferredDuringSchedulingIgnoredDuringExecution: PreferredSchedulingTerm array
- preference: nodeSelectorTerms
- weight: 0-100
- requiredDuringSchedulingIgnoredDuringExecution: NodeSelector
NodeSelector
参看第四章API Spec 以及安全机制 — Label 和 Selector
- nodeSelectorTerms
- matchExpressions array
- key
- operator: In, NotIn, Exists, DoesNotExist. Gt, Lt
- values: string array
- matchExpressions array
matchExpressions: - {key: disktype, operator: In, values: [ssd]} - {key: environment, operator: NotIn, values: [dev]}
nodeAffinity
apiVersion: v1kind: Podmetadata: name: with-node-affinityspec: affinity: nodeAffinity: requiredDuringSchedulingIgnoredDuringExecution: nodeSelectorTerms: - matchExpressions: - key: failure-domain.beta.kubernetes.io/zone operator: In values: - az1 - az2 containers: - name: with-node-affinity image: example
nodeAffinity
apiVersion: v1kind: Podmetadata: name: with-node-affinityspec: affinity: nodeAffinity: preferredDuringSchedulingIgnoredDuringExecution: - weight: 1 preference: matchExpressions: - key: disktype operator: In values: - ssd containers: - name: with-node-affinity image: example
podAffinity/podAntiAffinity
- preferredDuringSchedulingIgnoredDuringExecution: WeightedPodAffinityTerm array
- podAffinityTerm: PodAffinityTerm
- weight: 0-100
- requiredDuringSchedulingIgnoredDuringExecution: PodAffinityTerm array
- labelSelector: LabelSelector
- namespaces: string array
- topologyKey
podAffinity
apiVersion: v1kind: Podmetadata: name: with-pod-affinityspec: affinity: podAffinity: requiredDuringSchedulingIgnoredDuringExecution: - labelSelector: matchExpressions: - key: security operator: In values: - S1 topologyKey: failure-domain.beta.kubernetes.io/zone containers: - name: with-pod-affinity image: example
podAntiAffinity
apiVersion: v1kind: Podmetadata: name: zk lables: app: zkspec: affinity: podAntiAffinity: requiredDuringSchedulingIgnoredDuringExecution: - labelSelector: matchExpressions: - key: "app" operator: In values: - zk topologyKey: "kubernetes.io/hostname" containers: - name: zk image: zk
为什么要有 Taints 和 Tolerations
- Taints 隔离 Node
- 上线新 Node 验证
- 下线 Node 维护
- 专用 Node
- Tolerations Pod 对 Taints Node 的容忍
- 验证 Taints Node 是否工作正常
- 表明 Pod 有资格使用专用 Node
- 每个节点必须运行的基础 Pod
Taints 和 Tolerations
kubectl taint nodes node1 key=value:NoSchedule
- tolerations
- operator: Exists,Equal (default)
- effect: NoSchedule,PreferNoSchedule,NoExecute
```yaml
tolerations:
- key: “key”
operator: “Equal”
value: “value”
effect: “NoSchedule”
tolerationSeconds: 3600
```
Tolerations
apiVersion: extensions/v1beta1kind: DaemonSetmetadata: name: kube-proxyspec: template: spec: containers: - name: kube-proxy image: gcr.io/google_containers/hyperkube-amd64:1.7.9 tolerations: - key: "CriticalAddonsOnly" operator: "Exists" - key: "dedicated" operator: "Exists" - key: "node-role.kubernetes.io/master" effect: NoSchedule - key: node.cloudprovider.kubernetes.io/uninitialized effect: NoSchedule value: "true"
Taint based Evictions
kube-controller-manager --feature-gates=TaintBasedEvictions=true
内置的 taints
node.kubernetes.io/not-readynode.alpha.kubernetes.io/unreachablenode.kubernetes.io/out-of-disknode.kubernetes.io/memory-pressurenode.kubernetes.io/disk-pressurenode.kubernetes.io/network-unavailablenode.cloudprovider.kubernetes.io/uninitialized
DaemonSet Tolerations
node.alpha.kubernetes.io/unreachablenode.kubernetes.io/not-ready
Kubernetes 应用开发案例
- Java SpringCloud
- PHP Wordpress
Kubernetes SpringCloud 案例
- spring-cloud-kubernetes
- fabric8
spring-cloud-kubernetes
https://github.com/spring-cloud-incubator/spring-cloud-kubernetes
- DiscoveryClient
- ConfigMap/Secrets PropertySource
- Pod Health Indicator
- Ribbon/Zipkin discovery
fabric8
Integrated Development Platform for Kubernetes
fabric8-maven-plugin
- fabric8:run
- fabric8:build
- fabric8:push
- fabric8:deploy
SpringCloud 案例演示
准备 minikube 环境
#第一次启动要翻墙minikube start#没开启一个新的 terminal 都需要重新执行一下eval $(minikube docker-env)sudo route -n add 10.0.0.0/24 $(minikube ip)
spring-cloud-kubernetes-examples
- kubernetes-hello-world-example
mvn fabric8:run -Pkubernetes kubectl get service curl http://$clusterip #修改代码 重新执行上面的命令看结果
- kubernetes-reload-example
kubectl apply -f config-map.yml mvn fabric8:run -Pkubernetes kubectl logs -f $spring-cloud-reload-podid kubectl edit configmap reload-example # 可看到修改后的 configmap 被重新加载
spring-cloud-kubernetes-examples
- kubernetes-circuitbreaker-ribbon-example
cd name-service; mvn fabric8:run -Pkubernetes cd greeting-service; mvn fabric8:run -Pkubernetes curl $greeting-service-clusterIP/greeting kubectl scale --replicas=2 deployment name-service curl $greeting-service-clusterIP/greeting # 可以看到 ribbon 的效果
PHP Wordpress
- LoadBalancer
- PersistentVolumeClaim
- Secret
- MySQL
总结
- 对 Kubernetes 的 Pod 放置策略有一个整体的了解
- 了解在 Kubernetes 上开发应用的流程以及应用如何利用 Kubernetes 的特性
作业
- 思考自己所在公司的服务如果全部部署到 Kubernetes 中,需要如何规划 Node 的 Label,以及那些节点需要通过 taints 机制来专用,那些服务需要使用到 Affinity 机制。
- 通过 Kubernetes 去部署一个更复杂的微服务应用(根据自己熟悉的语言来选择)
- 以 Wordpress 为例,思考如果要做高可用,需要做哪些方面的改造(提示: 图片存储,数据库)。