0Pricing
Linux Command Line & Bash Scripting Mastery · Lezione

Modificare file di configurazione YAML con yq

Legga e modifichi direttamente file YAML di Kubernetes e CI usando yq, preservandone struttura e commenti.

Modificare file di configurazione YAML con yq è una lezione Linux Command Line & Bash Scripting Mastery gratuita su CoddyKit. Questa è la lezione 4 di 4. Puoi leggere la lezione completa qui gratuitamente — poi esercitati direttamente nel browser con un editor di codice integrato e un tutor IA disponibile 24/7. Fa parte del percorso di apprendimento Linux Command Line & Bash Scripting Mastery, e i tuoi progressi si sincronizzano tra il web e l'app CoddyKit. Il corso Linux Command Line & Bash Scripting Mastery include 4 lezioni in totale.

Che cos'è yq e perché usarlo per YAML?

yq è un processore YAML portabile da riga di comando, analogo a jq per la gestione del JSON. Consente di leggere, filtrare e modificare i file YAML senza scrivere uno script in Python o Ruby.

Esistono due strumenti popolari denominati yq:

  • mikefarah/yq (Go) — mantenuto attivamente, supporta YAML, JSON, XML e TOML. Questa lezione usa questa versione.
  • kislyuk/yq (Python) — un wrapper di jq per YAML; la sintassi è diversa.

Installate la versione Go:

  • brew install yq su macOS
  • snap install yq su Linux
  • Oppure scaricate il binario: wget https://github.com/mikefarah/yq/releases/latest/download/yq_linux_amd64 -O /usr/local/bin/yq && chmod +x /usr/local/bin/yq

Verificate l'installazione: yq --version dovrebbe stampare v4.x.x. La versione 4 usa una sintassi delle espressioni diversa dalla versione 3, quindi la versione è importante.

# Install yq (Go version) on Linux
wget -q https://github.com/mikefarah/yq/releases/latest/download/yq_linux_amd64 \
  -O /usr/local/bin/yq
chmod +x /usr/local/bin/yq

# Confirm version
yq --version

Lettura dei valori da un file YAML di Deployment Kubernetes

Prima di modificare qualsiasi cosa, imparate a leggere i campi YAML. Dato un Deployment Kubernetes, potete estrarre qualsiasi valore annidato usando percorsi con notazione a punti.

Esempio di deployment.yaml:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-app
  namespace: production
spec:
  replicas: 3
  template:
    spec:
      containers:
        - name: app
          image: my-app:1.0.0

Comandi principali per la lettura:

  • yq '.metadata.name' deployment.yaml — stampa my-app
  • yq '.spec.replicas' deployment.yaml — stampa 3
  • yq '.spec.template.spec.containers[0].image' deployment.yaml — stampa my-app:1.0.0

Per impostazione predefinita, l'output è testo semplice, senza virgolette. Aggiungete il flag -r oppure usate | yq -r se vi servono stringhe non elaborate negli script.

# Create a sample deployment YAML
cat > /tmp/deployment.yaml << 'EOF'
apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-app
  namespace: production
spec:
  replicas: 3
  template:
    spec:
      containers:
        - name: app
          image: my-app:1.0.0
EOF

# Read individual fields
echo "App name:    $(yq '.metadata.name' /tmp/deployment.yaml)"
echo "Replicas:    $(yq '.spec.replicas' /tmp/deployment.yaml)"
echo "Image:       $(yq '.spec.template.spec.containers[0].image' /tmp/deployment.yaml)"

Modifica in-place con il flag -i

Il flag più importante nell'uso reale è -i (in-place). Senza di esso, yq stampa i risultati nello stdout e lascia invariato il file.

Sintassi:

  • Sola lettura (stdout): yq '.spec.replicas' file.yaml
  • Modifica in-place: yq -i '.spec.replicas = 5' file.yaml

L'operatore di assegnazione = imposta un valore. L'espressione è un filtro yq completo, quindi potete combinare lettura e scrittura in un unico passaggio.

Importante: yq -i riscrive completamente il file. I commenti inseriti sulla stessa riga di un campo vengono generalmente conservati, ma i blocchi di commenti autonomi possono essere spostati. Eseguite sempre il commit del file YAML nel sistema di controllo versione prima di applicare modifiche in-place in blocco.

