#!/bin/bash
# Copyright 2025, VMware by Broadcom Corporation, All rights reserved.
#set -e

GreenLetter() {
    echo -e "\033[32m $1 \033[0m"
}
RedLetter() {
    echo -e "\033[31m $1 \033[0m"
}
YellowLetter() {
    echo -e "\033[33m $1 \033[0m"
}

TCAVER=${TCAVERSION:-"2.3"}
mc_name=""
wc_name=""
mc_kubeconfig_path=""
wc_kubeconfig_path=""
declare -A CLUSTERS_ARRAY
retry_count=12

# 2 temporary file used to create overlay secret will be deleted after the script exitd
nc_cert_overlay_file="nc_cert_overlay_file.yaml"
nc_webhook_overlay_file="nc_webhook_overlay_file.yaml"

temporary_files=()

parse_parameters() {
  local options
  options=$(getopt -o "m:w:q" --long "mc_name:,wc_name:query" -- "$@")

  if [[ $? -ne 0 ]]; then
    echo "Error parsing options." >&2
    return 1
  fi

  eval set -- "$options"

  while true; do
    case "$1" in
      -q|--query)
      list_clusters
      exit 0
      ;;
      -m|--mc_name) mc_name="$2"; shift 2 ;;
      -w|--wc_name) wc_name="$2"; shift 2 ;;
      --) shift; break ;;
      *) echo "Invalid option: $1" >&2; return 1 ;;
    esac
  done
  return 0
}

# Function for usage
function usage() {
    echo "Usage: $0 -i <image_url> -m <mc_name> -w <wc_name>"
    echo "Options:"
    echo "    -q, --query        List current management and workload clusters under this TCA-CP"
    echo "    -m, --mc_name      MC name value, mc_name is required"
    echo "    -w, --wc_name      WC name value, if wc_name is not provided, will go through all workload clusters under the management cluster"
    exit 1
}

prepare_kubeconfig() {
    wc_name=$1
    if ! GetWcKubeconfig "$mc_kubeconfig_path" "$wc_name"; then
        echo ""
        RedLetter "Failed to get kubeconfig for workload cluster $wc_name"
        return 1
    fi
    export KUBECONFIG=$wc_kubeconfig_path
    kubectl get nodes -o wide >/dev/null
    if [ $? -ne 0 ]; then
        echo ""
        RedLetter "Failed to get nodes for workload cluster $wc_name"
        cmd="kubectl get nodes -o wide"
        echo $cmd
        eval "$cmd"
        return 1
    fi
}


# store mc kubeconfig to $mc_kubeconfig_path
get_v1_wc_list (){
    local mc_name=$1
    if [[ "$TCAVER" != "2.3" ]]; then
        return  0
    fi
    local kbs_pod_ip="127.0.0.1"
    local mc_id=$(curl -s "http://${kbs_pod_ip}:8888/api/v1/managementclusters" | jq -r ".[] | select(.clusterName == \"${mc_name}\") | .id")
    if [ $? -ne 0 ]; then
        echo "Failed to get management cluster ID"
        return 1
    fi

    if [ -z "${mc_id}" ]; then
        RedLetter "mc_id is null, Please check if ${mc_name} is a valid management cluster name"
        return 1
    fi

    v1_wc_list=$(curl -s "http://${kbs_pod_ip}:8888/api/v1/workloadclusters"| jq -r "[.[] | select(.tkgMgmtClusterId == \"${mc_id}\") | .clusterName ]| join(\",\")")
    if [ $? -ne 0 ]; then
        RedLetter "Failed to get v1 wc cluster mc ${mc_name}"
        return 1
    fi

    YellowLetter "==== Detected V1 workload clusters for ${mc_name}: $v1_wc_list"
    return 0
}

# store mc kubeconfig to $mc_kubeconfig_path
GetMcKubeconfig (){
    local mc_name=$1
    local local_mc_kubeconfig_path="/tmp/${mc_name}-kubeconfig"
    temporary_files+=("$local_mc_kubeconfig_path")

    local kbs_pod_ip="127.0.0.1"
    if [[ "$TCAVER" != "2.3" ]]; then
        kbs_pod_ip=$(kubectl get pods -n tca-cp-cn -l app=k8s-bootstrapper -o json | jq -r '.items[0].status.podIP')
    fi

    local mc_id=$(curl -s "http://${kbs_pod_ip}:8888/api/v1/managementclusters" | jq -r ".[] | select(.clusterName == \"${mc_name}\") | .id")
    if [ $? -ne 0 ]; then
        echo "Failed to get management cluster ID"
        return 1
    fi

    if [ -z "${mc_id}" ]; then
        RedLetter "mc_id is null, Please check if ${mc_name} is a valid management cluster name"
        return 1
    fi
    echo "Get mc id ${mc_id}"

    local mc_kubeconfig=$(curl -s "http://${kbs_pod_ip}:8888/api/v1/managementcluster/${mc_id}/kubeconfig")
    if [ $? -ne 0 ]; then
        RedLetter "Failed to get kubeconfig for mc ${mc_name}"
        return 1
    fi

    echo "${mc_kubeconfig}" > "${local_mc_kubeconfig_path}"
    mc_kubeconfig_path="${local_mc_kubeconfig_path}"
    return 0
}

GetWcKubeconfig() {
    local local_mc_kubeconfig_path=$1
    local wc_name=$2
    local local_wc_kubeconfig_path="/tmp/${wc_name}-kubeconfig"
    temporary_files+=("$local_wc_kubeconfig_path")

    KUBECONFIG=${local_mc_kubeconfig_path} kubectl get secret -n ${wc_name} ${wc_name}-kubeconfig >/dev/null 2>&1
    if [ $? -ne 0 ]; then
        RedLetter "Failed to get kubeconfig for workload cluster ${wc_name}"
        exit 1
    fi
    local wc_kubeconfig=$(KUBECONFIG=${local_mc_kubeconfig_path} kubectl get secret -n ${wc_name} ${wc_name}-kubeconfig -o jsonpath="{.data.value}" 2>/dev/null | base64 -d > ${local_wc_kubeconfig_path})
    #echo "Stored wc kubeconfig to ${local_wc_kubeconfig_path}"
    wc_kubeconfig_path="${local_wc_kubeconfig_path}"
    return 0
}

