#!/usr/bin/env bash

set -euo pipefail
# When changing this script, remember to modify the corresponding github action
region=${1}
env=${2}
cloud=${3}
json_file_path=${4}
logicalRegionName=${5}

additional_args=$(jq -r '.' "${json_file_path}")

echo "additional_args: ${additional_args}"

irsa_role_arn=$(echo ${additional_args} | jq -r '.awsIrsaRoleArn')
assume_role_global_arn=$(echo ${additional_args} | jq -r '.awsAssumeRoleGlobalArn')
availability_zones=$(echo ${additional_args} | jq -r '.availabilityZones')
image_registry=$(echo ${additional_args} | jq -r '.imageRegistry')

dataplane_accounts=$(echo ${additional_args} | jq -r '.dataplaneAccounts')
autho0_audience=$(echo ${additional_args} | jq -r '.auth0Audience')
auth0_domain=$(echo ${additional_args} | jq -r '.auth0Domain')
global_controlplane_ips=$(echo ${additional_args} | jq -r '.globalControlplaneIPs')
regional_controlplane_ips=$(echo ${additional_args} | jq -r '.regionalControlplaneIPs')
o11y_regional_service_ips=$(echo ${additional_args} | jq -r '.o11yRegionalServiceIPs')
clinic_ips=$(echo ${additional_args} | jq -r '.clinicIPs')
bastion_ips=$(echo ${additional_args} | jq -r '.bastionIPs')
authorized_subjects=$(echo ${additional_args} | jq -r '.authorizedSubjects')
public_hosted_zone_domain=$(echo ${additional_args} | jq -r '.publicHostedZoneDomain')
public_hosted_zone_id=$(echo ${additional_args} | jq -r '.publicHostedZoneID')
o11y_regional_service_endpoint=$(echo ${additional_args} | jq -r '.o11yRegionalServiceEndpoint')
o11y_seed_cluster_id=$(echo ${additional_args} | jq -r '.o11ySeedClusterId')
pca_arn=$(echo ${additional_args} | jq -r '.pcaArn')

# new args for azure
controlplane_subscription_id=$(echo ${additional_args} | jq -r '.controlplaneSubscriptionID')
azure_drs_client_id=$(echo ${additional_args} | jq -r '.azureDrsClientID')
default_dataplane_account=$(echo ${additional_args} | jq -r '.defaultDataplaneAccount')
azure_tenant_id=$(echo ${additional_args} | jq -r '.azureTenantID')
crossplane_azure_client_id=$(echo ${additional_args} | jq -r '.crossplaneAzureClientID')
public_hosted_zone_resource_group=$(echo ${additional_args} | jq -r '.publicHostedZoneResourceGroup')
azure_admin_group_object_ids=$(echo ${additional_args} | jq -r '.azureAdminGroupObjectIDs')
app_registration_id=$(echo ${additional_args} | jq -r '.app_registration_id')
app_registration_name=$(echo ${additional_args} | jq -r '.app_registration_name')
app_registration_umi=$(echo ${additional_args} | jq -r '.app_registration_umi')


ROOT=$(cd $(dirname ${BASH_SOURCE[0]}) && pwd)
deploy_dir="${ROOT}/envs/${cloud}-${env}-${logicalRegionName}"
variant_dir="${ROOT}/variants/${env}-${cloud}"

if [ -e ${deploy_dir} ]; then
  echo "New region deploy directory already exist"
  exit 1
fi

mkdir "${deploy_dir}"
echo "Prepare manifest files"
cp "${variant_dir}/kustomization_tmpl.yaml" "${deploy_dir}/kustomization.yaml"
cp "${variant_dir}/version_tmpl.yaml" "${deploy_dir}/version.yaml"
cp "${variant_dir}/service_account_tmpl.yaml" "${deploy_dir}/service_account.yaml"
cp "${variant_dir}/deployment_tmpl.yaml" "${deploy_dir}/deployment.yaml"

