0% ont trouvé ce document utile (0 vote)
5 vues79 pages

Architecture JEE et Spring en 2022

Transféré par

Amal Touhami
Copyright
© All Rights Reserved
Nous prenons très au sérieux les droits relatifs au contenu. Si vous pensez qu’il s’agit de votre contenu, signalez une atteinte au droit d’auteur ici.
Formats disponibles
Téléchargez aux formats PDF, TXT ou lisez en ligne sur Scribd
0% ont trouvé ce document utile (0 vote)
5 vues79 pages

Architecture JEE et Spring en 2022

Transféré par

Amal Touhami
Copyright
© All Rights Reserved
Nous prenons très au sérieux les droits relatifs au contenu. Si vous pensez qu’il s’agit de votre contenu, signalez une atteinte au droit d’auteur ici.
Formats disponibles
Téléchargez aux formats PDF, TXT ou lisez en ligne sur Scribd

Architecture Web Distribuée "JEE et Spring"

Cycle d’ingenieur LSI

Pr. Lotfi ELAACHAK


Département Génie Informatique

2021 — 2022
Table des matières

1 Introduction à JEE 4
1.1 Architecture JEE . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
1.2 Services et Organisation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.2.1 Services d’infrastructures . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.2.2 Services de communications . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.2.3 Serveur d’application . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.2.4 Serveur d’objet . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
1.2.5 Organisation et Architecture . . . . . . . . . . . . . . . . . . . . . . . . . . 6
1.3 Le patron de conception MVC et standards JEE . . . . . . . . . . . . . . . . . . . 6
1.3.1 Structure d’une application Java EE . . . . . . . . . . . . . . . . . . . . . 6
1.3.2 Le modèle MVC . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7

2 JSF et JPA 10
2.1 Java Persistence API . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
2.1.1 La couche ORM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
2.1.2 JPA . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
2.1.3 Définition d’une entité JPA . . . . . . . . . . . . . . . . . . . . . . . . . . 11
2.1.4 Opérations sur les entités . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
2.1.5 Mise en relation d’entités . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
2.2 Java Server Faces . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 19
2.2.1 Introduction aux Frameworks MVC . . . . . . . . . . . . . . . . . . . . . . 19
2.2.2 Introduction JSF . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20
2.2.3 Structure d’une application JSF . . . . . . . . . . . . . . . . . . . . . . . . 20

3 Les Enterprise java Bean (EJB 3.x) 22


3.1 Applications distribuées JEE . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22
3.2 Les EJB 3.x . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22
3.2.1 Types d’EJB . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 23
3.2.2 Interfaces d’EJB Session . . . . . . . . . . . . . . . . . . . . . . . . . . . . 28
3.2.3 Utilisation des EJB . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29

4 Introduction à Srping et Spring boot 31


4.1 Spring . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31
4.1.1 Les caractéristiques de Spring . . . . . . . . . . . . . . . . . . . . . . . . . 31
4.1.2 Architecture de la technologie Spring . . . . . . . . . . . . . . . . . . . . . 32
4.1.3 Injection de dépendance . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
4.1.4 Spring ORM . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 38
4.1.5 Spring MVC . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 38
4.1.6 MVC Form Tag Library . . . . . . . . . . . . . . . . . . . . . . . . . . . . 38

1
4.1.7 Spring Security . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39
4.2 Spring boot . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41
4.2.1 Introduction Spring boot . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41
4.2.2 Architecture de Spring Boot . . . . . . . . . . . . . . . . . . . . . . . . . . 42
4.2.3 Composants du projet Spring Boot . . . . . . . . . . . . . . . . . . . . . . 44
4.2.4 Spring Boot View : Thymeleaf . . . . . . . . . . . . . . . . . . . . . . . . 46

5 Les web services JAX-RS et Srping RESTful 48


5.1 Qu’est-ce qu’un service Web ? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 48
5.1.1 Les caractéristiques d’un service Web . . . . . . . . . . . . . . . . . . . . . 48
5.1.2 Architecture d’un service Web . . . . . . . . . . . . . . . . . . . . . . . . . 48
5.2 Webservices Restful « JAX-RS » avec JEE . . . . . . . . . . . . . . . . . . . . . . 49
5.2.1 Qu’est ce que REST ? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 49
5.2.2 JAX-RS . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50
5.2.3 Les Annotations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50
5.3 Srping RESTful . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
5.3.1 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
5.3.2 Initialisation d’un projet de services Web RESTful avec Spring Boot . . . . 54

6 MicroServices 58
6.1 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 58
6.1.1 Principe de responsabilité unique . . . . . . . . . . . . . . . . . . . . . . . 59
6.1.2 Modélisé autour du domaine d’activité . . . . . . . . . . . . . . . . . . . . 59
6.1.3 Échec isolé . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 59
6.1.4 Automatisation des infrastructures . . . . . . . . . . . . . . . . . . . . . . 59
6.1.5 Déployer indépendamment . . . . . . . . . . . . . . . . . . . . . . . . . . . 59
6.2 Les défis de l’architecture des microservices . . . . . . . . . . . . . . . . . . . . . . 60
6.2.1 Contexte délimité . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 61
6.2.2 Augmentation et diminution dynamiques . . . . . . . . . . . . . . . . . . . 61
6.2.3 Surveillance . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 61
6.2.4 Tolérance aux pannes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62
6.2.5 Dépendance cyclique . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62
6.2.6 Culture DevOps . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62
6.3 Surveillance des microservices . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62
6.3.1 Outil de surveillance des microservices . . . . . . . . . . . . . . . . . . . . 63
6.4 Virtualisation des microservices . . . . . . . . . . . . . . . . . . . . . . . . . . . . 63
6.5 Composants des microservices . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 63
6.5.1 Serveur de nommage Netflix Eureka . . . . . . . . . . . . . . . . . . . . . . 63
6.5.2 Serveur Hystrix . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64
6.5.3 Serveur de passerelle API Netflix Zuul . . . . . . . . . . . . . . . . . . . . 64
6.5.4 Ruban Netflix . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64
6.5.5 Serveur distribué Zipkin . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64
6.6 Patrons de conception de microservices . . . . . . . . . . . . . . . . . . . . . . . . 64
6.6.1 Aggregator . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 64

Lotfi ELAACHAK Page 2


6.6.2 API Gateway . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 65
6.6.3 Chained or Chain of Responsibility . . . . . . . . . . . . . . . . . . . . . . 66
6.6.4 Asynchronous Messaging . . . . . . . . . . . . . . . . . . . . . . . . . . . . 66
6.6.5 Database or Shared Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . 67
6.6.6 Event Sourcing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 67
6.6.7 Branch . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 67
6.6.8 Command Query Responsibility Segregator . . . . . . . . . . . . . . . . . . 68
6.6.9 Circuit Breaker . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 68
6.6.10 Decomposition . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69
6.7 Mise en place d’un Microservice . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69
6.7.1 Créer un service Eurêka . . . . . . . . . . . . . . . . . . . . . . . . . . . . 70
6.7.2 Création d’un service de catalogue d’articles . . . . . . . . . . . . . . . . . 72
6.7.3 Création d’un service Edge . . . . . . . . . . . . . . . . . . . . . . . . . . . 73

Lotfi ELAACHAK Page 3


Chapitre 1
Introduction à JEE
J2EE (Java 2 Enterprise Edition) est une norme proposée par la firme Sun Micro service ra-
chetée par Oracle, visant à définir un standard de développement d’applications d’entreprises
multi-niveaux, basées sur des composants. On parle généralement de «plate-forme J2EE» pour
désigner l’ensemble constitué des services (API) offerts et de l’infrastructure d’exécution. J2EE.
Dans la mesure où J2EE s’appuie entièrement sur le Java, il bénéficie des avantages et inconvé-
nients de ce langage, en particulier une bonne portabilité et une maintenabilité du code.

1.1 Architecture JEE


L’architecture JEE repose sur des composantes distincts, interchangeables et distribuées, ce qui
signifie notamment :
— Qu’il est simple d’étendre l’architecture.
— Qu’un système reposant sur JEE peut posséder des mécanismes de haute disponibilité,
afin de garantir une bonne qualité de service.
— Que la maintenabilité des applications est facilitée.
Schéma des relations entre composants et « tiers » dans l’architecture JEE "Jakarta EE 9" :

4
1.2 Services et Organisation

1.2.1 Services d’infrastructures


— JDBC - Java Database Connectivity C’est une API d’accès aux bases de données. Les
serveurs d’application fournissent en plus des pools de connexion avec les bases de données.
Cela réduit le nombre de lignes à écrire et optimise son utilisation.
— JNDI C’une API d’accès aux services de nommage et aux annuaires d’entreprises tels que
DNS, NIS, LDAP, etc.
— JTA / JTS - Java Transaction Api / Java Transaction Services C’est un API définissant
des interfaces standard avec un gestionnaire de transactions.
— JCA (J2EE Connector Architecture) C’est une API de connexion au système d’information
de l’entreprise, notamment aux systèmes dits «Legacy» tels que les ERP.
— JMX (Java Management eXtension) Cette API fournit des extensions permettant de dé-
velopper des applications web de supervision d’applications

1.2.2 Services de communications


— JAAS (Java Authentification and Authorization Service) C’est une API de gestion de
l’authentification et des droits d’accès.
— RMI (Remote Method Invocation) C’est une API permettant la communication synchrone
entre objets.
— Web services Les Web services permettent de « partager » un ensemble de méthodes qui
pourront être appelées à distance. Cette technologie utilise XML, ce qui permet d’être
utilisée par n’importe quel langage et n’importe quelle plateforme.
— JMS (Java Message Service) Cette API fournit des fonctionnalités de communication
asynchrone (appelées MOM pour Middleware Object Message) entre applications.
— JavaMail C’est une API permettant l’envoi de courrier électronique.

1.2.3 Serveur d’application


Le serveur d’application est l’environnement d’exécution des applications côté serveur. Il prend en
charge l’ensemble des fonctionnalités qui permettent à N clients d’utiliser une même application :
— Gestion de la session utilisateur.
— Gestion des montées en charge et reprise sur incident.
— Ouverture sur de multiples sources de données .

1.2.4 Serveur d’objet


Le serveur d’objet et un environnement qui consiste à s’appuyer sur des objets métier (client,
fournisseur ...) afin de masquer la complexité d’accès aux données.
Pour gérer ces objets, un environnement d’exploitation est nécessaire : le serveur d’objets. Ce
serveur d’objets va devoir fournir des services tout à fait différents de ceux des serveurs d’appli-
cation :
— Gestion de la persistance des objets,.
— Gestion des transactions objets métier.
— Gestion des montées en charge.

Lotfi ELAACHAK Page 5


1.2.5 Organisation et Architecture

1.3 Le patron de conception MVC et standards JEE

1.3.1 Structure d’une application Java EE


Toute application web Java EE doit respecter une structure de dossiers standards, qui est définie
dans les spécifications de la plate- forme. Vous en trouverez le schéma à la figure suivante.

Lotfi ELAACHAK Page 6


Quelques précisions :
— La racine de l’application, en violet sur le schéma, est le dossier qui porte le nom de votre
projet et qui contient l’intégralité des dossiers et fichiers de l’application.
— Le dossier nommé WEB-INF est un dossier spécial. Il doit obligatoirement exister et être
placé juste sous la racine de l’application.
— Le fichier de configuration de l’application ([Link]) ;
— Un dossier nommé classes, qui contient à son tour les classescompilées (fichiers .class) ;
— un dossier nommé lib, qui contient à son tour les bibliothèques nécessaires au projet
(archives .jar).
— Bref, tous les dossiers et fichiers marqués en rouge sur le schéma doivent obligatoirement
être nommés et placés comme indiqué sur le schéma.
— Les fichiers et dossiers persos placés directement sous la racine, en bleu sur le schéma, sont
publics et donc accessibles directement par le client via leurs URL. (*)
— Les fichiers et dossiers persos placés sous le répertoire WEB- INF, en orange sur le schéma,
sont privés et ne sont donc pas accessibles directement par le client. (*)

1.3.2 Le modèle MVC


En anglais design pattern, un modèle de conception (ou encore patron de conception) est une
simple bonne pratique, qui répond à un problème de conception d’une application.

Ce paradigme regroupe les fonctions nécessaires en trois catégories :


— Un modèle (modèle de données) ;
— Une vue (présentation, interface utilisateur) ;
— Un contrôleur (logique de contrôle, gestion des événements,synchronisation).

Lotfi ELAACHAK Page 7


Modèle : des traitements et des données « EJB / java Beans »

Dans le modèle, on trouve à la fois les données et les traitements à appliquer à ces données. Ce
bloc contient donc des objets Java d’une part, qui peuvent contenir des attributs (données) et
des méthodes (traitements) qui leur sont propres, et un système capable de stocker des données
d’autre part. Rien de bien transcendant ici, la complexité du code dépendra bien évidemment de
la complexité des traitements à effectuer par votre application.

Vue : des pages JSP

Une page JSP est destinée à la vue. Elle est exécutée côté serveur et permet l’écriture de gabarits
(pages en langage "client" comme HTML, CSS, Javascript, XML, etc.). Elle permet au concep-
teur de la page d’appeler de manière transparente des portions de code Java, via des balises et
expressions ressemblant fortement aux balises de présentation HTML.

Contrôleur : des Servlets

Une servlet est un objet qui permet d’intercepter les requêtes faites par un client, et qui peut
personnaliser une réponse en conséquence. Il fournit pour cela des méthodes permettant de
scruter les requêtes HTTP. Cet objet n’agit jamais directement sur les données, il faut le voir
comme un simple aiguilleur : il intercepte une requête issue d’un client, appelle éventuellement
des traitements effectués par le modèle, et ordonne en retour à la vue d’afficher le résultat au
client.

