Reputation: 452
I am trying to access a kubernetes cluster using the rest api. I followed the instructions of this but i wanted to get the pods of the cluster.
APISERVER=$(kubectl config view --minify -o jsonpath='{.clusters[0].cluster.server}')
SECRET_NAME=$(kubectl get serviceaccount default -o jsonpath='{.secrets[0].name}')
TOKEN=$(kubectl get secret $SECRET_NAME -o jsonpath='{.data.token}' | base64 --decode)
curl $APISERVER/api/v1/pods --header "Authorization: Bearer $TOKEN" --insecure
the result is:
{
"kind": "Status",
"apiVersion": "v1",
"metadata": {
},
"status": "Failure",
"message": "pods is forbidden: User \"system:serviceaccount:default:default\" cannot list resource \"pods\" in API group \"\" at the cluster scope",
"reason": "Forbidden",
"details": {
"kind": "pods"
},
"code": 403
I tried the same (curl localhost:8001/api/v1/pods)
by running the command:
kubectl proxy --address='0.0.0.0' --disable-filter=true
at the master node of the cluster and now it works as desired.
How can I make the Athorization Bearer work in the same manner?
Upvotes: 1
Views: 3200
Reputation: 1
If you’re using a Kubernetes cluster with RBAC enabled, the service account may not be authorized to access the API server. The simplest way to allow you to query the API server is to work around RBAC by running the following command:
kubectl create clusterrolebinding permissive-binding --clusterrole=cluster-admin --group=system:serviceaccounts
This gives all service accounts (we could also say all pods) cluster-admin privileges, allowing them to do whatever they want. PLEASE NOTE: Obviously, doing this is dangerous and should never be done on production clusters. For test purposes, it’s fine.
Upvotes: 0
Reputation: 452
In order to be able to get the pods for all the namespaces then you have to define a cluster-role and a cluster-role-binding, instead of a role/role-binding pair
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: get-pods
rules:
- apiGroups: [""]
resources: ["pods"]
verbs: ["get"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: get-pods-binding
subjects:
- kind: ServiceAccount
name: default
namespace: default
roleRef:
kind: ClusterRole
name: get-pods
apiGroup: rbac.authorization.k8s.io
You may save this to a file named for example get_pods_role.yaml
and execute kubectl create -f get_pods_role.yaml
.
Then you will be able to get the desired output by this:
APISERVER=$(kubectl config view --minify -o jsonpath='{.clusters[0].cluster.server}')
SECRET_NAME=$(kubectl get serviceaccount default -o jsonpath='{.secrets[0].name}')
TOKEN=$(kubectl get secret $SECRET_NAME -o jsonpath='{.data.token}' | base64 --decode)
curl $APISERVER/api/v1/pods --header "Authorization: Bearer $TOKEN" --insecure
Upvotes: 0
Reputation: 6471
You are using default
service account to get pods. default
serviceaccount don't have that permission. You can check an action is allowed or not by running
$ kubectl auth can-i get pods --as system:serviceaccount:default:default
no
"message": "pods is forbidden: User \"system:serviceaccount:default:default\" cannot list resource \"pods\" in API group \"\" at the cluster scope",
as can be seen above the default service account cannot list pods
but when given proper role and role binding like below
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: demo-role
namespace: default
rules:
- apiGroups:
- ""
resources:
- pods
verbs:
- get
- list
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: demo-binding
namespace: default
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: demo-role
subjects:
- kind: ServiceAccount
name: default
namespace: default
Now if you check
$ kubectl auth can-i get pods --as system:serviceaccount:default:default
yes
If you want to list pods of default namespace using api then run
$ APISERVER=$(kubectl config view --minify -o jsonpath='{.clusters[0].cluster.server}')
$ SECRET_NAME=$(kubectl get serviceaccount default -o jsonpath='{.secrets[0].name}')
$ TOKEN=$(kubectl get secret $SECRET_NAME -o jsonpath='{.data.token}' | base64 --decode)
$ curl $APISERVER/api/v1/namespaces/default/pods --header "Authorization: Bearer $TOKEN" --insecure
{
"kind": "PodList",
"apiVersion": "v1",
"metadata": {
"selfLink": "/api/v1/namespaces/default/pods",
"resourceVersion": "1589"
},
"items": []
}
Upvotes: 3