Nessun risultato. Prova con un altro termine.
Guide
Notizie
Software
Tutorial

JPA visuale con Eclipse e i Dali tools

Introduciamo il Dali Java Persistence Tools mostrando come semplificare/velocizzare lo sviluppo di applicazioni che utilizzano JPA in Eclipse.
Introduciamo il Dali Java Persistence Tools mostrando come semplificare/velocizzare lo sviluppo di applicazioni che utilizzano JPA in Eclipse.
Link copiato negli appunti

JPA 2 è la specifica Java per l'accesso, la persistenza e la gestione dei dati tra oggetti Java e database relazionali. Abbiamo già introdotto la specifica in articoli precedenti in cui abbiamo presentato un confronto con JDO e visto che uno dei principali motivi per cui JPA è preferibile è l'ampia popolarità che ha portato alla diffusione di diversi tools a supporto degli sviluppatori.

In questo articolo esaminiamo il Dali Java Persistence Tools di Eclipse, uno strumento utile a snellire lo sviluppo di applicazioni che richiedono il supporto di JPA. Esamineremo alcune delle principali funzionalità del tool e vedremo come impostare un nuovo progetto che supporti direttamente JPA o come convertire uno esistente in un progetto JPA.

Ci occuperemo anche di feature che consentono di velocizzare la creazione delle entità o di importarle direttamente dalle tabelle di un database già esistente.

Precondizioni

Per seguire gli esempi che faremo occorre avere installato il Java Development Kit (JDK 6), aver impostata la variabile d'ambiente JAVA_HOME e aggiornato il Path di sistema.

Inoltre daremo per acquisiti i concetti di base di JPA 2. Ecco due articoli importanti per approfondire o rinfrescare le conoscenze:

>> Leggi Introduzione a JPA e confronto con JDO

>> Leggi JPA 2: generare chiavi primarie e relazioni

In questi articoli troviamo qualche informazione in più su Hibernate che è l'implementazione di JPA che utilizziamo in coppia con il database relazionale HSQLDB (HyperSQL).

>> Leggi Introduzione a HyperSQL.

In allegato abbiamo il file di properties server.properties per inizializzare il database che utilizzeremo negli esempi seguenti.

Configurare Eclipse

I Dali Java Persistence Tools per Eclipse sono inclusi come parte dell'"Eclipse Web Tools Platform (WTP) 3.1", tools che si trovano inclusi negli Eclipse IDE for Java EE Developers a partire da Eclipse 3.5 Galileo, pertanto non occorrono ulteriori configurazioni o installazioni.

Quindi la via più semplice è lavorare direttamente con la versione JEE dell'IDE.

In alternativa, disponendo dei soli IDE di base (Eclipse Classic o Eclipse ID for Java Developers, a partire dal 3.5), è possibile scaricare il corrispondente Java EE Package.

Come ulteriore possibilità, se non si vuole effettuare l'installazione dell'intero Java EE Package, possiamo scaricare il Web Tools Platform per l'IDE in uso alla voce Help/Install New Software...

Ad esempio, per la versione Eclipse Indigo, occorrerà selezionare (Work with) la voce Indigo e selezionare il Web, XML, Java EE and OSGi Enterprise Development. Al suo interno sarà possibile spuntare il Dali Java Persistence Tools - JPA Support e avviare il download.

Per le versioni precedenti alla Indigo, selezionare l'update WTP dal sito (Work with) http://download.eclipse.org/webtools/updates/.

Impostare un progetto JPA

Negli articoli precedenti abbiamo già visto che è sufficiente un normale Java Project per utilizzare il supporto JPA. Eclipse con i Dali Java Persistence Tools, fornisce un insieme di strumenti utili a velocizzare le attività connesse con la persistenza.

Per iniziare a sperimentare il tooltik iniziamo con il creare un progetto JPA: (File > New > JPA Project oppure File > New > Project... > JPA > JPA Project). Occorrerà poi configurare alcune voci.