Lotfi ELAACHAK Page 8


Lotfi ELAACHAK Page 9
Chapitre 2
JSF et JPA
2.1 Java Persistence API

2.1.1 La couche ORM


Le rôle d’un système ORM est de convertir automatiquement, à la demande, la base de données
sous forme d’un graphe d’objet. L’ORM s’appuie pour cela sur une configuration associant les
classes du modèle fonctionnel et le schéma de la base de donnés. L’ORM génère des requêtes SQL
qui permettent de matérialiser ce graphe ou une partie de ce graphe en fonction des besoins.

Pour bien faire, il nous faut une approche systématique. On peut par exemple décréter que :
— on crée une classe pour chaque entité ;
— on équipe cette classe avec des méthodes create(), get(), delete(), search(), ..., que l’on
implante en SQL/JDBC ;
— on implante la navigation d’une entité à une autre, à l’aide de requête SQL codées dans
les classes et exécutées en JDBC.

10
2.1.2 JPA
La Java Persistence API (abrégée en JPA), est une interface de programmation Java permettant
aux développeurs d’organiser desdonnées relationnelles dans des applications utilisant la plate-
forme Java.
La persistance dans ce contexte recouvre trois zones :
— l’API elle-même, définie dans le paquetage [Link].
— Le langage Java Persistence Query (JPQL).
— L’objet/les métadonnées relationnelles.
La Java Persistence API repose essentiellement sur l’utilisation des annotations, introduites dans
Java 5. Elles permettent de définir facilement des objets métier, qui pourront servir d’interface
entre la base de données et l’application, dans le cadre d’un mapping objet- relationnel.

2.1.3 Définition d’une entité JPA


Une entité JPA est, par définition, une classe Java qui doit avoir les propriétés suivantes :
— Elle doit posséder un constructeur vide, public ou protected. Rappelons que ce construc-
teur vide existe par défaut si aucun constructeur n’existe dans la classe. Dans le cas
contraire, il doit être ajouté explicitement.
— Elle ne doit pas être final, et aucune de ses méthodes ne peut être final.
— Une entité JPA ne peut pas être une interface ou une énumération.
— Une entité JPA peut être une classe concrête ou abstraite.
Personne Entity
@Entity
@Table(name = "personne", catalog = "gpersonne")
public class Personne implements Serializable{
@Id
@GeneratedValue(strategy = IDENTITY) @Column(name = "id_personne", unique = true,
nullable = false)

private int id_personne ;


@Column(name = "nom", nullable = true, length = 255)
private String nom ;

Lotfi ELAACHAK Page 11


public Personne(int id_personne, String nom)
{
super();
this.id_personne = id_personne; [Link] = nom;
}
public int getId_personne() { return id_personne;
}
public void setId_personne(int id_personne) {
this.id_personne = id_personne; }
public String getNom() { return nom;
}
public void setNom(String nom) { [Link] = nom;
}
}

2.1.4 Opérations sur les entités


Toutes les opérations que l’on peut faire sur des entités JPA passent directement ou indirectement
par l’entity manager. Cet objet est central dans cette API. Ainsi, toute entité JPA persistante
possède une référence sur l’entity manager, et un entity manager connaît toutes les entités JPA
qu’il gère.
Toutes les opérations de création, effacement ou modification doivent nécessairement se faire
dans une transaction. Une transaction démarre sur appel à la méthode begin() de la transaction
dans laquelle on se trouve, et est validée sur appel à sa méthode commit(). On peut annuler une
transaction par appel à sa méthode rollback().
Les spécifications JPA définissent cinq opérations sur une entité : PERSIST, REMOVE, RE-
FRESH, DETACH et MERGE. Ces opérations correspondent à autant de méthodes sur l’objet
EntityManager. Tous les opérations/transactions sur les entités peuvent être possible grâce au
fichier de configuration [Link] :
[Link]
<?xml version="1.0" encoding="UTF-8" ?>
<persistence xmlns="[Link]
instance"
xmlns:xsi="[Link]
xsi:schemaLocation="[Link]
[Link]
version="2.0">
<persistence-unit name="monService" transaction-
type="RESOURCE_LOCAL">
<properties>
<property name="[Link]"
value="[Link]"/>
<property name="[Link]"
value="jdbc:derby://localhost:1527/monBdd;create=true"/>
<property name="[Link]"
value="root"/>

Lotfi ELAACHAK Page 12


<property name="[Link]" value="
"/>
</properties>
</persistence-unit>
</persistence>

Exemple code java pour enregistrer une entité :


[Link]
public static void main(String[] args) {
EntityManagerFactory emf =
[Link]("jcg-JPA");
EntityManager em = [Link]();
[Link]().begin();
Employee employee = new Employee();
[Link]("Chandan");
[Link]("COMIITING");
[Link](employee);
[Link]().commit();
}

2.1.5 Mise en relation d’entités


Associations un-à-plusieurs

L’annotation @ManyToOne :
ManyToOne
@ManyToOne
@JoinColumn (name="id_realisateur")
private Artiste realisateur;
public void setRealisateur(Artiste a) {realisateur = a;}

Lotfi ELAACHAK Page 13


public Artiste getRealisateur() {return realisateur;}
}

L’annotation @OneToMany :
OneToMany
@OneToMany
@JoinColumn(name="id_realisateur")
private Set<Film> filmsRealises = new HashSet<Film>();
public void addFilmsRealise(Film f) {[Link](f) ;}
public Set<Film> getFilmsRealises() {return filmsRealises;}
}

Associations bidirectionnelles :
Bidirectionnelles
@ManyToOne
@JoinColumn (name="id_realisateur")
private Artiste realisateur;
public void setRealisateur(Artiste a) {realisateur = a;}
public Artiste getRealisateur() {return realisateur;}

@OneToMany @JoinColumn(name="id_realisateur")
private Set<Film> filmsRealises = new HashSet<Film>();
public void addFilmsRealise(Film f) {[Link](f) ;}
public Set<Film> getFilmsRealises() {return filmsRealises;}

Associations plusieurs-à-plusieurs

Sans Attributs :
MayToMany
@ManyToMany()
@JoinTable(name = "Role", joinColumns = @JoinColumn(name = "id_film"),
inverseJoinColumns = @JoinColumn(name = "id_acteur"))
Set<Artiste> acteurs = new HashSet<Artiste>();
public Set<Artiste> getActeurs() {
return acteurs;
}
}

@ManyToMany(mappedBy = "acteurs")
Set<Film> filmo;
public Set<Film> getFilmo() {

Lotfi ELAACHAK Page 14


return filmo;
}

Avec Attributs :
MayToMany
@ManyToMany()
@JoinTable(name = "Role", joinColumns = @JoinColumn(name = "id_film"),
inverseJoinColumns = @JoinColumn(name = "id_acteur"))
Set<Artiste> acteurs = new HashSet<Artiste>();
public Set<Artiste> getActeurs() {
return acteurs;
}
}

@ManyToMany(mappedBy = "acteurs")
Set<Film> filmo;
public Set<Film> getFilmo() {
return filmo;
}

MayToMany
import [Link].*;
@Embeddable
public class RoleId implements [Link] {
/** *
*/
private static final long serialVersionUID = 1L;
@ManyToOne
@JoinColumn(name = "id_acteur")
private Artiste acteur;
public Artiste getActeur() {
return acteur;
}
public void setActeur(Artiste a) {
[Link] = a;

Lotfi ELAACHAK Page 15


}
@ManyToOne
@JoinColumn(name = "id_film")
private Film film;
public Film getFilm() {
return film;
}

public void setFilm(Film f) {


[Link] = f;
}

L’héritage

L’héritage au sens strict :


Joint
@Entity
@Table(name = "employe")
@Inheritance(strategy = [Link])
public abstract class Employe implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy = [Link])
@Column(name = "id")
private int id;
@Column(name = "nom")
private String nom;

Lotfi ELAACHAK Page 16


@Column(name = "prenom")
private String prenom; }

@Entity
@Table(name = "ingenieur")
@PrimaryKeyJoinColumn(name = "id")
public class Ingenieur extends Employe {
private static final long serialVersionUID = 1L;
@Column(name = "statut")
private String statut;
@Column(name = "nb_projets")
private int nbProjets; }

@Entity
@Table(name = "technicien")
@PrimaryKeyJoinColumn(name = "id")
public class Technicien extends Employe {
private static final long serialVersionUID = 1L;
@Column(name = "poste")
private String poste;
@Column(name = "niveau")
private int niveau; }

Un pseudo-héritage : dupliquer les données pour éviter les jointures :


Data
@Entity
@Table(name = "employe")
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS) public abstract class
Employe implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@Column(name = "id")
private int id;
@Column(name = "nom")
private String nom;
@Column(name = "prenom")
private String prenom;
}

@Entity
@Table(name = "ingenieur")
public class Ingenieur extends Employe {
private static final long serialVersionUID = 1L;
@Column(name = "statut")
private String statut;
@Column(name = "nb_projets")

Lotfi ELAACHAK Page 17


private int nbProjets;
}

@Entity
@Table(name = "technicien")
public class Technicien extends Employe {
private static final long serialVersionUID = 1L;
@Column(name = "poste")
private String poste;
@Column(name = "niveau")
private int niveau; }

Une alternative intéressante : la table unique


Unique Table
@Entity
@Table(name = "employe")
@Inheritance(strategy = InheritanceType.SINGLE_TABLE) public abstract class Employe
implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy = [Link])
@Column(name = "id")
private int id;
@Column(name = "nom")
private String nom;
@Column(name = "prenom")
private String prenom; }

@Entity
@Table(name = "ingenieur")
public class Ingenieur extends Employe {
private static final long serialVersionUID = 1L;
@Column(name = "statut")
private String statut;
@Column(name = "nb_projets")
private int nbProjets;
}

@Entity
@Table(name = "technicien")
public class Technicien extends Employe {
private static final long serialVersionUID = 1L;
@Column(name = "poste")
private String poste;
@Column(name = "niveau")

Lotfi ELAACHAK Page 18


private int niveau;
}

Les Requêtes JPQL

La spécification JPA décrit un langage de requête, appelé JPQL (Java Persistence Query Lan-
guage). Ce langage, reprend les fonctionnalités du SQL, et permet d’interroger une base de
données en utilisant les entités JPA définies dans une unité de persistance.
Une requête JPQL est donc écrite indépendamment de la base de données à laquelle elle s’adresse,
ce qui est un gain important de productivité.
Le langage JPQL définit trois types de requêtes :
— les requêtes de sélections.
— les requêtes de mise à jour.
— les requêtes d’effacement.

Exemple de requête de sélection :


JPQL
// construction d'un objet Query
Query query = [Link]( "select marin from Marin marin where [Link] ='
Surcouf'") ;
// exécution et récupération de la liste résultat
List<Marin> marins = [Link]() ;
// analyse du résultat (classique)
for (Marin marin : marins) {
[Link]([Link]()) ;
}
}

Paramétrage d’une requête :


