Skip to main content

Contrôler la simultanéité des workflows et des tâches

Exécutez un seul travail à la fois.

Vue d’ensemble

Par défaut, GitHub Actions permet l'exécution simultanée de plusieurs projets au sein d'un même flux de travail, de plusieurs flux de travail au sein d'un même référentiel et de plusieurs flux de travail sur le compte d'un propriétaire de référentiel. Plusieurs flux de travail, projets ou étapes peuvent donc être exécutés simultanément.

GitHub Actions vous permet également de contrôler la concurrence des exécutions de flux de travail, afin de garantir qu'une seule exécution, un seul projet ou une seule étape s'exécute à la fois dans un contexte spécifique. Cette option peut être utile pour contrôler les ressources de votre compte ou de votre organisation dans des situations où l'exécution simultanée de plusieurs flux de travail, projets ou étapes pourrait provoquer des conflits ou consommer plus de minutes d'actions et de stockage que prévu.

Par exemple, la possibilité d'exécuter des flux de travail simultanément signifie que si plusieurs engagements sont envoyés à un référentiel en succession rapide, chaque envoi peut déclencher l'exécution d'un flux de travail distinct, qui se fera simultanément.

Utilisation de la concurrence dans différents scénarios

Vous pouvez utiliser jobs.<job_id>.concurrency pour vous assurer qu’un seul travail ou workflow utilisant le même groupe d’accès concurrentiel s’exécute à la fois. Un groupe d’accès concurrentiel peut être n’importe quelle chaîne ou expression. Contextes d’expression autorisés : github, inputs, vars, needs, strategy et matrix. Pour plus d’informations sur les expressions, consultez « Évaluer les expressions dans les workflows et les actions ».

Vous pouvez également spécifier concurrency au niveau du workflow. Pour plus d’informations, consultez concurrency.

Quand un travail ou un workflow simultané est mis en file d’attente, si un autre travail ou workflow utilisant le même groupe d’accès concurrentiel dans le dépôt est en cours d’exécution, le travail ou le workflow en file d’attente a la valeur pending. Tout travail ou workflow en attente dans le groupe d’accès concurrentiel est annulé. Cela signifie qu’il peut y avoir au plus un travail en cours d’exécution et un travail en attente dans un groupe d’accès concurrentiel à tout moment.

Pour annuler également un travail ou un workflow en cours d’exécution dans le même groupe d’accès concurrentiel, spécifiez cancel-in-progress: true. Pour annuler de façon conditionnelle les travaux ou les flux de travail en cours d’exécution dans le même groupe d’accès concurrentiel, vous pouvez spécifier cancel-in-progress en tant qu’expression avec l’un des contextes d’expression autorisés.

Remarques :

  • Le nom de groupe de la concurrence n'est pas sensible à la casse. Par exemple, prod et Prod sera traité comme le même groupe d’accès concurrentiel.
  • Le classement n’est pas garanti pour les travaux ou les exécutions de flux de travail à l’aide de groupes de concurrence. Les travaux ou les exécutions de flux de travail dans le même groupe de concurrence sont gérés dans un ordre arbitraire.

Exemple : utilisation de la concurrence et du comportement par défaut

Le comportement par défaut de GitHub Actions consiste à autoriser l'exécution simultanée de plusieurs projets ou les exécutions de flux de travail. Le mot clé concurrency vous permet de contrôler la concurrence des exécutions de flux de travail.

Par exemple, vous pouvez utiliser le mot clé concurrency immédiatement après le lieu de définition des conditions de déclenchement afin de limiter la concurrence des exécutions de l'ensemble du flux de travail pour une branche spécifique :

on:
  push:
    branches:
      - main

concurrency:
  group: ${{ github.workflow }}-${{ github.ref }}
  cancel-in-progress: true

Vous pouvez également limiter la concurrence des projets au sein d'un flux de travail en utilisant le mot-clé concurrency au niveau du projet :

on:
  push:
    branches:
      - main

jobs:
  job-1:
    runs-on: ubuntu-latest
    concurrency:
      group: example-group
      cancel-in-progress: true

Exemple : groupes de concurrence

Les groupes de concurrence permettent de gérer et de limiter l'exécution des flux de travail ou des projets qui partagent la même clé de concurrence.

La clé concurrency est utilisée pour regrouper des flux de travail ou des projets ensemble dans un groupe de concurrence. Lorsque vous définissez une clé concurrency, GitHub Actions garantit qu'un seul flux de travail ou projet avec cette clé s'exécute à tout moment. Si une exécution de flux de travail ou un projet est à nouveau lancé(e) avec la même clé concurrency, GitHub Actions annule tout flux de travail ou projet déjà en cours d'exécution avec cette clé. La clé concurrency peut être une chaîne codée en dur, ou il peut s'agir d'une expression dynamique qui inclut des variables de contexte.

Il est possible de définir des conditions de concurrence dans votre flux de travail afin que le flux de travail ou le projet fasse partie d'un groupe de concurrence.

