forked from kubeflow/kubeflow
-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Create a ksonnet package for injecting credentials through pod presets (
kubeflow#782) * Create a package for injecting credentials through pod presets Fixes kubeflow#732 * Typos
- Loading branch information
1 parent
5bffc37
commit 3690077
Showing
3 changed files
with
167 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,88 @@ | ||
# Credentials Pod Presets | ||
|
||
This package contains Kubernetes [PodPresets](https://kubernetes.io/docs/concepts/workloads/pods/podpreset/) for injecting credentials into Pods. | ||
|
||
> Note: Pod Presets are namespace-scoped. A separate Pod Preset needs to be created for every namespace that needs credentials injected into pods. | ||
# Google Cloud Service Account Credentials | ||
|
||
This is useful for injecting GCP Service Account Credentials into pods by using labels. Currently PodPresets is in alpha on GCP, so make sure that you are creating a GKE cluster with alpha features [enabled](https://cloud.google.com/kubernetes-engine/docs/concepts/alpha-clusters). | ||
|
||
``` | ||
# Ensure that you have podpresets available on your kubernetes cluster | ||
# This step should not return an error | ||
$ kubectl get podpreset | ||
``` | ||
|
||
Follow the steps below to create a service account, add roles to it and create a k8s secret containing its credentials. | ||
|
||
``` | ||
# Create a service account in a GCP Project | ||
SERVICE_ACCOUNT=kubeflow-gcp-service-account # Use any appropriate service account name | ||
PROJECT=agwl-kubeflow # Name of GCP Project | ||
gcloud iam service-accounts --project=${PROJECT} create ${SERVICE_ACCOUNT} \ | ||
--display-name "GCP Service Account for use with kubeflow" | ||
# Give the service account any roles that it requires. For example | ||
# here we're giving it storage.admin role so that it can write to GCS | ||
gcloud projects add-iam-policy-binding ${PROJECT} \ | ||
--member serviceAccount:${SERVICE_ACCOUNT}@${PROJECT}.iam.gserviceaccount.com \ | ||
--role=roles/storage.admin | ||
# Download a key file for the service account | ||
KEY_FILE=${HOME}/secrets/${SERVICE_ACCOUNT}@${PROJECT}.iam.gserviceaccount.com.json | ||
gcloud iam service-accounts keys create ${KEY_FILE} \ | ||
--iam-account ${SERVICE_ACCOUNT}@${PROJECT}.iam.gserviceaccount.com | ||
# Create a k8s secret with the key file | ||
SECRET_NAME="${SERVICE_ACCOUNT}-credentials" | ||
NAMESPACE=default | ||
kubectl create secret -n ${NAMESPACE} generic ${SECRET_NAME} --from-file="${SERVICE_ACCOUNT}-key.json"="${KEY_FILE}" | ||
``` | ||
|
||
Now create a PodPreset which injects ${SERVICE_ACCOUNT} credentials into all the pods created in a namespace. | ||
|
||
``` | ||
ks pkg install kubeflow/credentials-pod-preset | ||
COMPONENT_NAME=${SERVICE_ACCOUNT}-credentials-injector | ||
ks generate gcp-credentials-pod-preset ${COMPONENT_NAME} \ | ||
--serviceAccountName ${SERVICE_ACCOUNT} \ | ||
--secretName ${SECRET_NAME} \ | ||
--namespace ${NAMESPACE} | ||
KS_ENV=default | ||
ks apply ${KS_ENV} -c ${COMPONENT_NAME} | ||
``` | ||
|
||
## Testing the pod preset | ||
|
||
Any pod which has the label `inject_gcp_service_account: ${SERVICE_ACCOUNT}` and created in the `${NAMESPACE}` will be injected with the `${SERVICE_ACCOUNT}` credentials. | ||
|
||
``` | ||
# Create a simple pod manifest | ||
cat <<EOF > pod.yaml | ||
apiVersion: v1 | ||
kind: Pod | ||
metadata: | ||
name: website | ||
namespace: ${NAMESPACE} | ||
labels: | ||
inject_gcp_service_account: ${SERVICE_ACCOUNT} | ||
spec: | ||
containers: | ||
- name: website | ||
image: nginx | ||
ports: | ||
- containerPort: 80 | ||
EOF | ||
# Apply it | ||
kubectl apply -f pod.yaml | ||
# Print the pod manifest. You should see the Service | ||
# Account credentials injected into the pod | ||
kubectl get -n ${NAMESPACE} pod/website -oyaml | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
{ | ||
"name": "credentials-pod-preset", | ||
"apiVersion": "0.0.1", | ||
"kind": "ksonnet.io/parts", | ||
"description": "This package contains Kubernetes PodPresets for injecting credentials into Pods..\n", | ||
"author": "kubeflow-team <kubeflow-discuss@googlegroups.com>", | ||
"contributors": [ | ||
], | ||
"repository": { | ||
"type": "git", | ||
"url": "https://github.com/kubeflow/kubeflow" | ||
}, | ||
"bugs": { | ||
"url": "https://github.com/kubeflow/kubeflow/issues" | ||
}, | ||
"keywords": [ | ||
"kubernetes", | ||
"kubeflow", | ||
"machine learning" | ||
], | ||
"license": "Apache 2.0", | ||
} |
57 changes: 57 additions & 0 deletions
57
kubeflow/credentials-pod-preset/prototypes/gcp-credentials-pod-preset.jsonnet
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
// @apiVersion 0.1 | ||
// @name io.ksonnet.pkg.gcp-credentials-pod-preset | ||
// @description This prototype creates a pod preset which injects credentials into pods | ||
// @shortDescription This prototype creates a pod preset which injects credentials into pods | ||
// @param name string Name to give to each of the components | ||
// @param serviceAccountName string Name of the GCP service account | ||
// @param secretName string Name of the kubernetes secret containing the credentials | ||
// @optionalParam namespace string null Namespace to use for the pod preset. It is automatically inherited from the environment if not set. | ||
|
||
local k = import "k.libsonnet"; | ||
|
||
// updatedParams uses the environment namespace if | ||
// the namespace parameter is not explicitly set | ||
local updatedParams = params { | ||
namespace: if params.namespace == "null" then env.namespace else params.namespace, | ||
}; | ||
|
||
local podPreset = { | ||
apiVersion: "settings.k8s.io/v1alpha1", | ||
kind: "PodPreset", | ||
metadata: { | ||
name: "inject-" + updatedParams.serviceAccountName + "-credentials", | ||
namespace: updatedParams.namespace, | ||
}, | ||
spec: { | ||
selector: { | ||
matchLabels: { | ||
inject_gcp_service_account: updatedParams.serviceAccountName, | ||
}, | ||
}, | ||
env: [ | ||
{ | ||
name: "GOOGLE_APPLICATION_CREDENTIALS", | ||
value: "/secrets/gcp-service-account-credentials/" + updatedParams.serviceAccountName + "-key.json", | ||
}, | ||
], | ||
volumeMounts: [ | ||
{ | ||
mountPath: "/secrets/gcp-service-account-credentials", | ||
readOnly: true, | ||
name: updatedParams.serviceAccountName + "-credentials", | ||
}, | ||
], | ||
volumes: [ | ||
{ | ||
name: updatedParams.serviceAccountName + "-credentials", | ||
secret: { | ||
secretName: updatedParams.secretName, | ||
}, | ||
}, | ||
], | ||
}, | ||
}; // podPreset | ||
|
||
k.core.v1.list.new( | ||
podPreset | ||
) |