Accéder au contenu principal

Comment lancer un job indépendant avec Spring Boot pour votre application

Lancer une tache de fond, en continue et qui tourne à intervalle régulier, en même temps que le processus principale de votre application est une procédure assez courante: il s'agit de lancer un job indépendant mais gérer par votre application. Cette procédure est largement facilité par le framework spring et notamment sa mouture springboot.

Attention: Ici, ce tutoriel ne traite pas du scheduling des jobs avec quartz. Nous le traiterons dans un prochain tutoriel.



1. Pourquoi faire des jobs indépendants avec springboot

Comme nous l'avons vu dans l'un de nos tutoriels, springboot vous permettra de créer une application fonctionnelle rapidement avec le moins d'effort.

D'autre part, un job indépendant ne doit pas être lié au processus principale de votre application, car dans le cas contraire, votre application ne pourra plus effectuer de taches parallèles et toutes ses ressources seront allouées (bloquées) à ce job principal.

Springboot vous permettra de créer ce job indépendant, de manière simple et rapide comme nous le verrons ci dessous. Ce job sera en réalité un thead indépendant totalement géré par le framework spring.

2. Les dépendances

Nous créons simplement un projet springboot à l'aide SpringInitilizr, car le scheduling est présent nativement dans le framework spring.

Dépendances Gradle

plugins {
id 'java'
id 'org.springframework.boot' version '3.3.2'
id 'io.spring.dependency-management' version '1.1.6'
}

group = 'com.javatutorialshub.jobscheduling'
version = '0.0.1-SNAPSHOT'

java {
toolchain {
languageVersion = JavaLanguageVersion.of(17)
}
}

repositories {
mavenCentral()
}

dependencies {
implementation 'org.springframework.boot:spring-boot-starter'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
}

tasks.named('test') {
useJUnitPlatform()
}

Dépendances Maven

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>3.3.2</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.javatutorialshub</groupId>
<artifactId>jobscheduling</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>jobscheduling</name>
<description>jobscheduling</description>
<properties>
<java.version>17</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>

</project>

3. Comment faire des jobs indépendants (scheduled) dans une application springboot

La première étape consiste à activer le scheduling sur l'application à l'aide de l'annotation @EnableScheduling comme suit:

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.scheduling.annotation.EnableScheduling;

@SpringBootApplication
@EnableScheduling
public class JobschedulingApplication {

public static void main(String[] args) {
SpringApplication.run(JobschedulingApplication.class, args);
}

}

La seconde étape consiste à créer un composant spring (@Component) qui exposera la méthode représentant notre job. Cette méthode doit nécessairement être annotée avec l'annotation @Scheduled.

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.util.Random;

@Component
public class RandomNumberExtractor {

private static final Logger logger = LoggerFactory.getLogger(RandomNumberExtractor.class);

@Scheduled(fixedDelay = 1000)
public void doExtraction(){
new Random().doubles(10).findFirst().ifPresent(d -> {
double value = d * System.currentTimeMillis();
logger.info("Result: {}", value);
});
}
}

Dans l'exemple ci dessus, la méthode doExtraction est annotée avec @Scheduled et l'attribut fixedDelay = 1000, ce qui signifie que cette méthode sera exécutée dans un délai de 1s (1s = 1000ms) après la fin de la précédente exécution.

4. Les intervalles d'exécution et cron

  • fixedDelay: Le délai indiqué est chronométré dès la fin de la précédente exécution
  • fixedRate: Le délai indiqué est chronométré dès le début de la précédente exécution
  • initialDelay: le délai indiqué permet de décaler la première exécution