En d'autres termes, lorsqu'un flux de travail ou un projet est lancé, GitHub annule tous les flux de travail ou projets déjà en cours dans le même groupe de concurrence. Cette fonction est utile dans les scénarios où vous souhaitez empêcher les exécutions parallèles pour un certain ensemble de flux de travail ou de projets, comme ceux utilisés pour les déploiements dans un environnement intermédiaire, afin d'éviter les actions susceptibles de provoquer des conflits ou de consommer plus de ressources qu'il n'est nécessaire.

Dans cet exemple, job-1 fait partie d'un groupe de concurrence nommé staging_environment. En d'autres termes, si une nouvelle exécution de job-1 est déclenchée, toutes les exécutions du même projet dans le groupe de concurrence staging_environment qui sont déjà en cours seront annulées.

jobs:
  job-1:
    runs-on: ubuntu-latest
    concurrency:
      group: staging_environment
      cancel-in-progress: true

Par ailleurs, l'utilisation d'une expression dynamique comme concurrency: ci-${{ github.ref }} dans votre flux de travail signifie que le flux de travail ou le projet fera partie d'un groupe de concurrence dont le nom ci- est suivi de la référence de la branche ou de la balise qui a déclenché le flux de travail. Dans cet exemple, si un nouvel engagement est envoyé vers la branche primaire alors qu'une exécution précédente est toujours en cours, cette dernière sera annulée et la nouvelle lancée :

on:
  push:
    branches:
      - main

concurrency:
  group: ci-${{ github.ref }}
  cancel-in-progress: true

Exemple : Utilisation de la concurrence pour annuler un travail ou une exécution en cours

Pour utiliser la concurrence afin d'annuler un projet en cours ou une exécution dans GitHub Actions, vous pouvez utiliser la clé concurrency avec l'option cancel-in-progress définie sur true :

concurrency:
  group: ${{ github.ref }}
  cancel-in-progress: true

Notez que dans cet exemple, sans définir un groupe de concurrence particulier, GitHub Actions annulera toute exécution en cours du projet ou du flux de travail.

Exemple : Utilisation d’une valeur de secours

Si vous créez le nom de groupe avec une propriété définie uniquement pour des événements spécifiques, vous pouvez utiliser une valeur de secours. Par exemple, github.head_ref est défini uniquement pour les événements pull_request. Si votre workflow répond à d’autres événements en plus des événements pull_request, vous devez fournir une valeur de secours pour éviter une erreur de syntaxe. Le groupe d’accès concurrentiel suivant annule les travaux ou les exécutions en cours pour les événements pull_request uniquement. Si github.head_ref n’est pas défini, le groupe d’accès concurrent utilise l’ID d’exécution, qui offre la garantie d’être à la fois unique et défini pour l’exécution.

concurrency:
  group: ${{ github.head_ref || github.run_id }}
  cancel-in-progress: true

Exemple : Annuler uniquement les travaux ou les exécutions en cours pour le workflow actuel

Si vous avez plusieurs workflows dans le même dépôt, les noms de groupes d’accès concurrentiel doivent être uniques au sein de tous les workflows pour éviter l’annulation de travaux ou d’exécutions en cours à partir d’autres workflows. Sinon, tout travail en cours ou en attente est annulé, quel que soit le workflow.

Pour annuler uniquement les exécutions en cours du même workflow, vous pouvez utiliser la propriété github.workflow afin de créer le groupe d’accès concurrentiel :

concurrency:
  group: ${{ github.workflow }}-${{ github.ref }}
  cancel-in-progress: true

Exemple : Annuler uniquement les travaux en cours sur des branches spécifiques

Si vous souhaitez annuler des travaux en cours sur certaines branches, mais pas sur d’autres, vous pouvez utiliser des expressions conditionnelles avec cancel-in-progress. Par exemple, vous pouvez procéder ainsi si vous souhaitez annuler les travaux en cours sur les branches de développement, mais pas sur les branches de publication.

Pour n’annuler que les exécutions en cours du même workflow lorsqu’il n’est pas exécuté sur une branche de publication, vous pouvez définir cancel-in-progress comme une expression similaire à la suivante :

concurrency:
  group: ${{ github.workflow }}-${{ github.ref }}
  cancel-in-progress: ${{ !contains(github.ref, 'release/')}}

Dans cet exemple, plusieurs envois push vers une branche release/1.2.3 n’annulent pas les exécutions en cours. Les envois (push) vers une autre branche, par exemple main, annulent les exécutions en cours.

Monitoring de vos travaux en cours dans votre organisation ou votre entreprise

Pour identifier des contraintes liées à la concurrence ou la mise en file d’attente, vous pouvez vérifier le nombre de travaux actuellement traités sur les exécuteurs hébergés par GitHub dans votre organisation ou entreprise. Pour plus d’informations, consultez « Monitoring de vos travaux en cours ».