Nella prima schermata scegliamo il nome del progetto, ad esempio JPATestProject, e la versione di JPA (attualmente la 2.0). È possibile lasciare invariate le altre voci (ci viene chiesto ad esempio se le entità devono essere incluse nel file persistence.xml o scoperte in automatico).

Clicchiamo due volte sul pulsante Next passando alla schermata "JPA Facet". Qui possiamo scegliere la piattaforma JPA di riferimento. Se disponibile, scegliamo Hibernate (JPA 2.x), altrimenti possiamo utilizzare la voce Generic 2.0.

Occorre quindi scegliere il set di librerie dell'implementazione JPA. Scegliendo la voce Disable Library Configuration e ci assumiamo la responsabilità di importare le librerie successivamente. Scegliendo invece la voce User Library possiamo caricare o creare ex novo una libreria utente che accoglierà il set minimo di librerie di cui necessitiamo.

Se non è già disponibile una Libreria Utente idonea, come evidenziato dall'immagine seguente, scegliere l'opzione Manage libraries... quindi New o Import.

Figura 1. La schermata JPA Facet e il pulsante Manage libraries

JPA Facet e il pulsante Manage libraries

Una volta creata una Libreria Utente, i progetti JPA successivi potranno utilizzare direttamente questa libreria risparmiando il tempo necessario a caricare a mano i singoli Jar.

Scelto un nome, ad esempio "HibHSQL Libraries", senza spuntare la voce System library (a meno di non voler perdere inutilmente mezzo pomeriggio), possiamo caricare il set minimo di librerie già visto nell'articolo JPA 2 e la persistenza in Java. È possibile creare una Libreria Utente che includa sia le librerie dell'implementazione JPA di riferimento che i driver del database.

La voce Connection per ora può restare vuota (<None>). Ne scopriremo in seguito l'utilità.

Possiamo quindi premere Finish e osservare quanto prodotto. Il progetto inizializzato ospiterà in automatico la cartella META-INF con all'interno il file persistence.xml.

In generale, per ragioni di portabilità del progetto, è buona regola importare nel progetto stesso le librerie usate. Il JPA Project mette a disposizione la cartella "build", ma è possibile creare una nuova directory appositamente.

Quanto presentato finora è il caso standard nel quale si dispone di un database indipendente. È possibile fare riferimento a un embedded database messo a disposizione ad esempio da un Application Server. In questo caso occorrerà indicarlo nella prima schermata, alla voce Target runtime (ad esempio JBoss Runtime Server), per poi indicare le corrispondenti librerie (Library Provided by Target Runtime) nella terza schermata ("JPA Facet"). Ancora una volta, per l'impostazione del progetto non sarà necessario indicare esplicitamente la connessione.

Persistence XML Editor

L'XML è potente ma scomodo, soprattutto quando vogliamo popolare il file di configurazione come il persistence.xml. Per questo i Dali Tools mettono a disposizione un'interfaccia per agevolare l'inserimento dei dati.

Cliccando col tasto destro sul file persistence.xml, si potrà aprirlo in modalità Persistence XML Editor (persistence.xml > Open With > Persistence XML Editor).

Appariranno le informazioni su diverse schede. Per fare un po' di pratica, ricostruiamo il file properties.xml usato negli articoli precedenti precedenti.

La prima scheda è la scheda "General", contenente le informazioni sulle persistence-unit. Di default viene impostata una persistence-unit con il nome del progetto. Cambiamola in "testhsqldb". È interessante notare che, nonostante nei precedenti articoli su JPA abbiamo visto che è possibile avere in contemporanea più di una persistence-unit nel file persistence.xml, in questo caso l'azione verrebbe interpretata come un errore (nella sezione seguente vedremo come è possibile evitare il messaggio d'errore).

Nella scheda "Connection" modifichiamo il campo Transaction type, impostando Resource local.

Nella scheda "Properties" aggiungeremo (Add...) le seguenti voci:

Parametro Valore
hibernate.hbm2ddl.auto update
hibernate.connection.url jdbc:hsqldb:hsql://localhost/testdb1
hibernate.connection.username sa
hibernate.connection.password

