Migrer de Jenkins vers Azure Pipelines

Azure DevOps Services

Jenkins, un serveur d’automatisation open source, est traditionnellement installé par les entreprises dans leurs propres centres de données et gérés localement. De nombreux fournisseurs offrent également un hébergement Jenkins géré.

Azure Pipelines est également un pipeline d’intégration continue native cloud. Il fournit la gestion des pipelines multistages et crée des machines virtuelles Azure d’agent hébergées dans le cloud.

Azure Pipelines offre également une option entièrement locale avec Azure DevOps Server, pour les clients qui ont des problèmes de conformité ou de sécurité qui les obligent à conserver leur code et à créer dans le centre de données d’entreprise.

En outre, Azure Pipelines prend en charge les modèles cloud et locaux hybrides. Azure Pipelines peut gérer l’orchestration de build et de mise en production et activer des agents de build, à la fois dans le cloud et installés localement.

Cet article fournit un guide pour traduire une configuration de pipeline Jenkins vers Azure Pipelines. Il inclut des informations sur la migration des builds basés sur des conteneurs, la sélection des agents de compilation, le mappage des variables d'environnement, et la gestion de la réussite et des échecs de la chaîne de construction.

Paramétrage

Vous remarquerez une transition familière d’un pipeline Jenkins déclaratif vers une configuration YAML dans Azure Pipelines. Les deux sont conceptuellement similaires, prenant en charge la « configuration en tant que code » et vous permettant de vérifier votre configuration dans votre système de contrôle de version. Contrairement à Jenkins, toutefois, Azure Pipelines utilise le YAML standard pour configurer le pipeline de build.

Les concepts entre Jenkins et Azure Pipelines et la façon dont ils sont configurés sont similaires. Un fichier Jenkins répertorie une ou plusieurs étapes du processus de génération, chacune contenant une ou plusieurs étapes effectuées dans l’ordre. Par exemple, une phase de construction peut exécuter une tâche pour installer des dépendances nécessaires à la construction, puis effectuer une étape de compilation. Une phase de « test » peut appeler l'outil de test sur les fichiers binaires qui ont été produits lors de la phase de compilation.

Par exemple:

Jenkinsfile

pipeline {
    agent none
    stages {
        stage('Build') {
            steps {
                sh 'npm install'
                sh 'npm run build'
            }
        }
        stage('Test') {
            steps {
                sh 'npm test'
            }
        }
    }
}

Le fichier jenkinsfile se traduit facilement en une configuration YAML Azure Pipelines, avec un travail correspondant à chaque étape et des étapes à effectuer dans chaque travail :

azure-pipelines.yml

jobs:
- job: Build
  steps:
  - script: npm install
  - script: npm run build
- job: Test
  steps:
  - script: npm test

Builds basées sur des conteneurs

L’utilisation de conteneurs dans votre pipeline de build vous permet de générer et de tester dans une image Docker qui a les dépendances exactes dont votre pipeline a besoin, déjà configurée. Il vous évite d'avoir à inclure une étape de construction qui installe plus de logiciels ou configure l'environnement. Jenkins et Azure Pipelines prennent en charge les builds basées sur des conteneurs.

En outre, Jenkins et Azure Pipelines vous permettent de partager le répertoire de build sur l’agent hôte sur le volume de conteneur à l’aide de l’indicateur -v pour docker. Cela vous permet de chaîner plusieurs travaux de génération ensemble qui peuvent utiliser les mêmes sources et écrire dans le même répertoire de sortie. Cela est particulièrement utile lorsque vous utilisez de nombreuses technologies différentes dans votre pile ; vous pouvez créer votre back-end à l’aide d’un conteneur .NET Core et de votre front-end avec un conteneur TypeScript.

Par exemple, pour exécuter une build dans un conteneur Ubuntu 22.04 (« Jammy »), exécutez ensuite des tests dans un conteneur Ubuntu 24.04 (« Noble ») :

Jenkinsfile

pipeline {
    agent none
    stages {
        stage('Build') {
            agent {
                docker {
                    image 'ubuntu:jammy'
                    args '-v $HOME:/build -w /build'
                }
            }
            steps {
                sh 'make'
            }
        }
        stage('Test') {
            agent {
                docker {
                    image 'ubuntu:noble'
                    args '-v $HOME:/build -w /build'
                }
            }
            steps {
                sh 'make test'
            }
        }
    }
}

Azure Pipelines fournit des travaux de conteneur pour vous permettre d’exécuter votre build dans un conteneur :

azure-pipelines.yml

