Java EE
SERVLET ET VUE
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 58
Contenu
• Architecture
• Présentation du webcontainer
• Servlet
• Servlet par l’exemple
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 59
Qu’est ce qu’une Servlet ?
• Les servlets Java :
◦ Une technologie pour générer des pages web dynamiques (comme PHP, ASP,
[Link], ...)
◦ Tournent dans des serveurs dédiés dits « serveurs de servlets »,
◦ Possèdent un contexte qui permet de communiquer avec la configuration du
serveur
• La classe HttpServlet
◦ Permet la génération de contenu web dynamique (HTML, XML, JSON, etc …)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 60
Qu’est ce qu’une Servlet ? (2)
• Servlets
◦ Fournissent donc un framework général pour des services basés sur le
paradigme requête-réponse
◦ Portables sur n’importe quel serveur HTTP Java (léger comme Tomcat, Resin,
ou plus complet comme Jboss, Glassfish, Websphere)
◦ Ont accès à la famille des APIs de Java EE
◦ JDBC, JPA, EJB, JMS, JAX-WS, JTA, JTS, RMI, JNDI,
JAXP, ...
◦ Sont des containers pour l’injection de code (CDI)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 61
Servlet Services
• Java Servlets fournissent de nombreux “services”
◦ API de bas niveau pour construire des services internet
(requête, réponse, session, cookies, etc.)
◦ Element fondamental derrière les Java Server Pages (JSP)
et Java Server Faces (JSF)
◦ Peuvent délivrer plusieurs types de réponses
◦ XML, HTML, WML, GIF, etc...
◦ Servent de “Controleur web” dans les architectures
MVC JSP/Servlets (obsolète)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 62
Pourquoi utiliser des Servlets ?
• Java
◦ portable et répandu… c’est au coeur de la partie HTTP de Java EE
• Puissance
◦ Utilisation de toutes les APIs Java,
◦ Puissant mécanisme d’annotations,
◦ Intégration dans plusieurs profils “Java EE” : profil léger Web, gros profil
“Entreprise” pour faire des applications en clusters, etc
• Efficace
◦ Highly scalable, code ré-entrant, compilé
◦ Jusqu’à 100x plus rapide que PHP, même que C++
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 63
Pourquoi utiliser des Servlets (2)
• Sécurité
◦ Typage fort,
◦ Gestion de la mémoire efficace
• Integration forte avec le serveur
◦ Via des variables “contexte” échanges forts entre le serveur et les servlets :
configuration, partage de ressources (connexions BD) etc.
• Extensibilité & Flexibilité
◦ Théoriquemen,t le modèle Servlet n’est pas que pour HTTP,
◦ Puissants mécanismes de “filtres” et de “chainage” de traitements. Plus de
détails plus tard.
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 64
Date Servlet – Exemple
import [Link].*;
import [Link].*;
import [Link].*;
public class DateServlet extends HttpServlet {
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
// A éviter, normalement pas de HTML dans une servlet
PrintWriter out = Res [Link]();
[Link]("<HTML>");
[Link]("The time is: " +
new [Link]());
[Link]("</HTML>");
}
}
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 65
Java Servlets
ARCHITECTURE TECHNIQUE
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 66
Architecture d’une Servlet
• La classe HttpServlet
◦ Rôle = traiter la requête HTTP
• Pour chaque méthode HTTP :GET, POST, PUT, DELETE, etc. il y a une
méthode correspondante :
◦ doGet(…) – répond aux requêtes HTTP GET
◦ doPost(…) – répond aux requêtes HTTP GET
◦ doPut(…), doHead(…), doDelete(…), doTrace(…), doOptions(…)
• Conseil : implémenter au moins les deux premières méthodes ou
redéfinir la méthode service(…)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 67
Servlet HTTP et servlet générique
GenericServlet
Client
Server
request
response
service ( )
HTTPServlet
Browser
HTTP Server
request
doGet ( )
response
service ( )
doPost( )
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 68
Architecture d’une Servlet (2)
• Ces méthodes ont deux paramètres : la requête et la réponse
• L’objet HttpServletRequest
◦ Contient la requête du client
◦ En-tête de la requête HTTP
◦ Paramètres HTTP (données de formulaire ou paramètres passés avec l’URL)
◦ Autres données (cookies, URL, chemin relatif, etc.)
• L’objet HttpServletResponse
◦ Encapsule les données renvoyées au client
◦ En-tête de réponse HTTP (content type, cookies, etc.)
◦ Corps de la réponse (en tant que OutputStream)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 69
Architecture d’une Servlet (3)
• La méthode HTTP GET est utilisée quand :
◦ Le traitement de la requête ne modifie pas l’état du serveur,
◦ Si jamais il s’agit de l’envoi d’un formulaire, taille des données < 255
caractères,
◦ On veut pouvoir bookmarker l’URL
• La méthode HTTP POST est utilisée quand :
◦ Le traitement change l’état du serveur : exemple classique = un insert dans
une base de données.
◦ La quantité de données à envoyer est importante,
◦ On veut cacher dans l’URL les paramètres (ex : mot de passe)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 70
Servlets API
• Fonctions principales d’une Servlet :
◦ Traiter les paramètres HTTP reçus dans la requête (GET ou POST)
[Link](String)
◦ Récupérer un paramètre de configuration de l’application web (dans le
descripteur [Link])
[Link]()
◦ Récupérer un élément de l’en-tête HTTP
[Link](String)
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 71
Servlets API (2)
◦ Spécifier dans le header de réponse le type
[Link](<name>, <value>) /
[Link](String)
◦ Récupérer un Writer pour écrire la réponse
[Link]()
◦ …ou un flux binaire si la réponse est binaire
[Link]()
◦ Rediriger la requête vers un autre URL
[Link]()
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 72
Cycle de vie d’une Servlet
Le serveur gère ce New Destroyed
cycle,
Running
Les méthodes init() destroy()
“callback” du cycle de
vie ne doivent jamais service()
...()
être appelées par le doGet()
code qu’on écrit doDelete()
doPost() doPut()
• On implémente souvent la méthode init (invoquée lors de la
première exécution de la servlet) pour récupérer des ressources
ou paramètres d’initialisation.
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 73
La méthode init()
• Appelée à la première instanciation,
• La spécification garantit qu’aucune requête ne sera envoyée avant que
init() soit exécutée entièrement.
• On redéfinit init() quand :
◦ On doit ouvrir des ressources (connexions JDBC par ex)
◦ On doit initialiser l’état d’une Servlet,
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 74
La méthode service()
• Implémentée dans HTTPServlet dont on hérite,
• Détecte la méthode HTTP et appelle doGet(…), doPost(…), Sends the
result as HTTP response
• On ne la redéfinit pas dans les cas classiques
◦ Elle est redéfinie par les librairies d’implémentation des web services, par JSF
etc…
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 75
La méthode destroy()
• Appelée avant que la Servlet soit garbage collectée,
• La spécification garantit que toutes les requêtes seront traitées avant
l’appel à destroy()
• On la redéfinit lorsque :
◦ On doit libérer des ressources,
◦ On doit rendre persistent l’état de la servlet (en général fait par des librairies
spécialisées comme les Web Services).
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 76
Java Servlets
EXEMPLE
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 77
Exemple de traitement de
paramètre : Hello Servlet
• Servlet qui récupère le paramètre “nom” et qui répond : "Hello,
<nom>"
• Formulaire HTML :
<form method="GET ou POST" action="URL relatif de
la Servlet">
<input type="text" name="nom">
</form>
• Récupération du paramètre par la méthode doGet() ou doPost() :
String nom= [Link]("nom");
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 78
Hello Servlet : exemple complet
[Link]
<html><body>
<form method="GET" action="HelloServlet">
Entrez votre nom :
<input type="text" name="nom">
<input type="submit" value="OK">
</form>
</body></html>
[Link]
import [Link].*;
import [Link].*;
import [Link].*;
public class HelloServlet extends HttpServlet {
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 79
Hello Servlet – Example
[Link]
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
[Link]("text/html");
ServletOutputStream out = [Link]();
String nom= [Link]("nom");
[Link]("<html><head>");
[Link]("\t<title>Hello Servlet</title>");
[Link]("</head><body>");
[Link]("\t<h1>Hello, " + nom + "</h1>");
[Link]("</body></html>");
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 80
Hello Servlet – requête HTTP
• What happens when the user enters his name?
◦ Internet Explorer (IE) sends the following HTTP request to Tomcat
GET /FirstWebApp/HelloServlet?user_name=Nakov HTTP/1.1
Accept: image/gif, image/x-xbitmap, image/jpeg,image/pjpeg,
application/[Link]-excel, application/[Link]-powerpoint,
application/msword, application/x-shockwave-flash, */*
Accept-Language: bg
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT
5.1; Q312461)
Host: nakov:8084
Connection: Keep-Alive
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 81
Servlet qui construit et sert une
image
• On veut faire une Servlet qui construit une image avec un texte dedans
: un compteur de vues.
• La Servlet maintient un compteur
◦ On l’initialise dans la méthode init() et on l’incrémente dans la méthode
doGet()
• La Servlet produit une image binaire
◦ Le Content-type doit être "image/jpeg"
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 82
Image Counter Servlet (1)
import [Link].*;
import [Link].*;
...
public class ImageCounterServlet extends HttpServlet {
private String mStartDate;
private int mVisitCounter;
public void init() {
mStartDate = (new Date()).toString();
mVisitCounter = 0;
}
public BufferedImage createImage(String msg) {
... // ici on crée une image, on dessine un texte
// dedans et on renvoie l’image sous forme de
// BufferedImage (buffer binaire)
}
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 83
Image Counter Servlet (2)
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws IOException, ServletException {
String msg;
// Rappel les servlets sont ré-entrantes !
synchronized(this) {
mVisitCounter++;
msg = "" + mVisitCounter + " visits since" +
mStartDate;
}
BufferedImage image = createImage(msg);
[Link]("image/jpeg");
OutputStream out = [Link]();
// Encode l’image en jpeg et l’écrit sur le flux
// binaire de la réponse
[Link](image, "jpg", out);
}
}
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 84
Extrait du code de création de
l’image
// Create an image of our counter to be sent to the browser.
BufferedImage buffer = newBufferedImage(50, 20, BufferedImage.TYPE_INT_RGB);
Graphics2D g = [Link]();
[Link](RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
[Link](new Font("Monospaced", [Link], 14));
[Link]([Link]);
[Link](0, 0, 50, 20);
[Link]([Link]);
[Link](msg, 0, 20);
return buffer;
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 85
Résultat
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 86
Renvoyer un zip depuis une
Servlet
• Exemple de [Link]
• protected void doGet(HttpServletRequest request, HttpServletResponse
response) throws ServletException, IOException {
try {
String path = getServletContext().getRealPath("data");
File directory = new File(path);
String[] files = [Link]();
if (files != null && [Link] > 0) {
byte[] zip = zipFiles(directory, files);
ServletOutputStream sos = [Link]();
[Link]("application/zip");
[Link]("Content-Disposition", "attachment;
filename=\"[Link]\"");
[Link](zip); [Link]();
}
} catch (Exception e) {
[Link]();
}
}
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 87
Récupérer l’URL relatif de la
servlet
• Permet d’obtenir des informations depuis le header de la requête. Ex :
chemin relatif utilisé pour appeler la servlet :
• public class ContextPathDemo extends HttpServlet {
protected void doGet(HttpServletRequest req,
HttpServletResponse res) throws ServletException,
IOException {
// [Link]() returns the
// portion of the request URI that indicates the
//context of the request.
String contextPath = [Link]();
}
}
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 88
URI relatif à quoi cela sert-il ?
• Dans le cas où une même servlet est mappé sur plusieurs URLs,
• Exemple, une Servlet qui streame des fichiers mp3 dans /mp3/* a
besoin de récupérer le nom des fichiers… /mp3/toto.mp3,
/mp3/titi.mp3, on a besoin de récupérer toto.mp3 pour l’ouvrir…
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 89
Architecture
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 90
Fonctionnement
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 91
Classe Servlet
• Interface de base de toutes les servlets
• Classes implémentant Servlet :
◦ GenericServlet
◦ HttpServlet
◦ Abstraite
◦ 3 méthodes :
◦ doGet()
◦ doPost()
◦ doHead()
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 92
Suite du tutoriel : création d’une
servlet
• Nouvelle classe
◦ Hérite de HttpServlet
◦ Dans un package Servlet
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 93
[Link]
<?xml version="1.0" encoding="UTF-8"?>
<web-app
xmlns:xsi="[Link]
xmlns="[Link]
xsi:schemaLocation="[Link]
[Link]
id="WebApp_ID"
version="3.1">
</web-app>
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 94
Identification de la servlet
<servlet>
<servlet-name>Test</servlet-name>
<servlet-class>[Link]</servlet-class>
</servlet>
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 95
Association de la servlet à un url
<servlet-mapping>
<servlet-name>Test</servlet-name>
<url-pattern>/UrlTest</url-pattern>
</servlet-mapping>
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 96
[Link]
• Erreur 405
• Implémenter la méthode
◦ public void doGet( HttpServletRequest request, HttpServletResponse
response )
2021/2022 JAKARTA ENTREPRISE EDITION - SELMA BATTI ATTIA 97