Skip to content
This repository has been archived by the owner on Aug 28, 2021. It is now read-only.

add support for gcloud auth #145

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion Dockerfile
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
FROM linkyard/alpine-helm:2.16.7
LABEL maintainer "mario.siegenthaler@linkyard.ch"

RUN apk add --update --upgrade --no-cache jq bash curl git gettext libintl
RUN apk add --update --upgrade --no-cache jq bash curl git gettext libintl python
RUN curl -sSL https://sdk.cloud.google.com | bash

ENV PATH $PATH:/root/google-cloud-sdk/bin
ENV KUBERNETES_VERSION 1.16.9
RUN curl -L -o /usr/local/bin/kubectl https://storage.googleapis.com/kubernetes-release/release/v${KUBERNETES_VERSION}/bin/linux/amd64/kubectl; \
chmod +x /usr/local/bin/kubectl
Expand Down
152 changes: 89 additions & 63 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,36 +16,44 @@ resource_types:

## Source Configuration

* `cluster_url`: *Optional.* URL to Kubernetes Master API service. Do not set when using the `kubeconfig_path` parameter, otherwise required.
* `cluster_ca`: *Optional.* Base64 encoded PEM. Required if `cluster_url` is https.
* `insecure_skip_tls_verify`: *Optional* Skips verifying the `cluster_ca`. (Default: false). Ignored unless `cluster_url` is https. Useful for self-signed certificates. It is not recommended to use blindly.
* `token`: *Optional.* Bearer token for Kubernetes. This, 'token_path' or `admin_key`/`admin_cert` are required if `cluster_url` is https.
* `token_path`: *Optional.* Path to file containing the bearer token for Kubernetes. This, 'token' or `admin_key`/`admin_cert` are required if `cluster_url` is https.
* `admin_key`: *Optional.* Base64 encoded PEM. Required if `cluster_url` is https and no `token` or 'token_path' is provided.
* `admin_cert`: *Optional.* Base64 encoded PEM. Required if `cluster_url` is https and no `token` or 'token_path' is provided.
* `release`: *Optional.* Name of the release (not a file, a string). (Default: autogenerated by helm)
* `namespace`: *Optional.* Kubernetes namespace the chart will be installed into. (Default: default)
* `tillerless`: *Optional.* Set to true to use tiller-less mode (Default: false). See <https://rimusz.net/tillerless-helm/>.
* `tillerless_silent`: *Optional.* Set to `true` to make tiller-less mode silent (Default: true). Activating tillerless helm without making it silent **will make credentials to leak in the build output** when using `override_values` parameter with `hide: true`.
* `helm_init_server`: *Optional.* Installs helm into the cluster if not already installed. (Default: false). Not supported when using tillerless.
* `tiller_namespace`: *Optional.* Kubernetes namespace where tiller is running (or will be installed to). (Default: kube-system)
* `tiller_cert`: *Optional* Certificate for Tiller (only applies if tls_enabled and helm_init_server are true).
* `tiller_key`: *Optional* Key created for Tiller when doing a secure Tiller install (only applies if tls_enabled and helm_init_server are true).
* `tiller_service_account`: *Optional* Name of the service account that tiller will use (only applies if helm_init_server is true).
* `helm_ca`: *Optional* Private CA that is used to issue certificates for Tiller clients and servers (only applies if tls_enabled is true).
* `helm_cert`: *Optional* Certificate for Client (only applies if tls_enabled is true).
* `helm_key`: *Optional* Key created for Client when doing a secure Tiller install (only applies if tls_enabled is true).
* `tls_enabled`: *Optional* Uses TLS for all interactions with Tiller. (Default: false). Not supported when using tillerless.
* `helm_history_max`: *Optional.* Limits the maximum number of revisions. (Default: 0 = no limit)
* `helm_host`: *Optional* Address of Tiller. Skips helm discovery process. (only applies if `helm_init_server` is false).
* `repos`: *Optional.* Array of Helm repositories to initialize, each repository is defined as an object with properties `name`, `url` (required) username and password (optional).
* `plugins`: *Optional.* Array of Helm plugins to install, each defined as an object with properties `url` (required), `version` (optional).
* `stable_repo`: *Optional* Override default Helm stable repo <https://kubernetes-charts.storage.googleapis.com>. Useful if running helm deploys without internet access.
* `kubeconfig_namespace`: *Optional.* Use the kubeconfig context namespace as the helm namespace. (Default: false)
* `kubeconfig_tiller_namespace`: *Optional.* Use the kubeconfig context namespace as the tiller namespace. (Default: false)
* `tracing_enabled`: *Optional.* Enable extremely verbose tracing for this resource. Useful when developing the resource itself. May allow secrets to be displayed. (Default: false)
* `helm_init_wait`: *Optional.* When initializing the helm server, use the `--wait` option. (Default: false)
* `helm_setup_purge_all`: *Optional.* Delete and purge every helm release. Use with extreme caution. (Default: false)
- `gcloud_cluster_auth`: _Optional._ Set to true to use gcloud service account file for kubernetes cluster authentication.

