Last modified: March 11, 2025
·
3 min read

Come implementare una strategia di retry nella tua pipeline Jenkins

Implementare una strategia di retry e molto semplice se usi il plugin Naginator su Jenkins. Diventa piu complicato quando si ha a che fare con un job multibranch/multirepo: in quei casi non e possibile configurare il retry come post build action nella configurazione del job. Come si implementa quindi una strategia di retry via codice? In questo articolo mostro alcuni metodi usando la sintassi dichiarativa.

1. Usare solo retry()

retry(count: 3) {
  sleep(60)
  doSomething()
}
Pro:
  • Implementazione semplice
Contro:
  • Spreco di RAM. Se vogliamo riprovare dopo 1 minuto perche il progetto dipende da un altro i cui cambiamenti non sono ancora stati pubblicati, il job rimarra attivo per tutto quel tempo anche senza fare nulla
  • Se piu job rimangono in attesa del retry contemporaneamente, Jenkins potrebbe superare il numero massimo di build concorrenti. Questo significa che una pipeline avviata dopo, che potrebbe far riuscire il job corrente (ad esempio compilando un progetto da cui dipende), non potra partire, rendendo il tutto inutile
  • Non e possibile tenere traccia graficamente di quante volte si e riprovato prima di ottenere un risultato positivo

2. Chiamare un nuovo job

retry(count: 3) {
  script {
    if (params.retry) {
      def jobBuild = build  job: "$env.JOB_NAME", parameters: [
          booleanParam(name: "retry", value: false)
        ], wait: true, quietPeriod: 60
      params.retry = jobBuild.getResult() != "SUCCESS"
    }
  }
}
Pro:
  • E possibile tenere traccia graficamente di quante volte si e riprovato prima di ottenere un risultato positivo
Contro:
  • Stesso problema con la RAM
  • Stesso problema con le build concorrenti

3. Chiamare ricorsivamente un nuovo job

Richiamo il job con un parametro che conta il numero di retry. Se viene catturato un errore, viene chiamato un altro job ricorsivamente. Grazie alla ricorsione, non e necessario attendere il completamento del job downstream.

script {
  if ("${params.retriesCounter}".toInteger() < 3) {
    build  job: "$env.JOB_NAME", parameters: [
      string(name: "retriesCounter", value: ("${params.retriesCounter}".toInteger() + 1).toString())
    ], wait: false, quietPeriod: 60
  }
}
Pro:
  • Operazione piu leggera possibile. I job non occupano RAM mentre attendono di riprovare
  • Completamente asincrono: altre pipeline possono girare durante il quietPeriod di un job fallito
  • E possibile tenere traccia graficamente di quante volte si e riprovato prima di ottenere un risultato positivo
Contro:
  • Ogni job upstream che avvia questa pipeline perde le informazioni sullo stato del job downstream. Esempio:
up-job chiama test-pipeline(0)
    test-pipeline(0) lancia e cattura un errore
    test-pipeline(0) chiama test-pipeline(1)
    test-pipeline(1) completata con successo
    test-pipeline(0) completata con fallimento

Anche se test-pipeline e completata con successo dopo un retry, il job upstream che l'ha avviata risulta fallito.

Conclusione

In questo articolo abbiamo discusso diverse strategie per implementare un retry nelle pipeline Jenkins, illustrando pro e contro di ciascuna.

Stay in the loop
Subscribe to our newsletter to get the latest articles delivered to your inbox