prepare_vm_overlay_file() {
    cat >$vm_cert_overlay_file <<EOF
---
#@ load("@ytt:overlay", "overlay")
#@overlay/match by=overlay.and_op(overlay.subset({"kind": "Secret"}), overlay.subset({"metadata": {"name": "vmconfig-certs"}}))
---
data:
  tls.crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUVHakNDQXdLZ0F3SUJBZ0lVVzBkcDU0QmE2VUJNblBzVFcxYnc1cHRZZXhzd0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXhNekF5TWpVd01Gb1hEVE0xTURVeE1UQXlNalV3TUZvd2J6RUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14RXpBUkJnTlZCQXNUQ2t0MVltVnlibVYwWlhNeEVqQVFCZ05WCkJBTVRDV0ZrYldsemMybHZiakNDQVNJd0RRWUpLb1pJaHZjTkFRRUJCUUFEZ2dFUEFEQ0NBUW9DZ2dFQkFKN0kKUkRxSlpoMEdZMTV4TVUzUlRvdkpiR2VhRERXWEtYQmplb3JaczlNSDFNQ1pvN0NodzYvOVJvR1BtNHFoZExESQpFVldabVNWWDUwYS81cXVjbzVHQzlBYkdMMFROZHpYK0lIMDg4WUxrM1VUcGh2WWRWWGlaVE0xakw5STF0V2VHClJKelRiYlJsWmVacHpzK1o3UHI2WngzeXp2S2xyOVJ5QTY5QzdZcHNKdW84NFM3elpGMU5kdmhsM3RUdk9Kam0KZlRNTUhWQ1VSWW9OdW1qeFpOeTBSMEZEQ21IZERmMEtQOW5MSDdaR0s0UDUvaSsvZVdUZks0YVNYd3paN05RMApycGRhWVdtcDdrTy9rRmxGcmoyYWQrWGtHTFE3YXdjSnhMTjl3dHlMV2hmd3gzczBNUUJjQUl3NWxnc1RiaWwzCk1odUxtY3o3dXhYWm5tTEs4OEVDQXdFQUFhT0J0RENCc1RBT0JnTlZIUThCQWY4RUJBTUNCYUF3SFFZRFZSMGwKQkJZd0ZBWUlLd1lCQlFVSEF3RUdDQ3NHQVFVRkJ3TUNNQXdHQTFVZEV3RUIvd1FDTUFBd0hRWURWUjBPQkJZRQpGSUQ1SEtQUDQ2RGVmMmJzcWErZW1vVElpbTdnTUI4R0ExVWRJd1FZTUJhQUZMYVJDQnQ4UVp3NitSU2xCWDNXCmplRmRsNGEwTURJR0ExVWRFUVFyTUNtQ0ozWnRZMjl1Wm1sbkxYZGxZbWh2YjJzdGMyVnlkbWxqWlM1MFkyRXQKYzNsemRHVnRMbk4yWXpBTkJna3Foa2lHOXcwQkFRc0ZBQU9DQVFFQW9CbnhsTlFSbTNobHBwNkc1c1E2MUdFdwp6cmUwbE9DeWNVOHpla2d1K1NSMWZ6SVkzeWcxZWg0VldYUFBpOXZmcVRYMTNDaFp6OWNtOVFuQzdjQm1GZkNQCm9ndElNR1ZDWDZ3VldBMGtrdnN1Y0I0bm8yMFlFQ2YxUzFnZ0Z0cllFcWEvaDVwajRPdnBIdm1MYkVURE9HSFAKZmN3MDJ5Mk1SZGNaK2ZHUkd4Zm5QRG01clVrZ2pNWklFOStPOHVCLzl1aitoRzk2L05JbkFLR2piS1ZlcU5Hcgp0Q3ErQTdoL2UzYktacTU5K0s2RGFicFVyakdKdHlOZytIYW41cFErQlM3anMweHBKNndlYjBCMWp0MGVjQ0FCClN3czJFR3RjbzdJNzBzNS9VQU5VWjhkY0JleDZTb1RJNktUUUdOWVZ0c0Iya1dUWGFLQ3hUZUFXZnpGUjZBPT0KLS0tLS1FTkQgQ0VSVElGSUNBVEUtLS0tLQo=
  tls.key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlFcEFJQkFBS0NBUUVBbnNoRU9vbG1IUVpqWG5FeFRkRk9pOGxzWjVvTU5aY3BjR042aXRtejB3ZlV3Sm1qCnNLSERyLzFHZ1krYmlxRjBzTWdSVlptWkpWZm5Sci9tcTV5amtZTDBCc1l2Uk0xM05mNGdmVHp4Z3VUZFJPbUcKOWgxVmVKbE16V012MGpXMVo0WkVuTk50dEdWbDVtbk96NW5zK3ZwbkhmTE84cVd2MUhJRHIwTHRpbXdtNmp6aApMdk5rWFUxMitHWGUxTzg0bU9aOU13d2RVSlJGaWcyNmFQRmszTFJIUVVNS1lkME4vUW8vMmNzZnRrWXJnL24rCkw3OTVaTjhyaHBKZkRObnMxRFN1bDFwaGFhbnVRNytRV1VXdVBacDM1ZVFZdER0ckJ3bkVzMzNDM0l0YUYvREgKZXpReEFGd0FqRG1XQ3hOdUtYY3lHNHVaelB1N0ZkbWVZc3J6d1FJREFRQUJBb0lCQUhvc2lHc3VLN2Nyb2l3YQpGcURVNjRZZHYxN2NKb2Jad0JYdFJXNHZZdkYrOWhJWVpkNVVLaGx4WGQzMUhPNkhteDBuWkVja1A3Vi9OTUs0CmlBb0dKY21pSkpoTnlETTlrWHVuQldLNEVQRHhudHdXZ0RWQmp2R1RxNGZoeVBzTFBvRGd6RXlMVnI5V3doaVAKMDRUajRIZWhVdFMxYnMwLzlkSVd4SVVIajNWUTJpWUFkd2ZibHJTK1ZaNm5QNXFNWlJEbjQ4ZlhDV25rMmptcQpuUmorWGl4NmpVdXlCbVNGWWYwUWxQbFFTY1NNaUN4N3Zmd1hrMjRFOXllOGgrY0xYcXA3c1phRndHbU44dVF2CjdLSnQ4cFJuOEVTTTFFclJta1phREdSZTJFcVM0cm92ZjZSZy9hdUVNdTNhMjdKTk5NcTZvVWlhZDRpekZsSHAKS21ETmwxMENnWUVBenVUTjhpSnJlN0gzL3U1ZmxLZjBiZ1F0Q1pWZ2t6MkMxTEFReGFVU040ZUFzRW81Qm9PWApyV0I3bTFKaXNJckpZL0lsR1BoWWRqNitXYzhvQU51dEkwVmNhbE9TUHVINjRjeFQ1QkwzemY4U1dNcHYzNUhZCmxQWHBSUkxRa0R5WmpaNzBUbHJDYUpGRCtFTXIycVd4Tm5zVlJRVVkwdzJFUjU2c29iOW14THNDZ1lFQXhIZ2gKeDF6NDV1ZnUvclprZ0RacGZWS3lvcUhRUklFbUZQVGVxTzZqNFlvT1RZcEx0aWIxcFdYWDRoMC90czFhMENvUwpDOWh2a2FIUzRHZWJiak51dzgvZFdSZll4WGs2anNjNHFKelJRN3EvNFVWdXFrRUEvUXV0bGJ2N2pXc2dUellLCkV3azRmaVVUdWFDbStRdkd1c0t2M050QmhGZzBXUXZ6RGtqcVg3TUNnWUFqTmtuZTFnRFpFcGNVcWxsV0lhZTIKT2J1NGo5WForWFFVNHNwWCtSbzZuVE5IemJvYTQ3YWk2WExnSW90dFpKR1dFeFpCUTdNNm5MOGs1ZDczRm14SApQbnpXRTljbUlLdmtWalJJOHZsOTg5V1ppd3F6VUUwK1BRUXduMTBqejB5TEQreWdrVTNaSWpBaFJyMWwveUZFCkZucXVQb25WRWMzYnFxUFMrNUp3RlFLQmdRQ0xjRHVCRkJJdlIzTU80Z0pJSU5ZVHRRckZkQlN0V2YvZUpjQ1YKb3ZFNjFGRzhaS2ZCZXJzakRUbi82QVJkU0Rmb3Y4TVpGeDV2L0tyK3kybTc5OUxvTkhJRGxuSXFEUlVyV21keQovQUZsa1hnM2VLREhRdVZoc3RVYkRWVEdsTDVVbWFUaXg4dUpjK1VnL00wa3VsL3NFdHJmNDlrSEJkYjVVQXJNCkc2SUVFd0tCZ1FDUFk3OGxoUnVrS1ZXakk3MzI0Q21rUmlUZ3A5aFd5RHFKc1Q5bWdBS3A5dFlpMnJYZGVHbXEKYmxpYWNMRzM0NkU1emxkM3I1RlFzZ1RMNWltS1Zjd3V2K1B0QTRiMnlpKzJwTWUxWHF6YUlBNlRqclVGNGNueQphY1FMd0NBa0NyTEgzMW1jL2N6NW8wWHlzWmpQdURRU3d6bGs2V09Ucm9kVFBwdDlzeFhnV0E9PQotLS0tLUVORCBSU0EgUFJJVkFURSBLRVktLS0tLQo=
EOF
    cat >$vm_webhook_overlay_file <<EOF
---
#@ load("@ytt:overlay", "overlay")
#@overlay/match by=overlay.and_op(overlay.subset({"kind": "ValidatingWebhookConfiguration"}),overlay.subset({"metadata": {"name": "vmconfig-validator"}}),overlay.not_op(overlay.subset({"metadata":{"annotations":{"cert-manager.io/inject-ca-from": "tca-system/vmconfig-webhook-server-cert"}}}))), missing_ok=True
---
webhooks:
  #@overlay/match by="name",expects="1+"
  - name: validator.vmconfig.acm.vmware.com
    clientConfig:
      caBundle: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSURvRENDQW9pZ0F3SUJBZ0lVYnRpN2NkR0FZRCtTZjdDcDU3SWl4K1NXd293d0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXhNekF5TWpVd01Gb1hEVE13TURVeE1qQXlNalV3TUZvd2FERUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14Q3pBSkJnTlZCQXNUQWtOQk1STXdFUVlEVlFRREV3cExkV0psCmNtNWxkR1Z6TUlJQklqQU5CZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUF1RDMxZXhjcmhKRDMKVitMUUlsdjBtcTl3MGpTNmQ5Q0kza0R4dS9rVWEvSUJtS3R3UnhPMXlpNlNndnVtaSszU0prSUNHV1hyQXRWLwppeGUyTk94QmZTbWRlT012YVBEQXd3NHY0RHZURGtIUmFsZUZQd0k0Z2JzTStMRkE3R0w0RDZ4WEFBL3RaYXF3Cnc0eUVDeWV4ZEs5OW14RlN2cUpqbGh2bU1sZWxWNUdveDF1enJHRkhyVHhCd24xTERvUVoxOWVORC9pZEgyMUgKN3lkL1plQXRQVnRTZVFXaW41Unhrc1ZLVkFCcEJMODhxNnVidnhCekltbjBWV2RhNEU3S3o1Mm1lcEVlSXg4cwpIKzB1eDViVWVKNExBZFpTQW9SdTJlNmtzVmZQM1dBTmxuME1xOUpBTG9PaFFacnZoUHMrKy85MWhTMlNsOC9zCnFvZktpOWxydXdJREFRQUJvMEl3UURBT0JnTlZIUThCQWY4RUJBTUNBUVl3RHdZRFZSMFRBUUgvQkFVd0F3RUIKL3pBZEJnTlZIUTRFRmdRVXRwRUlHM3hCbkRyNUZLVUZmZGFONFYyWGhyUXdEUVlKS29aSWh2Y05BUUVMQlFBRApnZ0VCQUcrNXpqdjlOOXU2NzhOSEs5L2RxVXdhdkxTcmREMzBteExPY25ybUpxQVB5NWl1d0JIS1BJVnZEaTFTCkNjQ3c2cDN6NHNLdHBKMnNKKzlXVllWUWxhVHliVnVKZG1pNVUzT2o1VEQ4dE1KaDJnVHNKOHZ4MmUrZHR1Y3kKa0F4OWt0MjJ4cll3di9GSHB0bU0zSjhGZnhjUlcwTGZveVErbkVRVWpuZTNXRTRrMkV2WCsyWVZSTHhvU1ZCYgpNaU1yZWFVVDlKMno5T013N3dKVmp6a1pCN09IVjhweWUzQncwckNHTzBKK0dodER2SEQ4VFBjOGtTZEM3NTJ6CldIRUplSEs3SndFeG1ESFA4c3JwN1pyTmgva1lCakxHamNXZlNKWnJ1SVFVNjdXamlidUJGKzI4Y3VhU2Z1b2kKTXd6YnBGR3BpNXhyZmMvMmp2YVd0U21pVVQ0PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==
EOF
    cat >$vm_webhook_default_overlay_file <<EOF
---
#@ load("@ytt:overlay", "overlay")
#@overlay/match by=overlay.and_op(overlay.subset({"kind": "MutatingWebhookConfiguration"}),overlay.subset({"metadata": {"name": "vmconfig-defaulter"}}),overlay.not_op(overlay.subset({"metadata":{"annotations":{"cert-manager.io/inject-ca-from": "tca-system/vmconfig-webhook-server-cert"}}}))), missing_ok=True
---
webhooks:
  #@overlay/match by="name",expects="1+"
  - name: defaulter.vmconfig.acm.vmware.com
    clientConfig:
      caBundle: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSURvRENDQW9pZ0F3SUJBZ0lVYnRpN2NkR0FZRCtTZjdDcDU3SWl4K1NXd293d0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXhNekF5TWpVd01Gb1hEVE13TURVeE1qQXlNalV3TUZvd2FERUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14Q3pBSkJnTlZCQXNUQWtOQk1STXdFUVlEVlFRREV3cExkV0psCmNtNWxkR1Z6TUlJQklqQU5CZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUF1RDMxZXhjcmhKRDMKVitMUUlsdjBtcTl3MGpTNmQ5Q0kza0R4dS9rVWEvSUJtS3R3UnhPMXlpNlNndnVtaSszU0prSUNHV1hyQXRWLwppeGUyTk94QmZTbWRlT012YVBEQXd3NHY0RHZURGtIUmFsZUZQd0k0Z2JzTStMRkE3R0w0RDZ4WEFBL3RaYXF3Cnc0eUVDeWV4ZEs5OW14RlN2cUpqbGh2bU1sZWxWNUdveDF1enJHRkhyVHhCd24xTERvUVoxOWVORC9pZEgyMUgKN3lkL1plQXRQVnRTZVFXaW41Unhrc1ZLVkFCcEJMODhxNnVidnhCekltbjBWV2RhNEU3S3o1Mm1lcEVlSXg4cwpIKzB1eDViVWVKNExBZFpTQW9SdTJlNmtzVmZQM1dBTmxuME1xOUpBTG9PaFFacnZoUHMrKy85MWhTMlNsOC9zCnFvZktpOWxydXdJREFRQUJvMEl3UURBT0JnTlZIUThCQWY4RUJBTUNBUVl3RHdZRFZSMFRBUUgvQkFVd0F3RUIKL3pBZEJnTlZIUTRFRmdRVXRwRUlHM3hCbkRyNUZLVUZmZGFONFYyWGhyUXdEUVlKS29aSWh2Y05BUUVMQlFBRApnZ0VCQUcrNXpqdjlOOXU2NzhOSEs5L2RxVXdhdkxTcmREMzBteExPY25ybUpxQVB5NWl1d0JIS1BJVnZEaTFTCkNjQ3c2cDN6NHNLdHBKMnNKKzlXVllWUWxhVHliVnVKZG1pNVUzT2o1VEQ4dE1KaDJnVHNKOHZ4MmUrZHR1Y3kKa0F4OWt0MjJ4cll3di9GSHB0bU0zSjhGZnhjUlcwTGZveVErbkVRVWpuZTNXRTRrMkV2WCsyWVZSTHhvU1ZCYgpNaU1yZWFVVDlKMno5T013N3dKVmp6a1pCN09IVjhweWUzQncwckNHTzBKK0dodER2SEQ4VFBjOGtTZEM3NTJ6CldIRUplSEs3SndFeG1ESFA4c3JwN1pyTmgva1lCakxHamNXZlNKWnJ1SVFVNjdXamlidUJGKzI4Y3VhU2Z1b2kKTXd6YnBGR3BpNXhyZmMvMmp2YVd0U21pVVQ0PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==
EOF
}