mkdir "${deploy_dir}/config"
echo "Prepare config files"
cp "${variant_dir}/config/k8s-addon-templates.yaml" "${deploy_dir}/config/k8s-addon-templates.yaml"
cp "${variant_dir}/config/k8s-dedicated-templates_tmpl.yaml" "${deploy_dir}/config/k8s-dedicated-templates.yaml"
cp "${variant_dir}/config/k8s-dp-templates_tmpl.yaml" "${deploy_dir}/config/k8s-dp-templates.yaml"
cp "${variant_dir}/config/k8s-infra-templates_tmpl.yaml" "${deploy_dir}/config/k8s-infra-templates.yaml"
cp "${variant_dir}/config/root-config_tmpl.yaml" "${deploy_dir}/config/root-config.yaml"


if [[ "$OSTYPE" == "darwin"* ]]; then
    # macOS
    SED_IN_PLACE=(-i '')
else
    # Linux and others
    SED_IN_PLACE=(-i)
fi

find "${deploy_dir}" -type f -exec sed "${SED_IN_PLACE[@]}" "s|TMPL_REGION|${region}|g" {} \;
sed "${SED_IN_PLACE[@]}" "s|TMPL_IRSA_ROLE_ARN|${irsa_role_arn}|g" "${deploy_dir}/service_account.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_IRSA_ROLE_ARN|${irsa_role_arn}|g" "${deploy_dir}/deployment.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_AZURE_DRS_CLIENT_ID|${azure_drs_client_id}|g" "${deploy_dir}/service_account.yaml"
find "${deploy_dir}" -type f -exec sed "${SED_IN_PLACE[@]}" "s|IMAGE_REGISTRY|${image_registry}|g" {} \;
# replace the auth0 audience and domain
sed "${SED_IN_PLACE[@]}" "s|TMPL_AUTH0_AUDIENCE|${autho0_audience}|g" "${deploy_dir}/config/k8s-dedicated-templates.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_AUTH0_DOMAIN|${auth0_domain}|g" "${deploy_dir}/config/k8s-dedicated-templates.yaml"
# replace the public hosted zone domain and id
sed "${SED_IN_PLACE[@]}" "s|TMPL_PUBLIC_HOSTED_ZONE_DOMAIN|${public_hosted_zone_domain}|g" "${deploy_dir}/config/root-config.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_PUBLIC_HOSTED_ZONE_ID|${public_hosted_zone_id}|g" "${deploy_dir}/config/root-config.yaml"
# replace the o11y regional service endpoint
sed "${SED_IN_PLACE[@]}" "s|TMPL_O11Y_REGIONAL_SERVICE_ENDPOINT|${o11y_regional_service_endpoint}|g" "${deploy_dir}/config/root-config.yaml"
# replace the o11y seed cluster id
sed "${SED_IN_PLACE[@]}" "s|TMPL_O11Y_SEED_CLUSTER_ID|${o11y_seed_cluster_id}|g" "${deploy_dir}/config/root-config.yaml"
# replace the pca arn
sed "${SED_IN_PLACE[@]}" "s|TMPL_PCA_ARN|${pca_arn}|g" "${deploy_dir}/config/root-config.yaml"

# new args for azure
sed "${SED_IN_PLACE[@]}" "s|TMPL_PUBLIC_HOSTED_ZONE_RESOURCE_GROUP|${public_hosted_zone_resource_group}|g" "${deploy_dir}/config/root-config.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_CONTROLPLANE_SUBSCRIPTION_ID|${controlplane_subscription_id}|g" "${deploy_dir}/config/root-config.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_CONTROLPLANE_CROSSPLANE_PROVIDER_CONFIG_NAME|${controlplane_subscription_id}|g" "${deploy_dir}/config/root-config.yaml"

