Actions GitHub.com
Introduction
Les Actions de GitHub permettent d'automatiser, personnaliser et exécuter les workflows de développement logiciel de votre projet. Elles permettent notamment de mettre en place des taches d'Intégration Continue ou Continuous Integration (CI) et de Déploiement Continue ou Continuous Deployment
Il existe des outils tiers qui peuvent réaliser les mêmes automatisations si elles ont accès au dépôt Git du projet (que ce soit sur GitHub ou d'autre plateforme) mais, avec les Actions, GitHub propose la fonctionnalité directement au sein de la même plateforme. Certains outils tiers proposent plus d'options, mais GitHub Actions permet déjà de faire beaucoup de choses. (Certains diront aussi que la configuration des GitHub Actions est un peu trop verbeuse contrairement à d'autre outil ou à l'équivalent de GitLab)
CI : L'Intégration Continue ou Continuous Intégrations
L'intégration continue est un ensemble de pratiques utilisées en génie logiciel consistant à vérifier à chaque modification de code source que le résultat des modifications ne produit pas de régression dans l'application développée...
Il faut retenir que le but de l'Intégration Continue est de vérifier à chaque fois que l'on modifie le code que les modifications apportées n'empêche pas le bon fonctionnement dans le reste de l'application.
En pratique, le développeur doit mettre en place des tests automatisés pour chaque fonctionnalité qu'il développe. Ces tests peuvent avoir plusieurs formes. On peut avoir des tests unitaires et des tests d'intégrations.
Avec java, on peut utiliser l'outil Junit pour rédiger et exécuter ces tests. De plus Maven possède une phase de cycle de vie
test
qui permet d'exécuter tous les tests Junit d'un projet.
CD : Le Déploiement Continue ou Continuous Deployment
Le déploiement continu est une approche d'ingénierie logicielle dans laquelle les fonctionnalités logicielles sont livrées fréquemment par le biais de déploiements automatisés.
Il faut retenir que le but du déploiement continu est de livrer et déployer de façons automatiques les nouvelles releases.
Par exemple, le code source de votre application web est sur GitHub et vous hébergez votre application sur un serveur. Mettre en place une tache de déploiement continue pourrait consister à créer une tache qui va compiler ou construire votre application à partir des sources sur GitHub et les déployer sur le serveur qui héberge l'application et faire en sorte que cette tache s'exécute automatique quand vous créer une release sur GitHub. Ainsi, à chaque fois que vous ajoutez une fonctionnalité à votre application et que vous créez une nouvelle release, votre application sera automatiquement mis à jour grâce à la tâche que vous avez créé.
⚠️ Le sigle CD peut aussi être utilisé pour parler de Livraison Continue ou Continuous Delivery. C'est le même principe que le déploiement continue à la difference qu'on arrête la tache avant le déploiement. C'est-à-dire que la va uniquement compiler ou construire votre application et rendre disponible les livrables (le résultat de la compilation ou de la construction). Une intervention manuel reste donc nécessaire pour déployer l'application (la mettre à jour).
Mise en place des Actions GitHub
La bibliothèque de modèle de GitHub
Github propose un certain nombre de modèles directement sur la page du projet, dans l'onglet Actions quand vous souhaitez en créez une :
Les avantages de cette méthode sont que GitHub suggère des modèles des models en fonction des langages et des outils
utilisés dans le code sources (analyse du code automatique du code par GitHub, il n'y a pas besoin de préciser
manuellement les langages et les outils).
Également, Pour des taches simples comme compiler un projet JAVA
(uniquement pour vérifier que le code compile par pour de la
CI/CD) les modèles sont suffisants. Mais ils représentent aussi une bonne base à modifier pour créer des tâches plus complexe.
Paramétrage manuel du projet
Les fichiers de paramétrages des Actions doivent se placer dans le dossier .github/workflows
avec le dossier .github
à la racine du projet.
Pour créer une configuration il faut créer un fichier au format .yml
dans le dossier workflows
Vous pouvez créer autant de fichiers configurations que vous le souhaitez.
Modèle de fichier de configuration basique
name : Ma Config
on:
push:
branch: [ "main" ]
jobs:
job1:
runs-on: ubuntu-latest
steps:
- name: Etape 1
run: commande-système
- name: Etape 2
uses: actions/une_action_préconfigurée
La propriété
name
sert à donner un nom à la configuration. Toutes les taches décrites dans ce fichier de configurations seront regroupé sous ce nom sur GitHub.La rubrique
on
permet de définir le ou les évènements suite auxquels GitHub devra déclencher les tâches. Ici, on dit qu'on veut déclencher les tâches à chaque fois qu'unpush
est réalisé sur la branchemain
.
Comme vous pouvez le voir la propriété branch prend un tableau de chaine. Cela permet de déclarer plusieurs branches pour lesquelles les tâches doivent se déclencher (nom des branches dans une chaine de caractère et séparé par des virgules).La rubrique
jobs
permet de décrire les différentes taches.La rubrique
job1
permet d'indiquer qu'on démarre la description d'une nouvelle tache.job1
sera l'identifiant de la tache et il peut être remplacé par ce que vous voulez.La propriété
runs-on
permet de choisir sur quel système d'exploitation on veut exécuter la tâche. Attention le choix du système d'exploitation peut influencer les commandes à exécuter qui seront définis après dans la configuration.La rubrique
steps
permet de définir les différentes étapes qui composent la tâche.Une étape va être représentée par un
-
(à chaque nouveau-
on définit une nouvelle étape) et peut être composer de plusieurs propriétés :- La propriété `name` (optionnel) qui permet de donner un nom à afficher pour la tâche sur GitHub.
- La propriété `run` qui permet d'indiquer les commandes systèmes à exécuter. Ce sont ces commandes qui peuvent dépendredu système d'exploitation choisit : Pour une commande du jdk (ex :
javac
) ou de maven (ex :mvn compile
) il ne devrait pas y avoir de problème parce qu'elles sont les mêmes sur tous les systèmes, mais si vous avez besoin de manipuler des fichiers certaines commandes peuvent être différentes (ou fonctionner différemment) suivant le système.- La propriété `uses` qui permet d'utiliser des actions prédéfinies. Il faudra aller chercher sur internet ou sur la
doc de GitHub (lien ci-après) quelles actions prédéfinies sont utilisables. Vous avez aussi quelques exemples un peu plus bas.
Je fais juste un tour rapide des bases pour vous expliquer comment ça marche et vous donner quelques exemples. Si vous souhaitez aller plus loin, vous pouvez vous rendre sur la doc de GitHub.
Il faut bien faire attention à l'indentation lors de la rédaction d'un yml (espace à gauche de chaque ligne). Contrairement à Java, par exemple, où les blocs de code commence avec une accolade ouverte
{
et fini avec une accolade fermée}
, dans la norme yaml on se repère avec les indentations : On ajoute 1 indentation pour marquer le début d'un bloc et on retire une indentation pour marquer la fin d'un bloc.
Si les indentations ne sont pas respectées il pourrait y avoir des erreurs lors de la lecture de la configuration, voire la configuration pourrait ne pas être lue du tout.Pour la taille d'1 indentation, vous êtes assez libre (par convention, ce sera plutôt 2 ou 4 espaces) à la condition que vous respectiez toujours le même espacement (si 1 indentation = 2 espace, 2 indentation = 4 espace, etc...).
Comme avec java quand vous développez avec un IDE ou un éditeur de texte moderne, c'est déjà pris en charge. Quand vous appuyez sur tab l'éditeur va mettre une indentation de la taille configurée dans les paramètres.
Si vous voulez connaitre la taille qui est configurée au moment où vous codez, vous pouvez regarder dans la barre en bas de la fenêtre vous aurez souvent une indication du type "4 spaces" qui vous donne la taille de l'indentation.
(Ça peut aussi être quelque chose comme "1 tab", dans certaine convention on utilise plutôt le symbole de la tabulation à la place de des espaces)
Exemple pour essayer de compiler un projet JAVA avec maven
name : Lucas PREAUX - Java CI with Maven # Nom sous lequel les actions seront rassemblé dans GitHub
on: # Je veux que GitHub exécute les Actions de ce fichier à chaque push et pull request sur la branche lucas-preaux
push:
branches: [ "lucas-preaux" ]
pull_request:
branches: [ "lucas-preaux" ]
jobs:
tests: # Je créée 1 action/tâche dont l'id est "test"
runs-on: ubuntu-latest # J'exécute cette tache sur un système Ubuntu(Linux)
steps:
- uses: actions/checkout@v3 # 1ere étape : utilisation de l'action checkout qui doit permettre de récupérer le code source au dernier commit de la branche sélectionnée.
- name: Set up JDK 17 # 2eme étape : on lui donne "Set up JDK 17" comme nom
uses: actions/setup-java@v3 # on utilise un action pour setup java dans l'environnement
with: # on passe des informations à l'action qu'on veux utiliser (action/setup-java@v3)
java-version: '17' # On demande la version 17 de java
distribution: 'zulu' # Avec la distribution zulu fourni par Azul
cache: maven # On demande également le setup de maven pour pouvoir l'utiliser
- name: test with Maven # 3eme étape : on l'appelle "test with maven"
run : mvn compile # on demande au système d'exécuter la commande "mvn compile"
# Comme on n'a pas précisé de chemin d'accès la commande s'exécute à la racine du dépot git.
Exemple pour exécuter les tests d'un projet JAVA avec maven avec résultat sur Github
name : Lucas PREAUX - Java CI with Maven # Nom sous lequel les actions seront rassemblé dans GitHub
on: # Je veux que GitHub exécute les Actions de ce fichier à chaque push et pull request sur la branche lucas-preaux
push:
branches: [ "lucas-preaux" ]
pull_request:
branches: [ "lucas-preaux" ]
jobs:
tests: # Je créée 1 action/tâche dont l'id est "test"
runs-on: ubuntu-latest # J'exécute cette tache sur un système Ubuntu(Linux)
steps:
- uses: actions/checkout@v3 # 1ere étape : utilisation de l'action checkout qui doit permettre de récupérer le code source au dernier commit de la branche sélectionnée.
- name: Set up JDK 17 # 2eme étape : on l'appelle "Set up JDK 17"
uses: actions/setup-java@v3 # on utilise un action pour setup java dans l'environnement
with: # on passe des informations à l'action qu'on veux utiliser (action/setup-java@v3)
java-version: '17' # On demande la version 17 de java
distribution: 'zulu' # Avec la distribution zulu fourni par Azul
cache: maven # On demande également le setup de maven pour pouvoir l'utiliser
- name: test with Maven # 3eme étape : on l'appelle "test with maven"
run : mvn test # on demande au système d'exécuter la commande "mvn test"
# Comme on n'a pas précisé de chemin d'accès la commande s'exécute à la racine du dépot git.
Après avoir push ce fichier sur GitHub, quand on va voir l'onglet Actions on pourra commencer à voir ça :
Vous pouvez retrouver à gauche un menu listant les noms des données aux différentes configurations. Ce menu permet de filtrer les actions déjà réalisées ou en cours de réalisation.
Je vous laisse parcourir vous-même les quelques pages auxquelles vous aurez accès à partir de là. C'est plutôt simple et ergonomique. Vous pourrez trouver des rapports et des logs d'exécution.