prepare_overlay_file() {
    temporary_files+=("$nc_cert_overlay_file")
    temporary_files+=("$nc_webhook_overlay_file")
    cat >$nc_cert_overlay_file <<EOF
---
#@ load("@ytt:overlay", "overlay")
#@overlay/match by=overlay.and_op(overlay.subset({"kind": "Secret"}), overlay.subset({"metadata": {"name": "nodeconfig-certs"}}))
---
data:
  tls.crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUVGVENDQXYyZ0F3SUJBZ0lVZnk2RzI5Wmdxc1JrNmY1NTdieFF5aVVjRlVzd0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXdPVEE0TVRnd01Gb1hEVE0xTURVd056QTRNVGd3TUZvd2J6RUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14RXpBUkJnTlZCQXNUQ2t0MVltVnlibVYwWlhNeEVqQVFCZ05WCkJBTVRDV0ZrYldsemMybHZiakNDQVNJd0RRWUpLb1pJaHZjTkFRRUJCUUFEZ2dFUEFEQ0NBUW9DZ2dFQkFOWUsKNUZPM1ptMkhFNG16N2ZZcU1NR3VGSFl2QVNSN242b0NUc2JhQ2YwZGRTNy9Wei9rWnd5bFM0aVpJeWZqOVV0YQpFOXNpRkFPVndNdnhUYjJmT29CTVU4UUQ5bjBpTUVmb3NOSTM2N3ZsSEFLZ1lJNUR1bGFPODkwWURnQ0thRkhrCjYxZmlRdG9nSTRGajZEZ21zcXkwc3VJOWNRZDZrc3Jla3NwMjFNVUxpRkFoWUJtWHBVODdMTm1ZNjBJL0Y2Zk0KUXYrR3BpUU4vVHdsZmFtMnE4YWllWGhaUGU1MnlDN29EZHRQZk05cGpvOEdzYVdTVFF3YmM2WFlDWFhsYUNQNApOcTd4SHNMdEdwcG5BdXJLOGwzZVJJZW1HSGN2U1crRTk3N0NOUVBMeDBjNTVGOGZUdkE5bTg3RE5pTkZSbWcvCjV6RkhLczZyWm52c21DdWhKcmtDQXdFQUFhT0JyekNCckRBT0JnTlZIUThCQWY4RUJBTUNCYUF3SFFZRFZSMGwKQkJZd0ZBWUlLd1lCQlFVSEF3RUdDQ3NHQVFVRkJ3TUNNQXdHQTFVZEV3RUIvd1FDTUFBd0hRWURWUjBPQkJZRQpGTnRSbUdtcFBCOFExYVF5MmxndE1hblZoTkV5TUI4R0ExVWRJd1FZTUJhQUZHblpxM2lWMkJhTGZVeDNBbHdPCmZWT2VtazdBTUMwR0ExVWRFUVFtTUNTQ0ltNXZaR1ZqYjI1bWFXZDJZV3hwWkdGMGIzSXVkR05oTFhONWMzUmwKYlM1emRtTXdEUVlKS29aSWh2Y05BUUVMQlFBRGdnRUJBQkhmbTYzL0V4MG1oN1FFU1VUTkFuU2tDZ3dNeXAzSwoxTEsvVmp0ekVlT3AzUzQzaHYrOEh5NWgveXpNdGMwQ2lDYTMrblZTSW5RR3hESnprT2doVWtMa1hqUzJpRjNFCmlzTTQ3Ynd3MXMzSk5RMFQ5V0o0ZE5oYjlQdWtLeEg4Qk5adnVzWGRBTTM5MGtLOFhGY2UzRXptVDZwTFdRczQKMFZ5bENpVnpHUjFucDRFaCt3YldOQk53TTBoTGI1RFczRTAxaXBTRVdmdmsrNWhCR3liak1BeUg2RkhNcHlBLwp3SFNQejlrVXZSMFJzamw0aWlzVFJZMm5FV2IwNHVMQVJ4eUdXK2NqZU4xQXlDZ1NZTmMvRHQvTWdJcjVoRGo1CitiR1BDVGZndlQ2aHE1SW43S3IwR1FWb0h1Y2poUlV6ZDhLdlEvS0VzZmFZR01sODNOMGptTjA9Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K
  tls.key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlFcEFJQkFBS0NBUUVBMWdya1U3ZG1iWWNUaWJQdDlpb3d3YTRVZGk4QkpIdWZxZ0pPeHRvSi9SMTFMdjlYClArUm5ES1ZMaUprakorUDFTMW9UMnlJVUE1WEF5L0ZOdlo4NmdFeFR4QVAyZlNJd1IraXcwamZydStVY0FxQmcKamtPNlZvN3ozUmdPQUlwb1VlVHJWK0pDMmlBamdXUG9PQ2F5ckxTeTRqMXhCM3FTeXQ2U3luYlV4UXVJVUNGZwpHWmVsVHpzczJaanJRajhYcDh4Qy80YW1KQTM5UENWOXFiYXJ4cUo1ZUZrOTduYklMdWdOMjA5OHoybU9qd2F4CnBaSk5EQnR6cGRnSmRlVm9JL2cycnZFZXd1MGFtbWNDNnNyeVhkNUVoNllZZHk5SmI0VDN2c0kxQTh2SFJ6bmsKWHg5TzhEMmJ6c00ySTBWR2FEL25NVWNxenF0bWUreVlLNkVtdVFJREFRQUJBb0lCQUZqbGp5MGg1NzJuc3pxbQo2emNwRUxUd0t2bG16aytydElWMGplbFMxNEV6d2Q2eUdEZW1FaEtUZUVxVVo2Q0NzZmNJdzJSb3crMDFQaXkxCjNMYmJzZjFsTmdrY0tEeVNmWUR3S0xnMmw0YWpRajNwQkJFeUdlc25WaXRHZVZKS0tjZVJqeGtpRk9mcEh6WDMKRzVSdXBoakt0OXowN2NQUWFiVXVPY016RlcxOGVQc2lqaS9BblgybmRNa1Y1aVU1cHVMNWFNU1VTTUg0RjlpZwp5QWxQVHk0L3FXZlF2L25YSVZyczB3aWtFN05LR1NQdHFMZWlRYmp4a3YyRWRwWHFUY0trMklVSFpzTE1qbFZ3ClRtNEtNY29iU2JLQktiR2w4REk5Yk9KZjdYUmlKcFE0cmNObXRmaDhVaGFuR2lMZ1pDcmJGWWtiWk5YMXY4c0EKWWREb3FSMENnWUVBOXNWdW9RQ1Jqb05LUTlvSWwyTERteDc0RkROVm1TYmEwZ2d2SHVNTjg2NG5vaENiLy9XNwpaODFDWFR0bytxbVR6ek83QklzSDhvdE5tNXZublRHT1V4R0FQK2RuWmFMenRFOVYzSzFqYWFHdURoZHphRnNrCnk4eGR5am0vR2htV0szeFJ0WjRybjJoR2J0d0lxVHdORFJOMlBLNDNmc1ovQURocllvNEhKbThDZ1lFQTNnd2UKT2R4aGhpazQ1eHkycEdpVEM2RHVlMjVuQ3ZTRk1YWEdKeWNmK080R3VtZVBIdmR1MnA3SGdJTTk0NHRuVHNIagpyVWVWQ05PWVlFRGU0WnBFWG5pRXlCOFhlSWN6NFR6c3lrWEp1ZGloQUdoS0g3SE5xTkNjcGNSUi9QVFhTeXJ6ClRMb3h5MGkwRlRwL2VuVzJlQzhOUDRSRUNBQ0RHVkFQRzNuUjJWY0NnWUI4OXhaQzZpckw1S2lqRzdMbUZ0bS8Kb0RzNDM1WWxiSXU3ZVBHRHpxK3VDeTkrM3JKaE9HdWk4VXIrTTZ2QjVFWTUwNVNOaEdxTjVRVjBHOHQ2eXpHcgoxMXorLzR4WTUrQktHekw4QWNJcUovb2dvTGVNelRzaENXa2xrNEMzRXVYOU40T1pXWFAxMGJSNVIyd0xaNkdrClVZcTZ4KzdLZ0hLb0JlbzdpbmtNZVFLQmdRREJnbG9OSHN3MitWSEh4N1E4RDQ2bWdiZVVCaUR5NFNuNmNxTWYKbCs4N0oyVGhxa0tHUUNoeGloSmZJd0VhZm5DbnFEMWMwNWRFTy9MOVgwdGQzTzFjVHplWWw5QUNrQUZjZDVYOApxVmttQjI0NFJxcmllRGU4dVNEckxlNHR2c3FwaldLL0tUMGY1ZHBhN2NJTzNPc0tUaWNEaGFjc09oWUdSMGtECkx1VDh2UUtCZ1FEQ1RmSGVaREM2OGV0RCtwRk1zUWZ1VlhMMjg1dnJReE5qMndXaTVNK09jZmVjYmR3VFdZSjQKRGdFNnlGMXNsZGU2WmpEUFdWNTVQOERZSjhkbmFsMTRUZmdtRHhnakx3eVRSUFg4ODFiS1Vmbk9oVThveVBwMgpzbTNrV0MzWFNKNWViaktRNk0zdXM3aUNxM05QUDVQL1ZSUE4yV2xjRU9hMWhncUExZ1F4Umc9PQotLS0tLUVORCBSU0EgUFJJVkFURSBLRVktLS0tLQo=
EOF
    cat >$nc_webhook_overlay_file <<EOF
---
#@ load("@ytt:overlay", "overlay")
#@overlay/match by=overlay.and_op(overlay.subset({"kind": "ValidatingWebhookConfiguration"}), overlay.subset({"metadata": {"name": "nodeconfig-validator"}}))
---
webhooks:
  #@overlay/match by="name",expects="1+"
  - name: validator.nodeconfig.acm.vmware.com
    clientConfig:
      caBundle: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSURvRENDQW9pZ0F3SUJBZ0lVTXplWmU5MFArejlNd2R5amJXNnU1TGRGcmg4d0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXdPVEE0TVRnd01Gb1hEVE13TURVd09EQTRNVGd3TUZvd2FERUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14Q3pBSkJnTlZCQXNUQWtOQk1STXdFUVlEVlFRREV3cExkV0psCmNtNWxkR1Z6TUlJQklqQU5CZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUF6U3dtcDMrUVVCR24KTVU5R1dxelhtTlErbEZaYStmd1FBc2ZIczlpRE9DQ1N0cFEycVNyanFXRGhpWElmMTAwNFBHSkpJYk9hOFlpRApIaDdEWUg1TXBxSm9oVHhYWndqRzJmMFR5Q1BJVzVpTmo3ZlA1RWNrY0Q4dFJKMkF2bkE5RjdQOUg1SHJnV0lYCldYN2EvY0N3NlVmdERPaHdPVFlHVkdUYng0YkZud1pyTXk2UnNJN3NLb2JET0JFSExGQUZab0tyNGc4dnp5eXYKVUZudTEzYmpSSnh1OHVvNGxqWlpyUHkyUSsrbkE3NjlJdzJobEFtdExzUVVUbU9lY3dhM3VlMlY1M1FlSExoZQpsMUJFSXZRTU0yZ1U4UENSaytabGl0SlMrSFlkRVppQUJhQkVqdWtZMmF0a0cyNExQeUJzay8wQXlMTTdweTNHCjFrWXhkbVVWQ3dJREFRQUJvMEl3UURBT0JnTlZIUThCQWY4RUJBTUNBUVl3RHdZRFZSMFRBUUgvQkFVd0F3RUIKL3pBZEJnTlZIUTRFRmdRVWFkbXJlSlhZRm90OVRIY0NYQTU5VTU2YVRzQXdEUVlKS29aSWh2Y05BUUVMQlFBRApnZ0VCQUJPVURFOUdza1ZQMHVWTi94N1F2ZHBLR3VVc1ZSYVBIOWxEREIyakNyTkpDVFdzRDNhMTJ0d1I0WGVZClhOeHUyVEZuTHVaTVJRYndHWUJCZU0vRWhLaDRHdi9vVEQ2MjVseE9tbHlWcjZMbUpHQm1aQ0tFNGpySlFmTnYKUU9HVnp4NjIrR1M5ZkVxdmpJOG5IblhWdDFRZDd4OGlENkR1NXBzc1RFcTBPZTFYUnQ0Y3pLRXJUT2UyL3pRcgpmRHNVdHVzUS85MDhWWHhkZ0N2VHQ4Q01UR1p5OXo3VmRtbUJORlFscEVOeGRHTjNKKytldkE0c200YkUyeG5aCjZsdnFGaS8xWVlFdG9FbW80MEhhVEFsRUdsa1J3SGo4TFFlU1BBYkJxNUtYbmlHS3RDekV5ZDNDalp1QVU2YUwKWDNvd0RxQ0MrRVh6aG1xTVg5Z3ZMbjh5Sk5zPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==
EOF
}