JPQL Params
Query query = [Link]("select marin from Marin marin " +"where [Link] = :
nom and [Link] = :prenom") ;
[Link]("nom", "Surcouf") ;
[Link]("prenom", "Robert") ;
List<Marin> marins = [Link]() ;

2.2 Java Server Faces

2.2.1 Introduction aux Frameworks MVC


La brique de base de la plate-forme Java EE est la servlet. Tout passe par elle, et même nos
pages JSP sont transformées en servlets derrière les rideaux. Eh bien un framework MVC n’est
rien d’autre qu’une surcouche à cette technologie de base. une telle solution facilite le découpage
et la gestion du code d’une application. Elle intervient sur le cycle de vie d’une requête dans
l’application, et prend en quelque sorte la main sur son cheminement.
Il existe deux types de Framework MVC : Framework MVC basée sur les requêtes et Framework

Lotfi ELAACHAK Page 19


MVC basé sur les composantes.

Framework MVC basée sur les requêtes

C’est le type de frameworks MVC le plus simple à comprendre et à assimiler par les développeurs
qui ont déjà de l’expérience avec le développement Java EE en suivant MVC, car il reprend
dans les grandes lignes sensiblement les mêmes principes. Ce sont des solutions qui interviennent
directement sur le cycle de vie d’une requête au sein de l’application (on rejoint ici cette histoire
de "prise de contrôle").
Solutions existants : Struts, Spring.

Framework MVC basé sur les composantes

À la différence de ceux basés sur les requêtes, les frameworks basés sur les composants découpent
logiquement le code en "composants", masquant ainsi le chemin d’une requête au sein de l’appli-
cation. Ils essaient en quelque sorte d’abstraire les concepts de requête et réponse, et de traiter
une application comme une simple collection de composants qui présentent leur propre méthode
de rendu et des actions pour effectuer des tâches. Dans le MVC basé sur les composants, une
unique servlet jouant le rôle deFront Controllerva elle-même regrouper, convertir et valider les
paramètres de requête, et mettre à jour les valeurs du modèle. Le développeur n’a ainsi à se
soucier que des actions métier. La façon dont le contrôleur regroupe/convertit/valide/met à jour
les valeurs est définie dans un unique endroit, la vue. Puisque c’est impossible à réaliser à l’aide
de simple HTML "pur", un langage similaire spécifique est requis pour y parvenir. Dans le cas de
JSF, c’est un langage basé sur du XML (XHTML).
Solutions existants : JSF, Tapestry.

2.2.2 Introduction JSF


JSF (JavaServer Faces) est un framework MVC basé sur les composants. Il est construit sur l’API
Servlet et fournit des composants sous forme de bibliothèques de balises ressemblant très forte-
ment à la JSTL. JSF est un framework MVC et propose, en guise de contrôleur unique du cycle
de vie du traitement des requêtes, la [Link] Il n’y a qu’une seule servlet chargée
d’aiguiller l’intégralité des requêtes entrantes vers les bons composants, et ce pour l’application
tout entière ! Cette architecture porte un nom, il s’agit du pattern Front Controller.

2.2.3 Structure d’une application JSF


La structure globale est très similaire à celle d’une application web Java EE MVC traditionnelle :
— La vue est généralement assurée par des pages JSP ou par des pages XHTML (on parle
alors de Facelets) ;
— Le modèle est assuré par des entités ou des JavaBeans ;
— Lle contrôleur, auparavant incarné par nos servlets, est dorénavant décomposé en deux
éléments :
une unique servlet mère servant de point d’entrée à toute requête, la FacesServlet ;
un JavaBean particulier, déclaré via une annotation et désigné par le terme managed-
bean.
— Le tout est mis en musique par des fichiers de configuration : le classique [Link], mais
également un nouveau fichier nommé [Link].
Nous observons que la différence majeure qui ressort jusqu’à présent est l’absence de servlets
spécifiques à chaque page.

Lotfi ELAACHAK Page 20


Lotfi ELAACHAK Page 21
Chapitre 3
Les Enterprise java Bean (EJB 3.x)
3.1 Applications distribuées JEE
Le principe de l’application distribuée est mettre en place une architecture logicielle permettant
l’exécution d’un programme sur plusieurs ordinateurs.
Le modèle d’architecture « distribuée » impose l’idée qu’une application est découpée en plu-
sieurs unités. Cependant, il serait quasi impossible de créer ce type d’application à zéro « de rien ».

Des standards ont alors vu le jour. Le plus général est sans aucun doute Corba qui correspond
au modèle idéal des applications distribuées. Cependant, la lourdeur et la complexité de mise en
œuvre de ce genre d’applications sont les inconvénients majeurs de cette technologie, pour cette
raison Corba a été remplacé par le modèle EJB qui se base sur le protocole standard IIOP pour
l’échange de données.

3.2 Les EJB 3.x


Les EJB (Entreprise Java Bean) sont un des éléments très importants de la plate-forme Java EE
pour le développement d’applications distribuées.

La plate-forme Java EE propose de mettre en œuvre les couches métiers et persistance avec
les EJB. Particulièrement intéressants dans des environnements fortement distribués, jusqu’à la
version 3, leur mise en oeuvre est assez lourde sans l’utilisation d’outils tels que certains IDE ou
XDoclet.
La version 3 des EJB vise donc à simplifier le développement et la mise en oeuvre des EJB qui
sont fréquemment jugés trop complexes et trop lourds à mettre en oeuvre.
Cette nouvelle version majeure des EJB propose une simplification de leur développement tout
en conservant une compatibilité avec sa précédente version. Elle apporte de très nombreuses

22
fonctionnalités dans le but de simplifier la mise en oeuvre des EJB.

Cette simplification est rendue possible notamment par :

— l’utilisation des annotations


— la mise en œuvre de valeurs par défaut qui répondent à la plupart des besoins (configuration
par exception)
— le descripteur de déploiement est facultatif
— l’utilisation de POJO et de JPA pour les beans de type entity
— l’injection de dépendances côté serveur mais aussi côté client (l’interface Home qui gérait
le cycle de vie est abandonnée) qui remplace l’utilisation directe de JNDI.

Les principales différences entre les EJB 2.x et EJB 3.0 sont donc :

— les descripteurs de déploiement ne sont plus obligatoires grâce à l’utilisation d’annotations


et de valeurs par défaut.
— Les EJB sont de simples POJO annotés : ils n’ont plus besoin d’implémenter une interface
de l’API EJB.
— Le type de l’interface de l’EJB est précisé avec l’annotation @Local ou @Remote.
— L’interface métier est une simple POJI.
— Les EJB de type Entity CMP et BMP sont remplacés parl’utilisation du modèle de per-
sistance reposant sur l’API JPA.

Une classe POJO est une classe Java simple avec des méthodes Setter & Getter, mais elle n’est
ni implémentée ni étendue à partir d’une interface technologique spécifique ou d’une classe res-
pective.

Une interface Java qui ne s’étend pas à partir d’une interface spécifique à une technologie est
appelée POJI.

3.2.1 Types d’EJB


Il existe trois types d’EJB :

Lotfi ELAACHAK Page 23


Session Beans

Les EJB Session se sont des composants distribuées qui implémentent les traitements du logique
métier. Ces composants sont accessible à distance via des protocoles RMI et IIOP.
Ils existent trois types d’EJB Session :
Stateless (sans état) : Les beans de type stateless sont les plus simples et les plus véloces car le
conteneur gère un pool d’instances qui sont utilisées au besoin, ce qui évite des opérations d’ins-
tanciation et de destruction à chaque utilisation. Ceci permet une meilleure montée en charge de
l’application.

— Pas d’état : on ne peut pas garder d’information dans les variables d’instance du bean
— Annotation : @Stateless
— Très souvent utilisé pour l’accès aux données
— Injection d’EntityManager (JPA) par @PersistenceContext
[Link]
@Stateless
public class ForumBean {
@PersistenceContext
EntityManager em;

public Message addMessage(Message newMessage) {


[Link](newMessage);
return newMessage;
}

public Message getMessage(Long id) {


return [Link]([Link], id);
}

public List<MessageList> getAllMessages() {


return [Link]("select m from Message m").getResultList();
}

Lotfi ELAACHAK Page 24


}

Les EJB Session de type stateless peuvent utiliser les callbacks d’évènements marqués avec les
annotations suivantes :

— @PostConstruct
— @PreDestroy

Le cycle de vie d’un Bean Session Stateless :

Stateful (avec état) : Les beans de type Stateful sont capables de conserver leur état durant toute
leur utilisation par le client. Cet état n’est cependant pas persistant : les données sont perdues à
la fin de son utilisation ou à l’arrêt du serveur. Un exemple type d’utilisation de ce type de bean
est l’implémentation d’un caddie pour un site de vente en ligne.

— Bean à état, sera généralement stocké en session une fois créé


— Annotation @Stateful
— Doit être Serializable (sinon, pas de passivation possible)

Lotfi ELAACHAK Page 25


[Link]
@Stateful
public class BasketBean implements Serializable {

private HashSet<Product> products= new HashSet<Product>();

public void addProduct(Product p) {


// .....
}

@Remove
public void doOrder() {
// Sauve la commande dans la base de données
}
}

Les EJB session de type stateful peuvent utiliser les callbacks d’évènements marqués avec les
annotations suivantes :
— @PostConstruct
— @PostActivate
— @PreDestroy
— @PrePassivate
— @Remove
Le cycle de vie d’un Bean Session Stateful :

Singleton (instance unique) : création d’une instance unique

Lotfi ELAACHAK Page 26


— Bean qui n’existe qu’en un seul exemplaire sur un serveur (application répartie : éventuel-
lement un singleton par serveur)
— Exemple : catalogue chargé en mémoire, conversation entre utilisateurs (non permanente)
[Link]
@Singleton
@ConcurrencyManagement(ConcurrencyManagementType. CONTAINER)
public class InMemoryCatalog {
@EJB
ProductService productService;
public Collection<Product> products;
@PostConstruct
@Lock([Link])
public void initCatalog() {
products = new HashSet<Product>([Link]());
}
@Lock([Link])
public void rafraichirCatalogue() {
initCatalog();
}
@Lock([Link])
public Collection<Product> getProducts() {
return products;
}
}

Le cycle de vie d’un Bean Session Singleton :

Lotfi ELAACHAK Page 27


Entity Beans

Les EJB entités représentent les données manipulées par l’application, chaque EJB entité est
associée à une table de la base de données, dans la version 3 des EJB l’accès au source de
données se fait souvent avec l’API JPA .

Message Driven Beans

Les Beans des messages, un Listener qui permet de déclencher des traitements au niveau de
l’application suite à la réception d’un message asynchrone JMS.
[Link]
@MessageDriven(mappedName = "jms/TestQueue")
public class TestMessageDrivenBean implements MessageListener {
@Resource

MessageDrivenContext messageDrivenContext;
public void onMessage(Message message) {
try {
if (message instanceof TextMessage) {
TextMessage msg = (TextMessage) message;
[Link]();
}
} catch (JMSException e) {
[Link]();
} }
}

3.2.2 Interfaces d’EJB Session


L’interface Remote

Permet de déclarer les méthodes qui sont accessible à distance par des composants qui sont
déployées dans d’autres machines, cette interface est représentée par @Remote. Un EJB sans
annotation locale ou remote est considéré comme local.

Lotfi ELAACHAK Page 28


L’interface Local

Permet de déclarer les méthodes qui sont accessible en local par des composants qui sont déployées
dans la même machine « même serveur d’application », cette interface est représentée par @Local.

3.2.3 Utilisation des EJB


Il existe des nombreuses manières de faire référence à des entreprises java Beans :

En JSF

Injection de dépendance par l’utilisation de l’annotation : @EJB

Entre beans

Par des règles et l’injection de dépandance par les annotations@EJB et @Resource.

Depuis une application cliente

Pour appeler un EJB depuis une application cliente en utilise l’API JNDI.
JNDI ou Java Naming Directory Interface est un service d’annuaire qui permet la recherche de
ressources. Chaque ressource comme un EJB, une source de données ou une file d’attente JMS
s’exécutant sur un serveur d’applications reçoit un nom JNDI qui sera utilisé pour localiser la
ressource.
Pour cela l’EJB Session doit implémenter l’interface Remote pour activer l’accès à distance :
[Link]
Package [Link];
@Remote
public interface TestStatelessEjbRemote {
String sayHello(String name);
}

Coté client il faut procéder de la façon suivante :

Lotfi ELAACHAK Page 29


Convertir le projet java vers une projet Maven et insérer au niveau du fichier [Link] le depen-
dence Client EJB WildFly .
[Link]
<!-- [Link] -->
<dependency>
<groupId>[Link]</groupId>
<artifactId>wildfly-ejb-client-bom</artifactId>
<version>24.0.0.SP1</version>
<type>pom</type>
</dependency>

[Link]
public class TestEjbClient {
public static void main(String[] args) throws NamingException {

Properties jndiProperties = new Properties();

[Link](Context.INITIAL_CONTEXT_FACTORY, "[Link].
[Link]");
[Link](Context.URL_PKG_PREFIXES, "[Link]"
);
[Link](Context.PROVIDER_URL,"http-remoting://localhost:8080");
[Link]("[Link]",true);
Context context = new InitialContext(jndiProperties);
HelloEjbRemote helloTest = [Link]("ejb:/TestEjb/HelloTest!(
HelloEjbRemote) [Link]");
[Link]( [Link]("Test"));
}

Depuis une Servlet :


[Link]

public class TestServlet extends HttpServlet {

@EJB(mappedName="java:global/CliEJB/HelloTest![Link]")
TestStatelessEjb testStatelessEjb;
public void doGet(HttpServletRequest request, HttpServletResponse response) {
[Link]("Stackify Reader");
}
}

Lotfi ELAACHAK Page 30


Chapitre 4
Introduction à Srping et Spring boot
4.1 Spring
Spring est un framework opensource, crée pour objective de simplifier le développement des ap-
plications d ‘entreprise.L’un des principaux avantages du framework Spring est son architecture
en composée de plusieurs couches « N Tiers », qui permet un choix multiple de ses composants
fournit un framework cohérent pour le développement d’applications J2EE.
Le framework Spring a été initialement écrit par Rod Johnson et a été publié pour la première
fois sous la licence Apache 2.0 en juin 2003.

Spring est effectivement un conteneur dit « léger », donc une infrastructure similaire à un serveur
d’application J2EE. Il prend donc en charge la création d’objets et la mise en relation d’objets par
l’intermédiaire d’un fichier de configuration dans la plupart des cas une fichier XML, récemment
remplacer par un autre mécanisme base sur les annotations qui décrit les objets à construire et
les relations de dépendances entre ces objets.

4.1.1 Les caractéristiques de Spring


— Inversion de contrôle (IOC) : Le concept de base de l’injection de dépendance ou de
l’inversion de contrôle consiste a ne pas connecter directement les composants et services
dans un programme, mais plutôt de décrire quels services sont requis par quels composants
dans un fichier de configuration / fichier XML ou bien par une annotation. Le conteneur
Spring IOC est alors chargé de tout lier.
— Oriente aspect (AOP) : Spring prend en charge la programmation orientée aspect, l’AOP
est un nouveau paradigme qui sépare la partie logic/métier de la partie la partie traitement
« exception, log , etc » .
— Contenaire : Spring contient et gère le cycle de vie et la configuration des objets de
l’application.
— Le Framework MVC : Spring est livré avec le framework d’applications Web MVC, basé sur
les fonctionnalités de base de Spring. Il est configurable via des interfaces de stratégie et
il prend en charge plusieurs technologies d’affichage telles que JSP, Velocity, Tiles, iText
et POI. Cependant, d’autres frameworks peuvent être intégré à la place du framework
Spring MVC comme Struts 2, ou bien Tapestry.
— Gestion des Transactions : Le framework Spring fournit une couche d’abstraction générique
pour la gestion des transactions. Cela permet au développeur d’ajouter les gestionnaires de
transactions sans traiter les problèmes de bas niveau. La prise en charge des transactions
de Spring n’est pas liée aux environnements J2EE et peut également être utilisée dans des
environnements sans conteneur.
— JDBC Exception Handling : La couche d’abstraction JDBC de Spring propose une hiérar-
chie des exceptions significative, qui simplifie la stratégie de gestion des erreurs. Intégration
avec Hibernate, JDO et iBATIS : Spring fournit les meilleurs services d’intégration avec
Hibernate, JDO et iBATIS.

31
4.1.2 Architecture de la technologie Spring

Le framework est organisé en modules, reposant tous sur le module Spring Core :

Spring Core (Container)

implémente notamment le concept d’inversion de contrôle (injection de dépendance). Il est éga-


lement responsable de la gestion et de la configuration du [Link] container possède quatre
modules « Beans, Core,Context et SpEL ».
— Beans : il fournit BeanFactory, qui est une implémentation sophistiquée du modèle de
Factory.
— Core : il contient les éléments fondamentaux du cadre, y compris les fonctions IoC et
Injection de dépendance.
— Context : il s’appuie sur la base solide fournie par les modules Core et Beans et constitue
un moyen d’accéder à tous les objets définis et configurés. L’interface ApplicationContext
est le point central du module de contexte.
— SpEL : il fournit un puissant langage d’expression pour interroger et manipuler un graphe
d’objet lors de l’exécution.

Spring DATA / INTEGRATION

La couche d’accès aux données / d’intégration comprend les modules JDBC, ORM, OXM, JMS
et Transaction dont les détails sont les suivants :
— JDBC : Le module JDBC fournit une couche d’abstraction JDBC qui élimine le besoin
de codage fastidieux lié à JDBC.
— ORM : Le module ORM fournit des couches d’intégration pour les API de mappage objet-
relationnel populaires, notamment JPA, JDO, Hibernate et iBatis.
— OXM :Le module OXM fournit une couche d’abstraction qui prend en charge les implé-
mentations de mappage Object / XML pour JAXB, Castor, XMLBeans, JiBX et XStream.
— JMS : Le module JMS du service de messagerie Java contient des fonctionnalités permet-
tant de générer et de consommer des messages.
— Transaction : Le module Transaction prend en charge la gestion de transaction program-
matique et déclarative pour les classes implémentant des interfaces spéciales et pour tous
vos POJO.

Lotfi ELAACHAK Page 32


Spring AOP

Le module AOP fournit une implémentation de programmation orientée aspect qui permet de
définir des intercepteurs de méthode et des découpes en points afin de découpler proprement le
code implémentant des fonctionnalités à séparer.

Spring Aspects

Le module Aspects fournit une intégration à AspectJ, qui est à nouveau un cadre AOP puissant
et mature.

Spring Instrumentation

Le module Instrumentation fournit un support d’instrumentation de classe et des implémenta-


tions de chargeur de classe à utiliser sur certains serveurs d’applications.

Spring Messaging

Le module de messagerie prend en charge STOMP en tant que sous-protocole WebSocket à utiliser
dans les applications. Il prend également en charge un modèle de programmation d’annotation
pour le routage et le traitement des messages STOMP provenant de clients WebSocket.

Spring Web MVC

Implémentation du modèle MVC. Personnellement j’utilise plutôt Struts mais c’est surtout une
question d’habitude, c’est là la grande force de Spring, rien ne vous oblige à tout utiliser et vous
pouvez tout mélanger. Ce qui n’est pas forcément une bonne idée mais nous en reparlerons.

La couche Web comprend les modules Web, Web-MVC, Web-Socket et Web-Portlet, dont les
détails sont les suivants :
— Web : Le module Web fournit des fonctionnalités d’intégration Web de base, telles que
la fonctionnalité de téléchargement de fichiers en plusieurs parties et l’initialisation du
conteneur IoC à l’aide d’écouteurs de servlets et d’un contexte d’application Web.
— Web-MVC : Le module Web-MVC contient l’implémentation MVC (Model-View-Controller)
de Spring pour les applications Web.

Lotfi ELAACHAK Page 33


— Web-Socket : Le module Web-Socket prend en charge la communication bidirectionnelle
basée sur WebSocket entre le client et le serveur dans les applications Web.
— Web-Portlet : Le module Web-Portlet fournit l’implémentation MVC à utiliser dans un
environnement de portlet et reflète les fonctionnalités du module Web-Servlet.

Spring Test

Le module Test prend en charge le test des composants Spring avec les frameworks JUnit ou
TestNG.

4.1.3 Injection de dépendance


L’injection de dépendances (ID) est un patron de conception qui supprime la dépendance du
code de programmation afin qu’il soit facile de gérer et de tester l’application. L’injection de
dépendances rend notre code de programmation faiblement couplé.
L’injection de dépendance est un patron de conception qui supprime la dépendance des pro-
grammes. Dans ce cas, nous fournissons les informations de la source externe telle qu’un fichier
XML. Cela rend notre code faiblement couplé et plus facile à tester.
Le framework Spring fournit deux façons d’injecter une dépendance
— Par constructeur
— Par méthode Setter

Exemple d’injection de dépendances par constructeur

Nous pouvons injecter la dépendance par constructeur. Le sous-élément <constructor-arg> de


<bean> est utilisé pour l’injection de constructeur. Ici, nous allons injecter
— Valeurs primitives et basées sur des chaînes
— Objet dépendant (objet contenu)
— Valeurs de collection, etc.
[Link]
package [Link];

public class Employee {


private int id;
private String name;

public Employee() {[Link]("def cons");}

public Employee(int id) {[Link] = id;}

public Employee(String name) { [Link] = name;}

public Employee(int id, String name) {


[Link] = id;
[Link] = name;
}

void show(){

Lotfi ELAACHAK Page 34


[Link](id+" "+name);
}

[Link]
<?xml version="1.0" encoding="UTF-8"?>
<beans
xmlns="[Link]
xmlns:xsi="[Link]
xmlns:p="[Link]
xsi:schemaLocation="[Link]
[Link]

<bean id="e" class="[Link]">


<constructor-arg value="10" type="int"></constructor-arg>
</bean>

</beans>

[Link]
package [Link];

import [Link];
import [Link];
import [Link].*;

public class Test {


public static void main(String[] args) {

Resource r=new ClassPathResource("[Link]");


BeanFactory factory=new XmlBeanFactory(r);

Employee s=(Employee)[Link]("e");
[Link]();

}
}

Exemple d’injection de dépendances par méthode set

S’il existe une relation HAS-A entre les classes, nous créons d’abord l’instance de l’objet dépen-
dant (objet contenu) puis la transmettons comme argument du constructeur de classe principal.
Ici, notre scénario est l’adresse de l’employé HAS-A. L’objet de classe Adresse sera appelé objet
dépendant.

Lotfi ELAACHAK Page 35


[Link]
package [Link];

public class Address {


private String city;
private String state;
private String country;

public Address(String city, String state, String country) {


super();
[Link] = city;
[Link] = state;
[Link] = country;
}

public String toString(){


return city+" "+state+" "+country;
}
}

[Link]
package [Link];

public class Employee {


private int id;
private String name;
private Address address;//Aggregation

public Employee() {[Link]("def cons");}

public Employee(int id, String name, Address address) {


super();
[Link] = id;
[Link] = name;
[Link] = address;
}

void show(){
[Link](id+" "+name);
[Link]([Link]());
}

[Link]
<?xml version="1.0" encoding="UTF-8"?>

Lotfi ELAACHAK Page 36


<beans
xmlns="[Link]
xmlns:xsi="[Link]
xmlns:p="[Link]
xsi:schemaLocation="[Link]
[Link]

<bean id="a1" class="[Link]">


<constructor-arg value="ghaziabad"></constructor-arg>
<constructor-arg value="UP"></constructor-arg>
<constructor-arg value="India"></constructor-arg>
</bean>

<bean id="e" class="[Link]">


<constructor-arg value="12" type="int"></constructor-arg>
<constructor-arg value="Sonoo"></constructor-arg>
<constructor-arg>
<ref bean="a1"/>
</constructor-arg>
</bean>

</beans>

[Link]
package [Link];

import [Link];
import [Link];
import [Link].*;

public class Test {


public static void main(String[] args) {

Resource r=new ClassPathResource("[Link]");


BeanFactory factory=new XmlBeanFactory(r);

Employee s=(Employee)[Link]("e");
[Link]();

}
}

Lotfi ELAACHAK Page 37


4.1.4 Spring ORM
Spring fournit une API pour intégrer facilement Spring aux frameworks ORM tels que Hibernate,
JPA (Java Persistence API), JDO (Java Data Objects), Oracle Toplink et iBATIS.

Le framework Spring présente de nombreux avantages par rapport aux frameworks ORM. Il y a
comme suit :
— Moins de codage est requis : grâce au framework Spring, vous n’avez pas besoin d’écrire de
codes supplémentaires avant et après la logique de base de données réelle, comme obtenir
la connexion, démarrer la transaction, valider la transaction, fermer la connexion, etc.
— Facile à tester : l’approche IoC de Spring facilite le test de l’application.
— Meilleure gestion des exceptions : le framework Spring fournit sa propre API pour la
gestion des exceptions avec le framework ORM.
— Gestion intégrée des transactions : à l’aide du framework Spring, nous pouvons envelopper
notre code de mappage avec une classe wrapper de modèle explicite ou un intercepteur de
méthode de style AOP.

4.1.5 Spring MVC


Un Spring MVC est un framework Java utilisé pour créer des applications Web. Il suit le modèle
de conception Modèle-Vue-Contrôleur. Il implémente toutes les fonctionnalités de base d’un fra-
mework Spring de base comme l’inversion de contrôle, l’injection de dépendances.

Un Spring MVC fournit une solution élégante pour utiliser MVC dans le framework Spring à
l’aide de DispatcherServlet. Ici, DispatcherServlet est une classe qui reçoit la demande entrante
et la mappe à la bonne ressource telle que les contrôleurs, les modèles et les vues

— Comme le montre la figure, toutes les requêtes entrantes sont interceptées par le Dispat-
cherServlet qui fait office de contrôleur frontal.
— Le DispatcherServlet obtient une entrée de mappage de gestionnaire à partir du fichier
XML et transmet la demande au contrôleur.
— Le contrôleur renvoie un objet de ModelAndView.
— Le DispatcherServlet vérifie l’entrée du résolveur de vue dans le fichier XML et appelle le
composant de vue spécifié.

4.1.6 MVC Form Tag Library


Les balises de formulaire Spring MVC sont les blocs de construction configurables et réutilisables
d’une page Web. Ces balises fournissent JSP, un moyen facile de développer, lire et maintenir.

Lotfi ELAACHAK Page 38


Les balises de formulaire Spring MVC peuvent être considérées comme des balises prenant en
charge la liaison de données qui peuvent automatiquement définir des données sur un objet/bean
Java et également en récupérer. Ici, chaque balise prend en charge l’ensemble d’attributs de sa
contrepartie de balise HTML correspondante, rendant les balises familières et faciles à utiliser.

La bibliothèque de balises de formulaire se trouve sous le [Link]. Pour activer la


prise en charge de la bibliothèque de balises de formulaire, il est nécessaire de référencer une
configuration. Ajoutez donc la directive suivante au début de la page JSP :
[Link]
<%@taglib prefix="form" uri="[Link] %>

4.1.7 Spring Security


Spring Security est un framework qui fournit diverses fonctionnalités de sécurité telles que : l’au-
thentification, l’autorisation de créer des applications d’entreprise Java sécurisées.

C’est un sous-projet du framework Spring qui a été lancé en 2003 par Ben Alex. Plus tard, en
2004, il a été publié sous la licence Apache sous le nom de Spring Security 2.0.0.

Il surmonte tous les problèmes qui surviennent lors de la création d’applications de sécurité non
Spring et gère un nouvel environnement de serveur pour l’application.

Ce cadre cible deux domaines d’application majeurs sont l’authentification et l’autorisation. L’au-
thentification est le processus de connaissance et d’identification de l’utilisateur qui souhaite ac-
céder.

L’autorisation est le processus permettant à l’autorité d’effectuer des actions dans l’application.

Nous pouvons appliquer une autorisation pour autoriser la demande Web, les méthodes et l’accès
à un domaine individuel.

Lotfi ELAACHAK Page 39


Le framework Spring Security prend en charge une large gamme de modèles d’authentification.
Ces modèles sont fournis soit par des tiers, soit par le cadre lui-même. Spring Security prend en
charge l’intégration avec toutes ces technologies.

— En-têtes d’authentification HTTP BASIC


— En-têtes d’authentification HTTP Digest
— Échange de certificat client HTTP X.509
— LDAP (Protocole d’accès aux annuaires léger)
— Authentification par formulaire
— Authentification OpenID
— Authentification automatique par rappel de moi
— Kerberos
— JOSSO (Java Open Source Single Sign-On)
— AppFuse
— AndroMDA
— Mule ESB
— DWR (demande Web directe)

La beauté de ce cadre est sa nature d’authentification flexible pour s’intégrer à n’importe quelle
solution logicielle. Parfois, les développeurs souhaitent l’intégrer à un système hérité qui ne res-
pecte aucune norme de sécurité, Spring Security fonctionne bien.
[Link]
<beans:beans xmlns="[Link]
xmlns:beans="[Link]
xmlns:xsi="[Link]
xsi:schemaLocation="[Link]
[Link]
[Link]
[Link]
<http auto-config="true">
<intercept-url pattern="/admin" access="hasRole('ROLE_ADMIN')" />
</http>
<authentication-manager>
<authentication-provider>
<user-service>
<user name="admin" password="1234" authorities="hasRole(ROLE_ADMIN)" />
</user-service>
</authentication-provider>
</authentication-manager>
</beans:beans>

[Link]
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.anyRequest().authenticated()
.and()
.formLogin()

Lotfi ELAACHAK Page 40


.and()
.httpBasic();
}

Cette méthode fait les choses suivantes.


— Il s’assure que chaque demande faite par l’utilisateur nécessite à l’utilisateur d’être au-
thentifié
— Il permet à l’utilisateur de s’authentifier en utilisant une connexion basée sur un formulaire
— Il permet à l’utilisateur de s’authentifier avec l’authentification HTTP Basic

4.2 Spring boot

4.2.1 Introduction Spring boot


Spring Boot est un projet basé sur le framework Spring. Il offre un moyen plus simple et plus
rapide d’installer, de configurer et d’exécuter des applications simples.

Il s’agit d’un module Spring qui fournit la fonctionnalité RAD (Rapid Application Development)
au framework Spring. Il est utilisé pour créer une application autonome basée sur Spring qu’on
peut simplement exécuter car elle nécessite une configuration Spring minimale.

En bref, Spring Boot est la combinaison de Spring Framework et de serveurs intégrés.

Dans Spring Boot, la configuration XML (descripteur de déploiement) n’est pas requise. Il utilise
la convention sur le paradigme de conception de logiciel de configuration, ce qui signifie qu’il
diminue l’effort du développeur.

On peut utiliser Spring STS IDE ou Spring Initializr pour développer des applications Java
Spring Boot.

Pourquoi devrions-nous utiliser Spring Boot Framework ?

— L’approche d’injection de dépendance est utilisée dans Spring Boot.


— Il contient de puissantes capacités de gestion des transactions de base de données.
— Il simplifie l’intégration avec d’autres frameworks Java comme JPA/Hibernate ORM,
Struts, etc.
— Il réduit le coût et le temps de développement de l’application.

Lotfi ELAACHAK Page 41


Avec Spring Boot Framework, de nombreux autres projets Spring aident à créer des applications
répondant aux besoins des entreprises modernes. Les projets Spring associés a spring boot sont
les suivants :
— Spring Data : il simplifie l’accès aux données à partir des bases de données relationnelles
et NoSQL.
— Spring Batch : Il fournit un traitement par lots puissant.
— Spring Security : il s’agit d’un cadre de sécurité qui fournit une sécurité robuste aux
applications.
— Spring Social : Il prend en charge l’intégration avec les réseaux sociaux comme LinkedIn.
— Spring Integration : il s’agit d’une implémentation des modèles d’intégration d’entreprise.
Il facilite l’intégration avec d’autres applications d’entreprise à l’aide d’adaptateurs de
messagerie et déclaratifs légers.

Avantages de Spring Boot

— Il crée des applications Spring autonomes qui peuvent être démarrées à l’aide de Java -jar.
— Il teste facilement les applications Web à l’aide de différents serveurs HTTP embarqués
tels que Tomcat, Jetty, etc.
— Il fournit des POM « de démarrage » avisés pour simplifier notre configuration Maven.
— Il fournit des fonctionnalités prêtes pour la production telles que des métriques, des véri-
fications de l’état et une configuration externalisée.
— Il n’y a aucune exigence pour la configuration XML.
— Il offre un outil CLI pour développer et tester l’application Spring Boot.
— Il offre le nombre de plug-ins.
— Il minimise également l’écriture de plusieurs codes passe-partout (le code qui doit être
inclus à de nombreux endroits avec peu ou pas de modification), la configuration XML et
les annotations.
— Il augmente la productivité et réduit le temps de développement.

4.2.2 Architecture de Spring Boot


Spring Boot suit une architecture en couches dans laquelle chaque couche communique avec la
couche directement en dessous ou au-dessus (structure hiérarchique).

Avant de comprendre l’architecture Spring Boot, nous devons connaître les différentes couches et
classes qui y sont présentes. Il y a quatre couches dans Spring Boot :

— Couche de présentation
— Couche métier
— Couche de persistance
— Couche de base de données

Lotfi ELAACHAK Page 42


Presentation Layer : la couche de présentation gère les requêtes HTTP, traduit le paramètre
JSON en objet, authentifie la requête et la transfère à la couche métier. En bref, il se compose
de vues, c’est-à-dire d’une partie frontale.

Business Layer : La couche métier gère toute la logique métier. Il se compose de classes de ser-
vices et utilise des services fournis par des couches d’accès aux données. Il effectue également
l’autorisation et la validation.

Persistence Layer : la couche de persistance contient toute la logique de stockage et traduit les
objets métier depuis et vers les lignes de la base de données.

Database Layer : dans la couche de base de données, les opérations CRUD (create, retrive, update,
delete) sont effectuées.

Architecture de flux de Spring Boot

Lotfi ELAACHAK Page 43


4.2.3 Composants du projet Spring Boot
Spring Boot Annotations

Spring Boot Annotations est une forme de métadonnées qui fournit des données sur un pro-
gramme. En d’autres termes, les annotations sont utilisées pour fournir des informations supplé-
mentaires sur un programme. Il ne fait pas partie de l’application que nous développons. Cela
n’a pas d’effet direct sur le fonctionnement du code qu’ils annotent. Cela ne change pas l’action
du programme compilé.

— @Required : Cela s’applique à la méthode du bean setter. Il indique que le bean annoté
doit être rempli au moment de la configuration avec la propriété requise, sinon il lève une
exception BeanInitilizationException.

— @Autowired : Spring fournit un câblage automatique basé sur des annotations en four-
nissant une annotation @Autowired. Il est utilisé pour câbler automatiquement le bean
à ressort sur les méthodes setter, la variable d’instance et le constructeur. Lorsque nous
utilisons l’annotation @Autowired, le conteneur Spring câble automatiquement le bean en
faisant correspondre le type de données.

— @Configuration : il s’agit d’une annotation au niveau de la classe. La classe annotée avec


@Configuration utilisée par Spring Containers comme source de définitions de bean.

— @ComponentScan : il est utilisé lorsque nous voulons analyser un paquet pour les beans.
Il est utilisé avec l’annotation @Configuration. Nous pouvons également spécifier les pa-
ckages de base à analyser pour les composants Spring.

— @Bean : C’est une annotation au niveau de la méthode. C’est une alternative à la balise
XML <bean>. Il indique à la méthode de produire un bean à gérer par Spring Container.

— @Component : il s’agit d’une annotation au niveau de la classe. Il est utilisé pour marquer
une classe Java en tant que bean. Une classe Java annotée avec @Component est trouvée
pendant le chemin de classe. Le Spring Framework le récupère et le configure dans le
contexte de l’application en tant que Spring Bean.

— @Controller : Le @Controller est une annotation au niveau de la classe. C’est une spéciali-
sation de @Component. Il marque une classe en tant que gestionnaire de requêtes Web. Il
est souvent utilisé pour servir des pages Web. Par défaut, il renvoie une chaîne qui indique
la route à rediriger. Il est principalement utilisé avec l’annotation @RequestMapping.
— @Service : Il est également utilisé au niveau de la classe. Il indique au Spring que la classe
contient la logique métier.

— @Repository : il s’agit d’une annotation au niveau de la classe. Le référentiel est un DAO


(Data Access Object) qui accède directement à la base de données. Le référentiel effectue
toutes les opérations liées à la base de données.

— @RequestMapping : Il est utilisé pour mapper les requêtes Web. Il contient de nombreux
éléments facultatifs tels que consomme, en-tête, méthode, nom, paramètres, chemin, pro-
duit et valeur. Nous l’utilisons avec la classe ainsi que la méthode.
— @GetMapping : il mappe les requêtes HTTP GET sur la méthode de gestionnaire spéci-
fique. Il est utilisé pour créer un point de terminaison de service Web qui récupère Il est
utilisé au lieu d’utiliser : @RequestMapping(method = [Link])

Lotfi ELAACHAK Page 44


— @PostMapping : il mappe les requêtes HTTP POST sur la méthode de gestionnaire spéci-
fique. Il est utilisé pour créer un point de terminaison de service Web qui crée Il est utilisé
au lieu d’utiliser : @RequestMapping(method = [Link])

— @PutMapping : il mappe les requêtes HTTP PUT sur la méthode de gestionnaire spéci-
fique. Il est utilisé pour créer un point de terminaison de service Web qui crée ou met à
jour Il est utilisé au lieu d’utiliser : @RequestMapping(method = [Link])

— @DeleteMapping : il mappe les requêtes HTTP DELETE sur la méthode de gestionnaire


spécifique. Il est utilisé pour créer un point de terminaison de service Web qui supprime
une ressource. Il est utilisé au lieu d’utiliser : @RequestMapping(method = RequestMe-
[Link])

— @PatchMapping : il mappe les requêtes HTTP PATCH sur la méthode de gestionnaire


spécifique. Il est utilisé au lieu d’utiliser : @RequestMapping(method = RequestMe-
[Link])

— @RequestBody : Il est utilisé pour lier une requête HTTP à un objet dans un paramètre
de méthode. En interne, il utilise des convertisseurs de messages HTTP pour convertir le
corps de la requête. Lorsque nous annotons un paramètre de méthode avec @RequestBody,
le framework Spring lie le corps de la requête HTTP entrante à ce paramètre.
— @ResponseBody : il lie la valeur de retour de la méthode au corps de la réponse. Il in-
dique au Spring Boot Framework de sérialiser un objet de retour au format JSON et XML.

— @PathVariable : Il est utilisé pour extraire les valeurs de l’URI. Il convient le mieux au
service Web RESTful, où l’URL contient une variable de chemin. Nous pouvons définir
plusieurs @PathVariable dans une méthode.

— @RequestParam : Il est utilisé pour extraire les paramètres de la requête de l’URL. Il est
également appelé paramètre de requête. Il est le plus approprié pour les applications Web.
Il peut spécifier des valeurs par défaut si le paramètre de requête n’est pas présent dans
l’URL.

— @RequestHeader : Il est utilisé pour obtenir les détails sur les en-têtes de requête HTTP.
Nous utilisons cette annotation comme paramètre de méthode. Les éléments facultatifs
de l’annotation sont name, required, value, defaultValue. Pour chaque détail de l’en-tête,
nous devons spécifier des annotations distinctes. Nous pouvons l’utiliser plusieurs fois dans
une méthode.

— @RestController : il peut être considéré comme une combinaison d’annotations @Control-


ler et @ResponseBody. L’annotation @RestController est elle-même annotée avec l’annota-
tion @ResponseBody. Il élimine le besoin d’annoter chaque méthode avec @ResponseBody.

— @RequestAttribute : Il lie un paramètre de méthode à l’attribut de requête. Il fournit un


accès pratique aux attributs de requête à partir d’une méthode de contrôleur. Avec l’aide
de l’annotation @RequestAttribute, nous pouvons accéder aux objets qui sont remplis côté
serveur.

Lotfi ELAACHAK Page 45


Spring Boot Application Properties

Spring Boot Framework est livré avec un mécanisme intégré pour la configuration de l’application
à l’aide d’un fichier appelé [Link]. Il est situé dans le dossier src/main/resources.

Spring Boot fournit diverses propriétés qui peuvent être configurées dans le fichier applica-
[Link]. Les propriétés ont des valeurs par défaut. Nous pouvons définir une ou plusieurs
propriétés pour l’application Spring Boot. Spring Boot nous permet également de définir notre
propre propriété si nécessaire.

Le fichier [Link] nous permet d’exécuter une application dans un environnement


différent. En bref, nous pouvons utiliser le fichier [Link] pour :

— Configurer le framework Spring Boot


— Définir les propriétés de configuration personnalisées de l’application
[Link]
#configuring application name
[Link] = demoApplication
#configuring port
[Link] = 8081

4.2.4 Spring Boot View : Thymeleaf


Thymeleaf est un moteur de template, sous licence Apache 2.0, écrit en Java pouvant générer
du XML/XHTML/HTML5. Thymeleaf peut être utilisé dans un environnement web (utilisant
l’API Servlet) ou non web. Son but principal est d’être utilisé dans un environnement web pour
la génération de vue pour les applications web basées sur le modèle MVC.

— C’est un moteur de template écrit en Java traitant les fichiers XML, XHTML et HTML5.
— Thymeleaf permet de traiter à la fois les fichiers appartenant à un site web ou non. Il n’y
a pas dépendance vis-à-vis de l’API Servlet.
— Thymeleaf est composé de plusieurs modules appelés dialecte :
— Les caractéristiques d’un dialecte s’appliquent à travers les balises et/ou les attributs des
templates.
— Deux dialectes sont disponibles : Standard et le SpringStandard (pour les applications
Spring MVC mais en utilisant la même syntaxe que le dialecte Standard).
— Les développeurs peuvent étendre les fonctionnalités des dialectes proposés ou bien créer
leur propre dialecte.
— Plusieurs modes de template sont disponibles :
XML
XHTML 1.0 and 1.1
HTML5
— Le support de l’internationalisation des textes.
— La mise en œuvre d’un cache performant et configurable permet de réduire les entrées/-
sorties.
— Thymeleaf est extrêmement extensible et peut être utilisé comme framework de template.
— Une documentation très complète contenant de nombreux exemples est disponible.
Exemple
<table>

Lotfi ELAACHAK Page 46


<thead>
<tr>
<th th:text="#{[Link]}">Name</th>
<th th:text="#{[Link]}">Price</th>
</tr>
</thead>
<tbody>
<tr th:each="prod : ${allProducts}">
<td th:text="${[Link]}">Oranges</td>
<td th:text="${#[Link]([Link],1,2)}">0.99</td>
</tr>
</tbody>
</table>

Ce code met en évidence différentes caractéristiques de Thymeleaf :


— internationalisation par l’utilisation d’expression : #{ ... }
— évaluation d’expressions contenant des variables : ${ ... }
— fonction facilitatrice :#[Link]( ... )
Ce code HTML peut être affiché correctement directement par un navigateur sans utiliser Thy-
meleaf. C’est une caractéristique importante de Thymeleaf appelée template naturel.

Lotfi ELAACHAK Page 47


Chapitre 5
Les web services JAX-RS et Srping
RESTful
5.1 Qu’est-ce qu’un service Web ?
La technologie des services Web est un moyen rapide de distribution de l’information entre clients,
fournisseurs, partenaires commerciaux et leurs différentes plates-formes. Les services Web sont
basés sur le modèle SOA.
D’autres technologies telles que RMI, DCOM et CORBA ont précédemment adopté ce style
architectural mais ont généralement échoué en raison de la diversité des plates-formes utilisées
dans les organisations et aussi parce que leur usage n’était pas adapté à Internet (problème de
passage à travers des FireWalls, etc.) d’où la lenteur, voire l’absence de réponses sur ce réseau.
Les applications réparties fondées sur ces technologies offrent des solutions caractérisées par un
couplage fort entre les objets. Les solutions proposées par les services Web, permettent néanmoins
un couplage moins fort. De plus, l’utilisation des technologies standards du Web telles HTTP
et XML par les services Web facilite le développement d’applications réparties sur Internet, et
permet d’avoir des applications très faiblement couplées. L’intégration est sans doute le facteur
essentiel qui favorise l’utilisation des services Web.

5.1.1 Les caractéristiques d’un service Web


La technologie des services Web repose essentiellement sur une représentation standard des don-
nées (interfaces, messageries) au moyen du langage XML. Cette technologie est devenue la base
de l’informatique distribuée sur Internet et offre beaucoup d’opportunités au développeur Web.
Un service Web possède les caractéristiques suivantes :
— il est accessible via le réseau ;
— il dispose d’une interface publique (ensemble d’opérations) décrite en XML ;
— ses descriptions (fonctionnalités, comment l’invoquer et où le trouver ?) sont stockées dans
un annuaire ;
— il communique en utilisant des messages XML, ces messages sont transportés par des pro-
tocoles Internet (généralement HTTP, mais rien n’empêche d’utiliser d’autres protocoles
de transfert tels : SMTP, FTP, BEEP... ) ;
— l’intégration d’application en implémentant des services Web produit des systèmes faible-
ment couplés, le demandeur du service ne connaît pas forcément le fournisseur. Ce dernier
peut disparaître sans perturber l’application cliente qui trouvera un autre fournisseur en
cherchant dans l’annuaire.

5.1.2 Architecture d’un service Web


Les services Web reprennent la plupart des idées et des principes du Web (HTTP, XML), et les
appliquent à des interactions entre machines. Comme pour le World Wide Web, les services Web
communiquent via un ensemble de technologies fondamentales qui partagent une architecture
commune. Ils ont été conçus pour être réalisés sur de nombreux systèmes développés et déployés
de façon indépendante. Les technologies utilisées par les services Web sont HTTP, WSDL, REST,
XML-RPC, SOAP et UDDI.

48
REST

REST (Representational State Transfer) est une architecture de services Web. Élaborée en l’an
2000 par Roy Fiedling, l’un des créateurs du protocole HTTP, du serveur Apache HTTPd et
d’autres travaux fondamentaux, REST est une manière de construire une application pour les
systèmes distribués comme le World Wide Web.

XML-RPC

XML-RPC est un protocole simple utilisant XML pour effectuer des messages RPC. Les requêtes
sont écrites en XML et envoyées via HTTP POST. Les requêtes sont intégrées dans le corps de la
réponse HTTP. XML-RPC est indépendant de la plate-forme, ce qui lui permet de communiquer
avec diverses applications. Par exemple, un client Java peut parler de XML-RPC à un PerlServer !

SOAP

SOAP (Simple object Access Protocol) est un protocole standard de communication. C’est l’épine
dorsale du système d’interopérabilité. SOAP est un protocole décrit en XML et standardisé par le
W3C. Il se présente comme une enveloppe pouvant être signée et pouvant contenir des données ou
des pièces jointes. Il circule sur le protocole HTTP et permet d’effectuer des appels de méthodes
à distance.

WSDL

WSDL (Web Services Description Language) est un langage de description standard. C’est l’in-
terface présentée aux utilisateurs. Il indique comment utiliser le service Web et comment interagir
avec lui. WSDL est basé sur XML et permet de décrire de façon précise les détails concernant le
service Web tels que les protocoles, les ports utilisés, les opérations pouvant être effectuées, les
formats des messages d’entrée et de sortie et les exceptions pouvant être envoyées.

UDDI

UDDI (Universal Description, Discovery and Integration) est un annuaire de services. Il fournit
l’infrastructure de base pour la publication et la découverte des services Web. UDDI permet aux
fournisseurs de présenter leurs services Web aux clients.

5.2 Webservices Restful « JAX-RS » avec JEE


JAX-RS, Java API for RESTful Web Services, c’est simplement une interface de programmation
fournie par JEE afin d’implémenter des webservices avec une architecture REST (representational
state transfer).

5.2.1 Qu’est ce que REST ?


Les webservices REST contrairement à SOAP qui est un protocole, s’appuie totalement sur les
standards web et sur le protocole HTTP. REST a été décrit pour la première fois par Roy Fielding
en 2000. Le concept d’une architecture REST est simple et se base sur le concept de ressources,
dans REST tout est ressource et on y accède par l’intermédiaire des méthodes HTTP :
— DELETE pour la suppression
— GET pour la récupération

Lotfi ELAACHAK Page 49


— PATCH pour la modification partiel
— POST pour la création
— PUT pour la modification
— etc...
Chaque ressource est identifiée par une URI unique. Et enfin REST nous donne la possibilité de
récupérer ces différentes ressources sous différents formats tel que du texte, de l’XML , du JSON
etc...
Pour finir sur REST, si on respecte les standards que j’évoque ci- dessus on pourra parler d’ar-
chitecture RESTFul. Car beaucoup croient qu’ils font du REST en exposant des ressources par
Webservices, par exemple pour supprimer une ressource livre certains font :

GET /<context-root>/livre ?id=1&method=delete

Hors ici on ne s’appuie pas sur le verbe HTTP GET pour indiquer le type d’action que l’on désire
appliquer, dans un cadre RESTFul on devrait faire :

DELETE /<context-root>/livre/1

5.2.2 JAX-RS
Par la suite nous parlerons de JAX-RS 2.0 qui est fournit par JEE7 qui correspond à la JSR 339
qui succède à JAX-RS 1 qui découle de la JSR 311.

5.2.3 Les Annotations


Annotation Description
@ApplicationPath(String) Définit le pont d’entrée REST.
@Path(String) Définit le chemin de la ressource.
@DELETE Définit le verbe HTTP.
@GET Définit le verbe HTTP.
@POST Définit le verbe HTTP.
@PUT Définit le verbe HTTP.
@Consumes(String[]) Spécifie les Types MIME Rep .
@Produces(String[]) Spécifie les Types MIME accepté en entrée du service.
@CookieParam(String) Récupérer un cookie dans le service.
@FormParam(String) Récupérer un champ de formulaire dans le service.
@HeaderParam(String) Récupérer un header HTTP dans le service.
@PathParam(String) Récupérer un élément du Path d’appel.
@QueryParam(String) Récupérer un paramètre de l’url ( ? parametre=valeur).

Service REST

[Link]
package [Link];
import [Link];
import [Link];
import [Link];
import [Link];
import [Link];
import [Link];

Lotfi ELAACHAK Page 50


import [Link];
import [Link];
import [Link];
import [Link];
import [Link];

@Path("/ma-ressource")
public class MaRessourceRest {

@GET
@Produces(MediaType.APPLICATION_JSON)
public Response getMesRessources() {
// retourne une liste de ressoure List et un code HTTP 200
return [Link]([Link]()).build();
}

@GET
@Path("/{id}")
@Produces(MediaType.APPLICATION_JSON)
public Response getMaRessourceParId( @PathParam("id") String id) {
// retourne une ressoure : MaRessource et un code HTTP 200
return [Link](([Link](id)).build
();
}

@POST
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Response createMaRessource( MaRessourceJson maRessource ) {
// crée une ressoure MaRessource
//retourne l'ID de la ressource et un code HTTP 201
MaRessourceJson result = [Link](maRessource);
return [Link]([Link]).entity([Link]()).build();
}

@PUT
@Path("/{id}")
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
public Response updateMaRessource( @PathParam("id") String id, MaRessourceJson
maRessource) {
// retourne la ressource et un code HTTP 200
[Link](maRessource);
return [Link](maRessource).build();
}

Lotfi ELAACHAK Page 51


@DELETE
@Path("/{id}")
@Produces(MediaType.APPLICATION_JSON)
public Response deleteMaRessource( @PathParam("id") String id) {
// supprime une ressoure MaRessource et retourne un code HTTP 204
[Link](id);
return [Link](Status.NO_CONTENT).build();

[Link]
package [Link];

import [Link];

public class HelloWorldApplication extends ResourceConfig {


public HelloWorldApplication() {
// Define the package which contains the service classes.
packages("[Link]");
}

[Link]
<servlet>
<servlet-name>JerseyDemo</servlet-name>
<servlet-class>[Link]</servlet-class
>
<!-- Define the ResourceConfig class -->
<init-param>
<param-name>[Link]</param-name>
<param-value>[Link]</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>

<!-- Map all the URLs to the Jersey ServletContainer -->


<servlet-mapping>
<servlet-name>JerseyDemo</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>

Lotfi ELAACHAK Page 52


Client REST

[Link]
import [Link];
import [Link];
import [Link];
import [Link];
import [Link];
public class ClientRest {
public static void main(String[] args){
Client client =
[Link]().newClient();
WebTarget target =
[Link]("[Link]
target = [Link]("ma-ressource/" + 1);
[Link] builder = [Link]();
Response response = [Link]();
MaRessource maRessource =
[Link]([Link]);
} }

[Link]
<dependencies>
<dependency>
<groupId>[Link]</groupId>
<!-- if your container implements Servlet API older than 3.0, use "jersey-
container-servlet-core" -->
<artifactId>jersey-container-servlet</artifactId>
<version>2.32</version>
</dependency>
<!-- Required only when you are using JAX-RS Client -->
<dependency>
<groupId>[Link]</groupId>
<artifactId>jersey-client</artifactId>
<version>2.32</version>
</dependency>

<dependency>
<groupId>[Link]</groupId>
<artifactId>jersey-hk2</artifactId>
<version>2.32</version>
</dependency>

</dependencies>

Lotfi ELAACHAK Page 53


5.3 Srping RESTful

5.3.1 Introduction
Les services Web RESTful sont des applications client et serveur qui communiquent sur le Web.
Les services Web RESTful sont des services Web basés sur l’architecture REST. Dans l’architec-
ture REST, tout est ressource. Les services Web RESTful assurent la communication entre les
applications logicielles s’exécutant sur différentes plates-formes et frameworks. On peut considé-
rer les services web comme du code à la demande. Un service Web RESTful est une fonction
ou une méthode qui peut être appelée en envoyant une requête HTTP à une URL, et le service
renvoie le résultat comme réponse. Dans ce didacticiel, vous apprendrez les bases des services
Web RSETful avec des exemples et des projets appropriés.

La ressource a des représentations telles que XML, HTML et JSON. Capture de l’état actuel par
ressource de représentation. Lorsque nous demandons une ressource, nous fournissons la repré-
sentation de la ressource. Les méthodes importantes de HTTP sont :

— GET : Il lit une ressource.


— PUT : Il met à jour une ressource existante.
— POST : Cela crée une nouvelle ressource.
— SUPPRIMER : efface la ressource.

Par exemple, si nous voulons effectuer les actions suivantes dans l’application de médias sociaux,
nous obtenons les résultats correspondants.

— POST /users : Il crée un utilisateur.


— GET /users/id : Il récupère le détail d’un utilisateur.
— GET /users : Il récupère le détail de tous les utilisateurs.
— DELETE /users : supprime tous les utilisateurs.
— DELETE /users/id : efface un utilisateur.
— GET /users/id/posts/post_id : Il récupère le détail d’un message spécifique.
— POST / users/id/ posts : Il crée un post de l’utilisateur.

HTTP définit également le code d’état standard suivant :

— 404 : RESSOURCE NON TROUVÉE


— 200 : SUCCÈS
— 201 : CRÉÉ
— 401 : NON AUTORISÉ
— 500 : ERREUR DE SERVEUR

5.3.2 Initialisation d’un projet de services Web RESTful avec Spring


Boot
Accéder au référentiel Maven https ://[Link]/ et ajoutez les dépendances Spring
Web MVC, Spring Boot DevTools, JPA et Mysql, JDBC dans le fichier [Link]. Après avoir
ajouté les dépendances, le fichier [Link].

Le fichier java principal :

Lotfi ELAACHAK Page 54


[Link]
package [Link];
import [Link];
import [Link];
@SpringBootApplication
public class RestfulWebServicesApplication
{
public static void main(String[] args)
{
[Link]([Link], args);
}
}

La creation de hello word controller :


[Link]
package [Link];
import [Link];
import [Link];
import [Link];
//Controller
@RestController
public class HelloWorldController
{
//using get method and hello-world as URI
@RequestMapping(method=[Link], path="/hello-world")
public String helloWorld()
{
return "Hello World";
}
}

Ou bien avec une autre annotation :


[Link]
package [Link];
import [Link];
import [Link];
//Controller
@RestController
public class HelloWorldController
{
//using get method and hello-world as URI
@GetMapping(path="/hello-world")
public String helloWorld()
{
return "Hello World";
}

Lotfi ELAACHAK Page 55


}

On peut aussi améliorer le service Hello World pour retourner un Bean.


Créer une méthode helloWorldBean() dans le fichier [Link]. Mappez l’URI
sur "/hello-world-bean" et renvoyez HelloWorldBean.
[Link]
package [Link];
import [Link];
import [Link];
//Controller
@RestController
public class HelloWorldController
{
//using get method and hello-world URI
@GetMapping(path="/hello-world")
public String helloWorld()
{
return "Hello World";
}
@GetMapping(path="/hello-world-bean")
public HelloWorldBean helloWorldBean()
{
return new HelloWorldBean("Hello World"); //constructor of HelloWorldBean
}
}

[Link]
package [Link];
public class HelloWorldBean
{
public String message;
//constructor of HelloWorldBean
public HelloWorldBean(String message)
{
[Link]=message;
}
//generating getters and setters
public String getMessage()
{
return message;
}
public void setMessage(String message)
{
[Link] = message;
}
@Override

Lotfi ELAACHAK Page 56


//generate toString
public String toString()
{
return [Link] ("HelloWorldBean [message=%s]", message);
}
}

On peut aussi améliorer le service Hello World avec une variable de chemin.

[Link]
package [Link];
import [Link];
import [Link];
import [Link];
import [Link];
@Configuration
//Controller
@RestController
public class HelloWorldController
{
//using get method and hello-world URI
@GetMapping(path="/hello-world")
public String helloWorld()
{
return "Hello World";
}
@GetMapping(path="/hello-world-bean")
//method- which returns "Hello World"
public HelloWorldBean helloWorldBean()
{
return new HelloWorldBean("Hello World");//constructor of HelloWorldBean
}
//passing a path variable
@GetMapping(path="/hello-world/path-variable/{name}")
public HelloWorldBean helloWorldPathVariable(\@PathVariable String name)
{
return new HelloWorldBean([Link]("Hello World,%s", name)); //%s replace the
name
}
}

Lotfi ELAACHAK Page 57


Chapitre 6
MicroServices
6.1 Introduction
Selon Sam Newman, "les microservices sont les petits services qui fonctionnent ensemble."

Selon James Lewis et Martin Fowler, « le style architectural de microservice est une approche
pour développer une application unique en tant que suite de petits services. Chaque microservice
exécute son processus et communique avec des mécanismes légers. Ces services sont construits
autour de capacités commerciales et développés indépendamment par machines de déploiement
entièrement automatisées."

Il existe un strict minimum de gestion centralisée de ces services, qui peuvent être écrits dans
différents langages de programmation et utiliser différentes technologies de stockage de données.

— Ce sont les services qui sont exposés par REST.


— Ce sont de petites unités déployables bien choisies.
— Les services doivent être compatibles avec le cloud.

Le microservice définit une approche de l’architecture qui divise une application en un pool de
services faiblement couplés qui implémentent les exigences métier. C’est à côté de l’architecture
orientée services (SOA). La caractéristique la plus importante de l’architecture basée sur des
microservices est qu’elle peut effectuer la livraison continue d’une application volumineuse et
complexe.

Le microservice aide à casser l’application et à créer des applications plus petites logiquement
indépendantes. Par exemple, nous pouvons créer une application cloud avec l’aide d’Amazon
AWS avec un minimum d’efforts.

58
Les principes des Microservices :
— Principe de responsabilité unique
— Modélisé autour du domaine d’activité
— Isoler l’échec
— Automatisation des infrastructures
— Déployer indépendamment

6.1.1 Principe de responsabilité unique


Le principe de responsabilité unique stipule qu’une classe ou un module dans un programme ne
devrait avoir qu’une seule responsabilité. Un microservice ne peut pas servir plus d’une respon-
sabilité à la fois.

6.1.2 Modélisé autour du domaine d’activité


Le microservice ne se limite jamais à accepter la pile technologique ou la base de données appro-
priée. La pile ou la base de données est la plus appropriée pour résoudre l’objectif commercial.

6.1.3 Échec isolé


La grande application peut rester pratiquement insensible à la défaillance d’un seul module. Il
est possible qu’un service échoue à tout moment. Il est donc important de détecter rapidement
les pannes, si possible, de restaurer automatiquement les pannes.

6.1.4 Automatisation des infrastructures


L’automatisation de l’infrastructure est le processus de script des environnements. Avec l’aide
de l’environnement de script, nous pouvons appliquer la même configuration à un seul nœud
ou à des milliers de nœuds. Il est également connu sous le nom de gestion de configuration,
d’infrastructures scriptées et de gestion de configuration système.

6.1.5 Déployer indépendamment


Les microservices sont indépendants de la plate-forme. Cela signifie que nous pouvons les conce-
voir et les déployer indépendamment sans affecter les autres services.

Lotfi ELAACHAK Page 59


6.2 Les défis de l’architecture des microservices

L’architecture des microservices est plus complexe que l’ancien système. L’environnement de
microservice devient plus compliqué car l’équipe doit gérer et prendre en charge de nombreuses
pièces mobiles.

Lotfi ELAACHAK Page 60


Voici quelques-uns des principaux défis auxquels une organisation est confrontée dans son par-
cours de microservices :
— Contexte délimité
— Augmentation et diminution dynamiques
— Surveillance
— Tolérance aux pannes
— Dépendances cycliques
— Culture DevOps

6.2.1 Contexte délimité


Le concept de contexte délimité est issu des cercles de conception axée sur le domaine (DDD). Il
promeut la première approche du service du modèle objet, en définissant un modèle de données
dont le service est responsable et auquel il est lié. Un contexte limité clarifie, encapsule et définit
la responsabilité spécifique envers le modèle. Il garantit que le domaine ne sera pas distrait de
l’extérieur. Chaque modèle doit avoir un contexte défini implicitement dans un sous-domaine, et
chaque contexte définit des limites.

En d’autres termes, le service est propriétaire de ses données et est responsable de leur intégrité
et de leur mutabilité. Il prend en charge la caractéristique la plus importante des microservices,
à savoir l’indépendance et le découplage.

6.2.2 Augmentation et diminution dynamiques


Les charges sur les différents microservices peuvent être à une instance différente du type. En
plus de la mise à l’échelle automatique, votre microservice devrait également être mis à l’échelle
automatiquement. Cela réduit le coût des microservices. Nous pouvons répartir la charge dyna-
miquement.

6.2.3 Surveillance
La méthode traditionnelle de surveillance ne s’alignera pas bien avec les microservices, car nous
avons plusieurs services constituant la même fonctionnalité précédemment pris en charge par une

Lotfi ELAACHAK Page 61


seule application. Lorsqu’une erreur survient dans l’application, il peut être difficile de trouver
la cause première.

6.2.4 Tolérance aux pannes


La tolérance aux pannes est le service individuel qui ne met pas en panne l’ensemble du système.
L’application peut fonctionner avec un certain degré de satisfaction lorsque la panne se produit.
Sans tolérance aux pannes, une seule défaillance du système peut provoquer une panne totale. Le
disjoncteur peut atteindre la tolérance aux pannes. Le disjoncteur est un modèle qui encapsule
la demande au service externe et détecte quand ils sont défectueux. Les microservices doivent
tolérer les défaillances internes et externes.

6.2.5 Dépendance cyclique


La gestion des dépendances entre différents services et ses fonctionnalités sont très importantes.
La dépendance cyclique peut créer un problème, si elle n’est pas identifiée et résolue rapidement.

6.2.6 Culture DevOps


Les microservices s’intègrent parfaitement dans le DevOps. Il offre un service de livraison plus
rapide, une visibilité sur les données et des données rentables. Il peut étendre leur utilisation
du commutateur de conteneurisation de l’architecture orientée services (SOA) à l’architecture de
microservices (MSA).

6.3 Surveillance des microservices


La surveillance est le système de contrôle des microservices. Comme les microservices sont plus
complexes et plus difficiles à comprendre ses performances et à résoudre les problèmes. Compte
tenu des changements importants apportés à la livraison de logiciels, il est nécessaire de surveiller
le service. Il existe cinq principes de surveillance des microservices, comme suit :

— Surveillez le conteneur et ce qu’il contient.


— Alerte sur les performances du service.

Lotfi ELAACHAK Page 62


— Surveillez les services qui sont élastiques et multi-sites.
— Surveiller les API.
— Surveiller la structure organisationnelle.

Ces principes nous permettent d’aborder les évolutions technologiques associées aux microservices
et les changements organisationnels qui leur sont liés.

6.3.1 Outil de surveillance des microservices


Il existe trois outils de surveillance qui sont les suivants :
— Tableau de bord Hystrix
— Tableau de bord d’administration d’Eureka
— Tableau de bord de l’administrateur Spring Boot

6.4 Virtualisation des microservices


La virtualisation des microservices est la méthode permettant de simuler le comportement de
composants spécifiques dans diverses applications basées sur des composants telles que les ap-
plications basées sur le cloud, la SOA et l’architecture pilotée par API. La virtualisation des
services réduit également les coûts et fait gagner du temps. En combinant la virtualisation des
services, une organisation peut développer l’application qui peut être fournie à partir de divers
emplacements et d’environnements différents.

6.5 Composants des microservices


Il existe les composants suivants des microservices :

— Serveur de configuration Spring Cloud


— Serveur de nommage Netflix Eureka Serveur Hystrix
— Serveur de passerelle Netflix ZuulAPI
— Ruban Netflix
— Serveur de traçage distribué Zipkin
— Serveur de configuration Spring Cloud

Spring Cloud Config Server fournit l’API basée sur les ressources HTTP pour la configuration
externe dans le système distribué. Nous pouvons activer Spring Cloud Config Server en utilisant
l’annotation @EnableConfigServer.

6.5.1 Serveur de nommage Netflix Eureka


Netflix Eureka Server est un serveur de découverte. Il fournit l’interface REST vers l’extérieur
pour communiquer avec lui. Un microservice après son apparition, s’enregistre en tant que client
de découverte. Le serveur Eureka dispose également d’un autre module logiciel appelé Eureka
Client. Le client Eureka interagit avec le serveur Eureka pour la découverte de services. Le client
Eureka équilibre également les demandes des clients.

Lotfi ELAACHAK Page 63


6.5.2 Serveur Hystrix
Le serveur Hystrix agit comme un système robuste à tolérance de panne. Il est utilisé pour
éviter l’échec complet d’une application. Pour ce faire, il utilise le mécanisme du disjoncteur.
Si l’application s’exécute sans problème, le circuit reste fermé. S’il y a une erreur rencontrée
dans l’application, le serveur Hystrix ouvre le circuit. Le serveur Hystrix arrête la demande
supplémentaire au service appelant. Il fournit un système très robuste.

6.5.3 Serveur de passerelle API Netflix Zuul


Netflix Zuul Server est un serveur de passerelle à partir duquel toutes les demandes des clients sont
passées. Il agit comme une interface unifiée avec un client. Il dispose également d’un équilibreur
de charge intégré pour charger le solde de toutes les demandes entrantes du client.

6.5.4 Ruban Netflix


Netflix Ribbon est la bibliothèque de communication inter-processus (IPC) côté client. Il fournit
l’algorithme d’équilibrage côté client. Il utilise un équilibrage de charge Round Robin :

— L’équilibrage de charge
— Tolérance aux pannes
— Plusieurs protocoles (HTTP, TCP, UDP)
— Mise en cache et traitement par lots

6.5.5 Serveur distribué Zipkin


Zipkin est un projet open source m project. Cela fournit un mécanisme d’envoi, de réception et
de visualisation des traces.

6.6 Patrons de conception de microservices


Il existe plusieurs Patrons de cocenption pour la mise en place des microservices :
— Aggregator
— API Gateway
— Chained or Chain of Responsibility
— Asynchronous Messaging
— Database or Shared Data
— Event Sourcing
— Branch
— Command Query Responsibility Segregator
— Circuit Breaker
— Decomposition

6.6.1 Aggregator
Agrégateur dans le monde informatique fait référence à un site Web ou à un programme qui
collecte des éléments de données connexes et les affiche. Ainsi, même dans les modèles de mi-
croservices, Aggregator est une page Web de base qui appelle divers services pour obtenir les

Lotfi ELAACHAK Page 64


informations requises ou obtenir les fonctionnalités requises.

Ainsi, par exemple, si vous envisagez deux services : les services A et B, on pwut mettre à
l’échelle individuellement ces services simultanément en fournissant les données au microservice
composite.

6.6.2 API Gateway


Les microservices sont construits de manière à ce que chaque service ait sa propre fonctionnalité.
Mais, lorsqu’une application est décomposée en petits services autonomes, il peut y avoir peu de
problèmes auxquels un développeur peut être confronté. Les problèmes peuvent être les suivants :

— Comment puis-je demander des informations à plusieurs microservices ? Une interface


utilisateur différente nécessite des données différentes pour répondre au même service de
base de données
— backend
— Comment transformer les données en fonction des besoins des consommateurs à partir de
Microservices réutilisables
— Comment gérer plusieurs requêtes de protocole ?

Eh bien, la solution à ce genre de problèmes pourrait être l’API Gateway Design Pattern. L’API
Gateway Design Pattern répond non seulement aux problèmes mentionnés ci-dessus, mais il résout
de nombreux autres problèmes. Ce modèle de conception de microservice peut également être
considéré comme le service proxy pour router une requête vers le microservice concerné. Étant
une variante du service Agrégateur, il peut envoyer la demande à plusieurs services et agréger
de la même manière les résultats au composite ou au service consommateur. API Gateway agit
également comme point d’entrée pour tous les microservices et crée des API à grain fin pour
différents types de clients.

Lotfi ELAACHAK Page 65


6.6.3 Chained or Chain of Responsibility
Les modèles de conception chaînés ou de chaîne de responsabilité produisent une sortie unique qui
est une combinaison de plusieurs sorties chaînées. Ainsi, si vous avez trois services alignés dans
une chaîne, la demande du client est d’abord reçue par le service A. Ensuite, ce service commu-
nique avec le prochain service B et collecte des données. Enfin, le deuxième service communique
avec le troisième service pour générer la sortie consolidée. Tous ces services utilisent une requête
ou une réponse HTTP synchrone pour la messagerie. De plus, jusqu’à ce que la demande passe
par tous les services et que les réponses respectives soient générées, le client n’obtient aucune
sortie. Ainsi, il est toujours recommandé de ne pas faire une longue chaîne, car le client attendra
que la chaîne soit terminée.

Un autre aspect important que vous devez comprendre est que la demande du service A au service
B peut être différente du service B au service C. De même, la réponse du service C au service B
peut être complètement différente du service B au service A.

6.6.4 Asynchronous Messaging


D’après le modèle ci-dessus, il est assez évident que le client est bloqué ou doit attendre longtemps
dans la messagerie synchrone. Mais, si vous ne voulez pas que le consommateur attende longtemps,
alors vous pouvez opter pour la messagerie asynchrone. Dans ce type de modèle de conception de
microservices, tous les services peuvent communiquer entre eux, mais ils n’ont pas à communiquer
entre eux de manière séquentielle. Donc, si vous considérez 3 services : Service A, Service B et
Service C. La demande du client peut être directement envoyée au Service C et au Service B
simultanément. Ces demandes seront dans une file d’attente. En dehors de cela, la demande peut
également être envoyée au service A dont la réponse n’a pas besoin d’être envoyée au même
service par lequel la demande est arrivée.

Lotfi ELAACHAK Page 66


6.6.5 Database or Shared Data
Pour chaque application, il y a une énorme quantité de données présentes. Ainsi, lorsque nous
décomposons une application de son architecture monolithique aux microservices, il est très
important de noter que chaque microservice dispose d’une quantité de données suffisante pour
traiter une requête. Ainsi, soit le système peut avoir une base de données pour chaque service,
soit il peut avoir une base de données partagée par service. Vous pouvez utiliser une base de
données par service et une base de données partagée par service pour résoudre divers problèmes.
Les problèmes peuvent être les suivants :
— Duplication de données et incohérence
— Différents services ont différents types d’exigences de stockage
— Peu de transactions commerciales peuvent interroger les données, avec plusieurs services
— Dénormalisation des données

6.6.6 Event Sourcing


Le modèle de conception d’approvisionnement d’événements crée des événements concernant les
changements dans l’état de l’application. De plus, ces événements sont stockés sous la forme d’une
séquence d’événements pour aider les développeurs à savoir quelle modification a été apportée à
quel moment. Ainsi, avec l’aide de cela, vous pouvez toujours ajuster l’état de l’application pour
faire face aux changements passés. Vous pouvez également interroger ces événements, pour tout
changement de données et publier simultanément ces événements à partir du magasin d’événe-
ments. Une fois les événements publiés, vous pouvez voir les changements d’état de l’application
sur la couche de présentation.

6.6.7 Branch
Le modèle de conception de microservice de branche est un modèle de conception dans lequel
vous pouvez traiter simultanément les demandes et les réponses de deux ou plusieurs microser-
vices indépendants. Ainsi, contrairement au modèle de conception chaîné, la demande n’est pas
transmise dans une séquence, mais la demande est transmise à deux ou plusieurs chaînes de
microservices mutuellement exclusives. Ce modèle de conception étend le modèle de conception
Agrégateur et offre la possibilité de produire des réponses à partir de plusieurs chaînes ou d’une
seule chaîne. Par exemple, si vous envisagez une application de commerce électronique, vous de-
vrez peut-être récupérer des données à partir de plusieurs sources et ces données pourraient être
une sortie collaborative de données de divers services. Ainsi, vous pouvez utiliser le modèle de
branche pour récupérer des données à partir de plusieurs sources.

Lotfi ELAACHAK Page 67


6.6.8 Command Query Responsibility Segregator
Chaque conception de microservices a soit la base de données par modèle de service, soit la base
de données partagée par service. Mais, dans le modèle de base de données par service, nous ne
pouvons pas implémenter de requête car l’accès aux données n’est limité qu’à une seule base
de données. Ainsi, dans un tel scénario, vous pouvez utiliser le modèle CQRS. Selon ce modèle,
l’application sera divisée en deux parties : Commande et Requête. La partie commande gérera
toutes les requêtes liées à CREATE, UPDATE, DELETE tandis que la partie requête s’occupera
des vues matérialisées. Les vues matérialisées sont mises à jour via une séquence d’événements
qui sont créés à l’aide du modèle de source d’événement décrit ci-dessus.

6.6.9 Circuit Breaker


Comme son nom l’indique, le modèle de conception Circuit Breaker est utilisé pour arrêter le
processus de demande et de réponse si un service ne fonctionne pas. Ainsi, par exemple, disons
qu’un client envoie une demande pour récupérer des données à partir de plusieurs services. Mais,
en raison de certains problèmes, l’un des services est en panne. Maintenant, il y a principalement
deux problèmes auxquels vous serez confrontés : d’abord, puisque le client n’aura aucune connais-
sance de la panne d’un service particulier, la demande sera continuellement envoyée à ce service.
Le deuxième problème est que les ressources réseau seront épuisées avec de faibles performances
et une mauvaise expérience utilisateur.

Ainsi, pour éviter de tels problèmes, vous pouvez utiliser le modèle de conception de disjoncteur.
À l’aide de ce modèle, le client invoquera un service distant via un proxy. Ce proxy se comportera
essentiellement comme une barrière de circuit. Ainsi, lorsque le nombre de défaillances dépasse
le nombre seuil, le disjoncteur se déclenche pendant une période de temps particulière. Ensuite,
toutes les tentatives d’appel du service distant échoueront pendant cette période d’expiration.
Une fois cette période écoulée, le disjoncteur laissera passer un nombre limité de tests et si ces
demandes aboutissent, le disjoncteur reprend son fonctionnement normal. Sinon, s’il y a un échec,
le délai d’attente recommence.

Lotfi ELAACHAK Page 68


6.6.10 Decomposition
Les microservices sont développés avec une idée dans l’esprit des développeurs pour créer de
petits services, chacun ayant sa propre fonctionnalité. Mais, diviser une application en petites
unités autonomes doit se faire de manière logique. Ainsi, pour décomposer une petite ou une
grande application en petits services, vous pouvez utiliser les modèles de décomposition.

À l’aide de ce modèle, vous pouvez décomposer une application en fonction des capacités com-
merciales ou en fonction des sous-domaines.

6.7 Mise en place d’un Microservice


Dans cet exemple de microservices de démarrage de printemps, nous allons créer une application
Top Sports Brands qui disposera de 3 services :

— Service Eureka - Ce service enregistrera chaque microservice, puis le microservice client


recherchera le serveur Eureka pour obtenir un microservice dépendant pour faire le travail.
Ce serveur Eureka appartient à Netflix et, en cela, Spring Cloud offre un moyen déclaratif
de s’inscrire. et invoquer des services par annotation Java.
— Service de catalogue d’articles - Ce service générera la liste des marques de sport populaires
sur le marché.
— Service Edge - Il est similaire au service Item autonome créé dans Bootiful Development
avec Spring Boot et Angular. Cependant, il aura des capacités de secours qui empêchent
le client de recevoir une erreur HTTP lorsque le service n’est pas disponible.

Lotfi ELAACHAK Page 69


6.7.1 Créer un service Eurêka
Pour commencer, créez un projet EurekaServer Spring Starter dans Eclipse IDE. Cliquez sur
Spring Starter Project et cliquez sur Suivant.

Lotfi ELAACHAK Page 70


Maintenant, modifiez le fichier EurekaServer/src/main/resources/[Link] pour ajou-
ter un numéro de port et désactiver l’enregistrement.

[Link]
[Link]=8761
[Link]-with-eureka=false

Ouvrir EurekaServer/src/main/java/com/example/[Link] et ajouter @En-


ableEurekaServer au-dessus de @SpringBootApplication.

importer [Link] ;

@EnableEurekaServer
@SpringBootApplication

Après son démarrage, vous devriez pouvoir ouvrir http ://localhost :8761 et voir qu’aucun service
n’est disponible. Ouvrez maintenant http ://localhost :8761. Ici, Spring Eureka Server s’ouvrira
et affichera qu’aucun service ne sera en cours d’exécution.

Lotfi ELAACHAK Page 71


6.7.2 Création d’un service de catalogue d’articles
Créer à nouveau un nouveau projet. Utilisez Item-catalog-service pour le nom de l’artefact et
cliquez sur Suivant.

Ajouter les dépendances suivantes :

— Actuator : des fonctionnalités pour vous aider à surveiller et gérer votre application
— Eureka Discovery : pour l’inscription au service
— JPA : pour sauvegarder/récupérer des données
— Mysql : une base de données en mémoire
— Rest Repositories : pour exposer les référentiels JPA en tant que points de terminaison
REST
— Web : Spring MVC et Tomcat embarqué
— DevTools : pour recharger automatiquement l’application lorsque les fichiers changent
— Lombok : pour réduire le code passe-partout

Lotfi ELAACHAK Page 72


Ajouter un nom d’application dans le fichier item-catalog-service/src/main/resources/[Link]
à afficher dans le service Eureka et définissez le port sur 8088.

[Link]
[Link]=8088\newline
[Link]=item-catalog-service\newline

Maintenant, créer le fichier Cloud Properties


Cliquer sur Fichier -> Nouveau -> Autre -> Fichier et ajouter le code ci-dessous dans ce fichier
et enregistrez-le.
[Link]
[Link]=${[Link][0]:localhost}
[Link]=80
[Link]=${[Link].instance_id:${spring.
[Link]}:${[Link].instance_id:${[Link]}}}
[Link] = 5
[Link] = par défaut
[Link] = 5
[Link]=${[Link]
.uri}/eureka/

Maintenant, pour démarrer l’application : Ouvrir maintenant http ://localhost :8761. Ici, vous
verrez que le service de catalogue d’articles sera en cours d’exécution.

Ouvrir http ://localhost :8088/items

6.7.3 Création d’un service Edge


Il est similaire au service Item autonome créé dans Bootiful Development avec Spring Boot et
Angular. Cependant, il aura des capacités de secours qui empêcheront le client de recevoir une
erreur HTTP lorsque le service n’est pas disponible.
— Eureka Discovery : pour l’inscription au service

Lotfi ELAACHAK Page 73


— Feign : un client de service web déclaratif
— Zuul : fournit un routage intelligent
— Rest Repositories : pour exposer les référentiels JPA en tant que points de terminaison
REST
— Web : Spring MVC et Tomcat embarqué
— Hystrix : un disjoncteur pour arrêter les pannes en cascade et permettre la résilience
— Lombok : pour réduire le code passe-partout

Étant donné que le service item-catalog-service s’exécute sur le port 8088, vous devrez configurer
cette application pour qu’elle s’exécute sur un port différent. Modifiez edge-service/src/main/resources/appl
pour définir le port sur 8089 et définissez un nom d’application.
[Link]
[Link]=8089
[Link]=edge-service

[Link]
[Link]=${[Link][0]:localhost}
[Link]=80
[Link]=${[Link].instance_id:${spring.
[Link]}:${[Link].instance_id:${[Link]}}}
[Link] = 5
[Link] = default
[Link] = 5
[Link]=${[Link]
.uri}/eureka/

Pour activer Feign, Hystrix et l’enregistrement auprès du serveur Eureka, ajoutez les annotations
appropriées à [Link] :
[Link]
import [Link];
import [Link];

Lotfi ELAACHAK Page 74


import [Link];
import [Link];
import [Link];
import [Link];
import [Link];
import [Link];
import [Link];
import [Link];
import [Link].*;

import [Link];
import [Link];
import [Link];

@EnableFeignClients
@EnableCircuitBreaker
@EnableDiscoveryClient
@EnableZuulProxy
@SpringBootApplication
public class EdgeServiceApplication {

public static void main(String[] args) {


[Link]([Link], args);
}
}

Créer un Item DTO (Data Transfer Object) dans ce même fichier. @Data de Lombok générera
des méthodes toString(), des getters, des setters et des constructeurs appropriés.

Créer une interface ItemClient qui utilise Feign pour communiquer avec le service Item-catalog-
service.
[Link]
public class EdgeServiceApplication {

public static void main(String[] args) {


[Link]([Link], args);
}
}

@Data
class Item {
private String name;
}

public String getName() {


return name;

Lotfi ELAACHAK Page 75


}

public void setName(String name) {


[Link] = name;
}
@FeignClient("item-catalog-service")
interface ItemClient {

@GetMapping("/items")
Resources<Item> readItems();
}

Créer un RestController sous l’ItemClient qui filtrera les marques inférieures aux meilleures et
affichera un /top-brandsendpoint.
[Link]
@RestController
class GoodItemApiAdapterRestController {

private final ItemClient itemClient;

public GoodItemApiAdapterRestController(ItemClient ItemClient) {


[Link] = itemClient;
}
public Collection<Item> fallback() {
return new ArrayList<>();
}

@HystrixCommand(fallbackMethod = "fallback")
@GetMapping("/top-brands")
public Collection<Item> goodItems() {
return [Link]()
.getContent()
.stream()
.filter(this::isGreat)
.collect([Link]());
}

private boolean isGreat(Item item) {


return ![Link]().equals("Nike") &&
![Link]().equals("Adidas") &&
![Link]().equals("Reebok");
}
}

Démarrez l’application de service de périphérie avec Maven ou votre IDE et vérifiez qu’elle
s’enregistre avec succès auprès du serveur Eureka.

Lotfi ELAACHAK Page 76


Appeler maintenant localhost :8089/top-brands, voir la liste des meilleures marques du service
de catalogue.

Si on ferme l’application item-catalog-service, vous obtiendrez une erreur de serveur interne 500.
Pour résoudre ce problème, on peut utiliser Hystrix pour créer une méthode de secours et indiquer
à la méthode goodItems() de l’utiliser.
@HystrixCommand(fallbackMethod = "fallback")

Lotfi ELAACHAK Page 77


Bibliographie
https ://[Link]/blog/what-is-microservices/ https ://[Link]/creating-
a-simple-microservice

78

Vous aimerez peut-être aussi