Как реализовать параметр повтора для неудачных этапов в конвейерах Jenkins?

У меня есть Jenkinsfile с несколькими этапами, и один из них - фактически другое задание (развертывание), которое в некоторых случаях может завершиться сбоем.

Я знаю, что могу делать запросы, используя Jenkinsfile, но я не знаю, как реализовать механизм повторных попыток для этой работы.

Я хочу иметь возможность щелкнуть по неудачной стадии и выбрать повторную попытку. Дженкинс-трубопроводы-с-туры

3 ответа

Решение

Вы должны быть в состоянии объединить повторные попытки + ввод, чтобы сделать это Что-то подобное

stage('deploy-test') {
   try {
     build 'yourJob'
   } catch(error) {
     echo "First build failed, let's retry if accepted"
     retry(2) {
        input "Retry the job ?"
        build 'yourJob'
     }
   }
}

Вы также можете использовать тайм-аут для ввода, если вы хотите, чтобы он закончился, если никто не проверяет. Есть также waitUntil, который может быть полезен, но я еще не использовал его

Редактировать: WaitUntil кажется определенно лучшим, вы должны поиграть с ним немного, но что-то вроде этого чище:

stage('deploy-test') {
   waitUntil {
     try {
       build 'yourJob'
     } catch(error) {
        input "Retry the job ?"
        false
     }
   }
}

Между прочим, здесь есть все шаги, описанные здесь: https://jenkins.io/doc/pipeline/steps

Этот с хорошим постепенным ожиданием

stage('deploy-test') {
 def retryAttempt = 0
 retry(2) {
    if (retryAttempt > 0) {
       sleep(1000 * 2 + 2000 * retryAttempt)
    }

    retryAttempt = retryAttempt + 1
    input "Retry the job ?"
    build 'yourJob'
 }
}

Этот смысл (не мой) был одним из лучших вариантов, которые я нашел, пытаясь реализовать эту функцию тоже. https://gist.github.com/beercan1989/b66b7643b48434f5bdf7e1c87094acb9

Изменил его на метод в разделяемой библиотеке, который только что повторил или прервал для моих нужд. Также добавлено максимальное количество повторов и переменная тайм-аута, чтобы мы могли изменить ее в зависимости от задания или этапа, который в этом нуждается.

package com.foo.bar.jenkins

def class PipelineHelper {
    def steps

    PipelineHelper(steps) {
        this.steps = steps
    }

    void retryOrAbort(final Closure<?> action, int maxAttempts, int timeoutSeconds, final int count = 0) {
        steps.echo "Trying action, attempt count is: ${count}"
        try {
            action.call();
        } catch (final exception) {
            steps.echo "${exception.toString()}"
            steps.timeout(time: timeoutSeconds, unit: 'SECONDS') {
                def userChoice = false
                try {
                    userChoice = steps.input(message: 'Retry?', ok: 'Ok', parameters: [
                            [$class: 'BooleanParameterDefinition', defaultValue: true, description: '', name: 'Check to retry from failed stage']])
                } catch (org.jenkinsci.plugins.workflow.steps.FlowInterruptedException e) {
                    userChoice = false
                }
                if (userChoice) {
                    if (count <= maxAttempts) {
                        steps.echo "Retrying from failed stage."
                        return retryOrAbort(action, maxAttempts, timeoutMinutes, count + 1)
                    } else {
                        steps.echo "Max attempts reached. Will not retry."
                        throw exception
                    }
                } else {
                    steps.echo 'Aborting'
                    throw exception;
                }
            }
        }
    }
}

Пример использования с максимум 2 повторными попытками, ожидающими ввода 60 секунд.

def pipelineHelper = new PipelineHelper(this)

stage ('Retry Example'){
    pipelineHelper.retryOrAbort({
        node{
            echo 'Here is an example'
            throw new RuntimeException('This example will fail.')
        }
    }, 2, 60)
}

Просто не забудьте поместить узлы внутри замыкания, чтобы ожидание ввода не блокировало исполнителя.

Если у вас есть платная jenkins Enterprise Cloudbees, у нее есть плагин Checkpoint, который может лучше справиться с этим, но его выпуск с открытым исходным кодом Jenkins не планируется ( JENKINS-33846).

Другие вопросы по тегам