create_secret_for_overlay() {
    kube_path=$1
    secret_name=$2
    overlay_yaml=$3
    KUBECONFIG=${kube_path} kubectl -n tca-system create secret generic $secret_name -o yaml --dry-run=client --from-file=$overlay_yaml | KUBECONFIG=${kube_path} kubectl apply -f -
    #echo "kubectl get secret -n tca-system $secret_name -o yaml"
    #kubectl get secret -n tca-system $secret_name -o yaml
    #echo "Stored overlay $overlay_yaml to secret $secret_name"
}

patch_pkgi() {
    local kube_path=$1
    local pkgi_name=$2
    local id=$3
    local overyloy_secret_name=$4
    KUBECONFIG=${kube_path} kubectl -n tca-system annotate packageinstalls $pkgi_name --overwrite ext.packaging.carvel.dev/ytt-paths-from-secret-name.$id=$overyloy_secret_name
    if [[ "$?" != "0" ]]; then
        RedLetter "Patch pkgi $pkgi_name failed, check in target cluster with \"kubectl get pkgi -n tca-system $pkgi_name -oyaml\""
    fi
}

unpause_pkgi() {
    local kube_path=$1
    local pkgi_name=$2
    KUBECONFIG=${kube_path} kubectl patch pkgi/$pkgi_name -n tca-system -p '{"spec":{"paused":false}}' --type=merge
    if [[ "$?" != "0" ]]; then
        RedLetter "Unpause pkgi/$pkgi_name failed \"kubectl get pkgi -n tca-system $pkgi_name -oyaml\""
    fi
}

