Activité Premier serveur HTTP - partie 1

Situation

Vous êtes employé par une entreprise de développement spécialisée dans le logiciel en Java sans expérience dans le développement web. La direction a néanmoins accepté un mandat pour la réalisation d’une application web et le travail est en cours. Vous venez d’être intégré à l’équipe de développement et vous devez maintenant vous familiariser avec le framework Javalin. On vous propose de réaliser un livre d’or, c.-à-d. une page où les visiteurs peuvent laisser un message.

Consigne

Lisez les instructions ci-après et réalisez les tâches demandées.

Objectifs

À la fin de ce travail, vous devez :

  1. Être capable d’expliquer le fonctionnement d’un serveur HTTP réalisé avec Javalin.
  2. Être capable d’ajouter un gestionnaire de ressource, de l’associer à un chemin.
  3. Être capable d’expliquer ce qu’est un langage de template.
  4. Être capable de réaliser d’ajouter un template et de l’utiliser dans un gestionnaire de ressource.
  5. Connaître la directive <#list> de FreeMarker.
  6. Être capable d’utiliser un formulaire HTML pour envoyer une requête avec des données.
  7. Être capable de choisir entre la méthode GET et la méthode POST.
  8. Être capable de mettre en œuvre le pattern “Post-Redirect-Get”.

Résultat attendu

  • Un bref rapport qui décrit votre travail et votre démarche.
  • Le code source de votre application.

Ressources

Documents :

Logiciel :

  • VSCode
  • Chrome et Firefox
  • mariadb (mysql)

Mise en route

Récupérer le projet

Lancez Visual Studio Code, ouvrez une fenêtre de terminal intégré, rendez-vous dans le répertoire project et lancez la commande ci-après pour récupérer le projet.

1
git clone https://gitlab.epai-ict.ch/m133/activities/firstserver.git

Si git n’est pas installé, installez-le en suivant les instructions du guide d’installation que vous trouvez ici.

Lancez la commande code -r firstserver pour ouvrir le projet dans la fenêtre courante. Pressez ensuite shift-ctl-P ou shift-cmd-P, puis cherchez et lancez la commande « Dev Containers: Reopen in Container ».

Créer une base de données

Pour cette application, nous avons besoin d’une base de données. Pour cela, nous vous proposons d’utiliser le SGBDR MariaDB déjà installé sur votre machine virtuelle.

À la racine de votre projet (le répertoire où se trouve le fichier pom.xml), créez un répertoire data. Dans ce répertoire, créez un fichier de type SQL nommé «guestbook.sql» avec le code SQL suivant :

1
2
3
4
5
6
7
8
9
10
CREATE DATABASE guestbook DEFAULT CHARSET UTF8;
use guestbook;

CREATE TABLE message (
    messageID    INT UNSIGNED NOT NULL AUTO_INCREMENT,
    messageDate  TIMESTAMP DEFAULT NOW(),
    pseudo       VARCHAR(50),
    message      VARCHAR(512),
PRIMARY KEY (messageID)
);

Il reste maintenant à créer la base de données dans le serveur MySQL. Pour cela, ouvrez un terminal, rendez-vous dans le répertoire de votre projet et exécutez les commandes suivantes :

1
2
3
cd data
mysql -h db -u root -p < guestbook.sql
Enter password :

Lorsque vous y êtes invité, tapez le mot de passe de l’utilisateur root (par défaut, le mot de passe est epai123). La base de données est maintenant créée. Pour le vérifier, tapez les commandes suivantes :

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
dev@vmdev: mysql -h db -u root -p
Enter password :

mysql> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| test               |
+--------------------+
4 rows in set (0.00 sec)

mysql> use guestbook;
Database changed

mysql>  show tables;
+---------------------+
| Tables_in_guestbook |
+---------------------+
| message             |
+---------------------+

Remarque : pour modifier le schéma d’une base de données du serveur qui se trouve sur votre machine de développement, ne faites pas de modifications incrémentales. Modifier le fichier guestbook.sql; supprimez la base de données avec la commande drop database Guestbook; puis recréez-la avec le nouveau schéma.

Vous pouvez ajouter des données dans votre base de données à l’aide d’instructions INSERT INTO comme dans l’exemple ci-après :

1
2
3
4
USE guestbook;

INSERT INTO message (pseudo, message)
VALUES ("albert", "Salutations d'albert !");

Utiliser une base de données SQL en Java

Pour utiliser mariadb, nous avons besoin d’un driver JDBC. Pour cela, ouvrez le fichier pom.xml et dans l’élément dependencies, ajoutez la dépendance suivante :

1
2
3
4
5
6
<!-- mariadb driver -->
<dependency>
    <groupId>org.mariadb.jdbc</groupId>
    <artifactId>mariadb-java-client</artifactId>
    <version>3.3.1</version>
</dependency>

L’extrait de code ci-dessous vous montre comment lire les données d’une base de données de mariadb en utilisant JDBC.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
...
// La construction try-with-ressource permet de fermer automatiquement les
// objets de type "AutoClosable" à la fin du bloc try. Ici, les ressources
// sont les objets connexion et statement.
try (
        // Crée une connexion à la base de données à partir de l'url de connexion, du
        // nom d'utilisateur et du mot de passe.
        Connection connection = DriverManager.getConnection("jdbc:mariadb://db/guestbook", "root", "epai123");
        // Crée un objet de type "Statement" qui représente une instruction SQL.
        Statement statement = connection.createStatement();) {

    // Exécute l'instruction SQL pour récupérer les messages. Le résultat
    // de la fonction est un ensemble de résultats (ResultSet) dont chaque
    // élément représente un enregistrement de la table message.
    ResultSet rs = statement.executeQuery("SELECT * FROM message;");

    // Parcourt l'ensemble de résultats (result set).
    while (rs.next()) {
        // Récupère l'attribut messageID de l'enregistrement courant
        // dans la variable id.
        int id = rs.getInt("messageID");
        // Récupère l'attribut messageDate de l'enregistrement courant
        // dans la variable date (le type java.sql.Timestamp permet de
        // récupérer la date et l'heure; le type java.sql.Date permet
        // de récupérer la date uniquement).
        Timestamp date = rs.getTimestamp("messageDate");
        // Récupère l'attribut pseudo de l'enregistrement courant
        // dans la variable pseudo.
        String pseudo = rs.getString("pseudo");
        // Récupère l'attribut message de l'enregistrement courant
        // dans la variable body.
        String body = rs.getString("message");

        // Fait quelque chose avec les valeurs
        System.out.format("%s, %s, %s, %s\n", id, date.toString(), pseudo, body);
    }

} catch (Exception ex) {
    // Jette une runtime exception.
    // Les utilisateurs de la fonction n'ont pas à savoir que la source de données
    // est une base de données SQL.
    throw new RuntimeException("Can't get message list.", ex);
}
...

Tâches

Sur la base du code et des documents fournis :

  1. Commencez par étudier le projet “firstserver” que vous avez téléchargé et appliquez-vous à en comprendre le fonctionnement en effectuant éventuellement de petites modifications.
  2. Sur le modèle du gestionnaire de ressources HomeHandler.java et en vous aidant de l’extrait de code fourni, vous devez réaliser un nouveau gestionnaire de ressource pour la liste des messages du livre d’or (sans formulaire de saisie). La représentation HTML doit contenir une liste dont chaque entrée comprend la date, le pseudo de l’auteur et le texte du message. Le contenu de la réponse doit être en HTML 5 encodé en UTF-8. Le chemin de l’URI de la ressource doit être “/guestbook”.
  3. Modifiez le gestionnaire de ressource pour réaliser un formulaire pour la saisie de nouveaux messages. Le formulaire doit avoir un champ pour le pseudo, un champ multiligne pour le message, un bouton d’envoi, et doit se trouver dans le haut de page au-dessus du premier message.
  4. Ajoutez un gestionnaire de requête pour le traitement des données du formulaire. Le gestionnaire doit traiter les requêtes avec la méthode POST sur la ressource /guestbook. Vous devez implémenter le pattern “Post-Redirect-Get”.