sed "${SED_IN_PLACE[@]}" "s|TMPL_APP_REGISTRATION_ID|${app_registration_id}|g" "${deploy_dir}/config/root-config.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_APP_REGISTRATION_NAME|${app_registration_name}|g" "${deploy_dir}/config/root-config.yaml"
sed "${SED_IN_PLACE[@]}" "s|TMPL_APP_REGISTRATION_UMI|${app_registration_umi}|g" "${deploy_dir}/config/root-config.yaml"

yq e -i ".regionConfig.zones |= $availability_zones" ${deploy_dir}/config/root-config.yaml


mkdir "${deploy_dir}/account"
echo "Prepare account-list.yaml"
# genrate the account list, ptah: account/account-list.yaml
account_list=${deploy_dir}/account/account-list.yaml
cat <<EOF > ${account_list}
apiVersion: v1
kind: ConfigMap
metadata:
  name: account-list
  labels:
    cloud.pingcap.com/bizType: dedicated
data:
  default: "${default_dataplane_account}"
  list: |
EOF

for account in $(echo ${dataplane_accounts} | jq -r '.[]'); do
  cat <<EOF >> ${account_list}
    - azureaccountinfo:
        subscriptionID: ${account}
EOF
done


# genrate the providerconfig, path: config/providerconfig.yaml
echo "Prepare providerconfig.yaml"
providerconfig_config=${deploy_dir}/account/providerconfig.yaml
cat <<EOF > ${providerconfig_config}
apiVersion: aws.upbound.io/v1beta1
kind: ProviderConfig
metadata:
  name: "provider-aws-gr"
spec:
  assumeRoleChain:
  - roleARN: ${assume_role_global_arn}
  credentials:
    source: IRSA
EOF

cat <<EOF >> ${providerconfig_config}
---
apiVersion: azure.upbound.io/v1beta1
kind: ProviderConfig
metadata:
  name: "${controlplane_subscription_id}"
spec:
  credentials:
    source: OIDCTokenFile
  subscriptionID: ${controlplane_subscription_id}
  clientID: ${crossplane_azure_client_id}
  tenantID: ${azure_tenant_id}
EOF

# genrate the providerconfig
for account in $(echo ${dataplane_accounts} | jq -r '.[]'); do
  cat <<EOF >> ${providerconfig_config}
---
apiVersion: azure.upbound.io/v1beta1
kind: ProviderConfig
metadata:
  name: "${account}"
spec:
  credentials:
    source: OIDCTokenFile
  subscriptionID: ${account}
  clientID: ${crossplane_azure_client_id}
  tenantID: ${azure_tenant_id}
EOF
done

echo "set whitelist ip"
yq e -i ".appBoxConfig.apiserverPublicAccessCidrs |= ${bastion_ips} + ${global_controlplane_ips} + ${regional_controlplane_ips} + ${o11y_regional_service_ips}" \
  ${deploy_dir}/config/root-config.yaml
yq e -i ".[0].clusterProxy.helmValues.service.loadBalancerSourceRanges |= ${global_controlplane_ips} + ${regional_controlplane_ips} + ${clinic_ips}" \
  ${deploy_dir}/config/k8s-dedicated-templates.yaml
yq e -i ".[0].clusterGateway.helmValues.proxy.loadBalancerSourceRanges |= ${global_controlplane_ips} + ${regional_controlplane_ips} + ${clinic_ips}" \
  ${deploy_dir}/config/k8s-dedicated-templates.yaml
yq e -i ".[0].dataflowAgent.helmValues.service.loadBalancerSourceRanges |= ${global_controlplane_ips} + ${regional_controlplane_ips}" \
  ${deploy_dir}/config/k8s-dp-templates.yaml

echo "set authorized subjects"
yq e -i ".appBoxConfig.authorizedSubjects |= ${authorized_subjects}" ${deploy_dir}/config/root-config.yaml

echo "set azure admin group object ids"
yq e -i ".appBoxConfig.adminGroupObjectIDs |= ${azure_admin_group_object_ids}" ${deploy_dir}/config/root-config.yaml
