下面進行k8s的實戰,主要是pod,service,ingress,pv,pvc,configmap,secret這些,下面開始。
就按我上一篇帖子搭建的環境來操作:k8s集群環境搭建
k8s-new-master:192.168.192.8
k8s-new-node1:192.168.192.9
k8s-new-node2:192.168.192.10
用戶密碼:root/forever
控制臺:https://192.168.192.8:30110
登錄token:
eyJhbGciOiJSUzI1NiIsImtpZCI6IkVRZGZRRm52ZlJwcWRlc040dURELTluQ1daZjV2M3o2dnBzaEhReDBZbTAifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlcm5ldGVzLWRhc2hib2FyZCIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJhZG1pbi11c2VyLXRva2VuLXRqbXJwIiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQubmFtZSI6ImFkbWluLXVzZXIiLCJrdWJlcm5ldGVzLmlvL3NlcnZpY2VhY2NvdW50L3NlcnZpY2UtYWNjb3VudC51aWQiOiJmN2M3OGJkZi0xN2YzLTQxY2UtYmVhNS1lYzA0MDY4ZDgxYTQiLCJzdWIiOiJzeXN0ZW06c2VydmljZWFjY291bnQ6a3ViZXJuZXRlcy1kYXNoYm9hcmQ6YWRtaW4tdXNlciJ9.tUEW6nt4KvoV48eoAShBFqGUQx4e5KHb8nB8X24JhNf9vGhAfgAKgLo1S4HEgmqPkM1FUsMxxeNZMvRvjOI7Ju9AVUQkG7bz3skd1I_yZSoiOlcc6_woCXZ0az_nOGwvjjYeE8s8TuBT0nGkiKyZBiruyjyluHJyvv_wYex4DsyGUTKytX7ab0ndSz67JdVvzsfKjOrHmvSc_93D_mWvPwuboma-22qtdH5B-OZ3LOtj-15jRdSd3B4fTsZkw8Sijjgda5ltfncYvg-MJbAq0BEOhYYzmLL5p6CfD5Nq9rnDC1NcrMQfkUu3FblekDfWasHqRvM7iEBr_G0dvuh_Pg
相關命令
#查看節點
kubectl get nodes
#查看pod
kubectl get pods -A
查看pod的ip
kubectl get pods -owide
我們創建資源可以通過命令行直接創建,也可以通過YAML文件來創建
● 命令行
● YAML
名稱空間用來隔離資源
用命令行的模式建立
#創建
kubectl create ns hello
#查看
kubectl get ns
#刪除
kubectl delete ns hello
下面是用yaml的方式建立
建立文件helo-ns.yaml
apiVersion: v1
kind: Namespace
metadata:
name: hello
執行命令創建
kubectl apply -f helo-ns.yaml
運行中的一組容器,Pod是kubernetes中應用的最小單位.
用命令行的模式建立
kubectl run mynginx2 --image=nginx
因為之前搭建環境的時候已經建立過mynginx了,所以這里用mynginx2
運行如下命令進行相關操作
kubectl run mynginx --image=nginx
# 查看default名稱空間的Pod
kubectl get pod
# 描述
kubectl describe pod Pod名字
# 查看Pod的運行日志
kubectl logs Pod名字
# 每個Pod - k8s都會分配一個ip
kubectl get pod -owide
# 使用Pod的ip+pod里面運行容器的端口
curl 10.244.245.193
# 刪除
kubectl delete pod Pod名字
集群中的任意一個機器以及任意的應用都能通過Pod分配的ip來訪問這個Pod
我之前就是這個ping不通很奔潰才重新搭建,修改了pod的ip才行的,不然跟我的虛擬機有點沖突了。
如果是用yaml的話也很簡單,如下面的一個nginx一個tomcat對應的yaml文件
nginx
apiVersion: v1
kind: Pod
metadata:
labels:
run: mynginx3
name: mynginx3
# namespace: default
spec:
containers:
- image: nginx
name: mynginx3
tomcat/nginx,這個相當于一個pod里面有兩個容器,端口不通,nginx是80,tomcat是8080
apiVersion: v1
kind: Pod
metadata:
labels:
run: myapp
name: myapp
spec:
containers:
- image: nginx
name: nginx
- image: tomcat:8.5.68
name: tomcat
執行命令都是
kubectl apply -f yaml文件名
查看pod的IP
[root@k8s-new-master ~]# kubectl get pod -owide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
myapp 2/2 Running 0 2m41s 10.244.245.194 k8s-new-node1 <none> <none>
mynginx 1/1 Running 1 14h 10.244.53.2 k8s-new-node2 <none> <none>
mynginx2 1/1 Running 0 42m 10.244.245.193 k8s-new-node1 <none> <none>
mynginx3 1/1 Running 0 2m50s 10.244.53.3 k8s-new-node2 <none> <none>
訪問下myapp
curl 10.244.245.194:80
curl 10.244.245.194:8080
發現是可以正常訪問的。
此時創建的應用是還不能外部訪問的,需要后面的service才行。
控制Pod,使Pod擁有多副本,自愈,擴縮容等能力
用deployment創建的pod,等pod刪掉后,會自動啟動,下面來驗證下
kubectl create deployment mytomcat --image=tomcat:8.5.68
啟動后,執行刪除pod的命令
kubectl delete pod mytomcat-6f5f895f4f-ppz46
過一會發現又創建了,但是如果我們不是用Deployment方式創建的pod,刪除后將不會再創建。
[root@k8s-new-master ~]# kubectl get pod
NAME READY STATUS RESTARTS AGE
mytomcat-6f5f895f4f-9dx2n 1/1 Running 0 13s
mytomcat-6f5f895f4f-ppz46 0/1 Terminating 0 2m21s
得把所有pod刪掉先,不然怕內存不夠
kubectl delete pod myapp
kubectl delete pod mynginx
kubectl delete pod mynginx2
kubectl delete pod mynginx3
#查看部署
kubectl get deployments
#刪除部署
kubectl delete deployment mytomcat
部署只能刪除部署,如果只刪除pod會自愈的。
可以用命令行
kubectl create deployment my-dep --image=nginx --replicas=3
或者使用yaml創建多副本
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: my-dep
name: my-dep
spec:
replicas: 3
selector:
matchLabels:
app: my-dep
template:
metadata:
labels:
app: my-dep
spec:
containers:
- image: nginx
name: nginx
執行命令當然是
kubectl apply -f yaml文件名
查看可以知道
[root@k8s-new-master ~]# kubectl get pods
NAME READY STATUS RESTARTS AGE
my-dep-5b7868d854-495hg 0/1 ContainerCreating 0 22s
my-dep-5b7868d854-cz48b 1/1 Running 0 22s
my-dep-5b7868d854-fs78l 1/1 Running 0 22s
創建了三個副本,查看更加詳細的內容
[root@k8s-new-master ~]# kubectl get pods -owide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
my-dep-5b7868d854-495hg 1/1 Running 0 107s 10.244.53.5 k8s-new-node2 <none> <none>
my-dep-5b7868d854-cz48b 1/1 Running 0 107s 10.244.245.198 k8s-new-node1 <none> <none>
my-dep-5b7868d854-fs78l 1/1 Running 0 107s 10.244.53.4 k8s-new-node2 <none> <none>
發現有一個是在節點1,那我們嘗試把節點1,關閉,看看如何
[root@k8s-new-master ~]# kubectl get nodes
NAME STATUS ROLES AGE VERSION
k8s-new-master Ready control-plane,master 17h v1.20.9
k8s-new-node1 NotReady <none> 16h v1.20.9
k8s-new-node2 Ready <none> 16h v1.20.9
我們可以每隔一秒看看節點一的pod情況
watch -n 1 kubectl get pods -owide
等了大概十分鐘,節點1的副本就被停止了,重新在節點2啟動了
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
my-dep-5b7868d854-495hg 1/1 Running 0 9m35s 10.244.53.5 k8s-new-node2 <none> <none>
my-dep-5b7868d854-9zsmh 1/1 Running 0 39s 10.244.53.6 k8s-new-node2 <none> <none>
my-dep-5b7868d854-cz48b 1/1 Terminating 0 9m35s 10.244.245.198 k8s-new-node1 <none> <none>
my-dep-5b7868d854-fs78l 1/1 Running 0 9m35s 10.244.53.4 k8s-new-node2 <none> <none>
在運行過程中,我們可以隨著流量需求對pod進行擴縮容,比如我們一開始只部署了3個pod,因為搞活動導致流量暴增,我們就可以擴容到5個,等活動結束后又改為3個,當然這些擴縮容可以在控制臺界面直接修改,也可以用命令或者修改配置文件實現,下面演示使用命令方式實現
擴容到5
kubectl scale --replicas=5 deployment/my-dep
執行完就可以看到
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
my-dep-5b7868d854-495hg 1/1 Running 0 36m 10.244.53.5 k8s-new-node2 <none> <none>
my-dep-5b7868d854-4vfps 0/1 ContainerCreating 0 16s <none> k8s-new-node1 <none> <none>
my-dep-5b7868d854-9zsmh 1/1 Running 0 27m 10.244.53.6 k8s-new-node2 <none> <none>
my-dep-5b7868d854-fs78l 1/1 Running 0 36m 10.244.53.4 k8s-new-node2 <none> <none>
my-dep-5b7868d854-pjmkf 0/1 ContainerCreating 0 16s <none> k8s-new-node1 <none> <none>
正在部署兩個新的pod
我們可以修改配置文件縮容到2
kubectl edit deployment my-dep
#修改 replicas 到2
wq報錯完后就可以看到縮容了,有三個節點Terminating
[root@k8s-new-master ~]# kubectl get pods -owide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
my-dep-5b7868d854-495hg 0/1 Terminating 0 39m 10.244.53.5 k8s-new-node2 <none> <none>
my-dep-5b7868d854-4vfps 1/1 Running 0 3m6s 10.244.245.200 k8s-new-node1 <none> <none>
my-dep-5b7868d854-9zsmh 0/1 Terminating 0 30m 10.244.53.6 k8s-new-node2 <none> <none>
my-dep-5b7868d854-fs78l 0/1 Terminating 0 39m 10.244.53.4 k8s-new-node2 <none> <none>
my-dep-5b7868d854-pjmkf 1/1 Running 0 3m6s 10.244.245.199 k8s-new-node1 <none> <none>
這個在4-2多副本中已經演示了,啟動多個副本后,把其中一個節點停機,k8s自動在別的存活的節點啟動了。
指定新的鏡像后,會自動跟新所有容器
kubectl set image deployment/my-dep nginx=nginx:1.16.1 --record
kubectl rollout status deployment/my-dep
也可以修改配置中的鏡像版本來更新
kubectl edit deployment/my-dep
可以看到,已經修改位1.16.1的版本了,如果想要升級,修改為其它版本即可自動升級
...
spec:
containers:
- image: nginx:1.16.1
imagePullPolicy: Always
name: nginx
...
#歷史記錄
kubectl rollout history deployment/my-dep
#查看某個歷史詳情
kubectl rollout history deployment/my-dep --revision=2
#回滾(回到上次)
kubectl rollout undo deployment/my-dep
#回滾(回到指定版本)
kubectl rollout undo deployment/my-dep --to-revision=2
除了Deployment,k8s還有StatefulSet 、DaemonSet Job 等 類型資源。我們都稱為工作負載。
有狀態應用類似mysql,redis等使用 StatefulSet 部署,無狀態應用類似我們的微服務使用Deployment部署,具體可以查看:https://kubernetes.io/zh/docs/concepts/workloads/controllers/
將一組 Pods 公開為網絡服務的抽象方法。
我們在安裝k8s的時候,有執行如下命令
kubeadm init \
--apiserver-advertise-address=192.168.192.8 \
--control-plane-endpoint=k8s-new-master \
--image-repository registry.cn-hangzhou.aliyuncs.com/lfy_k8s_images \
--kubernetes-version v1.20.9 \
--service-cidr=10.96.0.0/16 \
--pod-network-cidr=10.244.0.0/16
這里我們知道,pod的ip是從10.244.0.0/16生成的,service是從10.96.0.0/16生成的,service跟pod的關系就類似于nginx跟應用的關系,我們pod有多個副本,我們可以通過訪問service負載均衡到pod,下面我們來測試下。
我們為之前的部署my-dep通過service暴露出去
#暴露Deploy
kubectl expose deployment my-dep --port=8000 --target-port=80
#使用標簽檢索Pod
kubectl get pod -l app=my-dep
也可以用文件的方式
apiVersion: v1
kind: Service
metadata:
labels:
app: my-dep
name: my-dep
spec:
selector:
app: my-dep
ports:
- port: 8000
protocol: TCP
targetPort: 80
我們查看service
[root@k8s-new-master ~]# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 19h
my-dep ClusterIP 10.96.191.91 <none> 8000/TCP 56s
通過訪問10.96.191.91來測試
curl 10.96.191.91:8000
我們驗證下有沒有負載均衡的效果
先查詢容器
[root@k8s-new-master ~]# kubectl get pod -l app=my-dep
NAME READY STATUS RESTARTS AGE
my-dep-5b7868d854-5jrv5 1/1 Running 0 29m
my-dep-5b7868d854-nk9t5 1/1 Running 0 29m
進入容器內部修改index.html
#這里進去設置為1
kubectl exec -ti my-dep-5b7868d854-5jrv5 -n default sh
cd /usr/share/nginx/html
echo '1' > index.html
exit
#這里進去設置為2
kubectl exec -ti my-dep-5b7868d854-nk9t5 -n default sh
cd /usr/share/nginx/html
echo '2' > index.html
exit
嘗試多次訪問curl 10.96.191.91:8000
發現是有實現負載均衡的
[root@k8s-new-master ~]# curl 10.96.191.91:8000
2
[root@k8s-new-master ~]# curl 10.96.191.91:8000
1
[root@k8s-new-master ~]# curl 10.96.191.91:8000
1
[root@k8s-new-master ~]# curl 10.96.191.91:8000
2
我們上面建的service,type默認是ClusterIP,是不能通過宿主機的ip來訪問的
# 等同于沒有--type的
kubectl expose deployment my-dep --port=8000 --target-port=80 --type=ClusterIP
apiVersion: v1
kind: Service
metadata:
labels:
app: my-dep
name: my-dep
spec:
ports:
- port: 8000
protocol: TCP
targetPort: 80
selector:
app: my-dep
type: ClusterIP
如果要宿主機可以訪問,需要用NodePort模式
命令版
kubectl expose deployment my-dep --port=8001 --target-port=80 --type=NodePort
yaml版:my-dep2.yaml
apiVersion: v1
kind: Service
metadata:
labels:
app: my-dep2
name: my-dep2
spec:
ports:
- port: 8000
protocol: TCP
targetPort: 80
selector:
app: my-dep
type: NodePort
創建
kubectl apply -f my-dep2.yaml
查看
[root@k8s-new-master ~]# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 20h
my-dep ClusterIP 10.96.191.91 <none> 8000/TCP 37m
my-dep2 NodePort 10.96.206.61 <none> 8000:31123/TCP 2m20s
[root@k8s-new-master ~]#
我們在瀏覽器訪問任意一個節點
http://192.168.192.8:31123
http://192.168.192.9:31123
http://192.168.192.10:31123
NodePort范圍在 30000-32767 之間,所以防火墻或者工作組要放開這些端口
Kubernetes關于服務的暴露主要是通過NodePort方式,通過綁定宿主機的某個端口,然后進行pod的請求轉發和負載均衡,但這種方式下缺陷是:
Service可能有很多個,如果每個都綁定一個node主機端口的話,主機需要開放外圍一堆的端口進行服務調用,管理混亂無法應用很多公司要求的防火墻規則。
理想的方式是通過一個外部的負載均衡器,綁定固定的端口,比如80,然后根據域名或者服務名向后面的Service ip轉發,Nginx很好的解決了這個需求,但問題是如果有新的服務加入,如何去修改Nginx的配置,并且加載這些配置? Kubernetes給出的方案就是Ingress,Ingress包含了兩大主件Ingress Controller和Ingress。
Ingress其實就是對nginx的封裝。
wget https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v0.47.0/deploy/static/provider/baremetal/deploy.yaml
#修改鏡像
vi deploy.yaml
#將image的值改為如下值:
registry.cn-hangzhou.aliyuncs.com/lfy_k8s_images/ingress-nginx-controller:v0.46.0
如果下載不了文件,就用這個https://www.suibibk.com//fileupload/files/ingress.yaml
kubectl apply -f ingress.yaml
# 檢查安裝的結果
kubectl get pod,svc -n ingress-nginx
# 最后別忘記把svc暴露的端口要放行
[root@k8s-new-master ~]# kubectl get pod,svc -n ingress-nginx
NAME READY STATUS RESTARTS AGE
pod/ingress-nginx-admission-create-c8gbj 0/1 Completed 0 2m34s
pod/ingress-nginx-admission-patch-f6dvr 0/1 Completed 0 2m34s
pod/ingress-nginx-controller-65bf56f7fc-59gmk 1/1 Running 0 2m34s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/ingress-nginx-controller NodePort 10.96.141.189 <none> 80:32276/TCP,443:32488/TCP 2m35s
service/ingress-nginx-controller-admission ClusterIP 10.96.185.85 <none> 443/TCP 2m35s
https://192.168.192.8:32488/
http://192.168.192.8:32276/
準備好如下test-ingress.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: hello-server
spec:
replicas: 2
selector:
matchLabels:
app: hello-server
template:
metadata:
labels:
app: hello-server
spec:
containers:
- name: hello-server
image: registry.cn-hangzhou.aliyuncs.com/lfy_k8s_images/hello-server
ports:
- containerPort: 9000
---
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx-demo
name: nginx-demo
spec:
replicas: 2
selector:
matchLabels:
app: nginx-demo
template:
metadata:
labels:
app: nginx-demo
spec:
containers:
- image: nginx
name: nginx
---
apiVersion: v1
kind: Service
metadata:
labels:
app: nginx-demo
name: nginx-demo
spec:
selector:
app: nginx-demo
ports:
- port: 8000
protocol: TCP
targetPort: 80
---
apiVersion: v1
kind: Service
metadata:
labels:
app: hello-server
name: hello-server
spec:
selector:
app: hello-server
ports:
- port: 8000
protocol: TCP
targetPort: 9000
上面會產生兩個service,一個是nginx-demo端口8000,負載到80端口的nginx-demo pod上,一個是hello-server,端口也是8000,負載到9000端口的hello-server pod上。
執行
kubectl apply -f test-ingress.yaml
查看
[root@k8s-new-master ~]# kubectl get svc -owide
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR
hello-server ClusterIP 10.96.189.213 <none> 8000/TCP 69s app=hello-server
nginx-demo ClusterIP 10.96.243.249 <none> 8000/TCP 69s app=nginx-demo
6-3-1、域名訪問
我們在本地的host準備如下兩個域名
C:\Windows\System32\drivers\etc\hosts
192.168.192.10 hello.suibibk.com
192.168.192.10 demo.suibibk.com
因為ingress創建后是在192.168.192.10,所以只能配置這個,不能配置其它節點,這個跟service不同
我們來部署個Ingress:test-ingress2.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress-host-bar
spec:
ingressClassName: nginx
rules:
- host: "hello.suibibk.com"
http:
paths:
- pathType: Prefix
path: "/"
backend:
service:
name: hello-server
port:
number: 8000
- host: "demo.suibibk.com"
http:
paths:
- pathType: Prefix
path: "/nginx" # 把請求會轉給下面的服務,下面的服務一定要能處理這個路徑,不能處理就是404
backend:
service:
name: nginx-demo ## java,比如使用路徑重寫,去掉前綴nginx
port:
number: 8000
部署
kubectl apply -f test-ingress2.yaml
查看下結果
[root@k8s-new-master ~]# kubectl get ingress
NAME CLASS HOSTS ADDRESS PORTS AGE
ingress-host-bar nginx hello.suibibk.com,demo.suibibk.com 80 9s
上面的部署的意思是,如果我們訪問
http://hello.suibibk.com/nginx 會訪問到service:hello-server
http://demo.suibibk.com/nginx 會訪問到service:nginx-demo
然而,訪問卻啥報錯,進不去,why,后面才發現ingress-controller的官方yaml默認注釋了hostNetwork 工作方式,以防止端口的在宿主機的沖突,沒有綁定到宿主機 80 端口;
需要在deployment里面加入
hostNetwork: true這個字段值
大概在這個位置,大家搜索dnsPolicy就可定位
...
spec:
hostNetwork: true
dnsPolicy: ClusterFirst
...
加上后,重新執行
kubectl replace --force -f ingress.yaml
就可以正常訪問了。
6-3-2、路徑重寫
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /$2
name: ingress-host-bar
spec:
ingressClassName: nginx
rules:
- host: "hello.suibibk.com"
http:
paths:
- pathType: Prefix
path: "/"
backend:
service:
name: hello-server
port:
number: 8000
- host: "demo.suibibk.com"
http:
paths:
- pathType: Prefix
path: "/nginx(/|$)(.*)" # 把請求會轉給下面的服務,下面的服務一定要能處理這個路徑,不能處理就是404
backend:
service:
name: nginx-demo ## java,比如使用路徑重寫,去掉前綴nginx
port:
number: 8000
#一個節點
kubectl exec -ti nginx-demo-7d56b74b84-tfpqt -n default sh
cd /usr/share/nginx/html
echo '1' > 1.html
exit
#另一個節點
kubectl exec -ti nginx-demo-7d56b74b84-xl7vq -n default sh
cd /usr/share/nginx/html
echo '1' > 1.html
exit
當我們訪問http://demo.suibibk.com/nginx/1.html,就相當于訪問http://demo.suibibk.com/1.html,注意這里并不是說瀏覽器上面的地址行會變。
6-3-3、流量控制
test-ingress4.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ingress-limit-rate
annotations:
nginx.ingress.kubernetes.io/limit-rps: "1"
spec:
ingressClassName: nginx
rules:
- host: "haha.suibibk.com"
http:
paths:
- pathType: Exact
path: "/"
backend:
service:
name: nginx-demo
port:
number: 8000
kubectl apply -f test-ingress4.yaml
這里需要在本機hosts加上
192.168.192.10 haha.suibibk.com
我們限制的limit-rps是1,瀏覽器訪問這個:http://haha.suibibk.com ,頻率高一點就會報下面的錯誤
503 Service Temporarily Unavailable
證明有進行流量控制。
我們可以指定容器的掛載目錄,統一存儲在一個地方,比如ceph,nfs,這里用nfs來舉例,后面我們就可以掛載redis,mysql的數據文件到nfs中,對應的pod出問題后,只要在別的節點啟動pod數據也不會丟失。
NFS就是Network File System的縮寫,它最大的功能就是可以通過網絡,讓不同的機器、不同的操作系統可以共享彼此的文件。
#所有機器安裝
yum install -y nfs-utils
#nfs主節點
echo "/nfs/data/ *(insecure,rw,sync,no_root_squash)" > /etc/exports
mkdir -p /nfs/data
systemctl enable rpcbind --now
systemctl enable nfs-server --now
#配置生效
exportfs -r
#這里要寫主節點的ip
showmount -e 192.168.192.8
#執行以下命令掛載 nfs 服務器上的共享目錄到本機路徑 /root/nfsmount
mkdir -p /nfs/data
mount -t nfs 192.168.192.8:/nfs/data /nfs/data
# 寫入一個測試文件
echo "hello nfs server" > /nfs/data/test.txt
可以發現,別的節點的/nfs/data目錄也有test.txt文件了
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx-pv-demo
name: nginx-pv-demo
spec:
replicas: 2
selector:
matchLabels:
app: nginx-pv-demo
template:
metadata:
labels:
app: nginx-pv-demo
spec:
containers:
- image: nginx
name: nginx
volumeMounts:
- name: html
mountPath: /usr/share/nginx/html
volumes:
- name: html
nfs:
server: 192.168.192.8
path: /nfs/data/nginx-pv
記得nfs server要輸入主節點的ip
創建
kubectl apply -f nginx-pv-demo.yaml
查看創建情況
kubectl get pods -owide
發現一直在創建中:ContainerCreating
查看創建詳情
kubectl describe pod nginx-pv-demo-5f6ccc5f79-d29tr
Output: mount.nfs: mounting 192.168.192.8:/nfs/data/nginx-pv failed, reason given by server: No such file or directory
喵的,忘記創建掛載文件夾
cd /nfs/data/
mkdir nginx-pv
再等等查看就發現已經創建了。去/nfs/data/nginx-pv 目錄下面創建個index.html
curl 10.244.53.16:80
返回了預期結果。
PV:持久卷(Persistent Volume),將應用需要持久化的數據保存到指定位置
PVC:持久卷申明(Persistent Volume Claim),申明需要使用的持久卷規格
1-5-1、創建pv池
靜態供應
#nfs主節點
mkdir -p /nfs/data/01
mkdir -p /nfs/data/02
mkdir -p /nfs/data/03
創建pv
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv01-10m
spec:
capacity:
storage: 10M
accessModes:
- ReadWriteMany
storageClassName: nfs
nfs:
path: /nfs/data/01
server: 192.168.192.8
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv02-1gi
spec:
capacity:
storage: 1Gi
accessModes:
- ReadWriteMany
storageClassName: nfs
nfs:
path: /nfs/data/02
server: 192.168.192.8
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv03-3gi
spec:
capacity:
storage: 3Gi
accessModes:
- ReadWriteMany
storageClassName: nfs
nfs:
path: /nfs/data/03
server: 192.168.192.8
注意server要修改為自己的主節點ip
kubectl apply -f pv.yaml
查看
[root@k8s-new-master ~]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
pv01-10m 10M RWX Retain Available nfs 26s
pv02-1gi 1Gi RWX Retain Available nfs 26s
pv03-3gi 3Gi RWX Retain Available nfs 26s
1-5-2、PVC創建與綁定
創建PVC
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: nginx-pvc
spec:
accessModes:
- ReadWriteMany
resources:
requests:
storage: 200Mi
storageClassName: nfs
創建Pod綁定PVC
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx-deploy-pvc
name: nginx-deploy-pvc
spec:
replicas: 2
selector:
matchLabels:
app: nginx-deploy-pvc
template:
metadata:
labels:
app: nginx-deploy-pvc
spec:
containers:
- image: nginx
name: nginx
volumeMounts:
- name: html
mountPath: /usr/share/nginx/html
volumes:
- name: html
persistentVolumeClaim:
claimName: nginx-pvc
執行完后再查看pv
[root@k8s-new-master ~]# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
pv01-10m 10M RWX Retain Available nfs 2m57s
pv02-1gi 1Gi RWX Retain Bound default/nginx-pvc nfs 2m57s
pv03-3gi 3Gi RWX Retain Available nfs 2m57s
發現pv02-1gi已被使用。我們pod申請的是200M,所以最靠近且滿足的就是pv02-1gi
抽取應用配置,并且可以自動更新
2-1-1、把之前的配置文件創建為配置集
# 創建配置,redis保存到k8s的etcd;這個需要先有redis.conf文件
kubectl create cm redis-conf --from-file=redis.conf
也可以用yaml創建
apiVersion: v1
data: #data是所有真正的數據,key:默認是文件名 value:配置文件的內容
redis.conf: |
appendonly yes
kind: ConfigMap
metadata:
name: redis-conf
namespace: default
查看cm
[root@k8s-new-master ~]# kubectl get cm
NAME DATA AGE
kube-root-ca.crt 1 24h
redis-conf 1 39s
2-1-2、創建redis
apiVersion: v1
kind: Pod
metadata:
name: redis
spec:
containers:
- name: redis
image: redis
command:
- redis-server
- "/redis-master/redis.conf" #指的是redis容器內部的位置
ports:
- containerPort: 6379
volumeMounts:
- mountPath: /data
name: data
- mountPath: /redis-master
name: config
volumes:
- name: data
emptyDir: {}
- name: config
configMap:
name: redis-conf
items:
- key: redis.conf
path: redis.conf
2-1-3、檢查默認配置
[root@k8s-new-master ~]# kubectl exec -it redis -- redis-cli
127.0.0.1:6379> CONFIG GET appendonly
1) "appendonly"
2) "yes"
127.0.0.1:6379>
發現就是用的我們創建的配置
2-1-3、修改配置
#找到配置名
kubectl get cm
#修改
kubectl edit configmap redis-conf
加上maxmemory 2mb和maxmemory-policy allkeys-lru
apiVersion: v1
data:
redis.conf: |
appendonly yes
maxmemory 2mb
maxmemory-policy allkeys-lru
kind: ConfigMap
metadata:
creationTimestamp: "2023-02-23T20:44:43Z"
name: redis-conf
namespace: default
resourceVersion: "57788"
uid: f99aea5f-41da-4755-aed0-7e4a66e2adac
檢查配置是否更新
[root@k8s-new-master ~]# kubectl exec -it redis -- redis-cli
127.0.0.1:6379> CONFIG GET maxmemory
1) "maxmemory"
2) "0"
配置值未更改,因為需要重新啟動 Pod 才能從關聯的 ConfigMap 中獲取更新的值。
原因:我們的Pod部署的中間件自己本身沒有熱更新能力
Secret對象類型用來保存敏感信息,例如密碼、OAuth 令牌和 SSH 密鑰。 將這些信息放在secret 中比放在Pod的定義或者容器鏡像中來說更加安全和靈活。
kubectl create secret docker-registry leifengyang-docker \
--docker-username=leifengyang \
--docker-password=Lfy123456 \
--docker-email=534096094@qq.com
##命令格式
kubectl create secret docker-registry regcred \
--docker-server=<你的鏡像倉庫服務器> \
--docker-username=<你的用戶名> \
--docker-password=<你的密碼> \
--docker-email=<你的郵箱地址>
[root@k8s-new-master ~]# kubectl get secret
NAME TYPE DATA AGE
default-token-gqkpn kubernetes.io/service-account-token 3 24h
leifengyang-docker kubernetes.io/dockerconfigjson 1 11s
使用,可以從自己的私有倉庫拉起
apiVersion: v1
kind: Pod
metadata:
name: private-nginx
spec:
containers:
- name: private-nginx
image: leifengyang/guignginx:v1.0
imagePullSecrets:
- name: leifengyang-docker
最后執行這個肯定是報錯的啦
kubectl describe pod private-nginx
可以看到密碼不對的提示
ailed to pull image "leifengyang/guignginx:v1.0": rpc error: code = Unknown desc = Error response from daemon: Head https://registry-1.docker.io/v2/leifengyang/guignginx/manifests/v1.0: unauthorized: incorrect username or password
好了,實戰結束。
教程參考:
1、視頻教程
https://www.bilibili.com/video/BV13Q4y1C7hS
2、筆記
https://www.yuque.com/leifengyang/oncloud/
爺爺讓我記住的老人言:
1.睡前不喝水,衣服不要穿三天
2.吃過的饃饃不香,嚼過的甘蔗不甜。
3.在家千日好,出家一時難。熟處好拜年,生處好賺錢。
4.白地不下種,白水不栽秧。
5.蜻蜓低飛江湖邊,必定大雨雷閃電。
6.蠅子見不得血,臟官見不得錢。
7.人多智謀廣,柴多火焰高。
8.水大不能漫船,官大不能欺親。
9.靜靜的心里,都有一道最美麗的風景。
10.不問過去人成熟,不問現在人聰慧。
11.凡是別人對你說:我來說句公道話吧,他分明就沒有站在“你這邊”。
12.有人說,世界上最美的是夢,最長的是路;最易做的是夢,最難走的是路。
13.人有失手,馬有漏蹄。
14.在沒有100萬之前,取消一切娛樂活動。
15.路是自己選的,后悔的話,也只能往自己的肚子里咽。
16.停下休息的時候不要忘記別人還在奔跑。
17.樹杈不修要長歪,子女不教難成材。
18.學而不厭,誨人不倦。
19.打牌的女人,失 身 多。
20.知交比情人更難得,朋友比愛情更長久。
21.身處困境時,別忘陪你的人;走投無路時,別忘領你的人;一無所有時,別忘愛你的人;窮困潦倒時,別忘疼你的人。人,你可以不知趣,但不可以不知理;你可以不感動,但不可以不感恩。
22.死亡教會人一切,如同考試之后公布的結果——雖然恍然大悟,但為時晚矣!
23.多喝涼白開,健康自然來。
24.大器不必晚成,趁著年輕,努力讓自己的才能創造最大的價值。
25.嘴巴兩張皮,隨說隨改意。
26.虱多不癢,債多不愁。
27.如果你改變不了現實,那么你就得去學會改變自己。
28. 勇敢開始,不戀過往,不困于今,不畏將來。早安,奮斗的人們!
29.成功就是一把梯子,雙手插在口袋的人是爬不上去的。
30.人不教不懂,鐘不敲不鳴,樹不修不長,娃不管不成。
31.天下之禍,不生于逆,而生于順。
32.心深似水潭,竹篙探不應。
33.親戚瞧不起你的父母,是因為你混得不好。
34.男女關系要謹慎,自古奸情出人命。
35.人一定要受過傷才會沉默專注,無論是心靈或肉體上的創傷,對成長都有益處。
36.打個巴掌再給個甜棗——堵嘴
37.不到江邊不脫鞋,不到火候不揭鍋。
38.相識滿天下,知心有幾人。
39.臘月二十六,殺豬割年肉。
40.身弱的人,最怕做一些長期輸出性的工作。
41.寧嫁八十老頭,不嫁十八小猴。
42.和窮人混,就是無效社交,雖難聽但是事實。
43.一個人去異性同事的辦公室,記得把門打開。
44.知事必須虛心,成事須有恒心。
45.沒有人可以打倒我,除非我自己先趴下!
46.施詭計者,自食其果。
47.群處守嘴,獨處守心。修己以清心為要,涉世以慎言為先。
48.不要辜負上天賜予你的健康體魄和智慧頭腦。
49.棋逢敵手難相勝,將遇良才不敢驕。
50.人可失才,但不可失禮,規矩就是教養。
#微頭條激勵計劃# #2023年度創作挑戰# #0粉也可以獲得創作收益啦# #人與人之間的潛規則# #南京頭條# #文章首發挑戰賽#