polo analisi ed esempi di persistenza in java. il progetto polo è unapplicazione crm ( customer...
Post on 02-May-2015
216 Views
Preview:
TRANSCRIPT
POLO Analisi ed esempi di persistenza in Java
Il Progetto
Polo è un’applicazione CRM (Customer Relationship Managemen) in Java, in via di sviluppo tramite lavori di Tesi di studenti della facoltà di Ingegneria Informatica del Politecnico di Milano e Como.Inoltre è un progetto pubblicato su SourceForge [http://www.sourceforge.org] ed è fruibile da tutti con licenza GPL (General Public License).
Come nasce
Polo nasce dall’esigenza delle aziende, con natura di tipo commerciale, che si avvalgono per la distribuzione di numerosi Agenti dei quali si vuole organizzare/programmare le diverse attività.Polo ha quindi 3 tipologie di utenza:- i singoli agenti - gli addetti al call center- l’amministratore del sistema
Gli utenti
In particolare: - i singoli agenti si collegano tramite computer
portatile, smart phone al server centrale per aggiornare i loro appuntamenti o per inviare il resoconto delle attività svolte.
- gli addetti al call center aggiornano in tempo reale gli appuntamenti degli agenti utilizzando dalle loro postazioni l’interfaccia web
- l’amministratore del sistema gestisce i diversi gruppi utenti, le tipologie degli appuntamenti
Architettura
Componenti
• Modulo client sviluppato in J2ME• Modulo server sviluppato in tecnologia
J2EE
Tecnologie impiegate: framework Struts, Hibernate,MeFast
Situazione attuale
• Modulo client sviluppato in J2ME• Modulo server sviluppato in PHP. Esiste
anche una versione Java, con modello dei dati DTO, con funzionalità limitate.
Migrazione
• Sviluppo e miglioramento del framework MeFast, per lo sviluppo rapido in J2ME
• Porting della parte server da PHP a Java• Primo porting modello DTO verso
l’utilizzo di Hibernate
Flusso Dati
XMLHTTP Request/Response
HTMLHTTP Request/Response
Apache HTTP oppure JbossMySQL
Bisogna aver chiaro…
Cos’è un oggetto?un oggetto è una "raccolta" di dati e procedure che agiscono sui dati.
Le procedure vengono, in questo caso, indicate con il termine di metodi.
L'unione di dati e metodi costituisce un mezzo più potente e preciso per rappresentare nel software gli oggetti del mondo reale.
Persistenza dei dati attuale
• Parte SERVER Attuale basata su DTO (Data Transfer Object)
I DAO (Data Access Object) non sono altro che degli oggetti che forniscono all’esterno i metodi per l’accesso a dati persistenti.I dati vengono incapsulatati in altri oggetti detti DTO (Data Transfer Object) che veicolano l’informazione proveniente dalle sorgenti dati.Ciò avviene in maniera del tutto trasparente, ed un eventuale modulo delegato alla logica di business non si deve preoccupare dell’accesso ai dati in quanto manipola semplici oggetti.Infine va sottolineato che le eventuali eccezioni che possono essere sollevate in un tipico accesso a DBMS (quindi eccezioni SQL) sono completamente mascherate da eccezioni proprie dei DAO.
Esempio DTO 1/2// da UtenteDto.java
public class UtenteDto {
private String nome;private String cognome;private String user;private String comune;private String provincia;
public String getNome(){return nome;
}public void setNome(String nome){
this.nome=nome;}public String getCognome(){
return cognome;}public void setCognome(String cognome){
this.cognome=cognome;}…
}
Esempio DTO 2/2public UtenteDto getUtente(Integer id_utente) { String sql = "SELECT * FROM utente WHERE id=“+id_utente; try{
ResultSet rs = stmt.executeQuery(sql);if (rs.first()==false)
{System.out.println("array non trovato");}else{
rs.first();while(rs.isAfterLast() == false){ dt = new UtenteDto(); dt.setUser(rs.getString("user")); dt.setNome(rs.getString("nome")); dt.setCognome(rs.getString("cognome")); dt.setComune(rs.getString("comune")); dt.setProvincia(rs.getString("provincia")); rs.next();
} } }catch (SQLException e) {
System.out.println(e.getMessage()); } return dt; }
Persistenza dei dati finale
• Parte SERVER Finale basata su Hibernate
Hibernate (spesso chiamato H8) è una soluzione Object-relational mapping (ORM) per il linguaggio di programmazione Java.È un software free, open source e distribuito sotto licenza LGPL. Hibernate fornisce un framework semplice da usare, che mappa un modello di dominio orientato agli oggetti in un classico database relazionale.
Hibernate 1/3
Hibernate non si occupa solo di mappare dalle classi Java in tabelle del database (e da tipi Java ai tipi SQL), ma fornisce anche degli aiuti per le query di dati, il recupero di informazioni e riduce significativamente il tempo che altrimenti sarebbe speso lavorando manualmente in SQL e con JDBC.
I mappaggi oggetto/relazione vengono definiti in un documento XML. Il documento di mappaggio è progettato per essere leggibile e modificabile a mano. Il linguaggio di mappaggio è java-centrico, nel senso che i mappaggi sono costruiti intorno alle dichiarazioni delle classi persistenti, non sulle dichiarazioni delle tabelle.
Hibernate 2/3
Oggetti persistenti e collezioni: sono oggetti di corta durata, che contengono stato persistente e funzioni applicative. Potrebbero essere normali oggetti POJO/Javabeans, con l'unica particolarità che in un dato momento sono associati con (esattamente) una Session. Nel momento in cui la Session viene chiusa, verranno staccati e saranno liberi di essere usati in qualsiasi strato applicativo (ad esempio direttamente come oggetti di trasferimento dei dati da e allo strato di presentazione).
Hibernate 3/3
Le classi persistenti sono quelle che in un'applicazione implementano le entità del problema di business (ad esempio Customer e Order in una applicazione di e-commerce). Le classi persistenti hanno, come implica il nome, istanze transienti ed istanze persistenti memorizzate nel database.
Hibernate funziona meglio se queste classi seguono alcune semplici regole, conosciute anche come il modello di programmazione dei "cari vecchi oggetti java" (in inglese e nel seguito si usa l'acronimo POJO che sta per "Plain Old Java Object").
Esempio Hibernate 1/2
// da Utente.hbm.xml
<?xml version="1.0" encoding='UTF-8'?><hibernate-mapping package="it.digi.polo.hibernate"> <class name="Utente" table="UTENTE"> <id name="idUtente" column="ID_UTENTE" type="java.lang.Integer"> <generator class=“native"/> </id> <property name="user" column="USER" type="java.lang.String" /> <property name="pass" column="PASS" type="java.lang.String" /> <property name="cognome" column="COGNOME" type="java.lang.String" /> <property name="nome" column="NOME" type="java.lang.String" />
<set name=“appuntamenti" inverse="true"> <key column="ID_UTENTE"/> <one-to-many class=“Appuntamenti"/> </set>
</class> </hibernate-mapping>
Esempio Hibernate 2/2
// da UtenteManagement.java
public Utente getUtente(Integer id_utente) {try{
Session hibSession=HibernateSessionFactory.currentSession(); Utente user=(Utente)hibSession.get(Utente.class, id_utente);
} catch (SQLException e) {
System.out.println(e.getMessage()); }return user;
}
In alternativa, esempio HQL:
Query q = hibSession.createQuery("from Utente ut where ut.idUtente = ?");q.setInteger(0, id_utente);Utente user = (Utente) query.uniqueResult();
Persistenza dei dati lato Client
Per la memorizzazione dei dati da parte del modulo client (dispositivo mobile con risorse limitate) si è scelto di sviluppare un framework ad hoc: MeFast
MeFast si occupa di strutturare/memorizzare le informazioni a partire da oggetti, in un file sequenziale e di recuperarne al suo interno, tramite una serie di filtri, i dati richiesti
Architettura MEFast
MEFast(XMLObj.java)
XML
XML
RecordSet
RecordSet
Struct
MEFast(DbWriter.java)
File
File
RecordSet
RecordSet
StructApplicazioneFrameworkSistemi persistenti
Esempio MEFast 1/4
// dalla Struct
intervento_testata.struttura.Addelement(4,"key_attivita_id");intervento_testata.struttura.Addelement(4,"key_cliente_id");intervento_testata.struttura.Addelement(2,"data");intervento_testata.struttura.Addelement(3,"ora_inizio");intervento_testata.struttura.Addelement(3,"ora_fine");intervento_testata.struttura.Addelement(1,"tipo_att_id");intervento_testata.struttura.Addelement(1,"chiusa_aperta");intervento_testata.struttura.Addelement(1,"nuovo");intervento_testata.struttura.Addelement(1,"mod");intervento_testata.struttura.Addelement(1,"del");
Esempio MEFast 2/4
//da DbWriter.java
public void DbaddRecordSet(Recordset recordset){byte[] raccolta;ByteArrayOutputStream strmBytes = new ByteArrayOutputStream();DataOutputStream strmDataType = new DataOutputStream(strmBytes);try {
for (int i = 0; i < recordset.size(); i++) { switch (Struttura.ReturnType(i)) {
case 1:
strmDataType.writeInt(Integer.parseInt( recordset.Campo(i).toString())); break;
case 2: DateManager datemgr=new DateManager();
strmDataType.writeLong(datemgr.StrLong( recordset.Campo(i).toString())); break;
Esempio MEFast 3/4
case 3: HourManager hourmgr=new HourManager();
strmDataType.writeLong(hourmgr.H_StrLong( recordset.Campo(i).toString()));
break;
case 4: strmDataType.writeUTF( recordset.Campo(i).toString());
break;
default: break;
} } strmDataType.flush(); raccolta= strmBytes.toByteArray(); Database.addRecord(raccolta, 0, raccolta.length); strmBytes.reset(); strmBytes.close(); strmDataType.close();} catch (Exception e) { e.printStackTrace(); }
}
Esempio MEFast 4/4
//da XmlObj.java
public Recordset[] XmlSelect(int inizio,int num,Struct strutt) throws DbException {struttura=strutt;
Recordset [] Records = null ;e.printStackTrace();
}
if(Records.length==0) { System.err.println("nn"); throw new DbException(2,"Nessun dato");
return Records;
}
Commento al codice
La classe che legge l’xml ritorna un’ array di oggetti Recordset che possono essere scritti tramite il metodo Write() direttamente sul database.
La classe di lettura riceve come parametro di ingresso la classe Struct che definisce i tipi dei campi che devono essere letti.
La classe Struct in MeFast rappresenta il mappaggio del db, definisce i tipi dei dati e il nome dei campi
Insorgenza di problemi
1. Mismatch del paradigma2. Problema della granularità3. Problema dell’identità
Mismatch del paradigma
Problema riguardante la progettazione del modello di dati: svilupparlo seguendo il modello object-oriented o il modello relational-oriented, oppure, un modello di dati programmabile che riunisca entrambi?
Problema risolto con l'Object Relation Mapping, realizzato tramite dei file hbm.xml, fra gli oggetti e le reali tabelle del database, creando vere e proprie associazioni anche fra collezioni di oggetti ad una singola istanza, senza l'aggiunta di ulteriore codice nei corrispondenti moduli.
Soluzione
• Vecchia versione Polo – Popolamento manuale dei DTO attraverso
interrogazione sql alla base dati (con Join tra tabelle)
• Nuova versione Polo: uso di Hibernate– Utilizzo di oggetti POJO che permettono di persistere i
dati nelle tabelle relazionali mappate attraverso un file XML
– Utilizzo di comodi metodi per recuperare Set di oggetti collegati (ovvero record di tabelle relazionate)
• Soluzione proprietaria (Client)– Definizione strutture mediante mappaggio e interfaccia
a file vari per recuperare, mediante chiavi, le dipendenze
Problema della granularità
Riferito al problema della separazione degli attributi dello stesso oggetto su vari oggetti relazionali.
Es. Oggetto Java Location, rappresentante tutto quello che concerne la propria ubicazione (paese, città, indirizzo, ecc..), che potrebbe essere rappresentato come una singola tabella, oppure splittato su n tabelle ognuna rappresentante un attributo dell'oggetto.
Soluzione
• Vecchia versione Polo – Popolamento manuale dei DTO attraverso
interrogazione sql alla base dati (con Join tra tabelle)
• Nuova versione Polo: uso di Hibernate– Utilizzo di oggetti POJO che permettono di persistere i
dati nelle tabelle relazionali mappate attraverso un file XML
– Utilizzo di comodi metodi per recuperare Set di oggetti collegati (ovvero record di tabelle relazionate)
• Soluzione proprietaria (Client)– Definizione strutture mediante mappaggio e interfaccia
a file vari per recuperare, mediante chiavi, le dipendenze
Problema dell’identità
In SQL non esiste una metodologia che eguagli il metodo equals() oppure l'operatore ==.
Nel linguaggio relazionale l'identità è determinata dalle Primary-Keys, o in maniera del tutto più approfondita guardando l'identità fra opportune Foreign-Keys.
Soluzione
• Vecchia versione Polo– Costruzione di metodi isEqual() che verificano
tramite una query sql l’identità delle chiavi
• Nuova versione Polo– Mappaggi xml delle chiavi della tabella– Creazione di metodi per la verifica dell’uguaglianza
• Soluzione proprietaria (client)– Definizione di metodi di verifica mediante il recupero
di chiavi definite sui file. Metodi per scorrere il file sequenziale e trovare elementi con la chiave richiesta
Ora tocca a voi…
Esercizio: date queste classi, relazionate fra di loro come in figura, provate a implementarne il codice e il relativo mappaggio Hibernate immaginando di avere a disposizione una base dati relazionale per memorizzare le informazioni
Corso
StudenteEsame
0...n
0...n
1,1
0...n
Riferimenti
l.pelizzeni@digitelematica.it
top related