Enabling kubelet server Bearer Token authentication

6/30/2017

Problem

I am trying to enable authentication on my kubelet servers using Bearer Tokens (not X.509 client certificate authentication), and fail to understand the workflow.

What I tried

According to the documentation page Kubelet authentication/authorization, starting the kubelet with the --authentication-token-webhook flag enables the Bearer Token authentication. I could confirm that by sending a request to the kubelet REST API using one of the default secrets created by the Controller Manager:

$ MY_TOKEN="$(kubectl get secret default-token-kw7mk \
      -o jsonpath='{$.data.token}' | base64 -d)"

$ curl -sS -o /dev/null -D - \
      --cacert /var/run/kubernetes/kubelet.crt \
      -H "Authorization : Bearer $MY_TOKEN" \
      https://host-192-168-0-10:10250/pods/

HTTP/1.1 200 OK
Content-Type: application/json
Date: Fri, 30 Jun 2017 22:12:29 GMT
Transfer-Encoding: chunked

However any communication with the kubelet via the API server (typically using the kubectl logs or exec commands) using the same Bearer Token as above fails with:

$ kubectl --token="$MY_TOKEN" -n kube-system logs \
      kube-dns-2272871451-sc02r -c kubedns

error: You must be logged in to the server (the server has asked for the client to provide credentials ( pods/log kube-dns-2272871451-sc02r))

Where I need clarification

My initial assumption was that the API server just passed the Bearer Token it received from the client directly to the kubelet, but my little experiment above proved me otherwise.

I see that the kube-apiserver documentation mentions a flag called --authentication-token-webhook-config-file but I'm unsure how to use it, or if it's even relevant for authenticating the API server against a kubelet.

Current configuration

My kubelet(s) run with:

  --anonymous-auth=false
  --authorization-mode=Webhook
  --authentication-token-webhook
  --cadvisor-port=0
  --cluster-dns=10.0.0.10
  --cluster-domain=cluster.local
  --read-only-port=0
  --kubeconfig=/etc/kubernetes/kubeconfig-kubelet
  --pod-manifest-path=/etc/kubernetes/manifests
  --require-kubeconfig

My API server runs with:

  --admission-control=NamespaceLifecycle,LimitRanger,ServiceAccount,PersistentVolumeLabel,DefaultStorageClass,ResourceQuota,DefaultTolerationSeconds
  --anonymous-auth=false
  --authorization-mode=AlwaysAllow
  (+ tls flags)
-- Antoine Cotten
kubernetes

1 Answer

7/1/2017

When making calls to the API server that require communication from the API server to the kubelet, that communication is done using the API server's client credentials, which only support x509 authentication to the kubelet.

The flags used to give the API server the credentials to use to contact the kubelet are listed in the "X509 client certificate authentication" section of https://kubernetes.io/docs/admin/kubelet-authentication-authorization/

API server webhook authentication options are unrelated to kubelet auth.

-- Jordan Liggitt
Source: StackOverflow