Una volta salvato, il file persistence.xml sarà pronto. Cliccando sulla scheda "Source", sarà possibile vedere direttamente il codice XML. Se si dispone dell'Hibernate Settings, tra le schede troveremo anche "Hibernate" con le principali proprietà impostabili.

Figura 2. Persistence XML Editor, scheda Hibernate
Persistence XML Editor, scheda Hibernate

Nella prossima sezione vedremo come creare entità e relazioni.

JPA Entity

Possiamo ora pensare a introdurre la prima entità del progetto. Utilizziamo il wizard messo a disposizione dai JPA tools. Una volta creato un package nella cartella src, lo chiamiamo "jpatestpack", premere con il tasto destro sul package, quindi New > JPA Entity (oppure New > Other > JPA > JPA Entity).

Inseriamo il nome della classe, "EntityTest", premiamo su Next e osserviamo le opzioni che abbiamo a disposizione nella scheda successiva.

Figura 3. JPA Entity wizard, Entity Properties
JPA Entity wizard, Entity Properties

Possiamo personalizzare il nome della tabella (Table name), scegliere il tipo di accesso (Access type), e soprattutto aggiungere gli attributi di cui necessitiamo. Come primo esempio, ci limitiamo ad aggiungere (Add...) due campi:

Type Name
int id
String nome

Spuntiamo la voce Key per il primo campo, rendendolo chiave primaria dell'entità.

