Plan du document
Problématique slide 3
Programmation d’application
Correspondance diagramme de classe slide 4
Bases de données avec Java UML vers schéma relationnel
Programmation BD avec JDBC slide 16
Gestion de la persistance en Java slide 35
INT
Ressources en ligne
http://mica/~oracle/IO21
1 2
Problématique Correspondance de schémas
mapping Schéma Transformer un diagramme de classes UML
classes relationnel (partie statique) en un schéma relationnel
déchargement
«équivalent»
Analogue à la transformation d’un schéma Entité-
objets tuples Association vers un schéma relationnel avec le
problème des hiérarchies de classes en plus
chargement
Plusieurs correspondances possibles
Processus (mémoire) SGBD
3 4
Bases de Données 1
Exemple Sémantique de la généralisation /
FicheEmprunt spécialisation
Document dateEmprunt
code dateLimite Client Sous ensemble d'entité hérite des attributs
nom
titre dépassé
prénom
de son super ensemble d'entité
auteur
année adresse Spécialisation peut être :
totale (toute instance est spécialisée dans au
moins un sous-ensemble) ou partielle
Audio Livre TarifNormal Abonné
classification nombrePage dateCotisation une partition (une instance ne peut être
dateInscription spécialisée dans plusieurs sous-ensembles) ou
Vidéo
TarifRéduit un recouvrement
dateInscription
duréeFilm
dateRenouvellement
mentionLégale
5 6
Exemple de généralisation / Correspondance 1
spécialisation
PERSONNE Une classe = une relation
nom
prénom La liaison entre les relations se fait via la clé
adresse
E∩S≠∅ Fonctionne quelle que soit la sémantique
P=E∪S
T/R d’héritage
ETUDIANT SALARIE Nécessite de reconstruire les objets par
noétud salaire jointure
cycle
S = PR ∪ PU T/P PR ∩ PU = ∅
PRIVE PUBLIC
prime indice
7 8
Bases de Données 2
Correspondance 1 pour Document Correspondance 2
Document(code, titre, auteur, année) Chaque classe spécialisée = une relation
Audio(code, classification) Classe mère = une vue
Vidéo(code, duréeFilm, mentionLégale) Pour sémantique partition et totale
Livre(code, nombrePage) Évite les jointures pour reconstruire les objets
Multiplie les relations (traduction
d’associations modèle E/A)
9 10
Correspondance 2 pour Document Correspondance 3
Audio(code, titre, auteur, année, classification) Ensemble des classes de la hiérarchie = une
Vidéo(code, titre, auteur, année, duréeFilm, seule relation
mentionLégale)
Livre(code, titre, auteur, année, nombrePage) Éventuellement chaque classe = une vue
Create View Document Introduit un attribut discriminant et des
As Select code, titre, auteur, année from Audio valeurs nulles
Union Select code, titre, auteur, année from Vidéo
Union Select code, titre, auteur, année from Livre Pour sémantique de partition
9 relations pour la classe FicheEmprunt ! Évite les jointures
11 12
Bases de Données 3
Correspondance 3 pour Document Correspondance 4
Document(code, titre, auteur, année, Variante de la correspondance 3 avec
typeDocument, classification, duréeFilm, utilisation d’un attribut booléen
mentionLégale, nombrePage) supplémentaire par sous classe
Create view Audio as Pour sémantique de recouvrement
Select code, titre, auteur, année, classification
From Document
Where typeDocument=‘Audio’
13 14
Correspondance 4 pour Document JDBC
Document(code, titre, auteur, année, AudioB, API Java pour manipuler des relations via
classification, VidéoB, duréeFilm, SQL (dans des fichiers locaux ou via un
mentionLégale, LivreB, nombrePage) SGBD)
Create view Audio as Une seule API uniforme (même niveau que
SQL CLI de X/open)
Select code, titre, auteur, année, classification
From Document Indépendance / SGBD cible (via des pilotes)
Where AudioB is true Code portable de bout en bout
Pas forcément construit au dessus de ODBC
15 16
Bases de Données 4
Interfaces SQL LPG Programmer avec une BD
Pilotes JDBC
Approche Java Autres langages JDBC non supporté en natif par les SGBD du
commerce (ou les systèmes de fichiers)
Transformations des appels JDBC en appels natifs
Embedded SQL SQLJ Pro*C
Un pilote pour chaque SGBD
4 catégories de pilotes en fonctions de :
SQL/CLI JDBC ODBC La présence ou non de pilote SGBD (non java) sur le client
Protocole de communication entre le client Java et le
serveur
PSM PL/SQL ou Java
17 18
Les pilotes (suite) Classes et interfaces du
"paquage"java.sql
application application Driver Statement Connection ResultSet ResultSetMetaData DatabaseMetaData
JDBC JDBC PreparedStatement
Driver JDBC/Oracle Driver JDBC/Oracle +
API Oracle-OCI middleware client CallableStatement
Oracle Java.lang.Object
Ora*net serveur
API Oracle-OCI
Java.util.Date DriverManager DriverPropertyInfo Types
Oracle Date Time TimeStamp
20
Bases de Données 5
Connexion JDBC Connexion à la base (suite)
Classe java.sql.Connection Class.forName("oracle.jdbc.driver.OracleDriver");
URL d’une source de données chargement dynamique de la classe implémentant le pilote Oracle
jdbc:<subprotocol>:<subname> String dburl = "jdbc:oracle:thin:@tanna:1521:TPIO";
construction de l’url pour Oracle INT
private final String URLDBORACLE=
Connection conn = DriverManager.getConnection(dburl, "toto", "titi");
"jdbc:oracle:thin:@tanna:1521:TPIO";
connexion à l’url avec un (user, passwd)=(toto, titi)
private final String URLDBMYSQL=
"jdbc:mysql//localhost/mediatheque";
Création d'un Statement Exécution d'une requête (1/2)
Un objet Statement symbolise une instruction SQL 3 types d'exécutions :
3 types de statement : executeQuery : pour les requêtes qui retournent un ensemble
(SELECT)
Statement : requêtes simples
executeUpdate : pour les requêtes INSERT, UPDATE, DELETE,
PreparedStatement : requêtes précompilées
CREATE TABLE et DROP TABLE
CallableStatement : procédures stockées execute : pour quelques cas rares (procédures stockées)
Création d'un Statement :
Statement stmt = conn.createStatement();
Bases de Données 6
Exécution d'une requête (2/2) Récupération des résultats (1/2)
Exécution de la requête : executeQuery() renvoie un ResultSet
Le RS se parcourt itérativement ligne par ligne
String myQuery = "SELECT code, titre, auteur " +
"FROM Document " +
Les colonnes sont référencées par leur numéro ou par leur nom
"WHERE (auteur LIKE ’L%') " + L'accès aux valeurs des colonnes se fait par les méthodes
getXXX() où XXX représente le type de l'objet
"ORDER BY titre";
ou bien par un getObject suivi d’une conversion explicite
ResultSet rs = stmt.executeQuery(myQuery);
Pour les types longs, on peut utiliser des streams.
Récupération des résultats (2/2) Exemple de SQL dynamique
java.sql.Statement stmt = conn.createStatement(); class Document { ...
ResultSet rs = stmt.executeQuery("SELECT code, titre, public static int updateDocument(int num, String
auteur from Document where auteur like ‘L%’"); nom) {
try {
while (rs.next()) Class.forName("oracle.jdbc.driver.OracleDriver");
{ String dburl ="jdbc:oracle:thin:@tanna:1521:TPIO";
// print the values for the current row. Connection conn = DriverManager.getConnection(dburl,
int i = rs.getInt("code"); "toto", "titi");
conn.setAutoCommit(false);
String s1 = rs.getString("titre");
PreparedStatement pstmt = conn.preparedStatement("UPDATE
String s2 = rs.getString("auteur"); Document SET auteur=? WHERE code=?");
System.out.println("ROW = " + i + " " + s1 + " " +s2); pstmt.setString(1, nom);
} pstmt.setInt(2, num);
int nbLignesModifiees = pstmt.executeUpdate();
if (nbLignesModifiees == 1) conn.commit();
else conn.rollback();
} catch (Exception e) {e.printStackTrace();}
}
28
Bases de Données 7
Accès aux méta-données Exemple de MetaData
class HTMLResultSet {
La méthode getMetaData() permet d'obtenir les méta- données private ResultSet rs;
d'un ResultSet. public HTMLResultSet (ResultSet rs){this.rs=rs;}
public String toString() {
Elle renvoie des ResultSetMetaData. StringBuffer out = new StringBuffer();
On peut connaître : out.append("<TABLE>");
Le nombre de colonne : getColumnCount()
ResultSetMetaData rsmd = rs.getMetaData();
int numcols = rsmd.getColumnCount();
Le nom d'une colonne : getColumnName(int col)
out.append("<TR>");
Le type d'une colonne : getColumnType(int col) for (int i=0;i<numcols;i++) {
... out.append("<TH>").append(rsmd.getColumnName(i));
}
out.append("</TR>");
...
}
}
30
Exemple d'interrogation JDBC Exemple d'insertion JDBC
import java.sql.*;
import java.sql.*;
class InsereDocument{
class TestDoc { public static void main (String args [])throws SQLException,
public static void main (String args []) throws SQLException, ClassNotFoundException {
ClassNotFoundException { Class.forName("oracle.jdbc.driver.OracleDriver");
Class.forName("oracle.jdbc.driver.OracleDriver"); Connection conn =
DriverManager.getConnection("jdbc:oracle:thin:@tanna:152
Connection conn = DriverManager.getConnection 1:TPIO", "toto", "titi");
("jdbc:oracle:thin:@tanna:1521:TPIO", "toto", "titi"); int codeDoc = 100;
Statement stmt = conn.createStatement(); String titreDoc = "un long dimanche de fiancailles";
ResultSet rset = stmt.executeQuery("select code, titre from String auteurDoc = "Japrisot";
Document"); Statement stmt = conn.createStatement();
int res = stmt.executeUpdate ("INSERT INTO Document(code,
while (rset.next()) { titre, auteur) VALUES(" + codeDoc + ", ‘ " + titreDoc +
System.out.print (rset.getInt(1)); "’, ‘" + auteurDoc + "’) ");
System.out.print (" "); if (res == 1) {
System.out.println("\nInsertion reussie\n");
System.out.println (rset.getString(2)); conn.commit();
} }else conn.rollback();
} }
} }
31 32
Bases de Données 8
Correspondance de type SQL/Java Evolution de JDBC
Type SQL Type Java Type Java retourné Méthode
JDBC 1.0 (janvier 1996)
par getObject() recommandée au JDBC 2.0 (Mars 1998)
lieu de getObject()
numeric Java.Math.BigDecimal Java.Math.BigDecimal Java.Math.BigDecimal JDBC 2.1 (2000)
GetBigDecimal()
integer int Integer Integer getInt()
Extensions de JDBC 2.x
parcours avant/arrière d’un ResultSet
float double Double Double getDoubel() mise à jour depuis un ResultSet
batch de plusieurs ordres SQL
char, varchar String String String getString()
support des types SQL3
date Java.sql.Date Java.sql.Date Java.sql.Date getDate() validation 2 phases via XA
notion de DataSource et utilisation de JNDI
pool de connexion, cache sur le client
33 34
Introduction de la persistance Structuration du code
Comment intégrer le code JDBC qui va Constructeur : chargement d’objet
assurer chargement et déchargement des « destructeur » : suppression d’objet
objets Java depuis la BD Opérations de mise à jour : modification
En structurant au mieux le code (limiter le nombre d’objets (attention à la granularité pour les
d’opérations à modifier)
transactions)
Quel(s) objet(s) charger et quand ?
quel(s) objet(s) décharger et quand ?
35 36
Bases de Données 9
Chargement / déchargement Chargement / déchargement (2)
Statique
Chargement Adapté aux petits volumes de données
Statique : constructeur de « collections » Faible taux de mises à jour
Dynamique : constructeur d’objet (nécessité d’une Simple à mettre en œuvre
clé pour sélectionner l’objet)
Dynamique
Déchargement
Adapté aux volumes de données importants
Statique : à la fin du programme (attention aux
Fort taux de mises à jour
pertes d’infos)
Meilleure résistance aux fautes
Dynamique : dans les opérations de mise à jour
Plus compliqué à programmer
37 38
Bases de Données 10