- `gcloud_service_account_key_file`: _Optional_ Manadatory if gcloud_cluster_auth is set to true. Pass gcloud service accon json contents as value.

- `gcloud_project_name`: _Optional_ Manadatory if gcloud_cluster_auth is set to true. Pass gcloud project name where cluster is installed.

- `gcloud_k8s_cluster_name`: _Optional_ Manadatory if gcloud_cluster_auth is set to true. Pass gcloud cluster name.

- `gcloud_k8s_zone`: _Optional_ Manadatory if gcloud_cluster_auth is set to true. Pass gcloud kubernetes cluster zone.

- `cluster_url`: _Optional._ URL to Kubernetes Master API service. Do not set when using the `kubeconfig_path` parameter, otherwise required.
- `cluster_ca`: _Optional._ Base64 encoded PEM. Required if `cluster_url` is https.
- `token`: _Optional._ Bearer token for Kubernetes. This, 'token_path' or `admin_key`/`admin_cert` are required if `cluster_url` is https.
- `token_path`: _Optional._ Path to file containing the bearer token for Kubernetes. This, 'token' or `admin_key`/`admin_cert` are required if `cluster_url` is https.
- `admin_key`: _Optional._ Base64 encoded PEM. Required if `cluster_url` is https and no `token` or 'token_path' is provided.
- `admin_cert`: _Optional._ Base64 encoded PEM. Required if `cluster_url` is https and no `token` or 'token_path' is provided.
- `release`: _Optional._ Name of the release (not a file, a string). (Default: autogenerated by helm)
- `namespace`: _Optional._ Kubernetes namespace the chart will be installed into. (Default: default)
- `tillerless`: _Optional._ Set to true to use tiller-less mode (Default: false). See <https://rimusz.net/tillerless-helm/>.
- `helm_init_server`: _Optional._ Installs helm into the cluster if not already installed. (Default: false). Not supported when using tillerless.
- `tiller_namespace`: _Optional._ Kubernetes namespace where tiller is running (or will be installed to). (Default: kube-system)
- `tiller_cert`: _Optional_ Certificate for Tiller (only applies if tls_enabled and helm_init_server are true).
- `tiller_key`: _Optional_ Key created for Tiller when doing a secure Tiller install (only applies if tls_enabled and helm_init_server are true).
- `tiller_service_account`: _Optional_ Name of the service account that tiller will use (only applies if helm_init_server is true).
- `helm_ca`: _Optional_ Private CA that is used to issue certificates for Tiller clients and servers (only applies if tls_enabled is true).
- `helm_cert`: _Optional_ Certificate for Client (only applies if tls_enabled is true).
- `helm_key`: _Optional_ Key created for Client when doing a secure Tiller install (only applies if tls_enabled is true).
- `tls_enabled`: _Optional_ Uses TLS for all interactions with Tiller. (Default: false). Not supported when using tillerless.
- `helm_history_max`: _Optional._ Limits the maximum number of revisions. (Default: 0 = no limit)
- `helm_host`: _Optional_ Address of Tiller. Skips helm discovery process. (only applies if `helm_init_server` is false).
- `repos`: _Optional._ Array of Helm repositories to initialize, each repository is defined as an object with properties `name`, `url` (required) username and password (optional).
- `plugins`: _Optional._ Array of Helm plugins to install, each defined as an object with properties `url` (required), `version` (optional).
- `stable_repo`: _Optional_ Override default Helm stable repo <https://kubernetes-charts.storage.googleapis.com>. Useful if running helm deploys without internet access.
- `kubeconfig_namespace`: _Optional._ Use the kubeconfig context namespace as the helm namespace. (Default: false)
- `kubeconfig_tiller_namespace`: _Optional._ Use the kubeconfig context namespace as the tiller namespace. (Default: false)
- `tracing_enabled`: _Optional._ Enable extremely verbose tracing for this resource. Useful when developing the resource itself. May allow secrets to be displayed. (Default: false)
- `helm_init_wait`: _Optional._ When initializing the helm server, use the `--wait` option. (Default: false)
- `helm_setup_purge_all`: _Optional._ Delete and purge every helm release. Use with extreme caution. (Default: false)