resources:
  containers:
  - container: jammy
    image: ubuntu:jammy
  - container: noble
    image: ubuntu:noble

jobs:
- job: build
  container: jammy
  steps:
  - script: make
- job: test
  dependsOn: build
  container: noble
  steps:
  - script: make test

En outre, Azure Pipelines fournit une tâche Docker qui vous permet d’exécuter, de générer ou d’envoyer (push) une image.

Sélection de l’agent

Jenkins propose une sélection d’agent de build à l’aide de l’option agent permettant de s’assurer que votre pipeline de build ( ou une étape particulière du pipeline) s’exécute sur un ordinateur d’agent de build particulier. De même, Azure Pipelines offre de nombreuses options pour configurer l’emplacement d’exécution de votre environnement de génération.

Sélection de l’agent hébergé

Azure Pipelines offre des agents de build hébergés dans le cloud pour les builds Linux, Windows et macOS. Pour sélectionner l’environnement de build, vous pouvez utiliser le vmimagemot clé. Par exemple, pour sélectionner une build macOS :

pool:
  vmimage: macOS-latest

En outre, vous pouvez spécifier une container et une image Docker pour un contrôle plus précis sur la façon dont votre build est exécutée.

Sélection de l’agent local

Si vous hébergez vos agents de build localement, vous pouvez définir les « fonctionnalités » de l’agent de build en fonction de l’architecture de l’ordinateur ou du logiciel sur lequel vous l’avez installé. Par exemple, si vous avez configuré un agent de build local avec les java fonctionnalités, vous pouvez vous assurer que votre travail s’exécute sur celui-ci à l’aide du demands mot clé :

pool:
  demands: java

Variables d'environnement

Dans Jenkins, vous définissez généralement des variables d’environnement pour l’ensemble du pipeline. Par exemple, pour définir deux variables d’environnement, CONFIGURATION=debug et PLATFORM=x86 :

Jenkinsfile

pipeline {
    agent any
    environment {
        CONFIGURATION = 'debug'
        PLATFORM      = 'x64'
    }
    stages {
        stage('Build') {
            steps {
                sh 'echo $CONFIGURATION $PLATFORM'
            }
        }
    }
}

De même, dans Azure Pipelines, vous pouvez configurer des variables qui sont utilisées à la fois dans la configuration YAML et qui sont définies comme variables d’environnement pendant l’exécution du travail :

azure-pipelines.yml

variables:
  configuration: debug
  platform: x64

En outre, dans Azure Pipelines, vous pouvez définir des variables définies uniquement pendant un travail particulier :

azure-pipelines.yml

jobs:
- job: debug build
  variables:
    configuration: debug
  steps:
  - script: ./build.sh $(configuration)
- job: release build
  variables:
    configuration: release
  steps:
  - script: ./build.sh $(configuration)

Variables prédéfinies

Jenkins et Azure Pipelines définissent un certain nombre de variables d’environnement pour vous aider à inspecter et à interagir avec l’environnement d’exécution du système d’intégration continue.

Descriptif Jenkins Azure Pipelines
Identificateur numérique unique pour l’appel de build actuel. BUILD_NUMBER BUILD_BUILDNUMBER
Identificateur unique (pas nécessairement numérique) pour l’appel de build actuel. BUILD_ID BUILD_BUILDID
L'URL qui affiche les journaux de compilation. BUILD_URL Cette valeur n’est pas définie en tant que variable d’environnement dans Azure Pipelines, mais vous pouvez la dériver d’autres variables. 1
Nom de l’ordinateur sur lequel la build actuelle s’exécute. NODE_NAME AGENT_NAME
Nom de ce projet ou définition de build. JOB_NAME RELEASE_DEFINITIONNAME
Chaîne d’identification de la version ; le numéro de version est un bon identificateur unique. BUILD_TAG BUILD_BUILDNUMBER
URL de l’hôte exécutant la build. JENKINS_URL SYSTEM_TEAMFOUNDATIONCOLLECTIONURI
Identificateur unique de l’exécuteur de build ou de l’agent de build qui s’exécute actuellement. EXECUTOR_NUMBER AGENT_NAME
Emplacement des sources extraites. WORKSPACE BUILD_SOURCESDIRECTORY
ID de validation Git correspondant à la version du logiciel en cours de génération. GIT_COMMIT BUILD_SOURCEVERSION
Chemin d’accès au dépôt Git sur GitHub, Azure Repos ou un autre fournisseur de référentiels. GIT_URL BUILD_REPOSITORY_URI
Branche Git en cours de construction. GIT_BRANCH BUILD_SOURCEBRANCH