Si ces attributs ne sont pas assez détaillés, pour répondre à votre besoin, vous pouvez utiliser les cron. Ainsi l'exemple suivant exécutera la méthode toute les secondes comme ci dessus:

  • Toutes les secondes : @Scheduled(cron = "* * * * * *")
  • Toutes les 5 secondes : @Scheduled(cron = "*/5 * * * * *")
  • Toutes les minutes : @Scheduled(cron = "0 * * * * *")
  • Toutes les heures : @Scheduled(cron = "0 0 * * * *")
  • Toutes les jours du mois : @Scheduled(cron = "0 0 0 ? * *")
  • Toutes les mois : @Scheduled(cron = "0 0 0 0 * *")
  • Toutes les jours de la semaine : @Scheduled(cron = "0 0 0 0 0 ?")

Et ainsi de suite. Avec les cron, vous avez une plus grande flexibilité quant au moment d'exécution de votre job (de votre tache)

La documentation sur les cron de spring scheduler peut être trouvé ici

Le code source de ce tutoriel est présent sur github à cette addresse: jobscheduling on github

Ne pas hésiter à commenter ou à poser une question ou à demander de l'aide autours de java et des technologies connexes. Nous nous ferons un plaisir de vous répondre.

Commentaires

Posts les plus consultés de ce blog

Comment valider les données utilisateur dans votre application Java : Guide pratique avec Jakarta Bean Validation

Lorsque vous développez une application qui interagit avec un utilisateur, en lui demandant de saisir des données, il est primordial de vérifier et valider ces données avant tout traitement. Et ceci pour plusieurs raisons: vous aurez la possibilité d'éviter des traitements inutiles si les données reçues ne sont pas conformes aux données attendues et aussi cela permet de protéger votre application en cas d'attaque orchestrée par des hackers. Dans le langage java, il existe une spécification qui vous permet de valider tout type de données transmis dans un bean: Java Bean Validation (ou plus récemment: Jakarta Bean Validation). Dans ce tutoriel, au travers d'une petite application de gestion d'une bibliothèque de quartier, nous allons voir ensemble comment utiliser Jakarta Bean Validation. 1. Pourquoi Jakarta Bean Validation L'objectif de Jakarta Bean Validation est de standardiser la validation des champs au travers de specification (JSR 380). Aussi cette standardisat...

Comprendre l'Inversion de Contrôle : Un Guide Pratique de Guice sur l'Injection des Dépendances dans le Développement de Logiciels

L'un des principes fondamentaux dans le développement de logiciels (ou d'applications) est la mise en oeuvre des principes SOLID. Le D ici indique: Dependency Inversion ou Dependency Injection ou encore Inversion Of Control (IoC). Autrement dit: Inversion de Contrôle ou Injection des Dépendances. L'injection des dépendances à pour principal objectif le découplage des modules entre eux. Cela implique donc de créer et développer les différents composants à base de classes abstraites ou d'interfaces, comme le permet Java. Ce faisant, l'application ou le logiciel devra utiliser une librairie ou un framework qui permette d'injecter les fameuses dépendances en question. Nous verrons dans la suite du tutoriel comment une librairie (ou framework léger) comme Guice (Google Guice) nous aidera dans cet objectif. Note: Spring Framework est l'un des framework les plus connus qui permettent de mettre en oeuvre l'Inversion de Contrôle.  1. Qu'est ce que l'Injec...

Gestion des exceptions en Java: Comprendre, Traiter et Créer

Apprenez à gérer efficacement les exceptions d'exécution en Java, améliorant ainsi la fiabilité et la stabilité de vos applications et programmes. 1. Qu'est ce qu'une exception Comme dans la plus part des languages de programmation, Java vous permet de gérer avec précision des erreurs imprévues (exceptions) qui pourraient survenir lors de l'exécution d'une instruction ou d'un traitement. Une exception est une erreur imprévue qui survient lors de l'exécution d'une instruction de votre code (de votre programme). Imaginons que vous souhaitiez faire la division de deux nombres dans votre programme: x = a / b.  Malheureusement si le diviseur b vaut zéro lors de l'exécution de votre programme, cette situation génèrera une erreur imprévue. On parlera alors d'une exception. Il faut garder à l'esprit que toute instruction dans un programme peut générer une exception (à moins que vos instructions soient des plus basiques et simples). Parfois lorsqu...