Pod K8s API权限检查脚本
https://www.cnblogs.com/iAmSoScArEd/p/19487570
#!/bin/bash
# Kubernetes API 权限检测脚本
# 颜色定义
GREEN='\033[0;32m'
BLUE='\033[0;34m'
YELLOW='\033[1;33m'
RED='\033[0;31m'
NC='\033[0m'
# 获取 ServiceAccount Token 和 API Server 地址
KUBE_TOKEN=$(cat /var/run/secrets/kubernetes.io/serviceaccount/token)
KUBE_CA=/var/run/secrets/kubernetes.io/serviceaccount/ca.crt
API_SERVER=https://kubernetes.default.svc
NAMESPACE=$(cat /var/run/secrets/kubernetes.io/serviceaccount/namespace)
echo -e "${BLUE}╔════════════════════════════════════════════════════════════════╗${NC}"
echo -e "${BLUE}║ Kubernetes API 权限检测脚本 ║${NC}"
echo -e "${BLUE}╚════════════════════════════════════════════════════════════════╝${NC}"
echo -e "当前命名空间: ${YELLOW}$NAMESPACE${NC}\n"
# 定义只读 API 端点
READONLY_APIS=(
# Core API v1
"api/v1/namespaces|list,get|命名空间列表/详情|管理多租户隔离"
"api/v1/pods|list,get|Pod列表/详情|查看容器运行状态"
"api/v1/services|list,get|Service列表/详情|查看服务暴露配置"
"api/v1/configmaps|list,get|ConfigMap列表/详情|查看配置数据"
"api/v1/secrets|list,get|Secret列表/详情|查看敏感数据(密码/证书)"
"api/v1/serviceaccounts|list,get|ServiceAccount列表/详情|查看服务账号配置"
"api/v1/persistentvolumeclaims|list,get|PVC列表/详情|查看存储声明"
"api/v1/persistentvolumes|list,get|PV列表/详情|查看持久化存储"
"api/v1/nodes|list,get|Node列表/详情|查看集群节点信息"
"api/v1/endpoints|list,get|Endpoints列表/详情|查看服务端点"
"api/v1/events|list,get|Event列表/详情|查看集群事件日志"
"api/v1/limitranges|list,get|LimitRange列表/详情|查看资源限制配置"
"api/v1/resourcequotas|list,get|ResourceQuota列表/详情|查看资源配额"
"api/v1/componentstatuses|list,get|组件状态|查看控制平面组件健康状态"
"api/v1/replicationcontrollers|list,get|RC列表/详情|查看副本控制器"
# Apps API
"apis/apps/v1/deployments|list,get|Deployment列表/详情|查看无状态应用部署"
"apis/apps/v1/daemonsets|list,get|DaemonSet列表/详情|查看守护进程集"
"apis/apps/v1/statefulsets|list,get|StatefulSet列表/详情|查看有状态应用"
"apis/apps/v1/replicasets|list,get|ReplicaSet列表/详情|查看副本集"
"apis/apps/v1/controllerrevisions|list,get|ControllerRevision列表|查看控制器版本历史"
# Batch API
"apis/batch/v1/jobs|list,get|Job列表/详情|查看批处理任务"
"apis/batch/v1/cronjobs|list,get|CronJob列表/详情|查看定时任务"
# RBAC API
"apis/rbac.authorization.k8s.io/v1/roles|list,get|Role列表/详情|查看命名空间角色权限"
"apis/rbac.authorization.k8s.io/v1/rolebindings|list,get|RoleBinding列表/详情|查看角色绑定关系"
"apis/rbac.authorization.k8s.io/v1/clusterroles|list,get|ClusterRole列表/详情|查看集群角色权限"
"apis/rbac.authorization.k8s.io/v1/clusterrolebindings|list,get|ClusterRoleBinding列表/详情|查看集群角色绑定"
# Networking API
"apis/networking.k8s.io/v1/networkpolicies|list,get|NetworkPolicy列表/详情|查看网络策略规则"
"apis/networking.k8s.io/v1/ingresses|list,get|Ingress列表/详情|查看入口流量规则"
"apis/networking.k8s.io/v1/ingressclasses|list,get|IngressClass列表/详情|查看Ingress控制器类型"
# Storage API
"apis/storage.k8s.io/v1/storageclasses|list,get|StorageClass列表/详情|查看存储类配置"
"apis/storage.k8s.io/v1/volumeattachments|list,get|VolumeAttachment列表|查看卷挂载状态"
"apis/storage.k8s.io/v1/csidrivers|list,get|CSIDriver列表|查看CSI驱动"
"apis/storage.k8s.io/v1/csinodes|list,get|CSINode列表|查看CSI节点信息"
"apis/storage.k8s.io/v1/csistoragecapacities|list,get|CSI存储容量|查看存储容量信息"
# Autoscaling API
"apis/autoscaling/v1/horizontalpodautoscalers|list,get|HPA列表/详情(v1)|查看Pod水平自动伸缩"
"apis/autoscaling/v2/horizontalpodautoscalers|list,get|HPA列表/详情(v2)|查看高级自动伸缩配置"
# Policy API
"apis/policy/v1/poddisruptionbudgets|list,get|PDB列表/详情|查看Pod中断预算"
# Certificates API
"apis/certificates.k8s.io/v1/certificatesigningrequests|list,get|CSR列表/详情|查看证书签名请求"
# Coordination API
"apis/coordination.k8s.io/v1/leases|list,get|Lease列表/详情|查看领导者选举租约"
# Discovery API
"apis/discovery.k8s.io/v1/endpointslices|list,get|EndpointSlice列表/详情|查看端点切片(新版)"
# Node API
"apis/node.k8s.io/v1/runtimeclasses|list,get|RuntimeClass列表/详情|查看容器运行时类型"
# Scheduling API
"apis/scheduling.k8s.io/v1/priorityclasses|list,get|PriorityClass列表/详情|查看Pod优先级配置"
# Admissionregistration API
"apis/admissionregistration.k8s.io/v1/mutatingwebhookconfigurations|list,get|MutatingWebhook配置|查看变更准入控制器"
"apis/admissionregistration.k8s.io/v1/validatingwebhookconfigurations|list,get|ValidatingWebhook配置|查看验证准入控制器"
# Apiextensions API
"apis/apiextensions.k8s.io/v1/customresourcedefinitions|list,get|CRD列表/详情|查看自定义资源定义"
# Flowcontrol API
"apis/flowcontrol.apiserver.k8s.io/v1beta2/flowschemas|list,get|FlowSchema列表|查看API流量控制规则"
"apis/flowcontrol.apiserver.k8s.io/v1beta2/prioritylevelconfigurations|list,get|优先级配置|查看API请求优先级"
# Metrics API
"apis/metrics.k8s.io/v1beta1/nodes|list,get|Node指标|查看节点CPU/内存使用率"
"apis/metrics.k8s.io/v1beta1/pods|list,get|Pod指标|查看Pod资源使用率"
)
check_api_access() {
local endpoint=$1
local verb=$2
local description=$3
local capability=$4
local url="${API_SERVER}/${endpoint}"
# 检查集群级别
response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"$url" 2>/dev/null)
if [ "$response" = "200" ]; then
echo -e "${GREEN}[✓] ${verb} ${description}${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别 (cluster-wide)"
echo -e " ${YELLOW}可执行操作:${NC} ${capability}"
echo ""
return 0
fi
# 检查命名空间级别
if [[ "$endpoint" == api/v1/* ]]; then
resource=$(echo $endpoint | sed 's|api/v1/||')
ns_url="${API_SERVER}/api/v1/namespaces/${NAMESPACE}/${resource}"
elif [[ "$endpoint" == apis/* ]]; then
api_group=$(echo $endpoint | cut -d'/' -f1-3)
resource=$(echo $endpoint | cut -d'/' -f4)
ns_url="${API_SERVER}/${api_group}/namespaces/${NAMESPACE}/${resource}"
fi
if [ ! -z "$ns_url" ]; then
ns_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"$ns_url" 2>/dev/null)
if [ "$ns_response" = "200" ]; then
echo -e "${GREEN}[✓] ${verb} ${description}${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别 (namespace: $NAMESPACE)"
echo -e " ${YELLOW}可执行操作:${NC} ${capability}"
echo ""
return 0
fi
fi
return 1
}
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}"
echo -e "${BLUE} 资源读取权限检测 (GET/LIST)${NC}"
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}\n"
for api_entry in "${READONLY_APIS[@]}"; do
IFS='|' read -r endpoint verb description capability <<< "$api_entry"
check_api_access "$endpoint" "$verb" "$description" "$capability"
done
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}"
echo -e "${BLUE} 权限审查能力检测${NC}"
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}\n"
# SelfSubjectAccessReview
sar_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
-H "Content-Type: application/json" \
-X POST \
-d '{"kind":"SelfSubjectAccessReview","apiVersion":"authorization.k8s.io/v1","spec":{"resourceAttributes":{"namespace":"default","verb":"get","resource":"pods"}}}' \
"${API_SERVER}/apis/authorization.k8s.io/v1/selfsubjectaccessreviews" 2>/dev/null)
if [ "$sar_response" = "201" ]; then
echo -e "${GREEN}[✓] create SelfSubjectAccessReview${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 检查自身是否有特定资源的特定操作权限"
echo -e " ${YELLOW}安全影响:${NC} 可枚举自身所有权限,辅助权限提升攻击\n"
fi
# SelfSubjectRulesReview
srr_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
-H "Content-Type: application/json" \
-X POST \
-d "{\"kind\":\"SelfSubjectRulesReview\",\"apiVersion\":\"authorization.k8s.io/v1\",\"spec\":{\"namespace\":\"$NAMESPACE\"}}" \
"${API_SERVER}/apis/authorization.k8s.io/v1/selfsubjectrulesreviews" 2>/dev/null)
if [ "$srr_response" = "201" ]; then
echo -e "${GREEN}[✓] create SelfSubjectRulesReview${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别"
echo -e " ${YELLOW}可执行操作:${NC} 列出自身在指定命名空间的所有权限规则"
echo -e " ${YELLOW}安全影响:${NC} 完整枚举权限列表,快速发现可利用的高危权限\n"
fi
# TokenReview
tr_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
-H "Content-Type: application/json" \
-X POST \
-d "{\"kind\":\"TokenReview\",\"apiVersion\":\"authentication.k8s.io/v1\",\"spec\":{\"token\":\"$KUBE_TOKEN\"}}" \
"${API_SERVER}/apis/authentication.k8s.io/v1/tokenreviews" 2>/dev/null)
if [ "$tr_response" = "201" ]; then
echo -e "${GREEN}[✓] create TokenReview${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 验证任意ServiceAccount Token的有效性和身份信息"
echo -e " ${YELLOW}安全影响:${NC} 可验证窃取的Token是否有效\n"
fi
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}"
echo -e "${BLUE} Pod 特殊操作权限检测${NC}"
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}\n"
# 获取第一个 Pod 用于测试
pods_response=$(curl -s --cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api/v1/namespaces/${NAMESPACE}/pods" 2>/dev/null)
if echo "$pods_response" | grep -q "\"kind\":\"PodList\""; then
pod_name=$(echo "$pods_response" | grep -o '"name":"[^"]*"' | head -1 | cut -d'"' -f4)
if [ ! -z "$pod_name" ]; then
# 检查 logs
logs_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api/v1/namespaces/${NAMESPACE}/pods/${pod_name}/log" 2>/dev/null)
if [ "$logs_response" = "200" ]; then
echo -e "${GREEN}[✓] get pods/log${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别 (namespace: $NAMESPACE)"
echo -e " ${YELLOW}可执行操作:${NC} 读取Pod容器的标准输出日志"
echo -e " ${YELLOW}安全影响:${NC} 可能泄露应用日志中的敏感信息(密码、Token等)\n"
fi
# 检查 status
status_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api/v1/namespaces/${NAMESPACE}/pods/${pod_name}/status" 2>/dev/null)
if [ "$status_response" = "200" ]; then
echo -e "${GREEN}[✓] get pods/status${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别 (namespace: $NAMESPACE)"
echo -e " ${YELLOW}可执行操作:${NC} 查看Pod运行状态、IP地址、容器状态等"
echo -e " ${YELLOW}安全影响:${NC} 获取网络拓扑和运行时信息\n"
fi
# 检查 exec (需要升级到WebSocket,这里只检查初始请求)
exec_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api/v1/namespaces/${NAMESPACE}/pods/${pod_name}/exec?command=ls&stdout=true" 2>/dev/null)
if [ "$exec_response" = "400" ] || [ "$exec_response" = "101" ]; then
echo -e "${GREEN}[✓] create pods/exec${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别 (namespace: $NAMESPACE)"
echo -e " ${YELLOW}可执行操作:${NC} 在Pod容器内执行任意命令"
echo -e " ${YELLOW}安全影响:${NC} ⚠️ 高危! 可直接获取容器Shell,读取secrets,逃逸等\n"
fi
# 检查 portforward
pf_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api/v1/namespaces/${NAMESPACE}/pods/${pod_name}/portforward" 2>/dev/null)
if [ "$pf_response" = "400" ] || [ "$pf_response" = "101" ]; then
echo -e "${GREEN}[✓] create pods/portforward${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别 (namespace: $NAMESPACE)"
echo -e " ${YELLOW}可执行操作:${NC} 转发Pod端口到本地进行访问"
echo -e " ${YELLOW}安全影响:${NC} 绕过NetworkPolicy访问内部服务\n"
fi
# 检查 attach
attach_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api/v1/namespaces/${NAMESPACE}/pods/${pod_name}/attach?stdout=true" 2>/dev/null)
if [ "$attach_response" = "400" ] || [ "$attach_response" = "101" ]; then
echo -e "${GREEN}[✓] create pods/attach${NC}"
echo -e " ${YELLOW}权限范围:${NC} 命名空间级别 (namespace: $NAMESPACE)"
echo -e " ${YELLOW}可执行操作:${NC} 附加到Pod容器的stdin/stdout/stderr"
echo -e " ${YELLOW}安全影响:${NC} 可与运行中的进程交互\n"
fi
fi
fi
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}"
echo -e "${BLUE} API Discovery 能力检测${NC}"
echo -e "${BLUE}═══════════════════════════════════════════════════════════════${NC}\n"
# API versions
api_versions=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/api" 2>/dev/null)
if [ "$api_versions" = "200" ]; then
echo -e "${GREEN}[✓] get /api${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 发现Core API组支持的版本"
echo -e " ${YELLOW}安全影响:${NC} 枚举API版本,寻找已知漏洞\n"
fi
# APIs
apis_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/apis" 2>/dev/null)
if [ "$apis_response" = "200" ]; then
echo -e "${GREEN}[✓] get /apis${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 列出所有API组和版本"
echo -e " ${YELLOW}安全影响:${NC} 发现扩展API和CRD,扩大攻击面\n"
fi
# Version
version_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/version" 2>/dev/null)
if [ "$version_response" = "200" ]; then
echo -e "${GREEN}[✓] get /version${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 获取Kubernetes版本信息"
echo -e " ${YELLOW}安全影响:${NC} 识别集群版本,查找对应CVE漏洞\n"
fi
# OpenAPI
openapi_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/openapi/v2" 2>/dev/null)
if [ "$openapi_response" = "200" ]; then
echo -e "${GREEN}[✓] get /openapi/v2${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 获取完整的API Schema定义"
echo -e " ${YELLOW}安全影响:${NC} 了解所有API接口和参数,辅助漏洞挖掘\n"
fi
# Healthz
healthz_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/healthz" 2>/dev/null)
if [ "$healthz_response" = "200" ]; then
echo -e "${GREEN}[✓] get /healthz${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 检查API Server健康状态"
echo -e " ${YELLOW}安全影响:${NC} 信息收集\n"
fi
# Livez
livez_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/livez" 2>/dev/null)
if [ "$livez_response" = "200" ]; then
echo -e "${GREEN}[✓] get /livez${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 检查API Server存活状态"
echo -e " ${YELLOW}安全影响:${NC} 信息收集\n"
fi
# Readyz
readyz_response=$(curl -s -o /dev/null -w "%{http_code}" \
--cacert $KUBE_CA \
-H "Authorization: Bearer $KUBE_TOKEN" \
"${API_SERVER}/readyz" 2>/dev/null)
if [ "$readyz_response" = "200" ]; then
echo -e "${GREEN}[✓] get /readyz${NC}"
echo -e " ${YELLOW}权限范围:${NC} 集群级别"
echo -e " ${YELLOW}可执行操作:${NC} 检查API Server就绪状态"
echo -e " ${YELLOW}安全影响:${NC} 信息收集\n"
fi
echo -e "${BLUE}╔════════════════════════════════════════════════════════════════╗${NC}"
echo -e "${BLUE}║ 检测完成 ║${NC}"
echo -e "${BLUE}╚════════════════════════════════════════════════════════════════╝${NC}"
俗人昭昭,我独昏昏。俗人察察,我独闷闷。

浙公网安备 33010602011771号