wait_kapp_reconcile() {
    local kube_path=$1
    local pkgi_name=$2
    YellowLetter "Wait 10sec for addon $pkgi_name reconcile"
    KUBECONFIG=${kube_path} kubectl delete pod -n tkg-system -l app=kapp-controller
    sleep 10
    KUBECONFIG=${kube_path} kubectl get pkgi -n tca-system $pkgi_name
    pkgi_status=`KUBECONFIG=${kube_path} kubectl get pkgi -n tca-system $pkgi_name`
    if [[ "$pkgi_status" != *"Reconcile succeeded"* ]]; then
        YellowLetter 'Pkgi reconcile not succeeded, will wait 10 sec and recheck'
        # after restart kapp wait for pkgi reconcile
        a=0
        while [ $a -lt $retry_count ]
        do
            sleep 10
            KUBECONFIG=${kube_path} kubectl get pkgi -n tca-system $pkgi_name
            pkgi_status=`KUBECONFIG=${kube_path} kubectl get pkgi -n tca-system $pkgi_name`
            if [[ "$pkgi_status" != *"Reconcile succeeded"* ]]; then
                YellowLetter 'Pkgi reconcile not succeeded, will wait 10 sec and recheck'
            else
                GreenLetter "Pkgi reconcile succeeded"
                break
            fi
            let a++
        done
    else
        GreenLetter "Pkgi $pkgi_name reconcile succeeded"
    fi
}

check_webhook_expire_date() {
    kube_path=$1
    kind=$2
    webhook_name=$3
    a=0
    while [ $a -lt $retry_count ]
    do
        out=$(KUBECONFIG=${kube_path} kubectl get $kind $webhook_name  -o jsonpath='{.webhooks[0].clientConfig.caBundle}' | base64 -d | openssl x509 -noout -dates)
        echo $out
        if [[ "$out" == *"2030 GMT"* ]]; then
            return 0
        else
            YellowLetter 'Cert date is not updated, will wait 10 sec and recheck'
        fi
        sleep 10
        let a++
    done
    return 1
}

check_apply_nodeconfig_cr() {
    kube_path=$1
    empty_nc_cr="empty_nc_cr.yaml"
    temporary_files+=("$empty_nc_cr")
    cat >$empty_nc_cr <<EOF
apiVersion: acm.vmware.com/v1alpha1
kind: NodeConfig
metadata:
  name: test-vm-empty
  namespace: tca-system
spec:
  config: '{}'
  jobType: profile
  nodeMatch:
  - kubernetes.io/hostname: test-vm
EOF
    a=0
    while [ $a -lt $retry_count ]
    do
        echo "Will sleep 10s waiting new cert take effect"
        sleep 10
        out=$(KUBECONFIG=${kube_path} kubectl apply -f $empty_nc_cr 2>&1)
        if [ $? -eq 0 ]; then
            echo "Applied an empty nodeconfig cr succesfully."
            KUBECONFIG=${kube_path} kubectl delete -f $empty_nc_cr --wait=false >/dev/null 2>&1 || true
            KUBECONFIG=${kube_path} kubectl patch NodeConfig test-vm-empty -n tca-system --type=json -p='[{"op": "remove", "path": "/metadata/finalizers"}]' >/dev/null 2>&1 || true
            return 0
        fi
        let a++
    done

    RedLetter "Fail to create a nodeconfig CR for testing."
    echo $out
    return 1
}


check_apply_nodepolicy_cr() {
    kube_path=$1
    empty_np_cr="empty_nodepolicy_cr.yaml"
    temporary_files+=("$empty_np_cr")
    cat >$empty_np_cr <<EOF
apiVersion: acm.vmware.com/v1alpha1
kind: NodePolicy
metadata:
  name: test-np-empty
  namespace: tca-system
spec:
  nodeSelector:
    telco.vmware.com/nodepool: test-np-empty
EOF
    a=0
    while [ $a -lt $retry_count ]
    do
        echo "Will sleep 10s waiting new cert take effect"
        sleep 10
        out=$(KUBECONFIG=${kube_path} kubectl apply -f $empty_np_cr 2>&1)
        if [ $? -eq 0 ]; then
            echo "Applied an empty nodepolicy cr succesfully."
            KUBECONFIG=${kube_path} kubectl delete -f $empty_np_cr --wait=false >/dev/null 2>&1 || true
            KUBECONFIG=${kube_path} kubectl patch NodePolicy test-np-empty -n tca-system --type=json -p='[{"op": "remove", "path": "/metadata/finalizers"}]' >/dev/null 2>&1 || true
            return 0
        fi
        let a++
    done

    RedLetter "Fail to create a nodeconfig CR for testing."
    echo $out
    return 1
}

post_check_vm() {
    kube_path=$1
    if check_webhook_expire_date ${kube_path} "ValidatingWebhookConfiguration" "vmconfig-validator"; then
        echo "Vmconfig ValidatingWebhookConfiguration cert is updated"
    else
        RedLetter "Patch vmconfig ValidatingWebhookConfiguration cert failed"
        return 1
    fi
    if check_webhook_expire_date ${kube_path} "MutatingWebhookConfiguration" "vmconfig-defaulter"; then
        echo "Vmconfig MutatingWebhookConfiguration cert is updated"
    else
        RedLetter "Patch vmconfig MutatingWebhookConfiguration cert failed"
        return 1
    fi

    if check_apply_nodepolicy_cr ${kube_path}; then
        GreenLetter "Verified new cert take effect with applying and deleting an empty nodepolicy CR successfully"
        return 0
    else
        RedLetter "Apply an empty nodepolicy CR failed. Please check with edit one nodepolicy CR manully"
        return 1
    fi
}

