版本:
K8S:v1.16.9
metrics-server:v0.3.7
源碼地址:https://github.com/kubernetes-sigs/metrics-server/
mkdir /data/metrics-server && cd /data/metrics-server
wget https://github.com/kubernetes-sigs/metrics-server/releases/download/v0.3.7/components.yaml
cp components.yaml components.yaml.ori
vi components.yaml
# 修改3個地方:
image: juestnow/metrics-server:v0.3.7 # 改成國內源
args:
- --kubelet-preferred-address-types=InternalIP,Hostname,InternalDNS,ExternalDNS,ExternalIP # 默認使用node的主機名,但是coredns里面沒有物理機主機名的解析,部署的時候添加一個參數
- --cert-dir=/tmp
- --secure-port=4443
- --kubelet-insecure-tls # 直接通過InternalIP進行訪問,忽略客戶端證書。
docker pull juestnow/metrics-server:v0.3.7
kubectl apply -f components.yaml
kubectl get pods -n kube-system
# 檢查是否正常啟動
metrics-server-7d65b797b7-w8d5g 1/1 Running 0 36m
# metrics-server 需要一段時間才會收集數據。使用命令
kubectl -n kube-system top pod metrics-server-7d65b797b7-w8d5g
NAME CPU(cores) MEMORY(bytes)
metrics-server-7d65b797b7-w8d5g 1m 13Mi
獲取 K8S pod 中的CPU,內存限制和實時資源使用率
vi k8s_pod_resource.sh
#!/bin/bash
PODFILE="/tmp/k8s-pod-tmp.txt"
LIMITSFILE="/tmp/k8s-pod-limits-tmp.txt"
NAMESPACE=$1
# 判斷輸入的 namespace 是否符正確
if [[ -z ${NAMESPACE} ]];then
echo "請輸入一個 K8S namespace; 可參考命令 kubectl get ns"
exit 1
fi
K8SNS=$(kubectl get ns|awk 'NR> 1{print $1}')
result=$(echo ${K8SNS}|grep -w ${NAMESPACE})
if [[ $result = "" ]];then
echo "你輸入的 namespace 不存在; 可參考命令 kubectl get ns"
exit 1
fi
# 獲取指定 namespace 下所有的 pod 實時的指標
kubectl -n ${NAMESPACE} top pod > ${PODFILE}
get_limits()
{
# 獲取CPU限制
CPU=$(kubectl -n ${NAMESPACE} describe pod $1 |grep -A 2 Limits|grep cpu |awk '{print $2}')
if [[ -z ${CPU} ]];then
CPU=0
fi
# 獲取內存限制
MEM=$(kubectl -n ${NAMESPACE} describe pod $1 |grep -A 2 Limits|grep memory |awk '{print $2}')
if [[ -z ${MEM} ]];then
MEM=0
fi
printf "%7s %10s\n" ${CPU} ${MEM}
}
podlist=$(cat ${PODFILE}|awk 'NR>1 {print $1}')
# 結果輸出到 ${LIMITSFILE}
printf "%s %s\n" CPU\(limits\) MEMORY\(limits\) > ${LIMITSFILE}
for l in ${podlist}
do
#kubectl -n ${NAMESPACE} describe pod ${l}
get_limits ${l} >> ${LIMITSFILE}
done
# 合並展示結果
paste ${PODFILE} ${LIMITSFILE}
# 測試
bash k8s_pod_resource.sh kube-system
NAME CPU(cores) MEMORY(bytes) CPU(limits) MEMORY(limits)
coredns-58cc8c89f4-5hvxg 4m 11Mi 0 170Mi
coredns-58cc8c89f4-frnpq 5m 10Mi 0 170Mi
etcd-k8s-master01 23m 54Mi 0 0
kube-apiserver-k8s-master01 57m 316Mi 0 0
kube-controller-manager-k8s-master01 29m 39Mi 0 0
kube-flannel-ds-amd64-z7ndv 2m 11Mi 100m 50Mi
kube-proxy-nnb4v 4m 15Mi 0 0
kube-scheduler-k8s-master01 2m 17Mi 0 0
metrics-server-7d65b797b7-5b82l 1m 15Mi 0 0
若你的 K8S 集群有容器注入了 istio 之類的,一個 pod 中有幾個 container 則需要使用下面的腳本
cat k8s_pod_resource.sh
#!/bin/bash
PODFILE="/tmp/k8s-pod-tmp.txt"
LIMITSFILE="/tmp/k8s-pod-limits-tmp.txt"
NAMESPACE=$1
# 判斷輸入的 namespace 是否符正確
if [[ -z ${NAMESPACE} ]];then
echo "請輸入一個 K8S namespace; 可參考命令 kubectl get ns"
exit 1
fi
K8SNS=$(kubectl get ns|awk 'NR> 1{print $1}')
result=$(echo ${K8SNS}|grep -w ${NAMESPACE})
if [[ $result = "" ]];then
echo "你輸入的 namespace 不存在; 可參考命令 kubectl get ns"
exit 1
fi
# 獲取指定 namespace 下所有的 pod 實時的指標
kubectl -n ${NAMESPACE} top pod > ${PODFILE}
get_limits()
{
# 獲取CPU限制
CPU=$(kubectl -n ${NAMESPACE} describe pod $1 |awk '/^Containers/,/Conditions/{if(i>1)print x;x=$0;i++}'|grep -A 2 Limits|grep cpu |awk '{print $2}')
if [[ -z ${CPU} ]];then
CPU=0
elif [[ $(echo ${CPU}|wc -w) != 1 ]];then
CPU=$(echo ${CPU}|awk '{print $1}')
fi
# 獲取內存限制
MEM=$(kubectl -n ${NAMESPACE} describe pod $1 |awk '/^Containers/,/Conditions/{if(i>1)print x;x=$0;i++}'|grep -A 2 Limits|grep memory |awk '{print $2}')
if [[ -z ${MEM} ]];then
MEM=0
elif [[ $(echo ${MEM}|wc -w) != 1 ]];then
MEM=$(echo ${MEM}|awk '{print $1}')
fi
printf "%7s %10s\n" ${CPU} ${MEM}
}
podlist=$(cat ${PODFILE}|awk 'NR>1 {print $1}')
# 結果輸出到 ${LIMITSFILE}
printf "%s %s\n" CPU\(limits\) MEMORY\(limits\) > ${LIMITSFILE}
for l in ${podlist}
do
#kubectl -n ${NAMESPACE} describe pod ${l}
get_limits ${l} >> ${LIMITSFILE}
done
# 合並展示結果
paste ${PODFILE} ${LIMITSFILE}