## Behavior

Expand All @@ -63,44 +71,41 @@ on the cluster.

#### Parameters

* `chart`: *Required.* Either the file containing the helm chart to deploy (ends with .tgz), the path to a local directory containing the chart or the name of the chart from a repo (e.g. `stable/mysql`).
* `namespace`: *Optional.* Either a file containing the name of the namespace or the name of the namespace. (Default: taken from source configuration).
* `release`: *Optional.* Either a file containing the name of the release or the name of the release. (Default: taken from source configuration).
* `values`: *Optional.* File containing the values.yaml for the deployment. Supports setting multiple value files using an array.
* `override_values`: *Optional.* Array of values that can override those defined in values.yaml. Each entry in
the array is a map containing a key and a value or path. Value is set directly while path reads the contents of
the file in that path. A `hide: true` parameter ensures that the value is not logged and instead replaced with `***HIDDEN***`.
A `type: string` parameter makes sure Helm always treats the value as a string (uses the `--set-string` option to Helm; useful if the value varies
and may look like a number, eg. if it's a Git commit hash).
A `verbatim: true` parameter escapes backslashes so the value is passed as-is to the Helm chart (useful for `((credentials))`).
The default behaviour of backslashes in `--set` is to quote the next character so `val\ue` is treated as `value` by Helm.
* `token_path`: *Optional.* Path to file containing the bearer token for Kubernetes. This, 'token' or `admin_key`/`admin_cert` are required if `cluster_url` is https.
* `version`: *Optional* Chart version to deploy, can be a file or a value. Only applies if `chart` is not a file.
* `delete`: *Optional.* Deletes the release instead of installing it. Requires the `name`. (Default: false)
* `test`: *Optional.* Test the release instead of installing it. Requires the `release`. (Default: false)
* `purge`: *Optional.* Purge the release on delete. (Default: false)
* `replace`: *Optional.* Replace deleted release with same name. (Default: false)
* `force`: *Optional.* Force resource update through delete/recreate if needed. (Default: false)
* `devel`: *Optional.* Allow development versions of chart to be installed. This is useful when wanting to install pre-release
charts (i.e. 1.0.2-rc1) without having to specify a version. (Default: false)
* `debug`: *Optional.* Dry run the helm install with the debug flag which logs interpolated chart templates. (Default: false)
* `wait_until_ready`: *Optional.* Set to the number of seconds it should wait until all the resources in
the chart are ready. (Default: `0` which means don't wait).
* `check_is_ready`: *Optional.* Requires that `wait_until_ready` is set to Default. Applies --wait without timeout. (Default: false)
* `atomic`: *Optional.* This flag will cause failed installs to purge the release, and failed upgrades to rollback to the previous release. (Default: false)
* `recreate_pods`: *Optional.* This flag will cause all pods to be recreated when upgrading. (Default: false)
* `show_diff`: *Optional.* Show the diff that is applied if upgrading an existing successful release. Will not be used when `devel` is set. (Default: false)
* `exit_after_diff`: *Optional.* Show the diff but don't actually install/upgrade. (Default: false)
* `reuse_values`: *Optional.* When upgrading, reuse the last release's values. (Default: false)
* `reset_values`: *Optional.* When upgrading, reset the values to the ones built into the chart. (Default: false)
* `wait`: *Optional.* Allows deploy task to sleep for X seconds before continuing to next task. Allows pods to restart and become stable, useful where dependency between pods exists. (Default: 0)
* `kubeconfig_path`: *Optional.* File containing a kubeconfig. Overrides source configuration for cluster, token, and admin config.
- `chart`: _Required._ Either the file containing the helm chart to deploy (ends with .tgz), the path to a local directory containing the chart or the name of the chart from a repo (e.g. `stable/mysql`).
- `namespace`: _Optional._ Either a file containing the name of the namespace or the name of the namespace. (Default: taken from source configuration).
- `release`: _Optional._ Either a file containing the name of the release or the name of the release. (Default: taken from source configuration).
- `values`: _Optional._ File containing the values.yaml for the deployment. Supports setting multiple value files using an array.
- `override_values`: _Optional._ Array of values that can override those defined in values.yaml. Each entry in
the array is a map containing a key and a value or path. Value is set directly while path reads the contents of
the file in that path. A `hide: true` parameter ensures that the value is not logged and instead replaced with `***HIDDEN***`.
A `type: string` parameter makes sure Helm always treats the value as a string (uses the `--set-string` option to Helm; useful if the value varies
and may look like a number, eg. if it's a Git commit hash).
- `token_path`: _Optional._ Path to file containing the bearer token for Kubernetes. This, 'token' or `admin_key`/`admin_cert` are required if `cluster_url` is https.
- `version`: _Optional_ Chart version to deploy, can be a file or a value. Only applies if `chart` is not a file.
- `delete`: _Optional._ Deletes the release instead of installing it. Requires the `name`. (Default: false)
- `test`: _Optional._ Test the release instead of installing it. Requires the `release`. (Default: false)
- `purge`: _Optional._ Purge the release on delete. (Default: false)
- `replace`: _Optional._ Replace deleted release with same name. (Default: false)
- `force`: _Optional._ Force resource update through delete/recreate if needed. (Default: false)
- `devel`: _Optional._ Allow development versions of chart to be installed. This is useful when wanting to install pre-release
charts (i.e. 1.0.2-rc1) without having to specify a version. (Default: false)
- `debug`: _Optional._ Dry run the helm install with the debug flag which logs interpolated chart templates. (Default: false)
- `wait_until_ready`: _Optional._ Set to the number of seconds it should wait until all the resources in
the chart are ready. (Default: `0` which means don't wait).
- `check_is_ready`: _Optional._ Requires that `wait_until_ready` is set to Default. Applies --wait without timeout. (Default: false)
- `recreate_pods`: _Optional._ This flag will cause all pods to be recreated when upgrading. (Default: false)
- `show_diff`: _Optional._ Show the diff that is applied if upgrading an existing successful release. Will not be used when `devel` is set. (Default: false)
- `exit_after_diff`: _Optional._ Show the diff but don't actually install/upgrade. (Default: false)
- `reuse_values`: _Optional._ When upgrading, reuse the last release's values. (Default: false)
- `reset_values`: _Optional._ When upgrading, reset the values to the ones built into the chart. (Default: false)
- `wait`: _Optional._ Allows deploy task to sleep for X seconds before continuing to next task. Allows pods to restart and become stable, useful where dependency between pods exists. (Default: 0)
- `kubeconfig_path`: _Optional._ File containing a kubeconfig. Overrides source configuration for cluster, token, and admin config.

## Example

### Out

Define the resource:
Define the resource for authentication with certificates as follows:

```yaml
resources:
Expand All @@ -116,6 +121,27 @@ resources:
url: https://somerepo.github.io/charts
```


Define the resource for authentication with gcloud sevice account json as follows:

```yaml
resources:
- name: myapp-helm-gcloud
type: helm
source:
gcloud_cluster_auth: true
gcloud_service_account_key_file: _plain service account json file_
gcloud_project_name: _project name_
gcloud_k8s_cluster_name: _k8s cluster name_
gcloud_k8s_zone: _k8s zone_
repos:
- name: some_repo
url: https://somerepo.github.io/charts
```




Add to job:

```yaml
Expand Down
40 changes: 37 additions & 3 deletions assets/common.sh
Original file line number Diff line number Diff line change
@@ -1,6 +1,29 @@
#!/bin/bash
set -e

setup_gcp_kubernetes() {
payload=$1
source=$2

gcloud_service_account_key_file=$(jq -r '.source.gcloud_service_account_key_file // ""' < $payload)
gcloud_project_name=$(jq -r '.source.gcloud_project_name // ""' < $payload)
gcloud_k8s_cluster_name=$(jq -r '.source.gcloud_k8s_cluster_name // ""' < $payload)
gcloud_k8s_zone=$(jq -r '.source.gcloud_k8s_zone // ""' < $payload)

if [ -z "$gcloud_service_account_key_file" ] || [ -z "$gcloud_project_name" ] || [ -z "$gcloud_k8s_cluster_name" ] || [ -z "$gcloud_k8s_zone" ]; then
echo "invalid payload for gcloud auth, please pass all required params"
exit 1
fi

echo "$gcloud_service_account_key_file" >> /gcloud.json
gcloud_service_account_name=($(cat /gcloud.json | jq -r ".client_email"))
gcloud auth activate-service-account ${gcloud_service_account_name} --key-file /gcloud.json
gcloud config set account ${gcloud_service_account_name}
gcloud config set project ${gcloud_project_name}
gcloud container clusters get-credentials ${gcloud_k8s_cluster_name} --zone ${gcloud_k8s_zone}
kubectl version
}

setup_kubernetes() {
payload=$1
source=$2
Expand All @@ -25,7 +48,7 @@ setup_kubernetes() {
token=$(jq -r '.source.token // ""' < $payload)
token_path=$(jq -r '.params.token_path // ""' < $payload)
insecure_skip_tls_verify=$(jq -r '.source.insecure_skip_tls_verify // "false"' < $payload)

if [ "$insecure_skip_tls_verify" = true ]; then
kubectl config set-cluster default --server=$cluster_url --insecure-skip-tls-verify
else
Expand Down Expand Up @@ -246,10 +269,21 @@ setup_resource() {
set -x
fi

echo "Initializing kubectl..."
setup_kubernetes $1 $2
gcloud_cluster_auth=$(jq -r '.source.gcloud_cluster_auth // "false"' < $1)
if [ "$gcloud_cluster_auth" = "true" ]; then
echo "Initializing kubectl access using gcloud service account file"
setup_gcp_kubernetes $1 $2
else
echo "Initializing kubectl using certificates"
setup_kubernetes $1 $2
fi

echo "Updating helm in server side..."
helm init --upgrade || true
kubectl rollout status deployment tiller-deploy -n kube-system || true
echo "Initializing helm..."
setup_tls $1
setup_helm $1 $2
setup_repos $1

}