is_date_before() {
  local not_after_str="$1"
  local date_str="${not_after_str#notAfter=}"

  local target_ts
  target_ts=$(date -d "$date_str" +%s 2>/dev/null)

  local cutoff_ts
  cutoff_ts=$(date -d "2027-01-01 00:00:00" +%s)

if [ -z "$target_ts" ] || [ -z "$cutoff_ts" ]; then
    echo "Invalid date"
    return 1
  fi
  if [ "$target_ts" -lt "$cutoff_ts" ]; then
    #echo "before 2027"
    return 1
  else
    #echo "after 2027"
    return 0
  fi
}

check_cert_update_needed(){
    kube_path=$1
    component=$2
    cluster_name=$3
    expired_date=$(KUBECONFIG=${kube_path} kubectl get ValidatingWebhookConfiguration ${component}  -o jsonpath='{.webhooks[0].clientConfig.caBundle}' | base64 -d | openssl x509 -noout -dates | grep notAfter)
    echo "current cert for ${component} in $cluster_name is $expired_date"
    if is_date_before "$expired_date"; then
        #echo "no need update"
        return 0
    else
        #echo "need update"
        return 1
    fi
}


post_check_nc() {
    kube_path=$1
    if check_webhook_expire_date ${kube_path} "ValidatingWebhookConfiguration" "nodeconfig-validator"; then
        GreenLetter "Nodeconfig cert is updated"
    else
        cmd="kubectl get ValidatingWebhookConfiguration nodeconfig-validator  -o jsonpath='{.webhooks[0].clientConfig.caBundle}' | base64 -d | openssl x509 -noout -dates"
        RedLetter "Check expired date failed. Please check with $cmd manully"
        eval "KUBECONFIG=${kube_path} $cmd"
        return 1
    fi
    if check_apply_nodeconfig_cr ${kube_path}; then
        GreenLetter "Verified with applying and deleting an empty nodeconfig cr successfully"
        return 0
    else
        RedLetter "Apply an empty nodeconfig CR still failed. Please check with edit one nodeconfig CR manully"
        return 1
    fi
}

cleanup_tmp_file(){
  for file in "${temporary_files[@]}"; do
    rm -rf $file
  done
}

patch_vmconfig(){
    kube_path=$1
    local cluster_name=$2
    if [[ "$TCAVER" != "2.3" ]]; then
        return 0
    fi
    if check_cert_update_needed $kube_path "vmconfig-validator" $cluster_name; then
        GreenLetter "No need update vmconfig cert, will skip cluster $cluster_name"
        return 0
    fi
    echo "Current vmconfig webhook cert date is"
    KUBECONFIG=${kube_path} kubectl get ValidatingWebhookConfiguration vmconfig-validator  -o jsonpath='{.webhooks[0].clientConfig.caBundle}' | base64 -d | openssl x509 -noout -dates
    echo "Will extend vmconfig cert to 2030"
    vm_cert_overlay_secret_name="vmconfig-overlay-cert"
    vm_webhook_overlay_secret_name="vmconfig-overlay-webhook"
    vm_webhook_overlay_secret_default_name="vmconfig-overlay-webhook-default"
    vm_cert_overlay_file="vm_cert_overlay_file.yaml"
    vm_webhook_overlay_file="vm_webhook_overlay_file.yaml"
    vm_webhook_default_overlay_file="vm_webhook_default_overlay_file.yaml"
    temporary_files+=("$vm_cert_overlay_file")
    temporary_files+=("$vm_webhook_overlay_file")
    temporary_files+=("$vm_webhook_default_overlay_file")
    prepare_vm_overlay_file
    create_secret_for_overlay $kube_path $vm_cert_overlay_secret_name $vm_cert_overlay_file
    create_secret_for_overlay $kube_path $vm_webhook_overlay_secret_name $vm_webhook_overlay_file
    create_secret_for_overlay $kube_path $vm_webhook_overlay_secret_default_name $vm_webhook_default_overlay_file

    patch_pkgi $kube_path "vmconfig-operator" "1" $vm_cert_overlay_secret_name
    patch_pkgi $kube_path "vmconfig-operator" "2" $vm_webhook_overlay_secret_name
    patch_pkgi $kube_path "vmconfig-operator" "3" $vm_webhook_overlay_secret_default_name
    unpause_pkgi $kube_path "vmconfig-operator"
    wait_kapp_reconcile ${kube_path} "vmconfig-operator"
    if ! post_check_vm $kube_path; then
        pkgi_name="vmconfig-operator"
        RedLetter "Post check for vmconfig-operator cert extend failed, will revert it."
        echo "Will remove annotation for vmconfig pkgi"
        KUBECONFIG=${kube_path} kubectl patch pkgi $pkgi_name -n tca-system --type=merge -p '{"metadata":{"annotations":null}}'
        echo "Will pause vmconfig pkgi to trigger kapp controller reconcile"
        KUBECONFIG=${kube_path} kubectl patch pkgi $pkgi_name -n tca-system -p '{"spec":{"paused":true}}' --type=merge
        sleep 5
        echo "Will unpause vmconfig pkgi to make old cert take effect"
        KUBECONFIG=${kube_path} kubectl patch pkgi $pkgi_name -n tca-system -p '{"spec":{"paused":false}}' --type=merge
        sleep 5
        echo "Will delete vmconfig-operator pod to make it take old cert"
        KUBECONFIG=${kube_path} kubectl get pod -A | grep vmconfig | awk '{print $2}'  | xargs KUBECONFIG=${kube_path} kubectl delete pod -n tca-system
        RedLetter "Please rerun the script to retry"
        exit 1
    fi
}

patch_one_cluster(){
    kube_path=$1
    local cluster_name=$2
    if check_cert_update_needed $kube_path "nodeconfig-validator" $cluster_name; then
        GreenLetter "No need update nodeconfig cert, will skip cluster $cluster_name"
        return 0
    fi

    echo ""
    GreenLetter "###### Will patch nodeconfig for cluster $cluster_name ######"

    # 2 secret for overlay wil be created in target cluster
    nc_cert_overlay_secret_name="nodeconfig-overlay-cert"
    nc_webhook_overlay_secret_name="nodeconfig-overlay-webhook"
    create_secret_for_overlay $kube_path $nc_cert_overlay_secret_name $nc_cert_overlay_file
    create_secret_for_overlay $kube_path $nc_webhook_overlay_secret_name $nc_webhook_overlay_file

    # patch secret tca-system/nodeconfig-certs and ValidatingWebhookConfiguration default/nodeconfig-validator
    patch_pkgi $kube_path "nodeconfig-operator" "1" $nc_cert_overlay_secret_name
    patch_pkgi $kube_path "nodeconfig-operator" "2" $nc_webhook_overlay_secret_name

    unpause_pkgi $kube_path "nodeconfig-operator"
    wait_kapp_reconcile ${kube_path} "nodeconfig-operator"
    if ! post_check_nc $kube_path; then
        RedLetter "Post check for cluster $cluster_name failed"
        echo ""
    else
        GreenLetter "###### Update nodeconfig cert for cluster $cluster_name successfully ######"
        echo ""
    fi
}

