Quelques patterns
pour la persistance des objets
avec DAO
Université de Nice Sophia-Antipolis
Version 1.4 – 30/8/07
Richard Grin
(cid:137) Ce cours présente des modèles de
conception utilisés pour effectuer la
persistance des objets
R. Grin
Mapping objet-relationnel
page 2
Principe de base
(cid:137) Il est plus fréquent de changer la façon
d’effectuer la persistance que de changer le
modèle « métier »
(cid:137) Pour faciliter les changements dans la
persistance il faut isoler le plus possible le
code qui gère la persistance
DAO
(cid:137) La persistance est isolée dans des objets
spécifiques, les DAO (Data Access Objects)
R. Grin
Mapping objet-relationnel
page 3
R. Grin
Mapping objet-relationnel
page 4
Le modèle de conception DTO
(Data Transfer Object)
Utilité des DTOs
(cid:137) Les DAOs sont situés dans une couche
proche de la base de données
(cid:137) Le code utilisateur des DAOs est souvent
situé sur une autre couche distante
(cid:137) Les DTOs peuvent être utilisés pour
transporter les données entre les différentes
couches distantes
R. Grin
Mapping objet-relationnel
page 5
R. Grin
Mapping objet-relationnel
page 6
1
Un fait important
Le problème à résoudre
(cid:137) Les appels de méthode distants sont
beaucoup plus coûteux que les appels locaux
(cid:137) Le coût dépend peu de la quantité de
données transférée à chaque appel
(cid:137) Un client souhaite récupérer des données en
interrogeant des objets distants non
facilement transportables sur le réseau
(cid:137) Exemple : récupérer les nom, prénom, salaire
et lieu de travail d’un employé
(cid:137) S’il utilise les accesseurs des classes des
objets (getNom, getPrenom, getSalaire,
getLieu), plusieurs appels distants sont
nécessaires
R. Grin
Mapping objet-relationnel
page 7
R. Grin
Mapping objet-relationnel
page 8
La solution DTO
(cid:137) Le client demande un objet qui contient
toutes les valeurs dont il a besoin
(cid:137) Cet objet, un Data Transfert Object (DTO),
est construit sur le site distant et passé en
une seule fois au client
(cid:137) Un DTO contient l’état d’un ou de plusieurs
objets métier, mais pas leur comportement
(cid:137) Synonyme : Transfert Object (TO)
Exemples d’utilisation des DTO
(cid:137) Transporter les données d’un objet distant
pas transportable sur le réseau (pas
sérialisable)
(cid:137) Transporter plusieurs objets distants en un
seul appel distant ; par exemple une facture
avec toutes les lignes de facture et les
informations sur les produits
(cid:137) Pour éviter les complications inutiles il faut
éviter les DTOs si l’application est locale (pas
distribuée)
R. Grin
Mapping objet-relationnel
page 9
R. Grin
Mapping objet-relationnel
page 10
DTO pour modifier
(cid:137) Un DTO peut aussi être utilisé, plus
généralement pour modifier un ou plusieurs
objets distants (ou les données de la base de
données) :
n le DTO est créé ou modifié sur une couche
de l’application
n il est passé à une couche distante qui
utilise ses données pour modifier un ou
plusieurs objets distants (ou la base de
données)
Le modèle de conception DAO
(Data Access Object)
R. Grin
Mapping objet-relationnel
page 11
R. Grin
Mapping objet-relationnel
page 12
2
Le problème à résoudre
La solution
(cid:137) Le code pour la persistance varie beaucoup
n avec le type de stockage (BD relationnelles,
BD objet, fichiers simples, etc.)
n avec les implémentations des fournisseurs
de SGBD
(cid:137) Si les ordres de persistance sont imbriqués
avec le code « métier », il est difficile de
changer de source de données
(cid:137) Encapsuler le code lié à la persistance des
données dans des objets DAO dont l’interface est
indépendante du support de la persistance
(cid:137) Le reste de l’application utilise les DAOs pour
gérer la persistance, en utilisant des interfaces
abstraites, indépendantes du support de
persistance ; par exemple,
Employe getEmploye(int matricule)
R. Grin
Mapping objet-relationnel
page 13
R. Grin
Mapping objet-relationnel
page 14
DAO
Utilité des DAOs
(cid:137) Quand l’application a besoin d’effectuer une
opération liée à la persistance d’un objet, elle
fait appel à un objet DAO à qui elle passe les
informations nécessaires pour effectuer
l’opération
(cid:137) Chaque classe d’objet métier a son propre type
de DAO (DAOEmploye, DAODepartement, …)
(cid:137) Mais le même objet DAO peut être utilisé pour
tous les objets d’une classe d’objet métier
(cid:137) Plus facile de modifier le code qui gère la
persistance (changement de SGBD ou même
de modèle de données)
(cid:137) Factorise le code d’accès à la base de données
(cid:137) Plus facile pour le spécialiste des BD
d’optimiser les accès (ils n’ont pas à parcourir
toute l’application pour examiner les ordres
SQL)
(cid:137) Sans doute le modèle de conception le plus
utilisé dans le monde de la persistance
R. Grin
Mapping objet-relationnel
page 15
R. Grin
Mapping objet-relationnel
page 16
Emplacement des DAOs
CRUD
(cid:137) Les DAOs sont placés dans la couche dite
« d’accès aux données » qui est souvent sur
une autre machine que la couche des objets
métiers
(cid:137) Les échanges de messages entre les DAOs
et les objets métiers engendrent donc
souvent des appels distants et des DTO
peuvent donc être utilisés pour améliorer la
vitesse des échanges
(cid:137) Cet acronyme désigne les opérations de base de
la persistance : create, retrieve, update et delete
(cid:137) Ces 4 opérations de base sont implémentées
dans un DAO
R. Grin
Mapping objet-relationnel
page 17
R. Grin
Mapping objet-relationnel
Advertisement
page 18
3
CRUD
(cid:137) Create pour créer une nouvelle entité dans la
base
(cid:137) Retrieve pour retrouver une ou plusieurs
entités de la base
(cid:137) Update pour modifier une entités de la base
(cid:137) Delete pour supprimer une entité de la base
(cid:137) Plusieurs variantes pour les signatures de
ces méthodes dans les DAOs
create - paramètres
(cid:137) Prend en paramètre l’état de la nouvelle entité
(cid:137) Cet état peut être donné
n par une série de paramètres des types des
données : create(int id, String nom,…)
n par un DTO : create(DTOxxx dto)
n par l’objet métier que l’on veut rendre
persistant : create(Article article)
R. Grin
Mapping objet-relationnel
page 19
R. Grin
Mapping objet-relationnel
page 20
create – type retour
create – comparaison des variantes
(cid:137) Le type retour peut être
n void (la variante la plus utilisée)
n boolean pour indiquer si la création a pu
avoir lieu (on peut utiliser une exception à la
place)
n l’identificateur de l’entité ajoutée (utile si la
clé primaire est générée automatiquement
dans la base de données)
n un objet métier ou un DTO correspondant à
l’entité ajoutée
(cid:137) Les variantes qui passent les différentes
valeurs individuellement sont les plus souples
(cid:137) Lorsque les DTOs sont utilisées par ailleurs,
les variantes avec DTO sont souvent
rencontrées
(cid:137) Les variantes avec objet métier ne conviennent
que si l’objet métier a toutes ses propriétés
publiques et s’il est facilement transportable
(cid:137) Mais elle peut être pratique et performante
dans les cas où elle sont applicables
R. Grin
Mapping objet-relationnel
page 21
R. Grin
Mapping objet-relationnel
page 22
Exemple de code JDBC pour create
private String insert =
"insert into STYLO (ref, nom, prix, couleur)
variable d’instance
values(?, ?, ?, ?)";
...
PreparedStatement ps =
méthode create
connexion.prepareStatement(insert);
ps.setString(1, reference);
ps.setString(2, nom);
ps.setString(3, couleur);
ps.setBigDecimal(4, prix);
ps.executeUpdate();
retrieve
(cid:137) 3 types de méthode, suivant qu’elle retourne
n un seul objet
n une collection d’objets
n une valeur calculée à partir de plusieurs
entités (agrégation)
(cid:137) Une méthode (ou un objet) qui retourne des
données de la base de données est souvent
appelée finder
R. Grin
Mapping objet-relationnel
page 23
R. Grin
Mapping objet-relationnel
page 24
4
Exemples de finders
Finderqui retourne un objet
(cid:137) On trouvera le plus souvent
n une méthode findById(id) (ou d’un
nom semblable…) qui retrouve une entité
en donnant son identificateur dans la base
n une méthode findAll() qui retrouve
toutes les entités du type géré par le DAO
(cid:137) Mais on trouvera aussi des finders qui
cherchent suivant des critères quelconques
ou suivant des critères bien précis (ces
finders dépendent des traitements métier)
(cid:137) On lui passe en paramètre un identificateur
de l’entité cherchée
(cid:137) Il retourne un objet métier qui correspond à
l’entité cherchée, ou un DTO qui contient les
données de l’entité cherchée
(cid:137) Si le finder retourne un objet unique, il
retourne null si rien n’a été trouvé
R. Grin
Mapping objet-relationnel
page 25
R. Grin
Mapping objet-relationnel
page 26
Finderqui retourne une collection
(cid:137) On lui passe en paramètre le critère de
sélection, sous une forme quelconque
n objet ou valeurs « critère de sélection »
n objet « exemple » (à la « query by
example »)
(cid:137) Le type retour peut être très divers :
n ResultSet
n RowSet
n Collection (Collection, List, Set,…)
d’objets métier ou de DTOs
n tableau (rare)
Résultat vide
(cid:137) Si le critère de la requête n’est vérifiée par
aucune valeur, le finder doit retourner une
« collection » (collection, resultset rowset ou
tableau) vide
(cid:137) Retourner la valeur null obligerait à un cas
particulier pour le traitement de la valeur
retournée (« if (result == null) » avant une
boucle qui parcourt le résultat)
R. Grin
Mapping objet-relationnel
page 27
R. Grin
Mapping objet-relationnel
page 28
Finderqui retourne
une valeur calculée
(cid:137) Les valeurs calculées à partir des données
de plusieurs entités (exemple : total des
salaires) peuvent s’obtenir à partir d’objets
chargés en mémoire
(cid:137) Mais il peut être préférable de ne pas créer
les objets et d’interroger directement la base
de données qui est optimisée pour ce type de
requête
(cid:137) Un DAO peut ainsi comporter une méthode
qui renvoie le total des salaires des employés
update
(cid:137) Des variantes diverses pour les paramètres :
n identificateur + valeurs (plusieurs
paramètres pour les valeurs ou un seul
DTO)
n l’objet métier dont on veut sauvegarder les
modifications (nécessite un accès public
aux valeurs qui seront modifiées)
(cid:137) Le type retour peut être
n void
n boolean pour indiquer si la modification a
pu avoir lieu
R. Grin
Mapping objet-relationnel
page 29
R. Grin
Mapping objet-relationnel
page 30
5
delete
Autres méthodes des DAOs
(cid:137) Variantes pour les paramètres :
n identificateur de l’entité à supprimer dans
la base
n l’objet métier (ou un DTO) correspondant à
l’entité à supprimer dans la base
(cid:137) Variantes pour le type retour :
n void
n boolean pour indiquer si la suppression a
pu avoir lieu
(cid:137) Outre les opérations CRUD, les DAO peuvent
aussi implémenter des méthodes spécifiques
au modèle métier de l’application
(cid:137) Le plus souvent ce sont des variantes de
l’opération « retrieve »
(cid:137) Par exemple une méthode qui renvoie les
Advertisement
candidats qui ont une mention à un examen
R. Grin
Mapping objet-relationnel
page 31
R. Grin
Mapping objet-relationnel
page 32
2 stratégies d’utilisation des DAOs
Stratégie 1
1. Chaque objet métier a une référence à son
DAO et l’utilise pour sa propre persistance.
Le programme qui manipule les objets
métier ne connaît pas les DAOs
2. Le programme qui manipule les objets
métier utilise directement les DAOs.
Les objets métier n’ont pas de référence à
un DAO (stratégie sans doute la plus
fréquemment utilisée)
(cid:137) Les programmes qui manipulent les objets
métier ne sont pas modifiés par rapport à un
programme qui n’utilise pas de DAO
(cid:137) Seuls les objets métier connaissent leur DAO
(cid:137) Les objets métier doivent avoir une référence
vers le DAO qu’ils utilisent
(cid:137) Cette référence peut être obtenue par une
méthode static de la classe DAO (ce qui
peut permettre de partager un DAO entre tous
les objets métier d’une même classe)
R. Grin
Mapping objet-relationnel
page 33
R. Grin
Mapping objet-relationnel
page 34
Exemple de code
class Stylo {
private StyloDAO dao;
...
public void sauvegardeToi() {
dao = getDAO();
dao.insertOrUpdate(this);
}
private StyloDAO getDAO() {
on peut aussi
construire un
DTO pour le
passer au DAO
Stratégie 2
(cid:137) On rencontre le plus souvent la stratégie 2
(cid:137) On perd sans doute de la pureté de la
programmation objet
if (dao == null)
StyloDAO.getDAO();
return dao;
Pour simplifier, on ne
tient pas compte des
exceptions
Mapping objet-relationnel
page 35
R. Grin
Mapping objet-relationnel
page 36
}
R. Grin
6
Exemple de code
Exemple de code (variante)
// ou styloDAO = new StyloDAO()
StyloDAO styloDAO = StyloDAO.getDAO();
int idStylo =
styloDAO.create("Marker", "noir ",
DTO ou objet
métier
120,...);
. . .
Stylo stylo = styloDAO.findById(idStylo);
styloDAO.update(idStylo, ...);
List<Stylo> l = styloDAO.findAll();
Nouvelles
valeurs pour
le stylo
// ou styloDAO = new StyloDAO()
StyloDAO styloDAO = StyloDAO.getDAO();
styloDAO.create(145, "Marker",
"noir ", 120,...);
. . .
Stylo stylo = styloDAO.findById(1234);
stylo.setPrix(45);
styloDAO.update(stylo);
List<Stylo> l = styloDAO.findAll();
R. Grin
Mapping objet-relationnel
page 37
R. Grin
Mapping objet-relationnel
page 38
Diagramme de classes (avec
utilisation de TO)
Diagramme de séquences
Cette image (et les suivantes) sont extraites du
« Core J2EE Pattern Catalog » de Sun
R. Grin
Mapping objet-relationnel
page 39
Modification de plusieurs attributs persistants en utilisant un DTO :
création du DAO, puis récupération des valeurs actuelles,
puis modification de ces valeurs
R. Grin
Mapping objet-relationnel
page 40
Problèmes avancés sur les DAO
Problèmes abordés
(cid:137) DAO et exceptions
(cid:137) DAO et connexions
(cid:137) DAO et transactions
(cid:137) DAO et objets composés
(cid:137) DAO et héritage
R. Grin
Mapping objet-relationnel
page 41
R. Grin
Mapping objet-relationnel
page 42
7
DAO et exceptions (1)
DAO et exceptions (2)
(cid:137) Les méthodes des DAO peuvent lancer des
exceptions puisqu’elles effectuent des
opérations d’entrées-sorties
(cid:137) Les exceptions ne doivent pas être liées à un
type de DAO particulier si on veut pouvoir
changer facilement de type de DAO
(cid:137) Pour cela, on crée une ou plusieurs classes
d’exception indépendantes du support de
persistance, désignons-les par DAException
(ou DataAccessException ou
DaoException)
(cid:137) Les méthodes des DAO attrapent les exceptions
particulières, par exemple les SQLException,
et relancent des DAException (auxquels sont
chaînées les exceptions d’origine pour faciliter la
mise au point)
R. Grin
Mapping objet-relationnel
page 43
R. Grin
Mapping objet-relationnel
page 44
DAO et connexions (1)
DAO et connexions (2)
(cid:137) Une connexion peut être ouverte au début
des méthodes du DAO, et fermée à la fin des
méthodes
(cid:137) Il est préférable que les connexions soient
ouvertes par les clients du DAO
(cid:137) En ce cas, les connexions ouvertes doivent
(cid:137) Cette stratégie va coûter cher si un pool de
être passées au DAO
connexions n’est pas utilisé
(cid:137) Pour cela le DAO peut comporter une
méthode setConnection(Connection c)
(la façon de faire dépend de l’API de
persistance que l’on utilise ; avec JPA on
passera le manager d’entité et avec
Hibernate la session)
R. Grin
Mapping objet-relationnel
page 45
R. Grin
Mapping objet-relationnel
page 46
Qui gère les transactions ?
Transactions gérées par les clients
(cid:137) Un DAO pourrait démarrer et terminer lui-
même les transactions à chaque méthode
(cid:137) Cependant il n’est pas rare de vouloir inclure
un ou plusieurs appels de méthodes de
DAOs dans une seule transaction
(cid:137) L’implémentation des DAOs doit donc
permettre cette dernière possibilité : ce sont
les clients du DAO qui vont gérer les
transactions
(cid:137) C’est le client du DAO, et pas le DAO qui va
Advertisement
indiquer quand une transaction doit être
validée ou invalidée
(cid:137) Le DAO utilise la transaction en cours si elle
existe
R. Grin
Mapping objet-relationnel
page 47
R. Grin
Mapping objet-relationnel
page 48
8
Exemple schématique JDBC - DAO
public class StyloDao {
private Connection conn;
public void setConnection(Connection c) {
this.conn = c;
}
public long create(...) {
PreparedStatement pstmt =
conn.prepareStatement(...);
pstmt.setString(...);
...
pstmt.executeUpdate();
Exemple schématique JDBC - client
Connection conn = ... ;
daoStylo.setConnection(conn);
daoRamette.setConnection(conn);
...
daoStylo.create(...);
daoFacture.update(...);
conn.commit();
}
R. Grin
Mapping objet-relationnel
page 49
R. Grin
Mapping objet-relationnel
page 50
Tout n’est pas parfait !
Solution partielle
(cid:137) On vient de voir qu’avec un DAO JDBC, il faut
passer une connexion ; avec un DAO JPA
(étudié dans une autre partie du cours) il faut
passer un gestionnaire d’entités
(cid:137) Il est donc difficile de rendre l’utilisation des
DAOs totalement indépendante du type de
persistance si on veut gérer des types de
persistance très différents
(cid:137) Malgré tout, l’utilisation des DAOs diminue
fortement la dépendance vis-à-vis des types de
persistance
(cid:137) Par exemple, pour la gestion des
transactions, le code différent concernera
l’initialisation des DAOs (avec une connexion
ou avec un autre objet)
(cid:137) La solution est de ne pas mettre la méthode
setConnection dans l’interface du DAO et
de caster le DAO dans un type concret, le
temps de l’initialiser
R. Grin
Mapping objet-relationnel
page 51
R. Grin
Mapping objet-relationnel
page 52
DAO et objets composés
(cid:137) Par exemple, pour une facture, la question
doit être posée : le dao pour les factures doit-
il retourner les lignes de la facture ?
(cid:137) Il n’y a pas de réponse générale ; la réponse
dépend du contexte
Le modèle de conception
« fabrique abstraite »
R. Grin
Mapping objet-relationnel
page 53
R. Grin
Mapping objet-relationnel
page 54
9
Un cas d’utilisation
Avec un constructeur
(cid:137) Une application fonctionne sur un ordinateur
portable
(cid:137) Une application peut utiliser une base locale
MySQL si l’ordinateur n’est pas connecté à
Internet, ou une base Oracle distante s’il est
connecté
(cid:137) Comment utiliser le bon DAO pour chaque
classe métier (par exemple, utiliser un
DAOStyloMySQL ou un DAOStyloOracle
suivant le cas) ?
(cid:137) Le code
DaoStylo dao = new DaoStyloOracle();
fixe le type de DAO créé
(cid:137) Il devra être modifié si on veut un autre type
R. Grin
Mapping objet-relationnel
page 55
R. Grin
Mapping objet-relationnel
page 56
Pattern « fabrique »
pour récupérer les DAO
(cid:137) Le pattern « fabrique » (factory) permet de
créer des instances en cachant le type
concret des instances créées
Avec une fabrique
(cid:137) DaoStylo dao =
fabriqueDaoStylo.getDao();
(cid:137) dao sera du type DaoStyloOracle ou
DaoStyloMySQL selon le cas
(cid:137) DaoStylo est une interface implémentée par
les classes concrètes de DAO
DaoStyloOracle et DaoStyloMySQL
(cid:137) Signature de getDao() :
DaoStylo getDao()
R. Grin
Mapping objet-relationnel
page 57
R. Grin
Mapping objet-relationnel
page 58
Avec une fabrique
(cid:137) Pour fixer le type renvoyé, il suffit de
l’indiquer auparavant à la fabrique par le code
fabriqueDaoStylo
.setTypeDao(typeDao);
(cid:137) typeDao peut, par exemple, être déterminé
en testant si l’ordinateur est connecté ou non
à Internet
Fabrique abstraite
(cid:137) Si on veut changer de base de données, le
type de DAO doit être fixé pour toutes les
fabriques de DAOs
(cid:137) Le pattern « fabrique abstraite » permet de
changer plus facilement de base de données
(cid:137) En une seule ligne de code tous les DAOs
peuvent être remplacés par des DAOs
adaptés à la nouvelle base de données
choisie
R. Grin
Mapping objet-relationnel
page 59
R. Grin
Mapping objet-relationnel
page 60
10
Fabrique abstraite
(cid:137) Une fabrique abstraite est un type abstrait qui
permet de cacher les types réels d’un
ensemble de fabriques concrètes
(cid:137) Chaque fabrique concrète fournit tous les
DAOs (DAOStylo, DAORamette,…)
associés à une certaine source de données
(cid:137) Dans la ligne de code, on récupère la bonne
fabrique de DAOs, associée à la bonne
source de données
R. Grin
Mapping objet-relationnel
page 61
Code pour fabrique abstraite
(cid:137) Le code qui suit est un exemple schématique
de l’utilisation du pattern DAO, avec le pattern
fabrique abstraite (inspiré fortement d’un
exemple donné par Sun)
(cid:137) Il utilise le pattern DTO/TO exposé dans la
1ère partie de ce cours
(cid:137) Ce pattern DTO peut être évité si les objets
persistants peuvent être transportés entre les
différentes couches d’une application (par
exemple, pour une application locale, ou en
utilisant les objets « détachés » de JPA ou de
Hibernate)
Mapping objet-relationnel
page 62
R. Grin
Le type
abstrait
Code client (début)
DAOFactory daoFactory =
DAOFactory.getDAOFactory(
La seule ligne de code
Advertisement
pour changer de
SGBD
DAOFactory.TypeDao.MYSQL);
styloDAO = daoFactory.getStyloDAO();
// crée un nouveau stylo dans la base
int styloNo = styloDAO.create(...);
// Trouve un stylo
StyloTO styloTO = styloDAO.find(...);
// Modifie des valeurs du DTO
styloTO.setPrix(125);
// Modifie le stylo dans la base
styloDAO.update(styloTO);
Code client (suite)
// Supprime un stylo de la base
styloDAO.delete(styloNo);
// Trouve tous les stylos d’une marque
// Utilise un stylo « exemple » de ce
// que l’on cherche
StyloTO styloEx = new StyloTO();
styloEx.setMarque("Marker");
Collection<StyloTO> listeStylos =
styloDAO.find(styloEx);
...
R. Grin
Mapping objet-relationnel
page 63
R. Grin
Mapping objet-relationnel
page 64
Fabrique abstraite – 1 DAO
Fabrique abstraite – 1 source de données
La fabrique
abstraite
Les fabriques
concrètes
Les DAOs
créés
Une fabrique concrète
crée tous les DAOs
associés à une source
de données
R. Grin
Mapping objet-relationnel
page 65
R. Grin
Mapping objet-relationnel
page 66
11
Fabrique abstraite – schéma global
Code pour fabrique abstraite
(cid:137) Le code qui suit est un exemple schématique
de l’utilisation du pattern DAO, avec le pattern
fabrique abstraite (inspiré fortement d’un
exemple donné par Sun)
(cid:137) Il utilise aussi le pattern DTO/TO
(cid:137) Important : ce pattern DTO peut être évité si
les objets persistants peuvent être
transportés entre les différentes couches
d’une application (par exemple, pour une
application locale, ou en utilisant les objets
« détachés » de JPA ou de Hibernate)
R. Grin
Mapping objet-relationnel
page 67
R. Grin
Mapping objet-relationnel
page 68
La fabrique abstraite
Une fabrique concrète
public abstract class DAOFactory {
public enum TypeFabrique {MYSQL, ORACLE};
public abstract StyloDAO getStyloDAO();
public abstract FactureDAO getFactureDAO();
...
public static DAOFactory getDAOFactory(
TypeFabrique typeFabrique) {
switch (typeFabrique) {
case MYSQL: return new MysqlDAOFactory();
case ORACLE: return new OracleDAOFactory();
default: ... ; // erreur
}
}
}
R. Grin
Mapping objet-relationnel
page 69
public class MySQLDAOFactory
extends DAOFactory {
@Override
public StyloDAO getStyloDAO() {
return new MySQLStyloDAO();
}
@Override
public FactureDAO getFactureDAO() {
return new MySQLFactureDAO(); }
...
}
R. Grin
Mapping objet-relationnel
page 70
Interface des DAO pour Stylo
DAO concret pour Stylo
public interface StyloDAO {
public int insert(...);
public boolean delete(...);
public StyloDTO find(...);
public boolean update(...);
public Collection<StyloTO> findAll(...);
public Collection<StyloTO> find(...);
...
référence
}
objet exemple
R. Grin
Mapping objet-relationnel
page 71
import java.sql.*;
public class MySQLStyloDAO
implements StyloDAO {
public MySQLStyloDAO() { ... }
public int insert(…) { ... }
public boolean delete(…) { ... }
public StyloTO find(…) { ... }
public boolean update(...);
public Collection<StyloTO> findAll(...);
...
}
R. Grin
Mapping objet-relationnel
page 72
12
TO pour Stylo
Inconvénient de ce pattern
import java.io.Serializable;
public class StyloTO implements Serializable {
private String reference;
private String name;
...
// Accesseurs et modificateurs
public String getReference() {...}
public void setReference(String ref) {...}
...
indispensable pour être
transporté d’une couche
à une autre
}
(cid:137) Si on veut ajouter un nouveau type de DAO
(par exemple, un DAO pour un autre article),
il faut modifier le code de toutes les fabriques
abstraite et concrètes
R. Grin
Mapping objet-relationnel
page 73
R. Grin
Mapping objet-relationnel
page 74
DAO et EJB
Bibliographie
(cid:137) Dans les applications construites selon la
spécification EJB, les DAOs seront le plus
souvent des beans sessions sans état
(@Stateless) avec des contextes de
persistance limités à une transaction (voir
cours sur JPA)
(cid:137) Patterns of Entreprise Application
Architecture de Martin Fowler – Addison
Wesley
(cid:137) Présentation du pattern DAO et
implémentation en Java, par Sun :
http://java.sun.com/blueprints/corej2eepattern
s/Patterns/DataAccessObject.html
R. Grin
Mapping objet-relationnel
page 75
R. Grin
Mapping objet-relationnel
page 76
13