Skip to content

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Repository files navigation

Gestione GitLab con Terraform

Provisioning e configurazione di sottogruppi e progetti con impostazioni standard (e variabili CI/CD opzionali) su GitLab (SaaS / gitlab.com) tramite il provider ufficiale gitlabhq/gitlab.

Membri e permessi NON sono gestiti da Terraform: l'accesso e' gestito tramite SAML Group Links. Tenerli fuori da Terraform evita conflitti (drift) tra i due sistemi.

L'infrastruttura e' descritta come codice (IaC): modifichi i file .tf, lanci terraform plan per vedere cosa cambierebbe e terraform apply per applicarlo.


1. Struttura del progetto

GitLab/
├── versions.tf              # Versioni richieste di Terraform e del provider
├── providers.tf             # Configurazione del provider GitLab (auth via env)
├── backend.tf               # Stato: locale ora, pronto a migrare su GitLab
├── variables.tf             # Variabili di input della root (es. gruppo radice)
├── main.tf                  # Lettura del gruppo radice esistente (data source)
├── inventory.tf             # CATALOGO (committato): elenco di sottogruppi/progetti
├── subgroups.tf             # Crea i sottogruppi ciclando sull'inventario (for_each)
├── projects.tf              # Crea i progetti ciclando sull'inventario (for_each)
├── outputs.tf               # Output utili dopo l'apply (URL, id, ...)
├── terraform.tfvars.example # Esempio di valori -> copialo in terraform.tfvars
├── .gitignore               # Esclude stato, segreti, .terraform/, ...
│
└── modules/                 # Moduli riutilizzabili (gli "stampi" standard)
    ├── subgroup/            #   crea un sottogruppo (+ variabili di gruppo opzionali)
    │   ├── versions.tf
    │   ├── variables.tf
    │   ├── main.tf
    │   └── outputs.tf
    └── project/             #   crea un progetto (+ variabili di progetto opzionali)
        ├── versions.tf
        ├── variables.tf
        ├── main.tf
        └── outputs.tf