patch_v1_cluster(){
    kube_path=$1
    cluster_name=$2
    if ! check_cert_update_needed $kube_path "nodeconfig-validator" $cluster_name; then
        echo "No need update nodeconfig cert, will skip cluster $cluster_name"
        return 0
    fi
    KUBECONFIG=${kube_path} kubectl get  ValidatingWebhookConfiguration nodeconfig-validator -o yaml >webhook.yaml
    sed -i 's/\(caBundle:\).*/\1 LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSURvRENDQW9pZ0F3SUJBZ0lVTXplWmU5MFArejlNd2R5amJXNnU1TGRGcmg4d0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXdPVEE0TVRnd01Gb1hEVE13TURVd09EQTRNVGd3TUZvd2FERUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14Q3pBSkJnTlZCQXNUQWtOQk1STXdFUVlEVlFRREV3cExkV0psCmNtNWxkR1Z6TUlJQklqQU5CZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUF6U3dtcDMrUVVCR24KTVU5R1dxelhtTlErbEZaYStmd1FBc2ZIczlpRE9DQ1N0cFEycVNyanFXRGhpWElmMTAwNFBHSkpJYk9hOFlpRApIaDdEWUg1TXBxSm9oVHhYWndqRzJmMFR5Q1BJVzVpTmo3ZlA1RWNrY0Q4dFJKMkF2bkE5RjdQOUg1SHJnV0lYCldYN2EvY0N3NlVmdERPaHdPVFlHVkdUYng0YkZud1pyTXk2UnNJN3NLb2JET0JFSExGQUZab0tyNGc4dnp5eXYKVUZudTEzYmpSSnh1OHVvNGxqWlpyUHkyUSsrbkE3NjlJdzJobEFtdExzUVVUbU9lY3dhM3VlMlY1M1FlSExoZQpsMUJFSXZRTU0yZ1U4UENSaytabGl0SlMrSFlkRVppQUJhQkVqdWtZMmF0a0cyNExQeUJzay8wQXlMTTdweTNHCjFrWXhkbVVWQ3dJREFRQUJvMEl3UURBT0JnTlZIUThCQWY4RUJBTUNBUVl3RHdZRFZSMFRBUUgvQkFVd0F3RUIKL3pBZEJnTlZIUTRFRmdRVWFkbXJlSlhZRm90OVRIY0NYQTU5VTU2YVRzQXdEUVlKS29aSWh2Y05BUUVMQlFBRApnZ0VCQUJPVURFOUdza1ZQMHVWTi94N1F2ZHBLR3VVc1ZSYVBIOWxEREIyakNyTkpDVFdzRDNhMTJ0d1I0WGVZClhOeHUyVEZuTHVaTVJRYndHWUJCZU0vRWhLaDRHdi9vVEQ2MjVseE9tbHlWcjZMbUpHQm1aQ0tFNGpySlFmTnYKUU9HVnp4NjIrR1M5ZkVxdmpJOG5IblhWdDFRZDd4OGlENkR1NXBzc1RFcTBPZTFYUnQ0Y3pLRXJUT2UyL3pRcgpmRHNVdHVzUS85MDhWWHhkZ0N2VHQ4Q01UR1p5OXo3VmRtbUJORlFscEVOeGRHTjNKKytldkE0c200YkUyeG5aCjZsdnFGaS8xWVlFdG9FbW80MEhhVEFsRUdsa1J3SGo4TFFlU1BBYkJxNUtYbmlHS3RDekV5ZDNDalp1QVU2YUwKWDNvd0RxQ0MrRVh6aG1xTVg5Z3ZMbjh5Sk5zPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==/g' webhook.yaml
    KUBECONFIG=${kube_path} kubectl apply -f webhook.yaml
    rm -rf webhook.yaml

    KUBECONFIG=${kube_path} kubectl get secret -n tca-system nodeconfig-certs -o yaml >nc_cert.yaml
    sed -i 's/\(tls.crt:\).*/\1 LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUVGVENDQXYyZ0F3SUJBZ0lVZnk2RzI5Wmdxc1JrNmY1NTdieFF5aVVjRlVzd0RRWUpLb1pJaHZjTkFRRUwKQlFBd2FERUxNQWtHQTFVRUJoTUNWVk14RHpBTkJnTlZCQWdUQms5eVpXZHZiakVSTUE4R0ExVUVCeE1JVUc5eQpkR3hoYm1ReEV6QVJCZ05WQkFvVENrdDFZbVZ5Ym1WMFpYTXhDekFKQmdOVkJBc1RBa05CTVJNd0VRWURWUVFECkV3cExkV0psY201bGRHVnpNQjRYRFRJMU1EVXdPVEE0TVRnd01Gb1hEVE0xTURVd056QTRNVGd3TUZvd2J6RUwKTUFrR0ExVUVCaE1DVlZNeER6QU5CZ05WQkFnVEJrOXlaV2R2YmpFUk1BOEdBMVVFQnhNSVVHOXlkR3hoYm1ReApFekFSQmdOVkJBb1RDa3QxWW1WeWJtVjBaWE14RXpBUkJnTlZCQXNUQ2t0MVltVnlibVYwWlhNeEVqQVFCZ05WCkJBTVRDV0ZrYldsemMybHZiakNDQVNJd0RRWUpLb1pJaHZjTkFRRUJCUUFEZ2dFUEFEQ0NBUW9DZ2dFQkFOWUsKNUZPM1ptMkhFNG16N2ZZcU1NR3VGSFl2QVNSN242b0NUc2JhQ2YwZGRTNy9Wei9rWnd5bFM0aVpJeWZqOVV0YQpFOXNpRkFPVndNdnhUYjJmT29CTVU4UUQ5bjBpTUVmb3NOSTM2N3ZsSEFLZ1lJNUR1bGFPODkwWURnQ0thRkhrCjYxZmlRdG9nSTRGajZEZ21zcXkwc3VJOWNRZDZrc3Jla3NwMjFNVUxpRkFoWUJtWHBVODdMTm1ZNjBJL0Y2Zk0KUXYrR3BpUU4vVHdsZmFtMnE4YWllWGhaUGU1MnlDN29EZHRQZk05cGpvOEdzYVdTVFF3YmM2WFlDWFhsYUNQNApOcTd4SHNMdEdwcG5BdXJLOGwzZVJJZW1HSGN2U1crRTk3N0NOUVBMeDBjNTVGOGZUdkE5bTg3RE5pTkZSbWcvCjV6RkhLczZyWm52c21DdWhKcmtDQXdFQUFhT0JyekNCckRBT0JnTlZIUThCQWY4RUJBTUNCYUF3SFFZRFZSMGwKQkJZd0ZBWUlLd1lCQlFVSEF3RUdDQ3NHQVFVRkJ3TUNNQXdHQTFVZEV3RUIvd1FDTUFBd0hRWURWUjBPQkJZRQpGTnRSbUdtcFBCOFExYVF5MmxndE1hblZoTkV5TUI4R0ExVWRJd1FZTUJhQUZHblpxM2lWMkJhTGZVeDNBbHdPCmZWT2VtazdBTUMwR0ExVWRFUVFtTUNTQ0ltNXZaR1ZqYjI1bWFXZDJZV3hwWkdGMGIzSXVkR05oTFhONWMzUmwKYlM1emRtTXdEUVlKS29aSWh2Y05BUUVMQlFBRGdnRUJBQkhmbTYzL0V4MG1oN1FFU1VUTkFuU2tDZ3dNeXAzSwoxTEsvVmp0ekVlT3AzUzQzaHYrOEh5NWgveXpNdGMwQ2lDYTMrblZTSW5RR3hESnprT2doVWtMa1hqUzJpRjNFCmlzTTQ3Ynd3MXMzSk5RMFQ5V0o0ZE5oYjlQdWtLeEg4Qk5adnVzWGRBTTM5MGtLOFhGY2UzRXptVDZwTFdRczQKMFZ5bENpVnpHUjFucDRFaCt3YldOQk53TTBoTGI1RFczRTAxaXBTRVdmdmsrNWhCR3liak1BeUg2RkhNcHlBLwp3SFNQejlrVXZSMFJzamw0aWlzVFJZMm5FV2IwNHVMQVJ4eUdXK2NqZU4xQXlDZ1NZTmMvRHQvTWdJcjVoRGo1CitiR1BDVGZndlQ2aHE1SW43S3IwR1FWb0h1Y2poUlV6ZDhLdlEvS0VzZmFZR01sODNOMGptTjA9Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K/g' nc_cert.yaml
    sed -i 's/\(tls.key:\).*/\1 LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlFcEFJQkFBS0NBUUVBMWdya1U3ZG1iWWNUaWJQdDlpb3d3YTRVZGk4QkpIdWZxZ0pPeHRvSi9SMTFMdjlYClArUm5ES1ZMaUprakorUDFTMW9UMnlJVUE1WEF5L0ZOdlo4NmdFeFR4QVAyZlNJd1IraXcwamZydStVY0FxQmcKamtPNlZvN3ozUmdPQUlwb1VlVHJWK0pDMmlBamdXUG9PQ2F5ckxTeTRqMXhCM3FTeXQ2U3luYlV4UXVJVUNGZwpHWmVsVHpzczJaanJRajhYcDh4Qy80YW1KQTM5UENWOXFiYXJ4cUo1ZUZrOTduYklMdWdOMjA5OHoybU9qd2F4CnBaSk5EQnR6cGRnSmRlVm9JL2cycnZFZXd1MGFtbWNDNnNyeVhkNUVoNllZZHk5SmI0VDN2c0kxQTh2SFJ6bmsKWHg5TzhEMmJ6c00ySTBWR2FEL25NVWNxenF0bWUreVlLNkVtdVFJREFRQUJBb0lCQUZqbGp5MGg1NzJuc3pxbQo2emNwRUxUd0t2bG16aytydElWMGplbFMxNEV6d2Q2eUdEZW1FaEtUZUVxVVo2Q0NzZmNJdzJSb3crMDFQaXkxCjNMYmJzZjFsTmdrY0tEeVNmWUR3S0xnMmw0YWpRajNwQkJFeUdlc25WaXRHZVZKS0tjZVJqeGtpRk9mcEh6WDMKRzVSdXBoakt0OXowN2NQUWFiVXVPY016RlcxOGVQc2lqaS9BblgybmRNa1Y1aVU1cHVMNWFNU1VTTUg0RjlpZwp5QWxQVHk0L3FXZlF2L25YSVZyczB3aWtFN05LR1NQdHFMZWlRYmp4a3YyRWRwWHFUY0trMklVSFpzTE1qbFZ3ClRtNEtNY29iU2JLQktiR2w4REk5Yk9KZjdYUmlKcFE0cmNObXRmaDhVaGFuR2lMZ1pDcmJGWWtiWk5YMXY4c0EKWWREb3FSMENnWUVBOXNWdW9RQ1Jqb05LUTlvSWwyTERteDc0RkROVm1TYmEwZ2d2SHVNTjg2NG5vaENiLy9XNwpaODFDWFR0bytxbVR6ek83QklzSDhvdE5tNXZublRHT1V4R0FQK2RuWmFMenRFOVYzSzFqYWFHdURoZHphRnNrCnk4eGR5am0vR2htV0szeFJ0WjRybjJoR2J0d0lxVHdORFJOMlBLNDNmc1ovQURocllvNEhKbThDZ1lFQTNnd2UKT2R4aGhpazQ1eHkycEdpVEM2RHVlMjVuQ3ZTRk1YWEdKeWNmK080R3VtZVBIdmR1MnA3SGdJTTk0NHRuVHNIagpyVWVWQ05PWVlFRGU0WnBFWG5pRXlCOFhlSWN6NFR6c3lrWEp1ZGloQUdoS0g3SE5xTkNjcGNSUi9QVFhTeXJ6ClRMb3h5MGkwRlRwL2VuVzJlQzhOUDRSRUNBQ0RHVkFQRzNuUjJWY0NnWUI4OXhaQzZpckw1S2lqRzdMbUZ0bS8Kb0RzNDM1WWxiSXU3ZVBHRHpxK3VDeTkrM3JKaE9HdWk4VXIrTTZ2QjVFWTUwNVNOaEdxTjVRVjBHOHQ2eXpHcgoxMXorLzR4WTUrQktHekw4QWNJcUovb2dvTGVNelRzaENXa2xrNEMzRXVYOU40T1pXWFAxMGJSNVIyd0xaNkdrClVZcTZ4KzdLZ0hLb0JlbzdpbmtNZVFLQmdRREJnbG9OSHN3MitWSEh4N1E4RDQ2bWdiZVVCaUR5NFNuNmNxTWYKbCs4N0oyVGhxa0tHUUNoeGloSmZJd0VhZm5DbnFEMWMwNWRFTy9MOVgwdGQzTzFjVHplWWw5QUNrQUZjZDVYOApxVmttQjI0NFJxcmllRGU4dVNEckxlNHR2c3FwaldLL0tUMGY1ZHBhN2NJTzNPc0tUaWNEaGFjc09oWUdSMGtECkx1VDh2UUtCZ1FEQ1RmSGVaREM2OGV0RCtwRk1zUWZ1VlhMMjg1dnJReE5qMndXaTVNK09jZmVjYmR3VFdZSjQKRGdFNnlGMXNsZGU2WmpEUFdWNTVQOERZSjhkbmFsMTRUZmdtRHhnakx3eVRSUFg4ODFiS1Vmbk9oVThveVBwMgpzbTNrV0MzWFNKNWViaktRNk0zdXM3aUNxM05QUDVQL1ZSUE4yV2xjRU9hMWhncUExZ1F4Umc9PQotLS0tLUVORCBSU0EgUFJJVkFURSBLRVktLS0tLQo=/g' nc_cert.yaml
    KUBECONFIG=${kube_path} kubectl apply -f nc_cert.yaml
    rm -rf nc_cert.yaml

    sleep 10
    if ! post_check_nc $kube_path; then
        RedLetter "Post check for cluster $cluster_name failed"
        echo ""
    else
        GreenLetter "###### Update nodeconfig cert for cluster $cluster_name successfully ######"
        echo ""
    fi
}