1 Pour dériver l’URL qui affiche les journaux de génération dans Azure Pipelines, combinez les variables d’environnement suivantes dans ce format :

${SYSTEM_TEAMFOUNDATIONCOLLECTIONURI}/${SYSTEM_TEAMPROJECT}/_build/results?buildId=${BUILD_BUILDID}

Gestion des réussites et des échecs

Jenkins vous permet d’exécuter des commandes lorsque la build a terminé, à l’aide de la post section du pipeline. Vous pouvez spécifier des commandes qui s’exécutent lorsque la build réussit (à l’aide de la success section), lorsque la build échoue (à l’aide de la failure section) ou toujours (à l’aide de la always section). Par exemple:

Jenkinsfile

post {
    always {
        echo "The build has finished"
    }
    success {
        echo "The build succeeded"
    }
    failure {
        echo "The build failed"
    }
}

De même, Azure Pipelines dispose d’une infrastructure d’exécution conditionnelle riche qui vous permet d’exécuter un travail ou d’effectuer des étapes d’un travail, en fonction de nombreuses conditions, notamment la réussite ou l’échec du pipeline.

Pour émuler des conditions de construction Jenkins post, vous pouvez définir des travaux qui s’exécutent en fonction des conditions always(), succeeded() ou failed().

azure-pipelines.yml

jobs:
- job: always
  steps:
  - script: echo "The build has finished"
    condition: always()

- job: success
  steps:
  - script: echo "The build succeeded"
    condition: succeeded()

- job: failed
  steps:
  - script: echo "The build failed"
    condition: failed()

Note

Jenkins prend en charge des conditions supplémentaires au-delà de post, always, success et failure.

  • changed: s’exécute uniquement si l’exécution du pipeline actuel a un état d’achèvement différent de celui de la précédente.
  • fixed: s’exécute uniquement si l’exécution actuelle réussit et que l’exécution précédente a échoué ou a été instable.
  • unstable : s'exécute uniquement lorsque l'exécution du pipeline actuel a un statut « instable » (généralement dû à des échecs de test).
  • cleanup: s’exécute après que toutes les autres postconditions ont été évaluées, quel que soit l’état du pipeline.

Dans Azure Pipelines, vous pouvez obtenir des fonctionnalités similaires à l’aide de conditions avec des expressions comme eq(variables['Agent.JobStatus'], 'SucceededWithIssues') pour les builds instables.

En outre, vous pouvez combiner d’autres conditions, comme la possibilité d’exécuter une tâche en fonction de la réussite ou de l’échec d’une tâche individuelle, des variables d’environnement ou de l’environnement d’exécution, pour générer un pipeline d’exécution enrichi.

Gestion des informations d’identification

Jenkins fournit un credentials() assistant au sein de la directive environment pour injecter en toute sécurité des informations d'identification dans votre pipeline. Jenkins prend en charge plusieurs types d’informations d’identification, notamment le texte secret, les paires nom d’utilisateur/mot de passe et les fichiers secrets.

Jenkinsfile

pipeline {
    agent any
    environment {
        AWS_ACCESS_KEY_ID     = credentials('aws-access-key-id')
        AWS_SECRET_ACCESS_KEY = credentials('aws-secret-access-key')
    }
    stages {
        stage('Deploy') {
            steps {
                sh 'aws s3 ls'
            }
        }
    }
}

Dans Azure Pipelines, vous pouvez gérer les secrets à l’aide de groupes de variables, d’intégration d’Azure Key Vault ou en définissant des variables secrètes directement dans votre pipeline :

azure-pipelines.yml

variables:
- group: my-aws-credentials  # Variable group linked to Azure Key Vault or containing secrets

jobs:
- job: Deploy
  steps:
  - script: aws s3 ls
    env:
      AWS_ACCESS_KEY_ID: $(AWS_ACCESS_KEY_ID)
      AWS_SECRET_ACCESS_KEY: $(AWS_SECRET_ACCESS_KEY)

Vous pouvez également référencer des secrets directement à partir d’Azure Key Vault à l’aide de la tâche AzureKeyVault@2 :

steps:
- task: AzureKeyVault@2
  inputs:
    azureSubscription: 'my-azure-subscription'
    KeyVaultName: 'my-key-vault'
    SecretsFilter: 'AWS-ACCESS-KEY-ID,AWS-SECRET-ACCESS-KEY'
- script: aws s3 ls
  env:
    AWS_ACCESS_KEY_ID: $(AWS-ACCESS-KEY-ID)
    AWS_SECRET_ACCESS_KEY: $(AWS-SECRET-ACCESS-KEY)