前言
舊遊無處不堪尋,無尋處,未有少年心
1.k8s簡介
簡介
Kubernetes
簡稱 k8s
。是用於自動部署,擴充套件和管理容器化應用程式的開源系統。
中文官網:https://kubernetes.io/zh/
中文社群:https://www.kubernetes.org.cn/
官方文件:https://kubernetes.io/zh/docs/home/
社群文件:http://docs.kubernetes.org.cn/
部署方式的進化
[概述 | Kubernetes]:https://kubernetes.io/zh-cn/docs/concepts/overview/
Docker Swarm
k8s排程、k8s自動恢復、k8s水平伸縮
2.k8s架構原理&核心概念
Kubernetes
叢集所需的各種元件
整體主從方式
Master 節點架構
-
kube-apiserver
- 對外暴露 K8S 的 api 介面,是外界進行資源操作的
- 提供認證、授權、訪問控制、API 註冊和發現等機制
-
etcd
- etcd 是兼具一致性和高可用性的鍵值資料庫,可以作為儲存 Kubernetes 所有集 群資料的後臺資料庫。
- Kubernetes 叢集的 etcd 資料庫通常需要有個備份計劃。
-
kube-scheduler
- 主節點上的元件,該元件監視那些新建立的未指定執行節點的 Pod,並選擇節點 讓 Pod 在上面執行。
- 所有對 k8s 的叢集操作,都必須經過主節點進行排程。
-
kube-controller-manage
- 在主節點上執行控制器的元件
- 這些控制器包括:
- Node 控制器:負責在節點出現故障時進行通知和響應。
- Job 控制器:監測代表一次性任務的 Job 物件,然後建立 Pod 來執行這些任務直至完成。
- EndpointSlice 控制器:填充 EndpointSlice 物件(以提供 Service 和 Pod 之間的連結)。
- ServiceAccount 控制器:為新的名稱空間建立預設的 ServiceAccount。
Node 節點架構
-
kubelet
- 一個在叢集中每個節點上執行的代理。它保證容器都執行在 Pod 中。
- 負責維護容器的生命週期,同時也負責 Volume(CSI)和網路(CNI)的管理;
-
kube-proxy
- 負責為 Service 提供 cluster 內部的服務發現和負載均衡;
-
容器執行環境(Container Runtime)
- 容器執行環境是負責執行容器的軟體。
- Kubernetes 支援許多容器執行環境,例如 containerd、 CRI-O 以及 Kubernetes CRI (容器執行環境介面)]的其他任何實現。
-
fluentd
- 是一個守護程序,它有助於提供叢集層面日誌 叢集層面的日
概念
- Container:容器,可以是 docker 啟動的一個容器。
- Pod:
- k8s 使用 Pod 來組織一組容器。
- 一個 Pod 中的所有容器共享同一網路。
- Pod 是 k8s 中的最小部署。
- Volume
- 宣告在 Pod 容器中可訪問的檔案
- 可以被掛載在 Pod 中一個或多個容器指定路勁下
- 支援多種後端儲存抽象(本地儲存,分散式儲存,雲存 儲…)
- Controllers:更高層次物件,部署和管理 Pod;
- ReplicaSet:確保預期的 Pod 副本數量
- Deplotment:無狀態應用部署
- StatefulSet:有狀態應用部署。
- DaemonSet:確保所有 Node 都執行一個指定 Pod
- Job:一次性任務
- Cronjob:定時任務
- Deployment
- 定義一組 Pod 的副本數目、版本等。
- 透過控制器(Controller)維持 Pod 數目(自動回 復失敗的 Pod)。
- 透過控制器以指定的策略控制版本(滾動升級,回滾等)。
- Service
- 定義一組 Pod 的訪問策略。
- Pod 的負載均衡,提供一個或者多個 Pod 的穩定 訪問地址。
- 支援多種方式(ClusterIP、NodePort、LoadBalance)
- Label:標籤,用於物件資源的查詢,篩選。
- Namespace:名稱空間,邏輯隔離
- 一個叢集內部的邏輯隔離機制(鑑權,資源)
- 每個資源都屬於一個 namespace
- 同一個 namespace 所有資源名不能重複
- 不同 namespace 可以資源名重複
- API
- 我們透過 kubernetes 的 API 來操作整個叢集。
- 可以透過 kubectl、ui、curl 最終傳送 http+json/yaml 方式的請求給 API Server,然後控制 k8s 叢集。
- k8s 裡的所有的資源物件都可以採用 yaml 或 JSON 格式的檔案定義或描述
3.k8s-叢集搭建
3.1環境準備
我這裡使用的是vmware
搭建的centos7
環境,可以參考我之前的文章
https://www.cnblogs.com/pengboke/p/18051066
3.2建立三個虛擬機器
BUG:Could not retrieve mirrorlist http://mirrorlist.centos.org/?release=7&arch=x86_64&repo=os&infra=stock error was
14: curl#6 - "Could not resolve host: mirrorlist.centos.org; 未知的錯誤"
參考地址:https://www.cnblogs.com/zengzuo613/p/18292809
開啟/etc/yum.repos.d/CentOS-Vault.repo
vim /etc/yum.repos.d/CentOS-Vault.repo
在 CentOS-Vault.repo 新增如下配置,以啟用 CentOS 7 的存檔倉庫,新增配置如下:
# 檔案路徑 /etc/yum.repos.d/CentOS-Vault.repo
# Vault
[Vault-base]
name=Vault - CentOS-$releasever - Base
baseurl=http://vault.centos.org/centos/$releasever/os/$basearch/
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-CentOS-$releasever
[Vault-updates]
name=Vault - CentOS-$releasever - Updates
baseurl=http://vault.centos.org/centos/$releasever/updates/$basearch/
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-CentOS-$releasever
[Vault-extras]
name=Vault - CentOS-$releasever - Extras
baseurl=http://vault.centos.org/centos/$releasever/extras/$basearch/
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-CentOS-$releasever
使用 enabled=0
禁用 CentOS-Base.repo 中的所有倉庫,修改後配置如下:
vim /etc/yum.repos.d/CentOS-Base.repo
[base]
name=CentOS-$releasever - Base
mirrorlist=http://mirrorlist.centos.org/?release=$releasever&arch=$basearch&repo=os&infra=$infra
#baseurl=http://mirror.centos.org/centos/$releasever/os/$basearch/
gpgcheck=1
enabled=0
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-CentOS-7
特別說明: CentOS 7 各子版本中,$releasever 值都為 7。具體原因請看:releaseve 變數詳解。
清除 YUM 快取,如有需要可再生成新的快取
yum clean all ; yum makecache
驗證方法
yum repolist
VMware克隆
之前我已經建立了一個虛擬機器,並且拍攝了快照
修改ip
vim /etc/sysconfig/network-scripts/ifcfg-ens33
重啟網路服務,檢視ip是否配置成功
service network restart
ifconfig
安裝docker
官方文件:https://docs.docker.com/engine/install/centos/
# 如果系統中已經存在舊的Docker,則先解除安裝
yum remove docker \
docker-client \
docker-client-latest \
docker-common \
docker-latest \
docker-latest-logrotate \
docker-logrotate \
docker-engine
# 安裝一個yum工具
yum install -y yum-utils
# 配置Docker的yum源 aliyun
sudo yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
# 安裝Docker
yum install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
配置映象加速
# 配置原始檔
cat <<EOF > /etc/docker/daemon.json
{
"registry-mirrors": [
"https://registry.docker-cn.com",
"https://docker.mirrors.ustc.edu.cn",
"https://mirror.baidubce.com",
"https://80cebfmn.mirror.aliyuncs.com",
"https://cr.console.aliyun.com",
"https://hub-mirror.c.163.com",
"http://mirrors.tuna.tsinghua.edu.cn",
"http://mirrors.aliyun.com"
]
}
EOF
常用命令
# 重新啟動
systemctl daemon-reload
systemctl restart docker
# 設定開機自啟
systemctl enable docker
給k8s-01拍攝快照
當前狀態是docker已安裝完成,在克隆節點時不用再安裝
然後建立k8s-02
、k8s-03
節點
k8s-02
修改ip為192.168.188.182
,修改k8s-02
時關閉k8s-01
# 修改ip
vim /etc/sysconfig/network-scripts/ifcfg-ens33
# 重啟網路卡
service network restart
k8s-03
修改ip為192.168.188.183
,修改k8s-03
時關閉k8s-02
三個虛擬機器建立完畢
3.3NAT網路和前置環境
修改三臺主機名
開啟hosts檔案
vi /etc/hosts
修改
# ip + 機器別名
cat >> /etc/hosts << EOF
192.168.188.181 k8s-01
192.168.188.182 k8s-02
192.168.188.183 k8s-03
EOF
ping
一下,三臺都能互相ping
通即可
ping k8s-01
BUG:unable to load client CA file /etc/kubernetes/pki/ca.crt: open /etc/kubernetes/pki/ca.crt: no such file or directory
檢查 /etc/kubernetes/pki/
目錄下是否存在 ca.crt
檔案:
ls -l /etc/kubernetes/pki/ca.crt
重新初始化 Kubernetes
sudo kubeadm reset
3.4安裝Docker、kubelet、kubeadm、kubectl
檢查作業系統的版本
檢查作業系統的版本(要求作業系統的版本至少在7.5以上):
cat /etc/redhat-release
關閉防火牆和禁止防火牆開機啟動
關閉防火牆:
systemctl stop firewalld
禁止防火牆開機啟動:
systemctl disable firewalld
設定主機名
語法:
hostnamectl set-hostname <hostname>
命令
# 192.168.188.181主機
hostnamectl set-hostname k8s-01
# 192.168.188.182主機
hostnamectl set-hostname k8s-02
# 192.168.188.183主機
hostnamectl set-hostname k8s-03
主機名解析
cat >> /etc/hosts << EOF
192.168.188.181 k8s-01
192.168.188.182 k8s-02
192.168.188.183 k8s-03
EOF
時間同步
kubernetes要求叢集中的節點時間必須精確一致,所以在每個節點上新增時間同步:
安裝ntpdate
yum install ntpdate -y
設定時間
ntpdate time.windows.com
關閉selinux
檢視selinux是否開啟:
getenforce
永久關閉selinux,需要重啟:
sed -i 's/enforcing/disabled/' /etc/selinux/config
臨時關閉selinux,重啟之後,無效:
setenforce 0
關閉swap分割槽
永久關閉swap分割槽,需要重啟:
sed -ri 's/.*swap.*/#&/' /etc/fstab
臨時關閉swap分割槽,重啟之後,無效:
swapoff -a
將橋接的IPv4流量傳遞到iptables的鏈
在每個節點上將橋接的IPv4流量傳遞到iptables的鏈:
cat > /etc/sysctl.d/k8s.conf << EOF
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1
vm.swappiness = 0
EOF
載入br_netfilter模組
modprobe br_netfilter
檢視是否載入
lsmod | grep br_netfilter
生效
sysctl --system
開啟ipvs
在kubernetes中service有兩種代理模型,一種是基於iptables,另一種是基於ipvs的。ipvs的效能要高於iptables的,但是如果要使用它,需要手動載入ipvs模組。
在每個節點安裝ipset和ipvsadm:
yum -y install ipset ipvsadm
在所有節點執行如下指令碼:
cat > /etc/sysconfig/modules/ipvs.modules <<EOF
#!/bin/bash
modprobe -- ip_vs
modprobe -- ip_vs_rr
modprobe -- ip_vs_wrr
modprobe -- ip_vs_sh
modprobe -- nf_conntrack_ipv4
EOF
授權、執行、檢查是否載入:
chmod 755 /etc/sysconfig/modules/ipvs.modules && bash /etc/sysconfig/modules/ipvs.modules && lsmod | grep -e ip_vs -e nf_conntrack_ipv4
檢查是否載入:
lsmod | grep -e ipvs -e nf_conntrack_ipv4
重啟三臺機器
reboot
安裝Docker
# 解除安裝docker
# sudo yum remove docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
wget https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo -O /etc/yum.repos.d/docker-ce.repo
# 第一步:安裝docker
yum -y install docker-ce-18.06.3.ce-3.el7
# 第二步:配置docker映象源
cat <<EOF > /etc/docker/daemon.json
{
"exec-opts": ["native.cgroupdriver=systemd"],
"registry-mirrors": [
"https://du3ia00u.mirror.aliyuncs.com",
"https://registry.docker-cn.com",
"https://docker.mirrors.ustc.edu.cn",
"https://mirror.baidubce.com",
"https://80cebfmn.mirror.aliyuncs.com",
"https://cr.console.aliyun.com",
"https://hub-mirror.c.163.com",
"http://mirrors.tuna.tsinghua.edu.cn",
"http://mirrors.aliyun.com"
],
"live-restore": true,
"log-driver":"json-file",
"log-opts": {"max-size":"500m", "max-file":"3"},
"storage-driver": "overlay2"
}
EOF
# 第三步:重啟
# 開機自啟動
systemctl enable docker && systemctl start docker
# 驗證版本
docker version
BUG:啟動docker的時候:Job for docker.service failed because the control process exited with error code. See "systemctl status docker.service" and "journalctl -xe" for details.
原因可能是低版本的docker配置檔案不支援json
[root@k8s-02 ~]# cd /etc/docker
[root@k8s-02 docker]# ls
daemon.json key.json
[root@k8s-02 docker]# mv daemon.json daemon.conf
新增阿里雲的YUM軟體源
由於kubernetes的映象源在國外,非常慢,這裡切換成國內的阿里雲映象源:
cat > /etc/yum.repos.d/kubernetes.repo << EOF
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes/yum/repos/kubernetes-el7-x86_64
enabled=1
gpgcheck=0
repo_gpgcheck=0
gpgkey=https://mirrors.aliyun.com/kubernetes/yum/doc/yum-key.gpg https://mirrors.aliyun.com/kubernetes/yum/doc/rpm-package-key.gpg
EOF
安裝kubeadm、kubelet和kubectl
由於版本更新頻繁,這裡指定版本號部署:
yum install -y kubelet-1.18.0 kubeadm-1.18.0 kubectl-1.18.0
為了實現Docker使用的cgroup drvier和kubelet使用的cgroup drver一致,建議修改"/etc/sysconfig/kubelet"檔案的內容:
vim /etc/sysconfig/kubelet
修改:
# 修改
KUBELET_EXTRA_ARGS="--cgroup-driver=systemd"
KUBE_PROXY_MODE="ipvs"
設定為開機自啟動即可,由於沒有生成配置檔案,叢集初始化後自動啟動:
systemctl enable kubelet
檢視k8s所需映象
kubeadm config images list
部署k8s的Master節點
部署k8s的Master節點(192.168.188.181)
如果失敗需要重新啟動時kubeadm reset
,是在不行,上面再檢查一下
如果kubeadm reset
失敗,需要刪除etcd
服務,執行一下命令sudo rm -rf /var/lib/etcd
# 由於預設拉取映象地址k8s.gcr.io國內無法訪問,這裡需要指定阿里雲映象倉庫地址
kubeadm init \
--apiserver-advertise-address=192.168.188.181 \
--image-repository registry.aliyuncs.com/google_containers \
--kubernetes-version v1.18.0 \
--service-cidr=10.96.0.0/12 \
--pod-network-cidr=10.244.0.0/16
根據提示訊息,在Master節點上使用kubectl工具:
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
部署k8s的Node節點
根據提示,在192.168.188.182和192.168.188.183上新增如下的命令:
kubeadm join 192.168.188.181:6443 --token qq2whn.e9i313jry0xc2uj5 \
--discovery-token-ca-cert-hash sha256:90396f2d1aecf4bc04b2f22a754a7e16fdbcf3b8a9c40c45befd210c1b63b34f
預設的token有效期為2小時,當過期之後,該token就不能用了,這時可以使用如下的命令建立token:
kubeadm token create --print-join-command
生成一個永不過期的token
kubeadm token create --ttl 0 --print-join-command
部署CNI網路外掛
根據提示,在Master節點上使用kubectl工具檢視節點狀態:
kubectl get nodes
kubernetes支援多種網路外掛,比如flannel、calico、canal等,任選一種即可,本次選擇flannel,如果網路不行,可以使用本人提供的[📎kube-flannel.yml],當然,你也可以安裝calico,請點這裡[📎calico.yaml],推薦安裝calico。
可以使用已經下載好的calico.yaml
,這個執行完成就不用執行下面的kube-flannel.yml
了
kubectl apply -f kube-flannel.yml
在Master節點上獲取flannel配置檔案(可能會失敗,如果失敗,請下載到本地,然後安裝):
wget https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
使用配置檔案啟動flannel:
kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
BUG:如果外掛狀態不是running
檢視那些外掛沒有running
kubectl get pods -n kube-system
使用docker pull
看看能不能手動拉取
docker pull
不可以的話檢查一下/etc/docker/daemon.json
vim /etc/docker/daemon.json
BUG:failed to find plugin "flannel" in path [/opt/cni/bin]]
flannel
外掛安裝完成後,所有狀態都是Running
,但節點k8s-02
、k8s-03
還是NotReady
檢視k8s-02
日誌,大致意思是找不到flannel
journalctl -f -u kubelet.service
解決辦法:把k8s-01
下的/opt/cni/bin/flannel
同步到k8s-02
、k8s-03
# 把flannel外掛同步到k8s-02
scp /opt/cni/bin/flannel root@k8s-02:/opt/cni/bin/
# 把flannel外掛同步到k8s-03
scp /opt/cni/bin/flannel root@k8s-03:/opt/cni/bin/
# 重啟k8s-02和k8s-03
systemctl restart kubelet
# 再次檢視節點狀態
kubectl get nodes
檢視部署CNI網路外掛進度:
kubectl get pods -n kube-system
再次在Master節點使用kubectl工具檢視節點狀態:
kubectl get nodes
檢視叢集健康狀況:
kubectl get cs
顯示當前 Kubernetes 叢集的基本資訊,包括主控元件(如 Kubernetes API server)的訪問地址和相關服務的地址
kubectl cluster-info
常用命令
除錯的時候經常用到的命令
rm flannel.tar.gz
curl -L https://github.com/flannel-io/flannel/releases/download/v0.17.1/flannel-v0.17.1-linux-amd64.tar.gz -o flannel.tar.gz
tar -xzf flannel.tar.gz -C /opt/cni/bin
journalctl -f -u kubelet.service
watch kubectl get pod -n kube-system -o wide
kubectl describe pod calico-kube-controllers-7dbc97f587-m9tqq -n kube-system
kubectl describe pod kube-flannel-ds-7pwlg -n kube-system
kubectl apply -f kube-flannel.yml
kubectl delete -f kube-flannel.yml
kubectl apply -f calico.yaml
kubectl delete -f calico.yaml
docker pull mirror.baidubce.com/nginx:latest
cat <<EOF > /etc/docker/daemon.json
{
"exec-opts": ["native.cgroupdriver=systemd"],
"registry-mirrors": [
"https://du3ia00u.mirror.aliyuncs.com",
"https://registry.docker-cn.com",
"https://mirror.baidubce.com",
"https://80cebfmn.mirror.aliyuncs.com",
"https://cr.console.aliyun.com",
"https://hub-mirror.c.163.com",
"http://mirrors.tuna.tsinghua.edu.cn",
"http://mirrors.aliyun.com",
"https://docker.mirrors.ustc.edu.cn"
],
"live-restore": true,
"log-driver":"json-file",
"log-opts": {"max-size":"500m", "max-file":"3"},
"storage-driver": "overlay2"
}
EOF
sudo systemctl daemon-reload
sudo systemctl restart docker
systemctl status docker
systemctl restart docker
docker pull nginx:latest
docker pull 80cebfmn.mirror.aliyuncs.com/nginx:latest
docker pull mirrors.cloud.aliyuncs.com/calico/kube-controllers:v3.17.1
docker pull 80cebfmn.mirror.aliyuncs.com/calico/kube-controllers:v3.17.1
kubectl logs -n kube-system coredns-7ff77c879f-l6xfh
kubectl describe pod coredns-7ff77c879f-l6xfh -n kube-system
docker load --input flannel-0.11.0-amd64.tar #匯入映象
cat /etc/hosts
3.5解除安裝kubelet、kubeadm、kubectl
首先,停止並禁用相關服務
sudo systemctl stop kubelet
sudo systemctl stop docker
sudo systemctl stop containerd
sudo systemctl disable kubelet
sudo systemctl disable docker
sudo systemctl disable containerd
解除安裝軟體包
sudo yum remove -y kubelet kubeadm kubectl
刪除 Kubernetes 配置檔案和資料目錄
sudo rm -rf /etc/kubernetes
sudo rm -rf /var/lib/kubelet
sudo rm -rf /var/lib/etcd
sudo rm -rf /var/lib/kube-proxy
sudo rm -rf /var/lib/cni
sudo rm -rf /var/run/kubernetes
刪除containerd
sudo rm -rf /var/lib/containerd
安裝時清空環境
sudo rm -rf /etc/kubernetes
sudo rm -rf /var/lib/etcd/*
4.8k8s-入門
4.1基本操作體驗
BUG:docker下載映象一直失敗
更新映象地址,然後重啟docker
# dockera安裝失敗,可以更新映象源地址
cat <<EOF > /etc/docker/daemon.json
{
"exec-opts": ["native.cgroupdriver=systemd"],
"registry-mirrors":[
"https://x9r52uz5.mirror.aliyuncs.com",
"https://dockerhub.icu",
"https://docker.chenby.cn",
"https://docker.1panel.live",
"https://docker.awsl9527.cn",
"https://docker.anyhub.us.kg",
"https://dhub.kubesre.xyz"
],
"live-restore": true,
"log-driver":"json-file",
"log-opts": {"max-size":"500m", "max-file":"3"},
"storage-driver": "overlay2"
}
EOF
sudo systemctl daemon-reload
sudo systemctl restart docker
安裝nginx
安裝nginx
# 刪除deployment命令,如果已建立需要刪除
# kubectl delete deployment nginx
kubectl create deployment nginx --image=nginx:latest
檢視pod
資訊
# 獲取當前名稱空間中的所有 Pod 的列表
kubectl get pods
# 獲取當前名稱空間中的所有 Pod 的詳細資訊
kubectl get pods -o wide
# 獲取當前名稱空間中所有型別的資源的列表
kubectl get all
模擬服務當機,容災恢復
剛才nginx
安裝在k8s-02
,我們關閉k8s-02
k8s-02
節點停止執行nginx
,k8s-03
節點重新執行nginx
# 獲取當前名稱空間中的所有 Pod 的列表
kubectl get pods
# 獲取當前名稱空間中的所有 Pod 的詳細資訊
kubectl get pods -o wide
# 獲取當前名稱空間中所有型別的資源的列表
kubectl get all
暴露訪問埠
Pod 的 80 對映容器的 80;service 會代理 Pod 的 8080
# 刪除命令,如果已建立需要刪除
# kubectl delete service nginx
kubectl expose deployment nginx --port=80 --target-port=8080 --type=NodePort
檢視叢集資訊
# 顯示k8s所有服務
kubectl get svc
# 在get svc顯示更詳細資訊
kubectl get svc -o wide
# 顯示叢集中所有的 Pod
kubectl get pods -o wide
獲取 k8s叢集中各種資源
kubectl get all
發現外部服務埠31050
,訪問http://192.168.188.182:31050/
動態擴容測試
# 檢視叢集中所有的部署
kubectl get deployment
# 將 nginx 部署的副本數(Pods 數量)調整為 3 個
kubectl scale --replicas=3 deployment nginx
# 顯示叢集中所有的 Pod
kubectl get pods -o wide
# 顯示所有服務(Services)及其詳細資訊
kubectl get svc -o wide
# 將 nginx 部署的副本數調整為 1 個
kubectl scale --replicas=1 deployment nginx
# 顯示叢集中所有的 Pod
kubectl get pods -o wide
檢視部署
將nginx
擴容3個
k8s-02
部署了2個,k8s-03
部署了1個
檢視服務
將nginx
縮容回1個
只有k8s-03
執行了1個
刪除
kubectl get all
# 刪除部署
kubectl delete deployment nginx
# 刪除服務
kubectl delete service nginx
4.2yaml&基本使用
kubectl
kubectl 文件:https://kubernetes.io/zh-cn/docs/reference/kubectl/
資源型別:https://kubernetes.io/zh-cn/docs/reference/kubectl/#資源型別
格式化輸出:https://kubernetes.io/zh-cn/docs/reference/kubectl/#格式化輸出
常用操作:https://kubernetes.io/zh-cn/docs/reference/kubectl/#示例-常用操作
命令參考:https://kubernetes.io/docs/reference/generated/kubectl/kubectl-commands
yaml 語法
yml 模版
Deployment服務yaml檔案
部署nginx
命令,檢視幫助
kubectl create deployment nginx --image=nginx:latest --help
生成部署nginx
的yaml
kubectl create deployment nginx --image=nginx:latest --dry-run -o yaml
生成並檢視nginx.yaml
# 進入k8s/
cd k8s/
# 生成nginx.yaml
kubectl create deployment nginx --image=nginx:latest --dry-run -o yaml > nginx.yaml
# 編輯nginx.yaml
vim nginx.yaml
執行nginx.yaml
kubectl apply -f nginx.yaml
kubectl get pods
Service服務yaml檔案
kubectl expose deployment nginx --port=80 --target-port=8080 --type=NodePort --dry-run -o yaml
Pod服務yaml檔案
檢視Pod
服務
kubectl get pods
kubectl get pod nginx-674ff86d-4phzq
kubectl get pod nginx-674ff86d-4phzq -o yaml
執行pod.yaml
# 刪除pods
# kubectl delete pod nginx-new
kubectl get pod nginx-674ff86d-4phzq -o yaml > mypod.yaml
vim mypod.yaml
kubectl apply -f mypod.yaml
kubectl get pods
mypod.yaml
apiVersion: v1
kind: Pod
metadata:
labels:
app: nginx-new
name: nginx-new
namespace: default
spec:
containers:
- image: nginx:latest
imagePullPolicy: IfNotPresent
name: nginx-new
4.3Pod、Service等概念
Pod&Controller
官方文件:https://kubernetes.io/zh-cn/docs/reference/kubectl/#資源型別
Pod 和控制器
控制器可以為您建立和管理多個 Pod,管理副本和上線,並在叢集範圍內提供自修復能力。 例如,如果一個節點失敗,控制器可以在不同的節點上排程一樣的替身來自動替換 Pod。 包含一個或多個 Pod 的控制器一些示例包括:
- Deployment
- StatefulSet
- DaemonSet
控制器通常使用您提供的 Pod 模板來建立它所負責的 Pod
Deployment&Service
Service 的意義
統一應用訪問入口;
Service 管理一組 Pod。 防止 Pod 失聯(服務發現)、定義一組 Pod 的訪問策略。
現在 Service 我們使用 NodePort 的方式暴露,這樣訪問每個節點的埠,都可以訪問到這 個 Pod,如果節點當機,就會出現問題。
labels and selectors
4.4Ingress
使用yaml安裝tomcat和nginx
清除環境
kubectl get all
kubectl delete deployment.apps/nginx
kubectl delete pod/nginx-new
tomcat
事例
kubectl create deployment tomcat --image=tomcat:8 --dry-run=client -o yaml > tomcat-deployment.yaml
kubectl apply -f tomcat-deployment.yaml
kubectl get all
kubectl expose deployment tomcat --port=80 --target-port=8080 --type=NodePort --dry-run=client -o yaml
kubectl get all
kubectl delete deployment.apps/tomcat
kubectl apply -f tomcat-deployment.yaml
tomcat-deployment.yaml
cat <<EOF > tomcat-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: tomcat
name: tomcat
spec:
replicas: 3
selector:
matchLabels:
app: tomcat
template:
metadata:
labels:
app: tomcat
spec:
containers:
- image: tomcat:8
name: tomcat
---
apiVersion: v1
kind: Service
metadata:
labels:
app: tomcat
name: tomcat
spec:
ports:
- port: 80
protocol: TCP
targetPort: 8080
selector:
app: tomcat
type: NodePort
EOF
nginx
事例
kubectl create deployment nginx --image=nginx:latest --dry-run=client -o yaml > nginx-deployment.yaml
kubectl apply -f nginx-deployment.yaml
kubectl get all
kubectl expose deployment nginx --port=80 --target-port=8080 --type=NodePort --dry-run=client -o yaml
kubectl get all
kubectl delete deployment.apps/nginx
kubectl apply -f nginx-deployment.yaml
nginx-deployment.yaml
cat <<EOF > nginx-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app: nginx
name: nginx
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- image: nginx:latest
name: nginx
---
apiVersion: v1
kind: Service
metadata:
labels:
app: nginx
name: nginx
spec:
ports:
- port: 80
protocol: TCP
targetPort: 8080
selector:
app: nginx
type: NodePort
EOF
安裝Ingress
將ingress-controller.yaml
上傳到伺服器,安裝Ingress
kubectl apply -f ingress-controller.yaml
kubectl get pods --all-namespaces
建立 Ingress 規則
kubectl apply -f ingress-demo.yaml
ingress-demo.yaml
cat <<EOF > ingress-demo.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: web
spec:
rules:
- host: tomcat.peng.com
http:
paths:
- backend:
serviceName: tomcat
servicePort: 80
EOF
我安裝的是tomcat8
,發現沒有預設的index.html
# 檢視所有服務
kubectl get all
# 進入容器,給一個容器建立ROOT/index.html
# kubectl exec -it tomcat-6fbdf4497-5vpbz -- /bin/bash
# kubectl exec -it tomcat-6fbdf4497-xbnmd -- /bin/bash
kubectl exec -it tomcat-6fbdf4497-4dn6z -- /bin/bash
cd $CATALINA_HOME/webapps/
mkdir ROOT
cd ROOT
cat <<EOF > index.html
<!DOCTYPE html>
<html>
<head>
<title>Welcome to Tomcat</title>
</head>
<body>
<h1>Tomcat is Running!</h1>
</body>
</html>
EOF
cd $CATALINA_HOME/webapps/ROOT
進入3個容器好,建立預設頁
配置SwitchHosts
192.168.188.182 tomcat.peng.com
訪問http://192.168.188.182:31123
、http://192.168.188.183:31123
、tomcat.peng.com
模擬當機
有2個tomcat
安裝在k8s-03
,關閉k8s-03
kubectl get pods -o wide
依舊可以訪問http://tomcat.peng.com/
打包下載的tomcat
映象
docker save -o tomcat8.tar tomcat:8
docker load -i tomcat8.tar
5.kubesphere-安裝
5.1前置環境
簡介
KubeSphere
是一款面向雲原生設計的開源專案,在目前主流容器排程平臺 Kubernetes
之 上構建的分散式多租戶容器管理平臺,提供簡單易用的操作介面以及嚮導式操作方式,在降 低使用者使用容器排程平臺學習成本的同時,極大降低開發、測試、運維的日常工作的複雜度。
版本文件:https://v3-1.docs.kubesphere.io/zh/docs/installing-on-kubernetes/introduction/prerequisites/
選擇自己k8s
合適的版本,我的k8s版本是v1.18.0
準備工作
k8s
版本問題,我k8s
叢集版本是v1.18.0
,所以我安裝KubeSphere v3.1.1
kubectl version
可用 CPU > 1 核;記憶體 > 2 G
free -g
檢查叢集中是否有預設 StorageClass(準備預設 StorageClass 是安裝 KubeSphere 的前提條件)
對於本地虛擬機器環境,常見的選擇包括:
- HostPath(僅用於測試)
- 用途:本地開發、測試
- 優點:簡單易用,支援本地磁碟儲存
- NFS(適合網路共享)
- 用途:簡單的測試和實驗
- 優點:無需額外安裝,只依賴本地檔案系統
- 缺點:僅適用於單節點或測試環境,資料不會在多個節點間共享
- Local Path(用於本地磁碟)
- 用途:多個節點間共享儲存
- 優點:支援網路共享,適合在多個虛擬機器之間共享資料
- 缺點:需要額外的 NFS 伺服器配置
安裝helm
# 下載 Helm
curl -L https://get.helm.sh/helm-v3.15.4-linux-amd64.tar.gz -o helm-v3.15.4-linux-amd64.tar.gz
# 檢查檔案完整性
file helm-v3.15.4-linux-amd64.tar.gz
# 解壓安裝包
tar -zxvf helm-v3.15.4-linux-amd64.tar.gz
# 進入該資料夾
cd linux-amd64
# 移動 Helm 可執行檔案: 將解壓後的 Helm 可執行檔案移動到系統的全域性路徑
sudo mv helm /usr/local/bin/
# 檢視 Helm 版本
helm version
# 新增 Helm 倉庫
helm repo add stable https://charts.helm.sh/stable
helm repo update
安裝OpenEBS
# 新增 OpenEBS 的 Helm 倉庫
helm repo add openebs https://openebs.github.io/charts/
helm repo update
# 安裝 OpenEBS
helm install openebs --namespace openebs --create-namespace openebs/openebs
建立 LocalPV StorageClass
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: openebs-local
annotations:
storageclass.kubernetes.io/is-default-class: "true"
provisioner: openebs.io/local
reclaimPolicy: Delete
volumeBindingMode: WaitForFirstConsumer
建立 PVC 使用 LocalPV
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: openebs-local-pvc
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 5Gi
storageClassName: openebs-local
執行
vim local-pv-sc.yaml
kubectl apply -f local-pv-sc.yaml
kubectl get sc
vim pvc-local.yaml
kubectl apply -f pvc-local.yaml
部署一個使用 PVC 的 Pod
apiVersion: v1
kind: Pod
metadata:
name: busybox
spec:
containers:
- name: busybox
image: busybox
command:
- sleep
- "3600"
volumeMounts:
- mountPath: "/mnt/disks"
name: openebs-local-vol
volumes:
- name: openebs-local-vol
persistentVolumeClaim:
claimName: openebs-local-pvc
執行
kubectl apply -f busybox-pod.yaml
prometheus-pvc.yaml
apiVersion: v1
kind: PersistentVolume
metadata:
name: prometheus-pv-0
spec:
capacity:
storage: 10Gi
accessModes:
- ReadWriteOnce
hostPath:
path: /mnt/data/prometheus0
storageClassName: openebs-local
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
---
apiVersion: v1
kind: PersistentVolume
metadata:
name: prometheus-pv-1
spec:
capacity:
storage: 10Gi
accessModes:
- ReadWriteOnce
hostPath:
path: /mnt/data/prometheus1
storageClassName: openebs-local
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
執行
# 三臺主機都需要建立/mnt/data/prometheus0
# 三臺主機都需要建立/mnt/data/prometheus1
mkdir -p /mnt/data/prometheus0
mkdir -p /mnt/data/prometheus1
# 三臺主機都需要新增許可權
# 三臺主機都需要新增許可權
chmod 777 /mnt/data/prometheus0
chmod 777 /mnt/data/prometheus1
# k8s-01(master)執行
vim prometheus-pvc.yaml
kubectl apply -f prometheus-pvc.yaml
kubectl get pvc -n kubesphere-monitoring-system
kubectl get pods -n kubesphere-monitoring-system
驗證
kubectl get sc
kubectl get pv -n kubesphere-monitoring-system
kubectl get pvc -n kubesphere-monitoring-system
kubectl get pods -n kubesphere-monitoring-system
重啟kubesphere命令
重啟 KubeSphere 的核心元件
kubectl rollout restart deployment ks-apiserver -n kubesphere-system
kubectl rollout restart deployment ks-controller-manager -n kubesphere-system
kubectl rollout restart deployment ks-console -n kubesphere-system
重啟 KubeSphere 的其他服務
kubectl get deployments -A | grep kubesphere | awk '{print "kubectl rollout restart deployment " $2 " -n " $1}' | sh
檢查服務狀態
kubectl get pods -A | grep kubesphere
如果需要,重啟整個 KubeSphere 名稱空間的 Pod
kubectl delete pod --all -n kubesphere-system
kubectl delete pod --all -n kubesphere-monitoring-system
kubectl delete pod --all -n kubesphere-controls-system
檢查叢集整體狀態
kubectl get pods -A
解除安裝kubesphere命令
刪除namespaces
kubectl get pods --all-namespaces
kubectl delete namespace kubesphere-controls-system --force --grace-period=0
kubectl delete namespace kubesphere-devops-system --force --grace-period=0
kubectl delete namespace kubesphere-monitoring-system --force --grace-period=0
# kubectl delete namespace kubesphere-system --force --grace-period=0
kubectl delete namespace kubesphere-alerting-system --force --grace-period=0
kubectl delete namespace kubesphere-monitoring-system --force --grace-period=0
刪掉finalizers
# 編輯名稱空間 kubesphere-alerting-system
kubectl edit namespace kubesphere-alerting-system
# 編輯名稱空間 kubesphere-controls-system
kubectl edit namespace kubesphere-controls-system
# 編輯名稱空間 kubesphere-devops-system
kubectl edit namespace kubesphere-devops-system
# 編輯名稱空間 kubesphere-monitoring-system
kubectl edit namespace kubesphere-monitoring-system
5.2最小化安裝完成
最小化安裝kubesphere
官方地址:https://v2-1.docs.kubesphere.io/docs/zh-CN/appendix/install-openebs/
地址:https://v3-1.docs.kubesphere.io/zh/docs/quick-start/minimal-kubesphere-on-k8s/
# 安裝命令
# 可以下載到本地安裝 這個過程比較耗時,對網路要求較高
# kubectl apply -f kubesphere-installer.yaml
# kubectl apply -f cluster-configuration.yaml
# 或者遠端地址安裝 這個過程比較耗時,對網路要求較高
kubectl apply -f https://github.com/kubesphere/ks-installer/releases/download/v3.1.1/kubesphere-installer.yaml
kubectl apply -f https://github.com/kubesphere/ks-installer/releases/download/v3.1.1/cluster-configuration.yaml
kubectl logs -n kubesphere-system $(kubectl get pod -n kubesphere-system -l app=ks-install -o jsonpath='{.items[0].metadata.name}') -f
kubectl get svc/ks-console -n kubesphere-system
# *************************************************
# 檢視和刪除命令
kubectl get pods --all-namespaces
kubectl get pods -n kubesphere-monitoring-system
kubectl delete -f kubesphere-installer.yaml
kubectl delete -f cluster-configuration.yaml
kubectl delete pod -n kubesphere-system ks-installer-7bd6b699df-nqxjh
kubectl logs -n kubesphere-system ks-installer-7bd6b699df-nqxjh
BUG:Failed to ansible-playbook result-info.yaml
從你提供的日誌來看,KubeSphere 的核心元件 (ks-apiserver
、ks-console
和 ks-controller-manager
) 無法建立 Pod,因為找不到 kubesphere-system
名稱空間中的 kubesphere
服務賬戶。這是導致 KubeSphere 安裝失敗的主要原因。
kubectl get events -n kubesphere-system
kubesphere-serviceaccount.yaml
apiVersion: v1
kind: ServiceAccount
metadata:
name: kubesphere
namespace: kubesphere-system
kubesphere-rolebinding.yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: kubesphere-rolebinding
namespace: kubesphere-system
subjects:
- kind: ServiceAccount
name: kubesphere
namespace: kubesphere-system
roleRef:
kind: ClusterRole
name: cluster-admin
apiGroup: rbac.authorization.k8s.io
執行
kubectl apply -f kubesphere-serviceaccount.yaml
kubectl apply -f kubesphere-rolebinding.yaml
BUG:重置密碼
安裝成功後,我是用預設的賬號登不上
官方提供重置管理員密碼命令
官方文件:https://v3-1.docs.kubesphere.io/zh/docs/faq/access-control/forgot-password/
kubectl patch users admin -p '{"spec":{"password":"P@88w0rd"}}' --type='merge' && kubectl annotate users admin iam.kubesphere.io/password-encrypted-
安裝完成
總算登入成功,太不容易了
5.3定製化安裝&介面介紹
定製化安裝
官方地址:https://v3-1.docs.kubesphere.io/zh/docs/pluggable-components/
主要需要DevOps 系統、告警系統
KubeSphere 3.1.1 版本沒有整合獨立的 Notification 系統(告警通知系統),該功能是在後續版本中引入的。
修改cluster-configuration.yaml
在執行kubesphere-installer.yaml
和cluster-configuration.yaml
kubectl apply -f https://github.com/kubesphere/ks-installer/releases/download/v3.1.1/kubesphere-installer.yaml
kubectl apply -f cluster-configuration.yaml
介面介紹
我的3.1.1和2版本有很多區別,自己多點點就可以了
6.kubesphere-進階
kubesphere成功安裝記得備份,拍攝快照,我後面因為k8s記憶體溢位需要重新搭建環境,還好我在這備份了
6.1建立多租戶系統
官方文件:https://v3-1.docs.kubesphere.io/zh/docs/quick-start/create-workspace-and-project/
建立賬號
建立user-manager
,所有密碼為Peng123456
登入user-manager
,建立四個賬號
ws-manager workspaces-manager 建立和管理所有企業空間。
ws-admin platform-regular 管理指定企業空間中的所有資源(在此示例中,此帳戶用於邀請新成員加入該企業空間)。
project-admin platform-regular 建立和管理專案以及 DevOps 工程,並邀請新成員加入專案。
project-regular platform-regular project-regular 將由 project-admin 邀請至專案或 DevOps 工程。該帳戶將用於在指定專案中建立工作負載、流水線和其他資源。
建立企業空間
以 ws-manager
身份登入 KubeSphere,它具有管理平臺上所有企業空間的許可權。在企業空間中,可以看到僅列出了一個預設企業空間 system-workspace
,即系統企業空間,其中執行著與系統相關的元件和服務,您無法刪除該企業空間。
點選右側的建立,將新企業空間命名為 peng-mall-workspace
,並將使用者 ws-admin
設定為企業空間管理員。完成後,點選建立。
以 ws-admin
身份重新登入。在企業空間設定中,選擇企業成員,然後點選邀請成員。
邀請 project-admin
和 project-regular
進入企業空間,分別授予 workspace-self-provisioner
和 workspace-viewer
角色,點選確定。
ws-admin workspace-admin 管理指定企業空間中的所有資源(在此示例中,此帳戶用於邀請新成員加入企業空間)。
project-admin workspace-self-provisioner 建立和管理專案以及 DevOps 工程,並邀請新成員加入專案。
project-regular workspace-viewer project-regular 將由 project-admin 邀請至專案或 DevOps 工程。該帳戶將用於在指定專案中建立工作負載、流水線和其他資源。
建立專案
以 project-admin
身份登入 KubeSphere Web 控制檯,在專案管理中,點選建立。
輸入專案名稱(例如 peng-mall
),然後點選確定完成,您還可以為專案新增別名和描述。
邀請 project-regular
至該專案,並授予該使用者 operator
角色。請參考下圖以瞭解具體步驟。
建立peng-mall-devops
建立角色
在賬戶角色右側點選建立,建立peng-hr
用於賬戶的CRUD
編輯許可權
6.2建立WorldPress應用-金鑰
官方文件:https://v3-1.docs.kubesphere.io/zh/docs/quick-start/wordpress-deployment/
建立金鑰
使用 project-regular
帳戶登入 KubeSphere 控制檯。訪問 peng-mall
的詳情頁並導航到配置中心。在金鑰中,點選右側的建立。
輸入基本資訊(例如,將其命名為 mysql-secret
)並點選下一步。在下一頁中,選擇型別為 Opaque(預設),然後點選新增資料來新增鍵值對。輸入如下所示的鍵 (Key) MYSQL_ROOT_PASSWORD
和值 (Value) 123456
,點選右下角 √ 進行確認。完成後,點選建立按鈕以繼續。
按照以上相同的步驟建立一個名為 wordpress-secret
的 WordPress 金鑰,輸入鍵 (Key) WORDPRESS_DB_PASSWORD
和值 (Value) 123456
。建立的金鑰顯示在列表中,如下所示:
建立儲存卷
訪問儲存管理下的儲存卷,點選建立。
輸入卷的基本資訊(例如,將其命名為 wordpress-pvc
),然後點選下一步。
在儲存卷設定中,需要選擇一個可用的儲存型別,並設定訪問模式和儲存卷容量。您可以直接使用如下所示的預設值,點選下一步繼續。
6.3建立WorldPress應用-建立容器
新增 MySQL 後端元件
官方文件:https://v3-1.docs.kubesphere.io/zh/docs/quick-start/wordpress-deployment/#步驟-3建立應用程式
導航到應用負載下的應用,選擇自制應用,再點選構建自制應用。
輸入基本資訊(例如,在應用名稱一欄輸入 wordpress
),然後點選下一步。
在服務元件中,點選新增服務以在應用中設定元件。
設定元件的服務型別為有狀態服務。
輸入有狀態服務的名稱(例如 mysql)並點選下一步。
在容器映象中,點選新增容器映象。
在搜尋框中輸入 mysql:5.6
,按下Enter鍵,然後點選使用預設埠。由於配置還未設定完成,請不要點選右下角的 √ 按鈕。
在高階設定中,請確保記憶體限制不小於 1000 Mi,否則 MySQL 可能因記憶體不足而無法啟動。
設定mysql
的CPU
和記憶體
配置環境變數
https://hub.docker.com/_/mysql
向下滾動到環境變數,點選引用配置檔案或金鑰。輸入名稱 MYSQL_ROOT_PASSWORD
,然後選擇資源 mysql-secret
和前面步驟中建立的金鑰 MYSQL_ROOT_PASSWORD
,完成後點選 √ 儲存配置,最後點選下一步繼續。
新增儲存卷模板
https://hub.docker.com/_/mysql
選擇掛載儲存中的新增儲存卷模板,輸入儲存卷名稱 (mysql
) 和掛載路徑(模式:讀寫
,路徑:/var/lib/mysql
)的值,如下所示:
新增WordPress前端元件
官方地址:https://v3-1.docs.kubesphere.io/zh/docs/quick-start/wordpress-deployment/#步驟-3建立應用程式
再次點選新增服務,這一次選擇無狀態服務。
輸入名稱 wordpress
並點選下一步。
與上述步驟類似,點選新增容器映象,在搜尋欄中輸入 wordpress:4.8-apache
並按下Enter鍵,然後點選使用預設埠。
配置WordPress
環境變數
官方地址:https://hub.docker.com/_/wordpress
對於此處新增的第二個環境變數,該值必須與建立 MySQL 有狀態服務設定的名稱完全相同。否則,WordPress 將無法連線到 MySQL 對應的資料庫。
向下滾動到環境變數,點選引用配置檔案或金鑰。這裡需要新增兩個環境變數,請根據以下截圖輸入值:
- 對於
WORDPRESS_DB_PASSWORD
,請選擇在步驟 1 中建立的wordpress-secret
和WORDPRESS_DB_PASSWORD
。 - 點選新增環境變數,分別輸入
WORDPRESS_DB_HOST
和mysql
作為鍵 (Key) 和值 (Value)。
在掛載儲存中,點選新增儲存卷,並選擇已有儲存卷。
檢視wordpress
容器配置的資料卷在/var/www/html
選擇上一步建立的 wordpress-pvc
,將模式設定為讀寫
,並輸入掛載路徑 /var/www/html
。點選 √ 儲存,再點選下一步繼續。
現在,前端元件也已設定完成。點選下一步繼續。
您可以在這裡設定路由規則(應用路由 Ingress),也可以直接點選建立。
建立後,應用將顯示在下面的列表中。
6.4建立WorldPress應用-外網訪問
驗證資源
在工作負載中,分別檢查部署和有狀態副本集中 wordpress-v1
和 mysql-v1
的狀態。如果它們的執行狀態如下圖所示,就意味著 WordPress 已經成功建立。
透過 NodePort 訪問 WordPress
若要在叢集外訪問服務,請首先導航到服務。點選 wordpress
右側的三個點後,選擇編輯外網訪問
在訪問方式中選擇 NodePort
,然後點選確定。
點選服務進入詳情頁,可以看到暴露的埠。
透過 {Node IP}:{NodePort}
訪問此應用程式(三臺機器的任意IP都可以),可以看到下圖:
6.5DevOps
專案開發需要考慮的維度
Dev:怎麼開發?
Ops:怎麼運維?
高併發:怎麼承擔高併發
高可用:怎麼做到高可用
DevOps
微服務,服務自治。
DevOps: Development 和 Operations 的組合
- DevOps 看作開發(軟體工程)、技術運營和質量保障(QA)三者的交集。
- 突出重視軟體開發人員和運維人員的溝通合作,透過自動化流程來使得軟體構建、測試、 釋出更加快捷、頻繁和可靠。
- DevOps 希望做到的是軟體產品交付過程中 IT 工具鏈的打通,使得各個團隊減少時間損 耗,更加高效地協同工作。專家們總結出了下面這個 DevOps 能力圖,良好的閉環可以大大 增加整體的產出。
CI&CD
持續整合(Continuous Integration)
- 持續整合是指軟體個人研發的部分向軟體整體部分交付,頻繁進行整合以便更快地發現 其中的錯誤。“持續整合”源自於極限程式設計(XP),是 XP 最初的 12 種實踐之一。
- CI 需要具備這些:
- 全面的自動化測試。這是實踐持續整合&持續部署的基礎,同時,選擇合適的 自動化測試工具也極其重要;
- 靈活的基礎設施。容器,虛擬機器的存在讓開發人員和 QA 人員不必再大費周 折;
- 版本控制工具。如 Git,CVS,SVN 等;
- 自動化的構建和軟體釋出流程的工具,如 Jenkins,flow.ci;
- 反饋機制。如構建/測試的失敗,可以快速地反饋到相關負責人,以儘快解決 達到一個更穩定的版本。
持續交付(Continuous Delivery)
持續交付在持續整合的基礎上,將整合後的程式碼部署到更貼近真實執行環境的「類生產環境」 (production-like environments)中。持續交付優先於整個產品生命週期的軟體部署,建立 在高水平自動化持續整合之上。
灰度釋出。
持續交付和持續整合的優點非常相似:
- 快速釋出。能夠應對業務需求,並更快地實現軟體價值。
- 編碼->測試->上線->交付的頻繁迭代週期縮短,同時獲得迅速反饋;
- 高質量的軟體釋出標準。整個交付過程標準化、可重複、可靠;
- 整個交付過程進度視覺化,方便團隊人員瞭解專案成熟度;
- 更先進的團隊協作方式。從需求分析、產品的使用者體驗到互動 設計、開發、測試、運 維等角色密切協作,相比於傳統的瀑布式軟體團隊,更少浪費。
持續部署(Continuous Deployment)
持續部署是指當交付的程式碼透過評審之後,自動部署到生產環境中。持續部署是持續交付的 最高階段。這意味著,所有透過了一系列的自動化測試的改動都將自動部署到生產環境。它 也可以被稱為“Continuous Release”。
“開發人員提交程式碼,持續整合伺服器獲取程式碼,執行單元測試,根據測 試結果決定是否部署到預演環境,如果成功部署到預演環境,進行整體 驗收測試,如果測試透過,自動部署到產品環境,全程自動化高效運轉。”
持續部署主要好處是,可以相對獨立地部署新的功能,並能快速地收集真實使用者的反饋。
“You build it, you run it”,這是 Amazon 一年可以完成 5000 萬次部署, 平均每個工程師每天部署超過 50 次的核心秘籍。
下圖是由 Jams Bowman 繪製的持續交付工具鏈圖
落地方案
Maven+Github+Jenkins(Hudson[現由甲骨文維護])+Docker
將 SonarQube 整合到流水線
安裝 SonarQube 伺服器
官方地址:https://v3-1.docs.kubesphere.io/zh/docs/devops-user-guide/how-to-integrate/sonarqube/#為新工程建立-sonarqube-token
安裝Helm
curl https://raw.githubusercontent.com/helm/helm/master/scripts/get-helm-3 | bash
檢視 Helm 版本,我這裡之前已經安裝了
helm version
安裝 SonarQube
伺服器
helm upgrade --install sonarqube sonarqube --repo https://charts.kubesphere.io/main -n kubesphere-devops-system --create-namespace --set service.type=NodePort
獲取 SonarQube 控制檯地址
執行以下命令獲取 NodePort 和節點的 IP 地址
export NODE_PORT=$(kubectl get --namespace kubesphere-devops-system -o jsonpath="{.spec.ports[0].nodePort}" services sonarqube-sonarqube)
export NODE_IP=$(kubectl get nodes --namespace kubesphere-devops-system -o jsonpath="{.items[0].status.addresses[0].address}")
echo http://$NODE_IP:$NODE_PORT
配置 SonarQube 伺服器
步驟 1:訪問 SonarQube 控制檯
訪問 SonarQube 控制檯,檢視sonarqube-sonarqube-5487d49d79-wvpv8
狀態Running
才能訪問控制檯
kubectl get pod -n kubesphere-devops-system
在瀏覽器中訪問 SonarQube 控制檯 http://{$Node IP}:{$NodePort}
然後使用預設帳戶 admin/admin
登入
步驟 2:建立 SonarQube 管理員令牌 (Token)
點選右上角字母 A,然後從選單中選擇 My Account 以轉到 Profile 頁面。
點選 Security 並輸入令牌名稱,例如 peng-mall-analyze
。
點選 Generate 並複製此令牌。
如提示所示,您無法再次檢視此令牌,因此請確保複製成功。
# kubesphere
b36a45e8c313beb1c99b9924082deed039bf1861
步驟 3:建立 Webhook 伺服器
執行以下命令獲取 SonarQube Webhook 的地址。
export NODE_PORT=$(kubectl get --namespace kubesphere-devops-system -o jsonpath="{.spec.ports[0].nodePort}" services ks-jenkins)
export NODE_IP=$(kubectl get nodes --namespace kubesphere-devops-system -o jsonpath="{.items[0].status.addresses[0].address}")
echo http://$NODE_IP:$NODE_PORT/sonarqube-webhook/
依次點選 Administration、Configuration 和 Webhooks 建立一個 Webhook。
點選 Create。
在彈出對話方塊中輸入 Name 和 Jenkins Console URL(即 SonarQube Webhook 地址)。點選 Create 完成操作。
ks-jenkins
http://192.168.188.181:30180/sonarqube-webhook/
步驟 4:將 SonarQube 配置新增到 ks-installer
執行以下命令編輯 ks-installer
。
kubectl edit cc -n kubesphere-system ks-installer
搜尋至 devops
。新增欄位 sonarqube
並在其下方指定 externalSonarUrl
和 externalSonarToken
。
devops:
enabled: true
jenkinsJavaOpts_MaxRAM: 2g
jenkinsJavaOpts_Xms: 512m
jenkinsJavaOpts_Xmx: 512m
jenkinsMemoryLim: 2Gi
jenkinsMemoryReq: 1500Mi
jenkinsVolumeSize: 8Gi
sonarqube: # Add this field manually.
externalSonarUrl: http://192.168.188.181:32467 # The SonarQube IP address.
externalSonarToken: b36a45e8c313beb1c99b9924082deed039bf1861 # The SonarQube admin token created above.
步驟 5:將 SonarQube 伺服器新增至 Jenkins
執行以下命令獲取 Jenkins 的地址
export NODE_PORT=$(kubectl get --namespace kubesphere-devops-system -o jsonpath="{.spec.ports[0].nodePort}" services ks-jenkins)
export NODE_IP=$(kubectl get nodes --namespace kubesphere-devops-system -o jsonpath="{.items[0].status.addresses[0].address}")
echo http://$NODE_IP:$NODE_PORT
請使用地址 http://{$Public IP}:30180
訪問 Jenkins。安裝 KubeSphere 時,預設情況下也會安裝 Jenkins 儀表板。此外,Jenkins 還配置有 KubeSphere LDAP,這意味著您可以直接使用 KubeSphere 帳戶(例如 admin/P@88w0rd
)登入 Jenkins。
點選左側的系統管理。
點選系統配置
搜尋到 SonarQube servers,然後點選 Add SonarQube。
輸入 Name 和 Server URL (http://{$Node IP}:{$NodePort}
)。點選新增,選擇 Jenkins,然後在彈出對話方塊中用 SonarQube 管理員令牌建立憑證(如下方第二張截圖所示)。建立憑證後,從 Server authentication token 旁邊的下拉選單中選擇該憑證。點選應用完成操作。
我這裡新增按鈕無效,可以使用下面方法新增憑據
如果點選新增按鈕無效(Jenkins 已知問題),您可以前往系統管理下的 Manage Credentials 並點選 Stores scoped to Jenkins 下的 Jenkins,再點選全域性憑據 (unrestricted),然後點選左側導航欄的新增憑據,參考上方第二張截圖用 SonarQube 管理員令牌新增憑證。新增憑證後,從 Server authentication token 旁邊的下拉選單中選擇該憑證。
前往系統管理下的 Manage Credentials
點選 Stores scoped to Jenkins 下的 Jenkins
再點選全域性憑據 (unrestricted)
然後點選左側導航欄的新增憑據
新增憑證
sonarqube
新增憑證後,從 Server authentication token 旁邊的下拉選單中選擇該憑證。
步驟 6:將 sonarqubeURL 新增到 KubeSphere 控制檯
執行以下命令
kubectl edit cm -n kubesphere-system ks-console-config
搜尋到 client
,新增 devops
欄位並指定 sonarqubeURL
client:
version:
kubesphere: v3.1.1
kubernetes: v1.18.0
openpitrix: v0.3.5
enableKubeConfig: true
devops: # Add this field manually.
sonarqubeURL: http://192.168.188.181:32467/ # The SonarQube IP address.
步驟 7:重啟服務
kubectl -n kubesphere-system rollout restart deploy ks-apiserver
kubectl -n kubesphere-system rollout restart deploy ks-console
6.6流水線-建立憑證
官方文件:https://v3-1.docs.kubesphere.io/zh/docs/devops-user-guide/how-to-use/create-a-pipeline-using-jenkinsfile/
步驟 1:建立憑證
使用project-admin
登入,建立憑證
憑證 ID 型別 用途
dockerhub-id 帳戶憑證 Docker Hub
github-id 帳戶憑證 GitHub
demo-kubeconfig kubeconfig Kubernetes
為 SonarQube 建立一個憑證 ID (sonar-token
),用於上述的階段 3(SonarQube 分析)。
sonar-token
b36a45e8c313beb1c99b9924082deed039bf1861
SonarQube
您還需要建立具有如下圖所示許可權的 GitHub 個人訪問令牌 (PAT),然後在 DevOps 專案中,使用生成的令牌建立用於 GitHub 認證的帳戶憑證(例如,github-token
)。
如需建立 GitHub 個人訪問令牌,請轉到您 GitHub 帳戶的 Settings,點選 Developer settings,選擇 Personal access tokens,然後點選 Generate new token。
建立具有如下圖所示許可權的 GitHub 個人訪問令牌 (PAT),然後在 DevOps 專案中,使用生成的令牌建立用於 GitHub 認證的帳戶憑證(例如,github-token
)。
在列表中看到已建立的五個憑證。
步驟 2:在 GitHub 倉庫中修改 Jenkinsfile
登入 GitHub 並 Fork GitHub 倉庫 devops-java-sample 至您的 GitHub 個人帳戶
點選Create fork
,取消Copy the master branch only
,複製所有分支
在您自己的 GitHub 倉庫 devops-java-sample 中,選擇sonarqube
分支,點選根目錄中的檔案 Jenkinsfile-online
。
點選右側的編輯圖示,編輯環境變數。
environment {
DOCKER_CREDENTIAL_ID = 'dockerhub-id'
GITHUB_CREDENTIAL_ID = 'github-id'
KUBECONFIG_CREDENTIAL_ID = 'peng-mall-kubeconfig'
REGISTRY = 'docker.io'
DOCKERHUB_NAMESPACE = 'pengeng'
GITHUB_ACCOUNT = 'pengpeng-github'
APP_NAME = 'devops-java-sample'
SONAR_CREDENTIAL_ID = 'sonar-token'
}
新增以下憑證
條目 值 描述資訊
DOCKER_CREDENTIAL_ID dockerhub-id 您在 KubeSphere 中為 Docker Hub 帳戶設定的憑證 ID。
GITHUB_CREDENTIAL_ID github-id 您在 KubeSphere 中為 GitHub 帳戶設定的憑證 ID,用於將標籤推送至您的 GitHub 倉庫。
KUBECONFIG_CREDENTIAL_ID demo-kubeconfig 您在 KubeSphere 中為 kubeconfig 設定的憑證 ID,用於訪問執行中的 Kubernetes 叢集。
REGISTRY docker.io 預設為 docker.io,用作推送映象的地址。
DOCKERHUB_NAMESPACE your-dockerhub-account 請替換為您的 Docker Hub 帳戶名,也可以替換為該帳戶下的 Organization 名稱。
GITHUB_ACCOUNT your-github-account 請替換為您的 GitHub 帳戶名。例如,如果您的 GitHub 地址是 https://github.com/kubesphere/,則您的 GitHub 帳戶名為 kubesphere,也可以替換為該帳戶下的 Organization 名稱。
APP_NAME devops-java-sample 應用名稱。
SONAR_CREDENTIAL_ID sonar-token 您在 KubeSphere 中為 SonarQube 令牌設定的憑證 ID,用於程式碼質量檢測。
Jenkinsfile 中
mvn
命令的引數-o
表示開啟離線模式。本教程中已下載相關依賴項,以節省時間並適應某些環境中的網路干擾。離線模式預設開啟。
步驟 3:建立專案
以 project-admin
身份登入 KubeSphere。在您建立 DevOps 工程的企業空間中建立以下兩個專案。
專案名稱 別名
kubesphere-sample-dev development environment
kubesphere-sample-prod production environment
請確保邀請 project-regular
帳戶至這兩個專案中並賦予 operator
角色。
kubesphere-sample-prod
kubesphere-sample-dev
6.7流水線-CICD完整體驗
KubeSphere服務建立內網穿透
配置KubeSphere服務內網穿透的ip和埠
使用內網穿透地址訪問KubeSphere
服務,這樣webhook的訊息可以正常推送了
步驟 4:建立流水線
建立構建新流水線
配置流水線名稱和選擇一個程式碼倉庫。
在 GitHub 選項卡,從下拉選單中選擇 github-token,然後點選確認來選擇您的倉庫
選擇您的 GitHub 帳戶,與該令牌相關的所有倉庫將在右側列出。選擇 devops-java-sample 並點選選擇此倉庫,點選下一步繼續。
在高階設定中,選中丟棄舊的分支旁邊的方框。本教程中,您可以為保留分支的天數和保留分支的最大個數使用預設值。
KubeSphere 預設用 -1 預填充這兩個欄位,表示已刪除的分支將被丟棄。
在行為策略中,KubeSphere 預設提供四種策略。本示例中不會使用從 Fork 倉庫中發現 PR 這條策略,因此您可以刪除該策略。您無需修改設定,可以直接使用預設值。
向下滾動到指令碼路徑。該欄位指定程式碼倉庫中的 Jenkinsfile 路徑。它表示倉庫的根目錄。如果檔案位置變更,則指令碼路徑也需要更改。請將其更改為 Jenkinsfile-online
,這是示例倉庫中位於根目錄下的 Jenkinsfile 的檔名。
配置webhock
步驟 5:執行流水線
流水線建立後,將顯示在下圖所示的列表中。點選該流水線進入其詳情頁面。
devops-java-sample
有幾個分支這裡就有幾個
在活動選項卡下,正在掃描三個分支。點選右側的執行,流水線將根據您設定的行為策略來執行。從下拉選單中選擇 sonarqube,然後新增標籤號,例如 v0.0.2
。點選確定觸發新活動。
創作不易,感謝支援。