list_clusters() {
    local mcspoke_pod_ip="127.0.0.1"
    if [[ "$TCAVER" != "2.3" ]]; then
        mcspoke_pod_ip=$(kubectl get pods -n tca-cp-cn -l app=k8s-bootstrapper -o json | jq -r '.items[0].status.podIP')
    fi

  echo "Start to get management cluster list under this TCA-CP"
  local mgmt_clusters=$(curl -s "http://${mcspoke_pod_ip}:8888/api/v1/managementclusters")
  if [ $? -ne 0 ] || [ -z "${mgmt_clusters}" ]; then
    RedLetter "Fail to get management cluster list. Please check whether tca-cp-cn/k8s-bootstrapper service is working well."
    return 1
  fi

  while read item; do
    data=(`echo $item`)
    if [ ${#data[@]} -eq 2 ]; then
      name=${data[0]}
      echo "start to get workload cluster list under management cluster $name"
      get_v1_wc_list $name
      GetMcKubeconfig ${name}
      if [ $? -ne 0 ]; then
        RedLetter "${ERROR_MSG}"
      else
      cmd="KUBECONFIG=${mc_kubeconfig_path} kubectl get tkc -A -o json | jq -r '.items[] | select (.metadata.name != \"${name}\")  | .metadata.name'"
      #echo $cmd
      wc_clusters=$(eval "$cmd")
        if [ $? -ne 0 ] || [ -z "${wc_clusters}" ]; then
          YellowLetter "No workload clusters found for management cluster ${name}"
          CLUSTERS_ARRAY[$name]="[]"
        else
          CLUSTERS_ARRAY[$name]="${wc_clusters}"
        fi
      fi
    fi
  done <<< $(echo ${mgmt_clusters} | jq -r '.[] | "\(.clusterName) \(.id)"')
  if [ ${#CLUSTERS_ARRAY[@]} -gt 0 ]; then
    echo "Get below management clusters and workload clusters under this TCA-CP"
    printf "%-64s" "Management Cluster"
    printf "%-80s\n" "Workload Clusters"
    printf -v spaces '%*s' 30 ''; printf '%s\n' ${spaces// /---}
    for cluster in ${!CLUSTERS_ARRAY[@]}
    do
      printf "%-64s" $cluster
      printf "%-80s\n" "${CLUSTERS_ARRAY[$cluster]}"
    done
  fi
}

################## main() ##################
# Call the function to parse parameters passed to the script
if ! parse_parameters "$@"; then
  usage
fi
trap cleanup_tmp_file EXIT

# Example usage of the parsed options
echo "MC Name: $mc_name"
echo "WC Name: $wc_name"
echo ""

if [ -z "$mc_name" ]; then
    echo "Error: No mc name provided"
    usage
fi

if ! GetMcKubeconfig "$mc_name"; then
    RedLetter "Failed to get MC kubeconfig"
    exit 1
fi

prepare_overlay_file
if [ -z "$wc_name" ]; then
    cmd="KUBECONFIG=${mc_kubeconfig_path} kubectl get cluster -A | grep -v '^NAME' | grep -v "tkg-system" | cut -d ' ' -f 1 | xargs | tr ' ' ','"
    wc_name_list=$(eval "$cmd")
    echo ""
    GreenLetter "###### Detected workload clusters $wc_name_list ######"
    echo ""

    # patch mc
    patch_vmconfig $mc_kubeconfig_path $mc_name

    patch_one_cluster $mc_kubeconfig_path $mc_name
    # patch both v1 and v2 wc
    IFS=','
    for item in $wc_name_list; do
        prepare_kubeconfig $item
        out=$(KUBECONFIG=$mc_kubeconfig_path kubectl get tcakubernetesclusters $item -n $item 2>&1)
        if [[ "$out" == *"not found"* || "$out" == *"No resources found"* ]]; then
            YellowLetter "No tcakubernetesclusters named as $item found. Will try it as v1 cluster"
            # echo "will patch v1 cluster $item"
            patch_v1_cluster $wc_kubeconfig_path $item
        else
            # echo "will patch v2 cluster $item"
            patch_one_cluster $wc_kubeconfig_path $item
        fi
    done
else
    prepare_kubeconfig $wc_name
    # for TCA2.3, need consider if v1 cluster exists
    KUBECONFIG=$mc_kubeconfig_path kubectl get tcakubernetesclusters $wc_name -n $wc_name 2>&1
    if [ $? -ne 0 ]; then
        YellowLetter "No tcakubernetesclusters named as $wc_name found. Will try it as v1 cluster"
        patch_v1_cluster $wc_kubeconfig_path $wc_name
    else
        patch_one_cluster $wc_kubeconfig_path $wc_name
    fi
fi