I cannot for the life of me find a detailed table of what all the Kubernetes RBAC verbs do. The only resource I see people recommending is this one, which is woefully inadequate.
So I've been working it out by experimentation.
Most are fairly straightforward so far, except for UPDATE. This does not seem to be able to do anything I would expect it to.
Permissions I gave my alias:
[GET, UPDATE] on [deployments] in default namespace.
Things I've tried:
kubectl set image deployment/hello-node echoserver=digitalocean/flask-helloworld --as user
kubectl edit deploy hello-node --as user
kubectl apply -f hello-node.yaml --as eks-user
These all failed with error: deployments.apps "hello-node" is forbidden: User "user" cannot patch resource "deployments" in API group "apps" in the namespace "default"
I then tried some rollout commands like:
k rollout undo deploy hello-node --as user
But they failed because I didn't have replica-set access.
TLDR: What is the point of the Kubernetes RBAC update verb?
For that matter, does anyone have a more detailed list of all RBAC verbs?
Following up this, I went to the Kubernetes REST API documentation, which has a long list of all the HTTP API calls you can make to the REST server.
I thought this would help because the one (1) table available describing what the different verbs can do did so by comparing them to HTTP verbs. So the plan was:
See what HTTP verb the update permission is equated to.
Go to the reference and find an example of using that HTTP verb on a deployment.
Test the kubectl equivalent.
So.
What HTTP verb equals the update permission?
PUT.
Example of using PUT for deployments?
Replace Scale: replace scale of the specified Deployment
HTTP Request
PUT /apis/apps/v1/namespaces/{namespace}/deployments/{name}/scale
What's the equivalent kubectl command?
Well we're scaling a deployment, so I'm going to say:
kubectl scale deployment hello-node --replicas=2
Can I run this command?
I extended my permissions to deployment/scale first, and then ran it.
Error from server (Forbidden): deployments.apps "hello-node" is forbidden: User "user" cannot patch resource "deployments/scale" in API group "apps" in the namespace "default"
Well. That also needs patch permissions, it would appear.
Despite the fact that the HTTP verb used is PUT according to the API docs, and PUT is equivalent to update according to the one (1) source of any information on these RBAC verbs.
Anyway.
My Conclusion: It appears that update is indeed pretty useless, at least for Deployments.
The RBAC setup seemed promising at first, but honestly it's starting to lose its lustre as I discover more and more edge cases and undocumented mysteries. Access permissions seem like the absolute worst thing to be vague about, or your security ends up being more through obscurity than certainty.
You can get a dump of the "allowed/supported" verbs using this krew plugin rbac-tool
# Generate a ClusterRole with all the available permissions for core and apps api groups
$ kubectl rbac-tool show --for-groups=,apps
While it won't tell you exactly the semantics of each verb - it will give yu a sense about the RBAC permissions universe your cluster have.
Related
I am studying "kubectl describe" sourcecodes at https://github.com/kubernetes/kubectl/blob/master/pkg/describe/describe.go
However, I still could not figure out how "kubectl decsribe [CRD]" works (as in which function/functions are called).
I am a Go newbie, so would like to get some pointers please. Thanks.
I have read describePod function and understand how it works more or less, but still could not figure out how "kubectl describe [CRD]" works.
The "kubectl describe " function can be found in the command-line interface (CLI) of Kubernetes, specifically in the "kubectl" tool. "kubectl" is used to manage and interact with a Kubernetes cluster and its resources.
enter image description here
Kubectl describe command helps to view the entire information about the kubernetes resources like Pods,deployments,services,nodes,jobs etc.
By using CRD(Custom Resource Definition) you can do CRUD operations like create, update, get and delete commands to access the resources. To use CRD we need to use the API groups.
Example:
Suppose you specify an API group as example.crd.com, which means you can issue the get, list, create, update, and delete commands to access the custom resources under the API group example.crd.com.
You can use kubectl describe crd <crd_name> to get a description of the CRD.
For more information refer this official doc
Try this similar SO’s SO1 and SO2 for more information
Such as system:masters、system:anonymous、system:unauthenticated.
Is there a way to have all system groups that do not contain external creation, just the system,kubectl command or a list?
I searched the Kubernetes documentation but didn't find a list or a way to get it.
There is no build-in command to list all the default user groups from the Kubernetes cluster.
However you can try to workaround in several options:
You can create your custom script (i.e. in Bash) based on kubectl get clusterrole command.
You can try install some plugins. Plugin rakkess could help you:
Have you ever wondered what access rights you have on a provided kubernetes cluster? For single resources you can use kubectl auth can-i list deployments, but maybe you are looking for a complete overview? This is what rakkess is for. It lists access rights for the current user and all server resources, similar to kubectl auth can-i --list.
See also more information about:
kubelet authentication / authorization
anonymous requests
I am surprised that nobody has yet asked this, but what exactly is deployment.apps?
I see it often in commands e.g
kubectl rollout pause deployment.apps/nginx-deployment
or even used interchangably for the deployments keyword:
kubectl get deployments= kubectl get deployment.apps
I do not understand what it indicates though. Even in K8s official docs, they just take for granted that the reader understands the term.
Could someone please explain it to me?
Kubernetes API has its different resources (e.g. Pods, Deployments, Ingress) grouped in what they call "api groups" and in the notation deployment.apps - "deployment" is the resource name and the "apps" is the api group name.
Also see the motivation for API groups
While there's a lot of documentation and examples on Kubernetes RBAC and also the available verbs for different resources, I couldn't find any rules on whether certain verbs are always used in combination or whether there are use cases to using them individually. In particular, I'm wondering about the verbs get, list, and watch. What uses are for combining them, and especially not combining them?
are there uses for allowing get on resources, but not list?
au contraire, are there uses for list without allowing get? Maybe along the lines of information sparseness?
get and list, but no watch? To restrict only trusted subjects and service accounts to put more strain on the API server and etcd?
watch without list or get? Wouldn't that cripple most clients because they're listwatchers?
Interesting question, here are some ideas and examples of usages in practice.
There are many more examples in practice. For example, you can inspect the default ClusterRoles by browsing through kubectl describe clusterroles. And to see which API requests kubectl makes under the hood, you can increase the log verbosity, for example, kubectl get pods -w -v 10.
get but not list
You want someone to be able to read resources they know by name but not discover what other resources exist. For example, allows to do kubectl get mypod, but not kubectl get pods.
Examples:
The system:node ClusterRole has get but not list permissions on Endpoints, PVs, and PVCs.
The system:coredns ClusterRole has get but not list permissions on Nodes.
The system:controller:expand-controller ClusterRole has get but not list permissions on Endpoints, Secrets, and Services.
list but not get
Allows to do, for example, kubectl get pods but not kubectl get pod mypod. It doesn't make much sense, because all the information you can get with get is also included in list. Nevertheless, there are some usages of this in practice.
Examples:
The system:kube-dns ClusterRole has list and watch permissions for Endpoints and Services, but not get.
The system:controller:daemon-set-controller ClusterRoel has list and watch permissions for Nodes, but not get.
The system:coredns ClusterRole has list and watch permissions for Endpoints, Namespaces, Pods, and Services, but not get.
get and list, but not watch
In practice, in most cases where there is list there is also watch. You could deprive someone of watch to reduce the number of watchers on etcd. Users can do kubectl get pods and kubectl get pods mypod, but not use the -w option.
Makes also sense if the API does not support watch operations, like, for example, the optional metric APIs.
Examples:
The system:controller:persistent-volume-binder ClusterRole has get and list permissions for Nodes, but not watch
watch, but not get and list
Regarding the use case, it doesn't make much sense, because all the information you can get with get and list is also included in watch. I don't know of any concrete usage of this in practice.
However, technically, it's possible. For example, if you have watch permissions for Pods, but not get and list, you can do:
✅ kubectl get --raw="/api/v1/watch/namespaces/default/pods"
✅ kubectl get --raw="/api/v1/watch/namespaces/default/pods/mypod"
And it works. However, these watch endpoints are deprecated and you should use the list endpoint with a watch parameter instead. But this also works:
✅ kubectl get --raw="/api/v1/namespaces/default/pods?watch=true"
However, you can't watch a single Pod like this, because the get endpoint doesn't have a watch parameter. So, the following is invalid:
❌ kubectl get --raw="/api/v1/namespaces/default/pods/mypod?watch=true"
And you can't watch resources with kubectl at all. The following fails:
❌ kubectl get pods -w
❌ kubectl get pods mypod -w
Because kubectl makes a list and get request, respectively, before the watch request, most probably to get the resourceVersion of the resources which will then be included in the subsequent watch request.
Note: that means, if you have list and watch, then kubectl get pods -w works, but kubectl get pods mypod -w doesn't, and if you have get and watch, then kubectl get pods mypod -w works but kubectl get pods -w doesn't.
1.6+ sees a lot of changes revolving around RBAC and ABAC. However, what is a little quirky is not being able to access the dashboard etc. by default as previously possible.
Access will result in
User "system:anonymous" cannot proxy services in the namespace "kube-system".: "No policy matched."
Documentation at the k8s docs is plenty, but not really stating how to gain access practically, as creator of a cluster, to become cluster-admin
What is a practical way to authenticate me as cluster-admin?
By far the easiest method is to use the credentials from /etc/kubernetes/admin.conf (this is on your master if you used kubeadm) . Run kubectl proxy --kubeconfig=admin.conf on your client and then you can visit http://127.0.0.1:8001/ui from your browser.
You might need to change the master address in admin.conf after you copied to you client machine.