Testate prima senza -i, poi aggiungetelo quando siete soddisfatti dell'output.

# Start with the deployment from the previous scene
echo 'Before:' && yq '.spec.replicas' /tmp/deployment.yaml

# Edit in place: scale to 5 replicas
yq -i '.spec.replicas = 5' /tmp/deployment.yaml

echo 'After:' && yq '.spec.replicas' /tmp/deployment.yaml

Aggiornamento del tag dell'immagine del container

Un'attività CI molto comune consiste nell'aggiornare il tag dell'immagine Docker in un manifest Kubernetes dopo la creazione di una nuova immagine. Con yq diventa un comando su una sola riga.

Lo schema è il seguente:

  • Individuate il container per nome usando select(), evitando di fissare l'indice dell'array a 0.
  • Usate |= (operatore di aggiornamento) oppure = per impostare il nuovo valore.

Usando l'indice dell'array (fragile se cambia l'elenco dei container):

  • yq -i '.spec.template.spec.containers[0].image = "my-app:2.1.0"' deployment.yaml

Usando select() (robusto):

  • yq -i '(.spec.template.spec.containers[] | select(.name == "app")).image = "my-app:2.1.0"' deployment.yaml

In una pipeline CI passereste il tag come variabile shell:

NEW_TAG="my-app:2.1.0"
CONTAINER_NAME="app"

# Robust update: target by container name, not index
yq -i \
  "(.spec.template.spec.containers[] | select(.name == \"${CONTAINER_NAME}\")).image = \"${NEW_TAG}\"" \
  /tmp/deployment.yaml

# Verify
yq '.spec.template.spec.containers[0].image' /tmp/deployment.yaml

Aggiunta e rimozione di campi

Oltre ad aggiornare i campi esistenti, yq può aggiungere nuove chiavi o eliminare quelle esistenti.

Aggiunta di un campo:

  • Assegnate semplicemente un valore a un percorso inesistente: yq -i '.metadata.labels.version = "v2"' file.yaml
  • Se manca la chiave padre (labels), yq la crea automaticamente.

Eliminazione di un campo:

  • Usate la funzione del(): yq -i 'del(.metadata.annotations)' file.yaml
  • Eliminate un elemento dell'array tramite indice: yq -i 'del(.spec.template.spec.containers[1])' file.yaml

Aggiunta di un elemento a un array:

  • yq -i '.spec.template.spec.containers += [{"name": "sidecar", "image": "envoy:latest"}]' file.yaml
# Add a label to the deployment
yq -i '.metadata.labels.version = "v2"' /tmp/deployment.yaml
yq -i '.metadata.labels.managed-by = "ci-pipeline"' /tmp/deployment.yaml

echo '--- Labels after adding ---'
yq '.metadata.labels' /tmp/deployment.yaml

# Delete one label
yq -i 'del(.metadata.labels.managed-by)' /tmp/deployment.yaml

echo '--- Labels after delete ---'
yq '.metadata.labels' /tmp/deployment.yaml

Utilizzo di file YAML con più documenti

I manifest Kubernetes raggruppano spesso più risorse in un unico file, separate da ---. Per impostazione predefinita, yq elabora tutti i documenti presenti nel file.

Tecniche principali:

  • Elencare tutti i tipi di documento: yq '.[].kind' multi.yaml — notate il prefisso .[] per iterare sui documenti.
  • Individuare un documento specifico per tipo: yq 'select(.kind == "Service")' multi.yaml
  • Modificare in-place solo i documenti corrispondenti:

yq -i 'select(.kind == "Deployment").spec.replicas = 2' multi.yaml

I documenti che non soddisfano il predicato select() vengono lasciati invariati, quindi le risorse Service, ConfigMap e le altre rimangono intatte.

Per dividere un file con più documenti in singoli file, potete iterare sull'output di yq oppure usare:

  • yq -s '.kind' multi.yaml — scrive un file per documento, denominato in base al valore di .kind.
cat > /tmp/multi.yaml << 'EOF'
apiVersion: apps/v1
kind: Deployment
metadata:
  name: web
spec:
  replicas: 1
---
apiVersion: v1
kind: Service
metadata:
  name: web-svc
spec:
  port: 80
EOF

# Scale ONLY the Deployment, leave Service untouched
yq -i 'select(.kind == "Deployment").spec.replicas = 4' /tmp/multi.yaml

echo '--- Deployment replicas ---'
yq 'select(.kind == "Deployment").spec.replicas' /tmp/multi.yaml

echo '--- Service port (unchanged) ---'
yq 'select(.kind == "Service").spec.port' /tmp/multi.yaml

Modifica di un file YAML CI di GitHub Actions

Anche i file di configurazione CI (.github/workflows/*.yml, .gitlab-ci.yml) sono file YAML. Gli stessi comandi yq funzionano, anche se i percorsi possono essere profondamente annidati.

Attività comuni di modifica della CI:

  • Fissare la versione del runner: aggiornate runs-on in tutti i job.
  • Aggiornare la versione di un'action: individuate i passaggi che usano una determinata action e incrementate il relativo campo uses.
  • Attivare o disattivare un flag: abilitate o disabilitate un'impostazione a livello di workflow.

Esempio: aggiornare alla versione 4 tutti i passaggi che usano actions/checkout:

yq -i '(.jobs[].steps[] | select(.uses == "actions/checkout@v3")).uses = "actions/checkout@v4"' .github/workflows/ci.yml

Questo idioma — iterare con [], restringere con select(), assegnare con = — è lo schema fondamentale per qualsiasi modifica a YAML strutturato.

cat > /tmp/ci.yml << 'EOF'
name: CI
on: [push]
jobs:
  build:
    runs-on: ubuntu-22.04
    steps:
      - uses: actions/checkout@v3
      - uses: actions/setup-node@v3
        with:
          node-version: 18
      - run: npm test
  lint:
    runs-on: ubuntu-22.04
    steps:
      - uses: actions/checkout@v3
      - run: npm run lint
EOF

# Bump all checkout steps from v3 → v4
yq -i '(.jobs[].steps[] | select(.uses == "actions/checkout@v3")).uses = "actions/checkout@v4"' \
  /tmp/ci.yml

# Verify both jobs were updated
yq '.jobs[].steps[] | select(.uses | test("checkout")).uses' /tmp/ci.yml

Utilizzo delle variabili d'ambiente nelle espressioni yq

Inserire valori direttamente nelle espressioni yq rende gli script fragili. yq supporta l'iniezione di variabili shell usando la funzione env() o la forma abbreviata strenv().

  • env(VAR_NAME) — legge la variabile d'ambiente e la converte nel tipo YAML appropriato (un numero rimane un numero, una stringa rimane una stringa).
  • strenv(VAR_NAME) — restituisce sempre una stringa, utile per i tag delle immagini.

In questo modo si evita l'incubo delle virgolette causato dall'interpolazione di variabili all'interno di stringhe shell tra virgolette doppie contenenti percorsi YAML.

Schema:

export IMAGE_TAG="my-app:3.0.0"
yq -i '.spec.template.spec.containers[0].image = strenv(IMAGE_TAG)' deployment.yaml

Usate env() quando impostate campi numerici come replicas, così il tipo YAML viene preservato (intero, non stringa tra virgolette).

export APP_IMAGE="my-app:3.0.0"
export REPLICA_COUNT=6

# Set image using strenv() — result is a YAML string
yq -i '.spec.template.spec.containers[0].image = strenv(APP_IMAGE)' \
  /tmp/deployment.yaml

# Set replicas using env() — result is a YAML integer
yq -i '.spec.replicas = env(REPLICA_COUNT)' \
  /tmp/deployment.yaml

# Confirm types are correct in the output
yq '.spec.replicas, .spec.template.spec.containers[0].image' /tmp/deployment.yaml

Unire due file YAML

A volte è necessario applicare un file di patch (un piccolo YAML di override) a una configurazione di base, ad esempio per gestire override specifici dell'ambiente nei workflow in stile Kustomize.

yq può unire due file usando l'operatore di merge *:

  • yq '. *= load("patch.yaml")' base.yaml — esegue un merge profondo della patch nella base e scrive il risultato su stdout.
  • Aggiunga -i per aggiornare direttamente il file di base: yq -i '. *= load("patch.yaml")' base.yaml

Comportamento del merge:

  • I valori scalari nella patch sovrascrivono quelli della base.
  • Le mappe vengono unite con un merge profondo (le chiavi non presenti nella patch vengono mantenute).
  • Le sequenze (array) vengono sostituite per impostazione predefinita, non accodate. Utilizzi *+ per accodarle.

Questo approccio sostituisce gli script sed fragili, che si rompono quando cambiano gli spazi bianchi.

cat > /tmp/base.yaml << 'EOF'
app:
  name: my-service
  port: 8080
  debug: false
database:
  host: localhost
  port: 5432
EOF

cat > /tmp/patch.yaml << 'EOF'
app:
  port: 9090
  debug: true
database:
  host: db.production.svc
EOF

# Deep-merge patch into base (stdout preview first)
yq '. *= load("/tmp/patch.yaml")' /tmp/base.yaml

# Apply in place
yq -i '. *= load("/tmp/patch.yaml")' /tmp/base.yaml

Convalidare YAML e convertire in JSON

Prima di applicare un YAML con patch a un cluster, è buona norma convalidarlo e, se necessario, convertirlo in JSON per altri strumenti.

Convalidare la sintassi:

  • yq '.' file.yaml && echo "Valid" — yq termina con il codice 1 in caso di errori di analisi, quindi questo comando è adatto ai controlli CI.

Convertire YAML in JSON:

  • yq -o=json '.' file.yaml — restituisce JSON formattato.
  • Invii l'output a jq per ulteriori elaborazioni JSON: yq -o=json '.' file.yaml | jq '.metadata.name'

Convertire JSON in YAML:

  • yq -P '.' file.json — il flag -P forza l'output in formato YAML (formattato) quando l'input è JSON.

Queste conversioni fanno di yq un ponte tra gli strumenti nativi YAML (Helm, kubectl) e quelli nativi JSON (Terraform, AWS CLI, jq).

# Validate YAML (exits 0 on success, 1 on parse error)
if yq '.' /tmp/deployment.yaml > /dev/null 2>&1; then
  echo "YAML is valid"
else
  echo "YAML parse error!" >&2
  exit 1
fi

# Convert to JSON and query with jq
yq -o=json '.' /tmp/deployment.yaml \
  | jq '{name: .metadata.name, image: .spec.template.spec.containers[0].image}'

# Round-trip: JSON snippet back to YAML
echo '{"replicas": 7, "strategy": "RollingUpdate"}' \
  | yq -P '.'

Uno script completo per applicare patch al deployment in CI

Riuniamo tutte le tecniche in uno script CI reale che applica patch a un manifest Kubernetes Deployment nell'ambito di una pipeline GitOps.

Lo script:

  1. Convalida il YAML di input prima di modificarlo.
  2. Utilizza env() / strenv() per tutte le sostituzioni di variabili.
  3. Aggiorna il tag dell'immagine del container usando un select() basato sul nome.
  4. Aumenta il numero di repliche.
  5. Imposta un'annotazione deploy-time con il timestamp corrente.
  6. Convalida nuovamente l'output prima del commit.

Questo approccio garantisce che, anche se la pipeline viene eseguita simultaneamente, ogni passaggio sia atomico e verificabile.

#!/usr/bin/env bash
set -euo pipefail

MANIFEST="/tmp/deployment.yaml"
export NEW_IMAGE="my-app:$(date +%Y%m%d)-abc1234"
export NEW_REPLICAS=3
export DEPLOY_TIME="$(date -u +%Y-%m-%dT%H:%M:%SZ)"
export CONTAINER="app"

# 1. Validate before patching
yq '.' "$MANIFEST" > /dev/null

# 2. Update image (by container name)
yq -i \
  '(.spec.template.spec.containers[] | select(.name == strenv(CONTAINER))).image = strenv(NEW_IMAGE)' \
  "$MANIFEST"

# 3. Set replicas
yq -i '.spec.replicas = env(NEW_REPLICAS)' "$MANIFEST"

# 4. Stamp annotation
yq -i '.metadata.annotations."deploy-time" = strenv(DEPLOY_TIME)' "$MANIFEST"

# 5. Validate result
yq '.' "$MANIFEST" > /dev/null && echo "Patch applied successfully"

# 6. Show diff summary
yq '{image: .spec.template.spec.containers[0].image, replicas: .spec.replicas}' "$MANIFEST"

Verifica delle conoscenze: modifica sicura di più documenti

Verifichi la Sua comprensione della modifica di file YAML Kubernetes composti da più documenti con yq.

Riepilogo della lezione: modificare YAML con yq

Ha completato la lezione sulla modifica dei file di configurazione YAML con yq. Ecco un riepilogo conciso di tutti gli argomenti trattati:

  • Installazione: utilizzi il binario Go mikefarah/yq (v4). Verifichi l'installazione con yq --version.
  • Lettura: percorsi con notazione puntata come .spec.replicas; accesso agli array con [0] o iterazione con [].
  • Modifica sul posto: il flag -i riscrive il file. Visualizzi sempre prima il risultato senza -i.
  • Selezione robusta: preferisca select(.name == "app") agli indici hard-coded degli array.
  • Aggiunta / eliminazione: assegni un valore a un nuovo percorso per crearlo; utilizzi del() per rimuovere i campi.
  • File composti da più documenti: utilizzi select(.kind == "...") per selezionare una risorsa e lasciare inalterate le altre.
  • Variabili CI: utilizzi strenv(VAR) per le stringhe e env(VAR) per i valori tipizzati, evitando i problemi di quoting della shell.
  • Merge: . *= load("patch.yaml") esegue un merge profondo di un file di override senza perdere le chiavi non incluse nella patch.
  • Convalida e conversione: utilizzi yq '.' come controllo lint; -o=json e -P per convertire il formato.

Il modello di base per qualsiasi patch YAML in CI è: convalidare → selezionare → assegnare → convalidare. Lo combini con strenv() e select() e non avrà più bisogno di ricorrere a one-liner sed fragili.

Domande Frequenti

La lezione «Modificare file di configurazione YAML con yq» è gratuita?

Sì — il testo completo di «Modificare file di configurazione YAML con yq» è gratuito qui sul web. Per esercitarvi in modo interattivo (un editor di codice integrato e un tutor IA 24/7) e sbloccare il resto del corso Linux Command Line & Bash Scripting Mastery, passa a CoddyKit PRO. Il corso Linux Command Line & Bash Scripting Mastery include 4 lezioni in totale.

Cosa imparerò in «Modificare file di configurazione YAML con yq»?

Legga e modifichi direttamente file YAML di Kubernetes e CI usando yq, preservandone struttura e commenti. Eserciti Linux Command Line & Bash Scripting Mastery con codice pratico che esegui direttamente nel browser, e un tutor IA 24/7 risponde alle tue domande mentre lavori sulla lezione.

Ho bisogno di esperienza per iniziare Linux Command Line & Bash Scripting Mastery?

Non è richiesta alcuna esperienza precedente. Linux Command Line & Bash Scripting Mastery su CoddyKit è strutturato per principianti e studenti avanzati, quindi puoi iniziare da qui o dall'inizio e procedere al tuo ritmo. Questa è la lezione 4 di 4.

Quanto tempo richiede la lezione «Modificare file di configurazione YAML con yq»?

La maggior parte delle lezioni CoddyKit richiede circa 5–10 minuti. Ogni lezione è breve e interattiva, quindi fai progressi costanti e riprendi esattamente da dove hai lasciato su web e app.

Posso scrivere ed eseguire codice in questa lezione Linux Command Line & Bash Scripting Mastery?

Sì. Ogni lezione Linux Command Line & Bash Scripting Mastery include un editor di codice integrato, quindi scrivi ed esegui codice reale direttamente nel tuo browser e ricevi feedback istantaneo dall'IA — nessuna configurazione locale necessaria.

Tutte le lezioni di questo corso

  1. Filtrare e selezionare JSON con le pipeline jq
  2. Trasformare e costruire oggetti JSON con jq
  3. Usare insieme curl e jq per consumare API REST
  4. Modificare file di configurazione YAML con yq
← Torna a Linux Command Line & Bash Scripting Mastery