Enabling GKE Workload Identity
In this blog, I will talk about the GKE Workload Identity feature and why to use this feature.
What’s the Problem?
An application running on GKE must authenticate to use Google Services such as Google Cloud Storage (GCS), Cloud SQL, BigQuery, etc. Authentication can be done by providing a service account key JSON file to an application using Kubernetes Secret space or a different method such as Vault.
However, in these approaches, the service account key JSON (which has a lifetime of 10 years) must be stored in plain text within the pod or Base64 encoded in Kubernetes secret space. Also, the key rotation process must be in a place (that is not a fun process).
We can avoid using the service account key by attaching a service account to a Kubernetes node, but then all the pods running on the node gets the same permission, which is not an ideal thing to do.
Goal
We want to assign a service account to a pod so we can isolate permissions for different pods.
Hurray: we have the Workload Identity feature available in beta, which solves this problem on GKE.
What Is Workload Identity?
As per the Google documentation:
“Workload Identity is the recommended way to access Google Cloud services from within GKE due to its improved security properties and manageability.“
GKE Workload identity allows us to attach the service account to the Kubernetes pod and remove the hassle to manage the service account credentials JSON file within the pod or cluster.
Workload Identity in a GKE Cluster
Prerequisites
If you have not setup
gcloud
on your workstation, then refer to my previous blog to get it up and running quickly. Alternatively, you can use Google Cloud Shell to run the commands.Make sure you are a Project Editor or Project Owner or have enough permissions to run the below commands.
Setup a GKE Cluster
Follow the below step to create a new GKE Cluster and enable Workload Identity.
1. Enable the Cloud IAM API.
2. Install and configure gke-gcloud-auth-plugin
. gke-gcloud-auth-plugin
is the new Kubectl authentication plugin for GKE. Please read the documentation for more details.
- Install plugin:
gcloud components install gke-gcloud-auth-plugin
Note: If gcloud CLI component manager
is disabled, use the yum
or apt
package to install this plugin. For Debian:
sudo apt-get install google-cloud-sdk-gke-gcloud-auth-plugin
- Configure plugin:
echo "export USE_GKE_GCLOUD_AUTH_PLUGIN=True" >> ~/.bashrc
source ~/.bashrc
3. Set GCP defaults.
- Set GCP Project:
export GCP_PROJECT_ID=<YOUR_GCP_PROJECT_ID>
gcloud config set project $GCP_PROJECT_ID
- Set default region and zone:
gcloud config set compute/region europe-west1
gcloud config set compute/zone europe-west1-b
4. Make sure you have kubectl
command installed.
sudo apt-get install kubectl
Run the following to verify:
kubectl help
5. Create a new Google Service Account (GSA).
gcloud iam service-accounts create workload-identity-test
Notes: You can use the existing service account.
Permission Required: iam.serviceAccounts.create
on the GCP Project.
6. Add permissions to the Google Service Account required by an application: for example, roles/storage.objectViewer
.
gcloud projects add-iam-policy-binding $GCP_PROJECT_ID \
--member serviceAccount:workload-identity-test@${GCP_PROJECT_ID}.iam.gserviceaccount.com \
--role roles/storage.objectViewer
7. Setup a GKE cluster with Workload Identity enabled.
export GKE_CLUSTER_NAME=gke-wi
gcloud container clusters create $GKE_CLUSTER_NAME \
--cluster-version=1.24 \
--workload-pool=$GCP_PROJECT_ID.svc.id.goog
8. Configure kubectl
command on your terminal.
gcloud container clusters get-credentials $GKE_CLUSTER_NAME
Notes: This will populate ~/.kube/config
file.
Permission Required: container.clusters.get
on the GCP Project.
9. (Optional) Create a Kubernetes namespace if you dont want to use the default
namespace.
kubectl create namespace newspace
10. Create Kubernetes Service Account (KSA).
kubectl create serviceaccount \
--namespace newspace \
workload-identity-test-ksa
11. Bind the Google Service Account (GSA) and Kubernetes Service Account (KSA), so that KSA can use the permissions granted to GSA.
gcloud iam service-accounts add-iam-policy-binding \
--role roles/iam.workloadIdentityUser \
--member "serviceAccount:${GCP_PROJECT_ID}.svc.id.goog[newspace/workload-identity-test-ksa]" \
workload-identity-test@${GCP_PROJECT_ID}.iam.gserviceaccount.com
12. Add annotation:
kubectl annotate serviceaccount \
--namespace newspace \
workload-identity-test-ksa \
iam.gke.io/gcp-service-account=workload-identity-test@${GCP_PROJECT_ID}.iam.gserviceaccount.com
13. Create a Pod with the KSA created to verify.
kubectl run --rm -it test-pod \
--image google/cloud-sdk:slim \
--namespace newspace \
--overrides='{ "spec": { "serviceAccount": "workload-identity-test-ksa" } }' sh
Running the above command will log in to Pod and provides its bash shell. Now run below command to see which service account this pod is configured with.
gcloud auth list
This should print the GSA name.
Credentialed Accounts
ACTIVE ACCOUNT
* workload-identity-test@workshop-demo-namwcb.iam.gserviceaccount.com
Cleanup
Don’t forget to clean up the resources, once you no longer need them.
Run the following commands:
1. Delete the GKE cluster.
gcloud container clusters delete $GKE_CLUSTER_NAME
2. Delete the Google Service Account (GSA).
gcloud iam service-accounts delete workload-identity-test@${GCP_PROJECT_ID}.iam.gserviceaccount.com
Below is the terminal recording:
I hope this blog helps you get familiar with Workload Identity and securely deploy apps on GKE.
If you have feedback or questions, please reach out to me on LinkedIn or Twitter.