Cliccando su Finish, potremo esplorare l'entità realizzata automaticamente. Di default la classe:

  • implementa l'interfaccia Serializable,
  • contiene i metodi di get e set per gli attributi aggiunti dall'utente,
  • viene aggiunta in automatico come tag <class>, nella persistence-unit del persistence.xml (con relativo nome dell'entità).

Creare semplici entità è molto semplice, ottenendo un POJO senza dovere mettere mano al codice. È possibile immettere tipi complessi come un java.util.ArrayList, specificando anche il parametro della lista (ad esempio java.util.ArrayList <String>).

Segnalazione di warnings ed errori

Hibernate non richiede la presenza dei nomi delle entità nel file persistence.xml. Provando a rimuovere il tag <class> relativo all'entità appena creata, otterremo per risposta la segnalazione di un errore del tipo:

Class "jpatestpack.EntityTest" is mapped, but is not included in any persistence unit

Negli articoli precedenti abbiamo visto però che lavorando con Hibernate questo non è un errore, pertanto possiamo modificare le impostazioni del progetto affinché tale errore non venga sollevato.

Possiamo scegliere se ignorarlo, oppure se segnalarlo come Info o come Warning. Ad esempio potremmo segnalarlo con un Warning giusto per tenerne traccia nel caso si decidesse di cambiare il persistence provider.

Per modificare le impostazioni, accedere alle proprietà del progetto, selezionare la sottoscheda JPA > Errors/Warnings, abilitare le modifiche (Enable project specific settings), esplorare il campo Type e modificare la voce "Class is mapped, but is not a persistence unit:", impostando nel menu a tendina la voce Warning e dare l'OK.

Figura 4. Impostare la segnalazione dei warning
Impostare la segnalazione dei warning

L'errore lascerà il posto a un semplice Warning. Allo stesso modo potremo evitare che la presenza di più di una persistence-unit generi un messaggio d'errore agendo sulla voce: Project/Multiple persistence units defined.

JPA Perspective, chiavi primarie e relazioni

Abbiamo esaminato un primo insieme di possibilità che ci viene offerto dal Dali tools. Aprendo la prospettiva JPA avremo a disposizione l'intero spettro di possibilità. Se la prospettiva non è già attiva: Window > Open Perspective > JPA (eventualmente Window > Open Perspective > Other… > JPA)

Figura 5. Dettaglio della prospettiva JPA, in evidenza le schede Data Source Explorer e JPA Details

Dettaglio della prospettiva JPA

In basso a destra osserviamo la scheda JPA Details. Premendo con il tasto sinistro sul nome di una entità, vedremo che la scheda ci fornirà una serie di dettagli customizzabili. Avremo ad esempio la possibilità di trasformarla in una classe Embeddable, o potremo impostare delle politiche automatiche di generazione della chiave primaria (Primary Key Generation).

Premendo con il tasto sinistro sugli attributi dell'entità, la scheda mostrerà i dettagli del mapping dei campi. Avremo la possibilità di mappare l'attributo come Transient, o di indicare la presenza di una relazione, ad esempio del tipo One-to-One, o di specificare la politica di Fetch (di default impostata su Eager).

Relazioni

Creando una seconda entità, ad esempio EntityTest2, tra i tipi messi a disposizione dall'Entity Properties sarà presente anche il tipo dell'entità creata in precedenza, EntityTest. Potremo pertanto impostare il tipo di relazione che lega le due classi.

Ipotizziamo dunque che l'entità EntityTest2 possiede un campo del tipo EntityTest. Cliccandoci sopra con il tasto sinistro del mouse potremo impostare il tipo di relazione nella scheda JPA Details.

Agendo sulle impostazioni del mapping, possiamo aggiungere l'annotazione desiderata, nel nostro caso @OneToOne. Una volta scelta l'annotazione nella scheda verranno mostrati una serie di dettagli personalizzabili, come entità target, tipo di Fetch, l'eventuale politica di Cascade, la strategia di Join. Per il nostro esempio è possibile lasciare tutto invariato.

Nella prossima sezione vedremo come generare le entità a partire dalle tabelle.

Connessione al database e generazione delle entità dalle tabelle

Finora abbiamo sempre ottenuto la tabella partendo dall'entità. JPA Project ci mette a disposizione il passaggio inverso, ottenere le entità partendo dalle tabella di un database. Per poter adoperare questo strumento serve però una connessione al database e un supporto non generico da parte delle piattaforma. In questa sezione vedremo come impostare la connessione, ottenere un supporto specializzato, per poter infine ottenere le entità partendo da un database già esistente.

Connessione al database

Avevamo già visto durante la creazione del progetto la possibilità di connettersi a un database ma l'avevamo tralasciata. Questa possibilità di norma non è necessaria, per cui avevamo sorvolato l'argomento.

Entrati nelle proprietà del progetto, accediamo alla voce JPA. Alla voce Connection potremo aggiungere una connessione (o selezionare una aggiunta in passato).

Figura 6. Scelta della connessione e pulsate per creare nuove connessioni
Scelta della connessione

Scelto di aggiungere una connessione (Add connection...), selezioniamo il RDBMS cui siamo interessati (nel nostro caso HSQLDB), modifichiamo il nome proposto (se interessati a farlo) e premiamo su Next.

Se è la prima volta che effettuiamo la connessione, potremmo dover definire un nuovo driver (il pulsante New Driver Definition mostrato nell'immagine precedente). E, sempre se è la prima volta che effettuiamo la connessione, potremmo dover indicare la posizione dei driver hsqldb.jar. In tal caso, dalla scheda JAR List selezionare la voce hsqldb.jar e cliccare sul pulsante Edit Jar/Zip..., ciò consentirà di selezionare la posizione corretta del jar (è possibile trovarlo nella cartella hsqldb/lib).

Figura 7. Definizione dei driver
ALT_TEXT

A questo punto si aprirà una schermata che ci permetterà di impostare i parametri di connessione al database. Ipotizziamo di avere già disponibile un database attivo in modalità server. Ipotizzando che il database si chiami "db1", alias "testdb1", con user e password impostati sui valori default, dovremo impostare i seguenti campi:

Campo Valore
Database db1
Database location hsql://localhost/testdb1

Per verificare il corretto inserimento dei dati utilizzare il tasto Test Connection. Se il test ha successo possiamo premere sul tasto Finish.

Impostata la connessione, se non si è scelto di attivarla alla chiusura del wizard (Connect when the wizard completes), occorrerà premere su Connect e il database sarà connesso.

Se la prospettiva JPA è attiva, le connessioni appaiono in basso a sinistra, nella scheda Data Source Explorer. La connessione ci permetterà di esplorare ed eventualmente interrogare il database cui siamo connessi. Dalla scheda sarà possibile avviare e interrompere la connessione. E sarà possibile trovare le tabelle normalmente inserite nel percorso: db1/Catalogs/PUBLIC/Schemas/PUBLIC/Tables

Hibernate Settings

Volendo generare le entità dal database, occorrerà qualcosa di più del supporto generico offerto dall'IDE. Accedendo alle proprietà del progetto, osservare la voce Platform. Se è disponibile o già selezionata la voce Hibernate (JPA 2.x), una volta selezionata questa voce non occorre fare altro, è possibile passare al prossimo paragrafo.

Se invece la voce non è disponibile e si vuole procedere con la generazione delle entità dalle tabelle del database, occorrerà installare il supporto Hibernate sull'IDE Eclipse. Per farlo, è possibile accedere all'Eclipse Marketplace, cercare la versione di Hibernate Tools idonea al proprio IDE e installarla.

Una volta completato il processo di installazione e riavviato l'IDE, occorrerà impostare la voce Platform (proprietà del progetto, scheda JPA) su Hibernate. È possibile a questo punto che sarà necessario modificare alcune delle impostazioni relative ai messaggi d'errore JPA, come visto nella precedente sezione.

Se permane un errore relativo al progetto (Console configuration "" does not exist), sarà necessario impostare le configurazioni di Hibernate (incorrere in problematiche di questo tipo non è raro nei progetti già esistenti). Occorre per prima cosa andare nelle configurazioni della console:

Run -> Run Configurations...

e selezionare le impostazioni di Hibernate, come mostrato nella figura seguente:

Figura 8. Configurazione della console di Hibernate

Configurazione della console di Hibernate

Occorrerà creare una nuova configurazione (tasto destro su Hibernate Console Configuration, quindi premere New), scegliere il progetto cui applicarle (nel nostro caso il progetto JPATestProject), impostare come tipo (Type) JPA (jdk 1.5+) e impostare come Database Connection la voce [JPA Project Configured Connection]. Applicare le modifiche e accedere alle proprietà del progetto. Alla voce Hibernate Settings abilitare il supporto (Enable Hibernate support) e scegliere tra le configurazioni (Default Hibernate Console configuration) la configurazione appena creata.

Una volta premuto OK, è possibile che l'errore continui a rimanere. A questo punto effettuare un clean del progetto (Project -> Clean...). Se il problema permane, non rimane che spegnere l'IDE e riattivarlo.

Generate Entities from Tables

Impostata una connessione (non deve essere necessariamente attiva, è sufficiente che sia stata impostata e provata per verificarne il corretto funzionamento) e impostato correttamente il supporto della piattaforma, siamo finalmente in grado di generare le entità partendo direttamente dalle tabelle.

Premendo con il tasto destro sul progetto troveremo tra le scelte la voce JPA Tools > Generate Entities from Tables...

Una volta scelto il package di destinazione (se scelto un package non esistente verrà creato automaticamente), sarà possibile utilizzare la configurazione della console già impostata, oppure (rimuovendo la spunta dalla voce Use Console Configuration), sarà possibile scegliere una specifica connessione al database. È possibile lasciare invariato l'autodetect per il dialetto del database.

Premuto il tasto Finish, le entità saranno importate nel progetto. A questo punto è possibile la presenza di alcune entità ripetute o eventuali segnalazioni di errori dovute al disallineamento tra il file persistence.xml e le entità, nel caso in cui non sia stata disattivata la segnalazione di errore riguardante la presenza di entità non mappate sul file persistence.xml.

SQL statements e Named Queries

Tra gli strumenti messi a disposizione dalla prospettiva JPA c'è l'editor per la scrittura ed esecuzione di statements SQL. Di norma può essere utilizzato come un'alternativa al Database Manager, con il vantaggio di non richiedere una finestra esterna all'IDE. Per attivare l'editor occorrerà premere sul pulsante Open scrapbook to edit SQL statements, presente nella scheda Data Source Explorer, cerchiato in rosso nell'immagine seguente in basso a sinistra.

Figura 9. SQL statements, gli elementi principali

SQL statements, gli elementi principali

L'immagine evidenzia i principali elementi di interesse. Premuto il pulsante indicato, si aprirà il Connection profile (ovale rosso in alto) che chiederà gli estremi della connessione. Viene richiesto tipo, nome della connessione e schema del database. È sufficiente inserire il nome della connessione scegliendola tra quelle già impostate, il tipo verrà individuato automaticamente. Se le tabelle che vogliamo interrogare sono pubbliche, non è nemmeno necessario scegliere lo schema. È però necessario che la connessione sia avviata (è possibile avviarla dal Data Source Explorer).

Ora è possibile scrivere una interrogazione nella scheda SQL Scrapbook. Per verificarne le funzionalità possiamo inserire una query semplice, del tipo:

select * from EntityTest

Premendo con il tasto destro sulla scheda SQL Scrapbook e scegliendo l'opzione Execute Current Text, sarà possibile eseguire la query. I risultati verranno presentati nella scheda SQL Results. La scheda Status mostrerà alcuni dati statistici come il tempo necessario per l'esecuzione, mentre la scheda ResultX mostrerà il risultato dell'interrogazione.

Named Queries

Per la creazione di Named Queries, una volta selezionata una entità, sarà possibile aggiungerne una dalla scheda JPA Details. Esplorando il menu Queries, aggiungere (Add...) una query impostandone il nome e il tipo (Named Query o Named Native Query). Selezionata la query aggiunta, verranno visualizzati nella stessa scheda ulteriori dettagli e la possibilità di specificare la forma della query.

Convertire un progetto Java in un progetto JPA

Abbiamo visto che è possibile lavorare con normali progetti Java, ma che i tools del JPA Project possono risultare comodi, soprattutto nel caso di grossi progetti. Può risultare utile allora convertire un progetto Java già esistente in un progetto JPA. Per convertire un progetto esistente premere con il tasto destro sul progetto e scegliere l'opzione Configure > Convert to JPA Project...

Spuntare la voce JPA (di norma dovrebbe essere già spuntata), premere Next due volte e... ritorneremo alla schermata "JPA Facet" che ormai ci è divenuta familiare. A questo punto potremo specificare la piattaforma, le librerie e la connessione, tutti task già affrontati in precedenza.

Una volta terminato di impostare la schermata possiamo premere FINISH e il progetto verrà convertito. Potrebbe essere sollevato qualche errore (ad esempio il solito errore dovuto all'assenza del mapping delle entità nel file persistence.xml o qualche imprecisione nel file di persistenza), ma in compenso se si imposterà la piattaforma Hibernate le impostazioni Hibernate (Hibernate Settings) verranno impostate in automatico.

Perché utilizzare un progetto JPA

Abbiamo già visto che è possibile utilizzare JPA con un comune progetto Java. Perché allora ricorrere al progetto JPA? Un progetto JPA permette di risparmiare tempo, ad esempio evitando la necessità di scrivere i POJO, fornendo dei comodi wizard per l'impostazione delle entità o ottenendo le entità partendo direttamente dalle tabelle di un database. Inoltre la panoplia di strumenti messi a disposizione spesso evita la necessità di ricorrere a interfacce esterne all'IDE, ad esempio l'editor per SQL Statements consente di minimizzare l'uso del Database Manager.

Se si vuole cercare un difetto, l'unico riscontrato riguarda il tempo necessario ad estendere le funzionalità del'IDE. Se abbiamo un IDE per progetti JEE, probabilmente non occorrerà aggiungere niente, mentre se lavoriamo con un IDE classico e sarà necessario un po' di tempo per installare Dali Tools e supporti complementari per le funzionalità avanzate. Considerando i vantaggi precedentemente descritti, non è comunque tempo perso.

Ti consigliamo anche