Perche' questa struttura?

  • Inventario (inventory.tf): l'elenco di cosa creare, espresso come dati (le mappe subgroups e projects). E' qui che aggiungi una voce per creare un nuovo sottogruppo/progetto. E' versionato in git: ogni modifica passa da una MR.
  • Root (gli altri .tf): il "motore". subgroups.tf/projects.tf ciclano con for_each sull'inventario e richiamano i moduli; non li tocchi quasi mai. Terraform unisce automaticamente tutti i .tf della stessa cartella.
  • Moduli (modules/): "stampi" riutilizzabili che descrivono come si crea un sottogruppo o un progetto, con i default di sicurezza (es. visibilita' privata). Lo standard si scrive una volta e vale per tutti.

2. Prerequisiti

2.1 Installare Terraform (dentro la WSL OracleLinux)

Apri la shell della tua WSL (OracleLinux_9_5) ed esegui:

sudo dnf install -y dnf-plugins-core
sudo dnf config-manager --add-repo https://rpm.releases.hashicorp.com/RHEL/hashicorp.repo
sudo dnf -y install terraform
terraform -version

In alternativa puoi usare OpenTofu (fork open source, compatibile): i comandi diventano tofu init, tofu plan, ecc. Il codice di questo progetto funziona con entrambi.

2.2 Creare un token di accesso GitLab

  1. Su GitLab: User Settings → Access Tokens (Personal Access Token) — oppure usa un Service Account dedicato (consigliato per l'automazione).
  2. Scope: api.
  3. Il token deve appartenere a un utente con ruolo Owner o Maintainer sul gruppo radice (serve per creare sottogruppi/progetti).
  4. Copia il token (glpat-...): lo vedrai una sola volta.

Nota: i Project/Group Access Token hanno permessi piu' limitati e possono dare errori su alcune risorse. Per iniziare, un Personal Access Token e' la scelta piu' semplice.


3. Setup iniziale

# 1) Entra nella cartella del progetto
cd ~/PlatformTeam/Terraform/GitLab

# 2) Crea il tuo file di variabili a partire dall'esempio
cp terraform.tfvars.example terraform.tfvars
#    poi modifica parent_group_path con il full path del tuo gruppo radice

# 3) Esporta il token (NON va nei file .tf!)
export GITLAB_TOKEN="glpat-xxxxxxxxxxxxxxxxxxxx"

Suggerimento: l'export vale solo per la sessione corrente del terminale. Per non riscriverlo ogni volta puoi usare uno strumento come direnv con un file .envrc (da NON committare), oppure rilanciarlo ad ogni sessione.


4. Comandi base

terraform fmt        # formatta i file .tf in modo canonico
terraform init       # scarica il provider e inizializza la cartella (la prima volta)
terraform validate   # controlla che la configurazione sia sintatticamente valida
terraform plan        # mostra COSA verrebbe creato/modificato/distrutto (nessuna modifica)
terraform apply       # applica le modifiche (chiede conferma: scrivi "yes")
terraform destroy     # distrugge tutto cio' che e' gestito da questo stato (attenzione!)

Flusso tipico: fmt → init (la prima volta) → validate → plan → apply.

Parti sempre da plan: e' una "anteprima" sicura, non tocca nulla su GitLab.


5. Come usarlo ed estenderlo

Tutto ruota attorno a inventory.tf: e' l'unico file che modifichi per creare o rimuovere sottogruppi e progetti. subgroups.tf e projects.tf ci ciclano sopra e non vanno toccati.

Aggiungere un sottogruppo

In inventory.tf, aggiungi una voce alla mappa subgroups (la chiave e' il path):

locals {
  subgroups = {
    "terraform-sandbox" = { name = "Terraform Sandbox" }
    "team-backend"      = { name = "Team Backend" } # <- nuovo
  }
}

Aggiungere un progetto

Aggiungi una voce alla mappa projects. Il campo subgroup indica in quale sottogruppo crearlo (= una chiave di subgroups):

locals {
  projects = {
    "hello-terraform" = { name = "Hello Terraform", subgroup = "terraform-sandbox" }
    "billing"         = { name = "Billing", subgroup = "team-backend" } # <- nuovo
  }
}

Poi terraform plan (anteprima) e terraform apply. Nessun nuovo file, nessun nuovo blocco: solo una riga di dati.

Membri e permessi

Non si gestiscono qui: l'accesso e' gestito tramite SAML Group Links, fuori da Terraform (vedi la nota all'inizio del README).

Variabili CI/CD (opzionale)

I moduli accettano una mappa ci_variables (default: vuota). Quando vorrai gestirle dai dati, si aggiunge il campo nell'inventario e lo si inoltra al modulo. Forma:

ci_variables = {
  "APP_ENV"      = { value = "production" }
  "DEPLOY_TOKEN" = { value = "...", masked = true, protected = true }
}

6. Migrazione dello stato su GitLab (quando vorrai)

Ora lo stato e' un file locale (terraform.tfstate). Per passare allo stato gestito da GitLab (lock automatico, condivisibile in team), senza perdere nulla:

  1. Crea (o scegli) un progetto GitLab che faccia da contenitore dello stato e prendi nota del suo Project ID (lo trovi nella home del progetto).

  2. Scommenta il blocco backend "http" in backend.tf.

  3. Crea un file backend.hcl (gia' nel .gitignore) con gli indirizzi:

    address        = "https://gitlab.com/api/v4/projects/<PROJECT_ID>/terraform/state/platform"
    lock_address   = "https://gitlab.com/api/v4/projects/<PROJECT_ID>/terraform/state/platform/lock"
    unlock_address = "https://gitlab.com/api/v4/projects/<PROJECT_ID>/terraform/state/platform/lock"
    username       = "<il-tuo-username-gitlab>"

    (platform e' il nome dello stato: puoi sceglierlo.)

  4. Passa il token come password del backend ed esegui la migrazione:

    export TF_HTTP_PASSWORD="$GITLAB_TOKEN"
    terraform init -migrate-state -backend-config=backend.hcl

    Terraform copiera' lo stato locale su GitLab. Da quel momento puoi cancellare i file terraform.tfstate* locali.


7. Best practices applicate qui (e perche')

  • Niente segreti nel codice. Token via GITLAB_TOKEN, valori sensibili fuori dai .tf. Lo stato e i *.tfvars sono nel .gitignore.
  • Versioni bloccate. versions.tf fissa Terraform >= 1.5 e il provider ~> 19.0. Committa .terraform.lock.hcl (NON e' ignorato) per run riproducibili.
  • Moduli riutilizzabili. Logica di creazione in modules/, configurazione nella root: meno duplicazione, piu' coerenza.
  • for_each invece di count. L'inventario e le variabili usano mappe con chiavi stabili: aggiungere/rimuovere un elemento non "sposta" gli altri nello stato.
  • Validazioni di input. La visibilita' e' validata: errori chiari prima di chiamare le API.
  • Separazione dei compiti. Terraform gestisce la struttura; i membri li gestisce SAML Group Links. Mai due sistemi sulla stessa cosa.
  • Workflow plan prima di apply. Rivedi sempre il piano prima di applicare.

8. Troubleshooting

Problema Causa probabile / Soluzione
401 Unauthorized GITLAB_TOKEN mancante/scaduto o senza scope api.
403 Forbidden su creazione L'utente del token non e' Owner/Maintainer sul gruppo radice.
404 sul data "gitlab_group" parent_group_path errato: usa il full path, non il nome.
Errore sul default_branch L'istanza usa un branch iniziale diverso da main. Imposta default_branch di conseguenza o lascia initialize_with_readme = true.
409 Conflict / risorsa gia' esistente Il sottogruppo/progetto esiste gia': importalo con terraform import invece di ricrearlo.

Riferimenti

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages