rapport de projet d'application pour l'internettraores/jee_rapport.pdf · fragment...

12
ENSEEIHT Rapport de Projet d'Application pour l'Internet Site de location de matériel et d'édition de devis Bastien BARTHET, Adrien CHAMPION, Benoit ESTEVENON, Thibaut ETIENNE, Bastien LEHMANN Juin 2009

Upload: others

Post on 03-Jun-2020

9 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

ENSEEIHT

Rapport de Projet d'Application pour l'Internet

Site de location de matériel et d'édition de devis

Bastien BARTHET, Adrien CHAMPION, Benoit ESTEVENON, Thibaut ETIENNE, Bastien LEHMANN

Juin 2009

Page 2: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

2

1 Sommaire 2 Introduction ..................................................................................................................................... 3

3 Cahier des charges du client ............................................................................................................ 3

4 Technologies employées ................................................................................................................. 3

5 Côté serveur .................................................................................................................................... 4

5.1 Modèle entité de la base de données ..................................................................................... 4

5.2 Beans ....................................................................................................................................... 5

6 Sécurité et authentification ............................................................................................................. 5

7 Côté client........................................................................................................................................ 5

7.1 L’architecture du site ............................................................................................................... 5

7.2 AJAX ......................................................................................................................................... 6

7.2.1 Ajax.Request .................................................................................................................... 6

7.2.2 Ajax.Updater .................................................................................................................... 7

7.2.3 D’autres façons de gérer les requêtes ............................................................................. 7

7.2.4 Les effets graphiques ....................................................................................................... 7

7.3 Servlet et JSP ........................................................................................................................... 8

7.3.1 Création d’un client ......................................................................................................... 8

7.3.2 Identification d’un client ................................................................................................. 8

7.3.3 Edition d’un profil client .................................................................................................. 9

8 Génération de devis et facture en PDF ......................................................................................... 10

8.1 Pourquoi ? ............................................................................................................................. 10

8.2 Intégration générale à l’architecture du site ......................................................................... 10

8.3 Outils utilisés pour la génération .......................................................................................... 10

9 Répartition du travail..................................................................................................................... 10

10 Problèmes rencontrés ............................................................................................................... 11

10.1 Castage d'ArrayList ................................................................................................................ 11

10.2 Internet Explorer vs Firefox ................................................................................................... 11

10.3 Adressage relatif des fichiers PDF généré ............................................................................. 11

11 Conclusion ................................................................................................................................. 12

Page 3: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

3

2 Introduction Après avoir étudié plusieurs technologies web en cours, le présent projet a pour objectif de les

mettre en application sous la forme d’un site web. Le thème de ce dernier n’est pas imposé, mais il

doit être du type e-commerce. C'est-à-dire qu’il doit proposer la vente ou location de différents

objets.

3 Cahier des charges du client Ici, il s’agira d’un site de location en ligne de matériel d’une association de technique de spectacle

(Son&Lumière).

Il s’agit d’un élément primordial. En effet, c’est lui qui va aiguiller le développement du site. Il vise à

définir exhaustivement les spécifications de base du site à réaliser.

La demande est de pouvoir parcourir le parc de matériel, d'en faire un panier à la manière d'un

quelconque site de e-commerce, et enfin de pouvoir éditer les devis, facture et bon de livraison.

Le stockage de toutes les commandes passées doit être également assuré.

Deux types d'utilisateurs sont prévus quant à l'utilisation du site :

les clients. Ils peuvent consulter les produits, constituer un panier, voir leurs commandes

passées ou en cours, et éditer leur devis et ainsi que leur profil.

l'administrateur. Il peut modifier la base de données des produits, modifier n'importe quelle

commande, et visualiser les clients. Il est le seul à pouvoir éditer une facture ou un bon de

livraison.

4 Technologies employées Le but des technologies employées est de bien séparer le modèle, la vue et le contrôleur (MVC). Ainsi

il est aisé de travailler sur chaque parti indépendamment. De plus, la modularité ainsi apportée

permet de répartir facilement les différentes tâches entre les différents membres du groupe.

Le côté serveur, ou Back End, est écrit en EJB3 simplifiant ainsi la gestion des entités de la base de

Page 4: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

4

données et la communication avec les clients. Des Servlets de manipulation des EJB sont déployés

côté client pour chaque action potentiellement effectuée par le client. L'interface utilisateur se

présente sous forme de pages HTML intégrant du JavaScript, de l'AJAX, du CSS et interaction avec les

Servlets via des JSP.

5 Côté serveur

5.1 Modèle entité de la base de données

Voici le schéma Entité-relation de la base de données déployée. Chaque client possède des

commandes. Chaque commande possède des produits sous la forme de couple (produit, quantité),

regroupé dans le type ProduitQuantité, pointant sur la base de données des produits.

Une fois une commande validée, l'objet Commande est supprimé et est remplacé par un objet

CommandeValidee, de façon à ne plus évoluer avec la BD. En effet si l'administrateur modifie le prix

d'un produit dans la BD, toutes les commandes en cours utilisant ce produit se verront modifiées

(aucun prix total n'est stocké, mais uniquement les prix unitaires et les quantités).

Afin de mieux distinguer les produits d'une catégorie ou d'une sous-catégorie, et de pouvoir lister

une commande par catégorie, des structures plus complexes de stockage furent envisagées, comme

définir des types génériques ou des HashMap. Le choix d’une liste ordonnée c’est finalement imposé

pour représenter les produits d'une commande. La fonction d'ajout regroupe le nouveau produit

N

1

1 N 1

1 N 1 1

Adresse

int id

String ville

String rue

int codePostale

Client

String login

String role

int reduction

String password

String beneficiaire

String email

String tel

Adresse adr

Collection<Commande>

Collection<CommandeValidee>

CommandeValidee

int id

String nom

String cheminVersImage

String cheminVersFacture

String cheminVersBonDeLivraison

Produit

Int id

String name

String description

int quantite

Float prix

String cheminVersImage

String categorie

ProduitQuantite

Int id

Produit p

int quantite

Commande

int id

String titreCommande

Date dateSortieMateriel

Date dateRetourMateriel

Collection<ProduitQuantite>

Page 5: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

5

avec ceux de sa catégorie/sous-catégorie, afin de pouvoir ensuite lister les produits de façon plus

claire sur les devis.

5.2 Beans Pour manipuler ces entités, 3 classes de type SessionBeans ont été déployées pour gérer

respectivement les Produits, les Commandes et les Clients. Chacun fourni au client les fonctions

nécessaires à l'utilisation, en restreignant ainsi les risques de mauvaise utilisation.

6 Sécurité et authentification Le problème de l'authentification des clients et de l'identification du rôle de celui-ci (administrateur

ou simple client) a été géré par l'ajout de la clé client à la session. La session, de type HttpSession,

permet de faire persister des informations tout au long d'une connexion, jusqu'à un time-out ou un

retrait des informations. Tout ceci est géré par les servlets. Le client rentre donc son login et mot de

passe, qui sont ensuite contrôlé coté Beans, puis en cas de bonne identification le serveur renvoi au

client son rôle, qui est inscrit dans la session avec la clé client. Ce contrôle se passe donc côté Servlet

et permet ainsi à chaque action du client de savoir, d'une part si il est bien authentifié et autorisé à

appeler la méthode qu'il appelle, et d'autre part à connaître l'identité du client à chaque instant.

7 Côté client

7.1 L’architecture du site Notre site ne dispose vraiment que de trois pages:

la page d'accueil

la page client (une fois ceux-ci loggés)

la page administrateur (une fois celui-ci loggé)

A l'intérieur de ces pages, toutes les actualisations se font par mise à jour par fragment à l'aide

d'AJAX et en particulier de la librairie prototype.js (http://www.prototypejs.org/).

Deux objets sont principalement utilisés, Ajax.Request et Ajax.Updater.

Page 6: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

6

7.2 AJAX

7.2.1 Ajax.Request

Voici un exemple d'utilisation d'Ajax.Request :

Page 7: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

7

function adminGetClients() {

var date = new Date();

var param = "dummy=" + date;

new Ajax.Request('ActionListerClient', {

method : 'post',

parameters : param,

onComplete : function(response) {

$('mainDisplay').innerHTML = response.responseText;

}

});

}

Ajax.Request est adapté aux appels à une servlet. Une fois la requête terminée, l'action définie dans

le champ onComplete est exécutée, ici on actualise le fragment central avec la liste des clients

(renvoyée sous forme d'une JSP par la servlet appelée).

7.2.2 Ajax.Updater

Voici un exemple d'utilisation d'Ajax.updater:

function ajaxUpdater(container, url) {

new Ajax.Updater(container, url);

}

Nous utilisons exclusivement Ajax.Updater pour des appels directs aux JSPs sans passer par une

servlet. La fonction considérée ici permet de mettre à jour un fragment (typiquement un div) dont

l'id est « container » avec la JSP à l'adresse « url ».

7.2.3 D’autres façons de gérer les requêtes

Prototype.js est compatible avec le standard JSON (http://www.prototypejs.org/learn/json) qui, pour

ce que nous en avons lu, semble présenter des avantages certains et est fortement recommandé par

les « gros bonnets » du domaine. Cependant, à cause du nombre conséquent de projets en simultané

et de l'approche des partiels nous avons préféré nous en tenir à des technologies plus facilement

abordables.

A noter également que prototype.js gère également les formats couramment employés pour la

création de pages ou de fragments dynamiques tels que XML et DOM.

7.2.4 Les effets graphiques

Pour étoffer l'aspect visuel du site, nous avons tout d'abord commencé à nous pencher sur plusieurs

librairies isolées telles que Rico (http://openrico.org/), ainsi que sur des scripts spécialisés (comme

on peut en trouver ici : http://www.miniajax.com/).

Rapidement sont apparus de gros problèmes de compatibilité entre les librairies et les scripts par

rapport aux noms de variables, aux noms de fonctions, ainsi qu'au CSS pour les scripts spécialisés. De

plus, les librairies telles que Rico fournissent des effets de trop haut niveau assez peu modifiables à

moins de modifier le code source, chose que nous n'avions pas le temps de faire.

Il a donc été décidé d'utiliser scriptaculous (http://script.aculo.us/) qui donne accès à des effets assez

simples mais plutôt efficaces et surtout plus facilement adaptables au cas par cas.

Page 8: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

8

Les effets principalement utilisés sont Effect.BlindUp, Effect.BlindDown, Effect.Appear, Effect.Fold...

(http://wiki.github.com/madrobby/scriptaculous).

En particulier, il a été défini une petite fonction très pratique:

// Fonction d'apparition et de disparition

function slideThat (that) {

var dis = document.getElementById(that);

var state = dis.getAttribute("class");

if (state == "on") {

Effect.BlindUp(that);

dis.setAttribute("class", "off");

} else {

Effect.BlindDown(that);

dis.setAttribute("class", "on");

}

}

Elle permet de faire apparaître ou disparaître un fragment (un div) très facilement. Cependant elle

n'est pas très propre et pose un problème : dans la mesure où la classe du fragment est utilisée pour

savoir s'il est visible ou non, deux clics trop rapprochés rendront incohérent l'état de classe si le

fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics.

7.3 Servlet et JSP Le but est ici de créer des servlets permettant de manipuler les clients, les produits et les

commandes. La première phase étant la création d'un nouveau client, qu'il puisse s'authentifier et

modifier son profil.

7.3.1 Création d’un client

De manière classique, tous les paramètres nécessaires à la création d'un client sont récupérés :

String login = request.getParameter("login");

String password = request.getParameter("password");

String rue = request.getParameter("rue");

Grâce au générateur de contexte, un clientSessionBean est créé auquel se rajoute le nouveau client

ainsi crée :

ClientSessionBeanRemote sessionBean =

GenerateurContext.getClientSessionBeanRemote();

Client c = new Client(login, role, reduc, password, beneficiaire, email,

tel, adr, listeDesCommande);

sessionBean.creer(c);

La redirection se fait alors vers une JSP personnalisée souhaitant la bienvenue à l'utilisateur identifié

avec succès. Sinon, il est invite à s’identifier de nouveau via des alertes AJAX.

7.3.2 Identification d’un client

Comme précédemment, tous les paramètres nécessaires à l'identification d'un client sont récupérés

et un clientSessionBean est créé/récupéré grâce au générateur de contexte.

Page 9: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

9

String login = request.getParameter("login");

String password = request.getParameter("password");

Sur ce session bean, la méthode identifierClient renvoie le rôle du client, admin ou client. Pour la

suite des opérations, en plus d’insérer le login à la session, le rôle y est également ajouté, ce qui

déterminera les actions possible à une personne connectée. Un client ne pourra pas effectuer les

mêmes actions qu'un administrateur.

ClientSessionBeanRemote sessionBean =

GenerateurContext.getClientSessionBeanRemote();

String role = sessionBean.identifier(login, password);

HttpSession session = request.getSession(true);

request.setAttribute("login", login);

Ensuite, une redirection s'effectue en fonction du rôle de la personne connectée.

if (role.equals("admin")) {

request.getRequestDispatcher("jsp/logAdmin.jsp").forward(request,resp

onse);

} else {

request.getRequestDispatcher("jsp/logClient.jsp").forward(request,res

ponse);

}

7.3.3 Edition d’un profil client

Encore une fois, les bons paramètres nécessaires à l'édition d'un client sont récupérés. La page web

affectant les valeurs à ces paramètres se charge de passer la valeur de paramètre déjà existante si

l'utilisateur ne souhaite pas la modifier.

Ensuite, toutes les fonctions disponibles sont appelées dans le haricot pour effectuer les

changements. Petit plus, si le nouveau mot de passe n'est pas vide, l'ancien est conservé.

Il est également possible pour un administrateur d'éditer tous les clients, de la même manière que

précédemment, à ceci prés qu'il peut changer sa réduction, mais pas les paramètres

d’authentification, login et mot de passe.

Pour les produits et les commandes le fonctionnement est assez similaire, en effet les fonctions de

création, d'édition, et de suppression fonctionnent de la même manière. A la différence près que

selon le rôle de la personne connectée certaines actions ne seront pas disponibles. En effet l'ajout

d'un produit dans la base de données ainsi que son édition et sa suppression ne seront accessibles

qu'à un administrateur.

Mis à part le fait que graphiquement ces actions ne seront disponibles que pour un administrateur

connecté, un test sur le rôle est effectué pour éviter toute fraude de la part d'un client malveillant.

HttpSession session = request.getSession();

String role = (String)session.getAttribute("role");

if (role.equals("admin")){

try {

ProduitSessionBeanRemote sessionBean =

GenerateurContext.getProduitSessionBeanRemote();

sessionBean.creerProduit(name, description, prix,

categorie, sousCategorie, quantite, cheminversImage);

Page 10: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

10

} catch (Exception e) {

request.setAttribute("error",e);

request.getRequestDispatcher("error.jsp").forward(request,

response);

}

}

else {

//renvoyer a l'identification

}

8 Génération de devis et facture en PDF

8.1 Pourquoi ? Afin de conserver trace des prestations qu'a offert le Club Animation, il est nécessaire de conserver

un élément qui rende compte de la transaction à une certaine date, indépendamment des évolutions

des prix et du parc matériel. Pour cette raison, la génération de fichiers PDF est excellente car une

fois écrit, son contenu restera statique même s'il y a des modifications en Back End. Les fichiers

générés seront stockés sur serveur grâce à leur n° de commande et leur type (facture, devis ou bon

de livraison). En ayant le chemin d'accès inscrit en Base de données, il serait ainsi simple de les

retrouver pour les renvoyer au client par la suite. A noter que pour plus de portabilité il serait plus

judicieux de stocker uniquement le n° de facture et que le Front End reconstitue lui-même le chemin

d'accès selon sa propre méthode de stockage.

8.2 Intégration générale à l’architecture du site L'intégration se fait logiquement du côté où les fichiers sont écrits, c'est à dire en Front End. La

génération étant de plus "interactive" (i.e. lancée par l'utilisateur), les Servlets semblent toutes

indiquées pour ce genre de traitement. Le traitement de l'intégralité de la tâche n'est pas compliqué

en soit :

La commande et le client étant fournis (l’authentification est donc obligatoire), il suffit de les

disséquer pour en tirer les informations importantes et les écrire dans un fichier avec une

présentation particulière.

La clé du chemin d'accès au fichier doit ensuite être mémorisée dans la base de données

pour un appel ultérieur.

8.3 Outils utilisés pour la génération L'idée était au départ de générer un fichier source LaTeX pour le compiler à la volée et générer le

PDF. Cette solution a été abandonnée car les librairies LaTeX n'auraient pas forcément été

présentes/installables sur le serveur. De plus, ces librairies sont très lourdes puisqu'il y a plusieurs

centaines de Mo.

A la place, il a été choisi d'utiliser du Java pour générer les PDF. Grâce à la librairie iText (disponible

sur http://www.lowagie.com/iText/), il est possible de décrire un document PDF en y ajoutant des

éléments au fur et à mesure. Par contre, l'étape d'écriture d'un fichier source est sautée. Pour

comparaison avec le LaTeX, la commande du site serait notre fichier source et notre servlet serait le

compilateur LaTeX.

Page 11: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

11

9 Répartition du travail Nous avons très vite défini notre projet et reparti les tâches selon les envies de chacun. Bastien L.

s'est chargé du Back End, épaulé pour la conception papier par Benoit. Benoit a donc aidé sur le Back

End, bien que son rôle principal ait été la génération de PDF, via la librairie iText, à partir d'une

servlet. Bastien B. a réalisé l'ensemble des servlets, gérant ainsi l'authentification, et les liens entre

Beans et JSP, selon les besoins des autres parties. Adrien a conçu les JSP, classe JavaScript et l'AJAX

du site, aidé par Thibaut. Thibaut s'est occupé du CSS, de l'HTML et du graphisme, en aidant ensuite

Bastien B. sur les servlets et Adrien sur les JSP.

Les parties étant clairement définies, le travail a très vite évolué individuellement, et collectivement

via un SVN global. Le SVN a vraiment permis d'avoir des tâches autonomes puisque pour les liens

avec les autres parties, il était possible d'aller voir ce qui avait été fait. Cependant certaines tâches

furent des bloquantes, nécessaires à l'avancement général, notamment le BackEnd dont les

interfaces et entités ont du très vite être défini.

10 Problèmes rencontrés

10.1 Castage d'ArrayList Lors d'un accès à une collection issue d'un lien OneToMany, le castage en ArrayList lève une

exception, expliquant qu'il est impossible de caster le PersistenteBag. Aucune solution n'a été trouvé,

d'où l'impossibilité de rattacher une commande à un client (accès possible via l'administrateur pour

l'instant, qui récupère la liste complète des commandes), ni de rattacher des produits à une

commande. Les modifications des paramètres de fetch, des types de liste (List, ArrayList, Collection)

n'ont rien donné.

Pour pouvoir cependant présenter une génération de PDF sans réel commande, le modèle entité-

relation a été rapidement recopié en Front End de façon à pouvoir tester le générateur sur une

commande non vide!

10.2 Internet Explorer vs Firefox Lors de la conception du CSS divers problèmes de compatibilité ont été rencontrés. En effet, IE et FF

n'interprètent pas exactement de la même manière le code. De fait, la position de certains boutons

est aléatoire, ce qui est très irritant. Suite à plusieurs tentatives de résolution, il s'est avéré que

c'était peut être l'insertion de code avec AJAX ainsi que les effets graphiques qui perturberaient la

lecture du CSS.

10.3 Adressage relatif des fichiers PDF générés Le problème majeur est posé par la portabilité : comment savoir où vont aller les fichiers, en

particulier si on change de machine serveur. On ne peut donc pas utiliser de chemin absolu pour

indiquer où stocker les fichiers. Heureusement les chemins relatifs sont utilisables lors de l'écriture

du fichier, en écrivant dans le répertoire courant, c'est le répertoire bin de JBOSS qui sera utilisé.

Sachant cela, il est possible de les stocker à l’endroit souhaité.

Vient ensuite la récupération du fichier par la servlet et là les choses sont plus difficiles : en chemin

relatifs ou absolus, il n'a pas été possible de récupérer les fichiers générés. Le problème a donc été

contourné en mettant le lien hypertexte vers le fichier directement dans la page du client.

Page 12: Rapport de Projet d'Application pour l'Internettraores/jee_rapport.pdf · fragment n'a pas eu le temps de terminer l'effet (apparition ou disparition) entre les deux clics. 7.3 Servlet

12

11 Conclusion Ce projet fut très intéressant de part son intérêt. En effet, construire un site de e-commerce permet

d'utiliser les connaissances théoriques dans un but extrêmement précis et dont le résultat est

immédiatement visible. D'autre part, la répartition des tâches s'est avérée être un point clé du

déroulement du projet. De manière générale, la communication entre membres s'est très bien

déroulée, ceci grâce à une bonne entente, une bonne ambiance et au SVN.

Cependant, face à la simultanéité des projets et partiels et à la configuration chaotique des

différents outils de développement, il nous a été difficile de mener à bien ce projet comme nous

l'aurions souhaité. Bien que la majeure partie du site fonctionne, il reste quelques fonctionnalités à

implémenter qui mériteraient que l'on se penche dessus plus tard.

In fine, ce projet nous a beaucoup apporté tant sur le plan technique que relationnel. Et bien que

partiellement inachevé, nous sommes heureux de ce que nous avons pu réaliser en aussi peu de

temps.