Skip to content
This repository was archived by the owner on Jan 13, 2024. It is now read-only.

Commit 6a29e62

Browse files
abhinavrauAbhinav Raubharathkkbmorgante
authored
feat: Hub registration using kubeconfig and labels support (terraform-google-modules#785)
* initial support for using kubecontext for hub registration * Tested with GKE using kubectl * Tested with GKE using kubectl * Fixed typo in README * Fixed formatting errors * Fixed formatting errors * Fixed formatting and renamed example to be more consistent * Fixed formatting and renamed example to be more consistent * remove test files * fixed typo in README * use a flag to switch gke vs kubeconfig instead of having two scripts * Update modules/hub/scripts/gke_hub_registration.sh specify PROJECT_ID to be more specific Co-authored-by: Bharath KKB <bharathkrishnakb@gmail.com> * Update modules/hub/scripts/gke_hub_unregister.sh fix number of arguments check Co-authored-by: Bharath KKB <bharathkrishnakb@gmail.com> * update simple_zonal_with_hub_kubeconfig to use kind cluster Co-authored-by: Abhinav Rau <arau@google.com> Co-authored-by: Bharath KKB <bharathkrishnakb@gmail.com> Co-authored-by: Morgante Pell <morgantep@google.com>
1 parent 32db990 commit 6a29e62

File tree

10 files changed

+236
-14
lines changed

10 files changed

+236
-14
lines changed
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
# Kind Cluster Registered using kubeconfig
2+
3+
This example illustrates how to register a non-GKE Kubernetes Cluster with [Anthos](https://cloud.google.com/anthos/multicluster-management/environs) a.k.a Attached cluster.
4+
5+
It creates a [kind](https://kind.sigs.k8s.io/) cluster, sets current kubecontext to the cluster and registers the cluster using the [Hub registration module](../../modules/hub).
6+
7+
<!-- BEGINNING OF PRE-COMMIT-TERRAFORM DOCS HOOK -->
8+
## Inputs
9+
10+
| Name | Description | Type | Default | Required |
11+
|------|-------------|------|---------|:--------:|
12+
| project\_id | The project ID (environ) to register the cluster in | `any` | n/a | yes |
13+
14+
## Outputs
15+
16+
| Name | Description |
17+
|------|-------------|
18+
| kubernetes\_endpoint | Kube API endpoint for the kind cluster |
19+
20+
<!-- END OF PRE-COMMIT-TERRAFORM DOCS HOOK -->
21+
22+
To provision this example, run the following from within this directory:
23+
- `terraform init` to get the plugins
24+
- `terraform plan` to see the infrastructure plan
25+
- `terraform apply` to apply the infrastructure build
26+
- `terraform destroy` to destroy the built infrastructure
27+
28+
Example:
29+
30+
```
31+
terraform init
32+
33+
terraform apply \
34+
-var project_id=${PROJECT} \
35+
```
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
/**
2+
* Copyright 2018 Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
module "hub" {
18+
source = "../../modules/hub"
19+
project_id = var.project_id
20+
location = "remote"
21+
cluster_name = kind_cluster.test-cluster.name
22+
cluster_endpoint = kind_cluster.test-cluster.endpoint
23+
gke_hub_membership_name = kind_cluster.test-cluster.name
24+
gke_hub_sa_name = "sa-for-kind-cluster-membership"
25+
use_kubeconfig = true
26+
labels = "testlabel=usekubecontext"
27+
}
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
/**
2+
* Copyright 2018 Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
terraform {
18+
required_providers {
19+
kind = {
20+
source = "kyma-incubator/kind"
21+
version = "0.0.6"
22+
}
23+
}
24+
}
25+
provider "kind" {}
26+
27+
# creating a cluster with kind of the name "test-cluster" with kubernetes version v1.18.4 and two nodes
28+
resource "kind_cluster" "test-cluster" {
29+
name = "test-cluster"
30+
node_image = "kindest/node:v1.18.4"
31+
wait_for_ready = true
32+
kind_config {
33+
kind = "Cluster"
34+
api_version = "kind.x-k8s.io/v1alpha4"
35+
node {
36+
role = "control-plane"
37+
}
38+
node {
39+
role = "worker"
40+
}
41+
}
42+
provisioner "local-exec" {
43+
command = "kubectl config set-context kind-test-cluster"
44+
}
45+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
/**
2+
* Copyright 2018 Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
output "kubernetes_endpoint" {
18+
value = kind_cluster.test-cluster.endpoint
19+
description = "Kube API endpoint for the kind cluster"
20+
}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
/**
2+
* Copyright 2018 Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
variable "project_id" {
18+
description = "The project ID (environ) to register the cluster in"
19+
}

modules/hub/README.md

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ Specifically, this module automates the following steps for [registering a clust
66

77
## Usage
88

9-
There is a [full example](../../examples/simple_zonal_with_asm) provided. Simple usage is as follows:
9+
There is [GKE full example](../../examples/simple_zonal_with_asm) and a [Generic K8s example](../../examples/simple_zonal_with_hub_kubeconfig) provided. Simple usage is as follows:
1010

1111
```tf
1212
module "hub" {
@@ -37,13 +37,15 @@ To deploy this config:
3737
| cluster\_name | The unique name to identify the cluster in ASM. | `string` | n/a | yes |
3838
| enable\_gke\_hub\_registration | Enables GKE Hub Registration when set to true | `bool` | `true` | no |
3939
| gcloud\_sdk\_version | The gcloud sdk version to use. Minimum required version is 293.0.0 | `string` | `"296.0.1"` | no |
40-
| gke\_hub\_membership\_name | Memebership name that uniquely represents the cluster being registered on the Hub | `string` | `"gke-hub-membership"` | no |
40+
| gke\_hub\_membership\_name | Membership name that uniquely represents the cluster being registered on the Hub | `string` | `"gke-hub-membership"` | no |
4141
| gke\_hub\_sa\_name | Name for the GKE Hub SA stored as a secret `creds-gcp` in the `gke-connect` namespace. | `string` | `"gke-hub-sa"` | no |
42+
| labels | Comma separated labels in the format name=value to apply to cluster in the GCP Console. | `string` | `""` | no |
4243
| location | The location (zone or region) this cluster has been created in. | `string` | n/a | yes |
4344
| module\_depends\_on | List of modules or resources this module depends on. | `list` | `[]` | no |
4445
| project\_id | The project in which the resource belongs. | `string` | n/a | yes |
4546
| sa\_private\_key | Private key for service account base64 encoded. Required only if `use_existing_sa` is set to `true`. | `string` | `null` | no |
4647
| use\_existing\_sa | Uses an existing service account to register membership. Requires sa\_private\_key | `bool` | `false` | no |
48+
| use\_kubeconfig | Use existing kubeconfig to register membership. Set this to true for non GKE clusters. Assumes kubectl context is set to cluster to register. | `bool` | `false` | no |
4749
| use\_tf\_google\_credentials\_env\_var | Optional GOOGLE\_CREDENTIALS environment variable to be activated. | `bool` | `false` | no |
4850

4951
## Outputs

modules/hub/main.tf

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,12 @@
1616

1717
locals {
1818
gke_hub_sa_key = var.use_existing_sa ? var.sa_private_key : google_service_account_key.gke_hub_key[0].private_key
19+
20+
is_gke_flag = var.use_kubeconfig ? 0 : 1
21+
create_cmd_gke_entrypoint = "${path.module}/scripts/gke_hub_registration.sh"
22+
create_cmd_gke_body = "${local.is_gke_flag} ${var.gke_hub_membership_name} ${var.location} ${var.cluster_name} ${local.gke_hub_sa_key} ${var.project_id} ${var.labels}"
23+
destroy_gke_entrypoint = "${path.module}/scripts/gke_hub_unregister.sh"
24+
destroy_gke_body = "${local.is_gke_flag} ${var.gke_hub_membership_name} ${var.location} ${var.cluster_name} ${var.project_id}"
1925
}
2026

2127
data "google_client_config" "default" {
@@ -50,8 +56,8 @@ module "gke_hub_registration" {
5056
use_tf_google_credentials_env_var = var.use_tf_google_credentials_env_var
5157
module_depends_on = concat([var.cluster_endpoint], var.module_depends_on)
5258

53-
create_cmd_entrypoint = "${path.module}/scripts/gke_hub_registration.sh"
54-
create_cmd_body = "${var.gke_hub_membership_name} ${var.location} ${var.cluster_name} ${local.gke_hub_sa_key} ${var.project_id}"
55-
destroy_cmd_entrypoint = "gcloud"
56-
destroy_cmd_body = "container hub memberships unregister ${var.gke_hub_membership_name} --gke-cluster=${var.location}/${var.cluster_name} --project ${var.project_id}"
59+
create_cmd_entrypoint = local.create_cmd_gke_entrypoint
60+
create_cmd_body = local.create_cmd_gke_body
61+
destroy_cmd_entrypoint = local.destroy_gke_entrypoint
62+
destroy_cmd_body = local.destroy_gke_body
5763
}

modules/hub/scripts/gke_hub_registration.sh

Lines changed: 25 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -15,16 +15,18 @@
1515

1616
set -e
1717

18-
if [ "$#" -lt 4 ]; then
18+
if [ "$#" -lt 5 ]; then
1919
>&2 echo "Not all expected arguments set."
2020
exit 1
2121
fi
2222

23-
MEMBERSHIP_NAME=$1
24-
CLUSTER_LOCATION=$2
25-
CLUSTER_NAME=$3
26-
SERVICE_ACCOUNT_KEY=$4
27-
PROJECT_ID=$5
23+
GKE_CLUSTER_FLAG=$1
24+
MEMBERSHIP_NAME=$2
25+
CLUSTER_LOCATION=$3
26+
CLUSTER_NAME=$4
27+
SERVICE_ACCOUNT_KEY=$5
28+
PROJECT_ID=$6
29+
LABELS=$7
2830

2931
#write temp key, cleanup at exit
3032
tmp_file=$(mktemp)
@@ -33,4 +35,20 @@ trap "rm -rf $tmp_file" EXIT
3335
base64 --help | grep "\--decode" && B64_ARG="--decode" || B64_ARG="-d"
3436
echo "${SERVICE_ACCOUNT_KEY}" | base64 ${B64_ARG} > "$tmp_file"
3537

36-
gcloud container hub memberships register "${MEMBERSHIP_NAME}" --gke-cluster="${CLUSTER_LOCATION}"/"${CLUSTER_NAME}" --service-account-key-file="${tmp_file}" --project="${PROJECT_ID}" --quiet
38+
if [[ ${GKE_CLUSTER_FLAG} == 1 ]]; then
39+
echo "Registering GKE Cluster."
40+
gcloud container hub memberships register "${MEMBERSHIP_NAME}" --gke-cluster="${CLUSTER_LOCATION}"/"${CLUSTER_NAME}" --service-account-key-file="${tmp_file}" --project="${PROJECT_ID}" --quiet
41+
else
42+
echo "Registering a non-GKE Cluster. Using current-context to register Hub membership."
43+
#Get the kubeconfig
44+
CONTEXT=$(kubectl config current-context)
45+
gcloud container hub memberships register "${MEMBERSHIP_NAME}" --context="${CONTEXT}" --service-account-key-file="${tmp_file}" --project="${PROJECT_ID}" --quiet
46+
fi
47+
48+
49+
# Add labels to the registered cluster
50+
if [ -z ${LABELS+x} ]; then
51+
echo "No hub labels to apply."
52+
else
53+
gcloud container hub memberships update "${MEMBERSHIP_NAME}" --update-labels "$LABELS" --project="${PROJECT_ID}"
54+
fi
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
#!/bin/bash
2+
# Copyright 2018 Google LLC
3+
#
4+
# Licensed under the Apache License, Version 2.0 (the "License");
5+
# you may not use this file except in compliance with the License.
6+
# You may obtain a copy of the License at
7+
#
8+
# http://www.apache.org/licenses/LICENSE-2.0
9+
#
10+
# Unless required by applicable law or agreed to in writing, software
11+
# distributed under the License is distributed on an "AS IS" BASIS,
12+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
# See the License for the specific language governing permissions and
14+
# limitations under the License.
15+
16+
set -e
17+
18+
if [ "$#" -lt 5 ]; then
19+
>&2 echo "Not all expected arguments set."
20+
exit 1
21+
fi
22+
23+
GKE_CLUSTER_FLAG=$1
24+
MEMBERSHIP_NAME=$2
25+
CLUSTER_LOCATION=$3
26+
CLUSTER_NAME=$4
27+
PROJECT_ID=$5
28+
29+
30+
31+
if [[ ${GKE_CLUSTER_FLAG} == 1 ]]; then
32+
echo "Un-Registering GKE Cluster."
33+
gcloud container hub memberships unregister "${MEMBERSHIP_NAME}" --gke-cluster="${CLUSTER_LOCATION}"/"${CLUSTER_NAME}" --project "${PROJECT_ID}"
34+
else
35+
echo "Un-Registering a non-GKE Cluster. Using current-context to unregister Hub membership."
36+
#Get Current context
37+
CONTEXT=$(kubectl config current-context)
38+
gcloud container hub memberships unregister "${MEMBERSHIP_NAME}" --context="${CONTEXT}" --project="${PROJECT_ID}"
39+
fi

modules/hub/variables.tf

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ variable "gke_hub_sa_name" {
5959
}
6060

6161
variable "gke_hub_membership_name" {
62-
description = "Memebership name that uniquely represents the cluster being registered on the Hub"
62+
description = "Membership name that uniquely represents the cluster being registered on the Hub"
6363
type = string
6464
default = "gke-hub-membership"
6565
}
@@ -81,3 +81,14 @@ variable "module_depends_on" {
8181
type = list
8282
default = []
8383
}
84+
85+
variable "use_kubeconfig" {
86+
description = "Use existing kubeconfig to register membership. Set this to true for non GKE clusters. Assumes kubectl context is set to cluster to register."
87+
default = false
88+
}
89+
90+
variable "labels" {
91+
description = "Comma separated labels in the format name=value to apply to cluster in the GCP Console."
92+
type = string
93+
default = ""
94+
}

0 commit comments

Comments
 (0)