Skip to content
Merged
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
51 changes: 43 additions & 8 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,49 @@
# Cosmo Tech shared
*Install common resources on Kubernetes clusters required by tenants*









## Requirements
- working Kubernetes cluster deployed from Cosmo Tech terraform-*provider* (like [terraform-azure](https://github.com/Cosmo-Tech/terraform-azure) for example)
- [terraform](https://developer.hashicorp.com/terraform/tutorials/aws-get-started/install-cli)
> If using Windows, Terraform must be accessible from PATH

## How to
* clone & open the repository
```
git clone https://github.com/Cosmo-Tech/terraform-shared.git --branch <tag>
cd terraform-shared
```
* deploy
* fill terraform.tfvars variables according to your needs
* run pre-configured script
> ℹ️ comment/uncomment the terraform apply line at the end to get a plan without deploy anything
* Linux
```
./_run-terraform.sh
```
* Windows
```
./_run-terraform.ps1
```

## Known errors
* None known error for now !
> resolution description will takes place here

## Developpers
* modules
* *chart_cert_manager* = install Cert Manager
* *chart_harbor* = install Harbor
* *chart_ingress_nginx* = install Ingress Nginx
* *chart_keycloak* = Keycloak
* *chart_prometheus_stack* = Prometheus Stack (Prometheus/Grafana)
* *kube_namespaces* = create namespaces for all others modules
* Terraform state
* The state is stored beside the cluster Terraform state, in the current cloud s3/blob storage service (generally called `cosmotech-states` or `cosmotechstates`, depending on what the cloud provider allows in naming convention)
* File backend.tf
* dynamically created at each run of `_run-terraform`
* permit to have multi-cloud compatibility with Terraform
* it instanciate the needed Terraform providers based on the variable `cloud_provider` from terraform.tfvars
* this file is a workaround to avoid having unwanted variables related to cloud providers not targetted in current deployment

<br>
<br>
Expand Down
148 changes: 148 additions & 0 deletions _run-terraform.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@


# Script to run terraform modules
# Usage :
# - ./script.ps1


# Stop script if missing dependency
$required_command = 'terraform'
foreach ($command in $required_command) {
if (!(Get-Command -errorAction SilentlyContinue -Name $command)) {
echo "error: required command not found in the PATH: $command"
exit
}
}


# Get value of a variable declared in a given file from this pattern: variable = "value"
# Usage: get_var_value <file> <variable>
function get_var_value {
param($File, $Variable)

$value = (cat $File | select-string $Variable | select-string '=' | select-string -Pattern '#.*' -NotMatch | select -first 1)
$value -replace '.*=.*\"(.*)\".*','$1'
}
$cloud_provider = (get_var_value 'terraform.tfvars' 'cloud_provider')
$cluster_region = (get_var_value 'terraform.tfvars' 'cluster_region')
$cluster_name = (get_var_value 'terraform.tfvars' 'cluster_name')
$state_file_name = "tfstate-shared-$cluster_name"


# Clear old data
rm -Recurse -Confirm:$false .terraform*
rm -Recurse -Confirm:$false terraform.tfstate*


# The trick here is to write configuration in a dynamic file created at the begin of the
# execution, containing the config that the concerned provider is waiting for Terraform backend.
# Then, Terraform will automatically detects it from its .tf extension.
$backend_file = 'backend.tf'
switch ($cloud_provider) {
"azure" {
$state_storage_name = 'cosmotechstates'
echo "
terraform {
backend ""azurerm"" {
resource_group_name = ""$state_storage_name""
storage_account_name = ""$state_storage_name""
container_name = ""$state_storage_name""
key = ""$state_file_name""
}
}

provider ""azurerm"" {
features {}
subscription_id = var.azure_subscription_id
tenant_id = var.azure_entra_tenant_id
}

variable ""azure_subscription_id"" { type = string }
variable ""azure_entra_tenant_id"" { type = string }

data ""terraform_remote_state"" ""terraform_cluster"" {
backend = ""azurerm""
config = {
resource_group_name = ""$state_storage_name""
storage_account_name = ""$state_storage_name""
container_name = ""$state_storage_name""
key = ""tfstate-cluster-$cluster_name""
}
}

# Trick to get the resource group of the cluster (get it from instanciated Kubernetes nodes)
data ""kubernetes_nodes"" ""selected"" {
metadata {
labels = {
""cosmotech.com/tier"" = ""db""
}
}
}

data ""azurerm_public_ip"" ""lb_ip"" {
name = ""$cluster_name-lb-ip""
resource_group_name = [for node in data.kubernetes_nodes.selected.nodes : node.metadata.0.labels].0[""kubernetes.azure.com/cluster""]
}

data ""azurerm_client_config"" ""current"" {}
" > $backend_file
}

"aws" {
$state_storage_name = 'cosmotech-states'
echo "
terraform {
backend ""s3"" {
key = ""$state_file_name""
bucket = ""$state_storage_name""
region = ""$cluster_region""
}
}

provider ""aws"" {
region = var.cluster_region
}
" > $backend_file
}

"gcp" {
$state_storage_name = 'cosmotech-states'
echo "
terraform {
backend ""gcs"" {
bucket = ""$state_storage_name""
prefix = ""$state_file_name""
}
}

provider ""google"" {
project = var.project_id
region = var.cluster_region
}

variable ""project_id"" { type = string }

data ""terraform_remote_state"" ""terraform_cluster"" {
backend = ""gcs""
config = {
bucket = ""$state_storage_name""
}
}

data ""google_client_config"" ""current"" {}
" > $backend_file
}
}
# Convert backend_file to UNIX format, otherwise Terraform will not be able to read it
((Get-Content $backend_file) -join "`n") + "`n" | Set-Content -NoNewline $backend_file


# Deploy
terraform fmt $backend_file
terraform init -lock=false -upgrade -reconfigure
terraform plan -lock=false -out .terraform.plan
# terraform apply -lock=false .terraform.plan


echo ''
exit 0
8 changes: 7 additions & 1 deletion _run-terraform.sh
Original file line number Diff line number Diff line change
@@ -1,14 +1,20 @@
#!/bin/sh

# Script to run terraform modules
# Usage :
# - ./script.sh


# Stop script if missing dependency
required_commands="terraform jq"
required_commands="terraform"
for command in $required_commands; do
if [ -z "$(command -v $command)" ]; then
echo "error: required command not found: \e[91m$command\e[97m"
exit 1
fi
done


# Get value of a variable declared in a given file from this pattern: variable = "value"
# Usage: get_var_value <file> <variable>
get_var_value() {
Expand Down
Loading