Il DAO con JPA e Spring

1. Panoramica

Questo articolo mostrerà come implementare il DAO con Spring e JPA . Per la configurazione principale di JPA, vedere l'articolo su JPA con Spring.

2. Niente più modelli primaverili

A partire dalla Spring 3.1, JpaTemplate e il corrispondente JpaDaoSupport sono stati deprecati a favore dell'utilizzo dell'API Java Persistence nativa.

Inoltre, entrambe queste classi sono rilevanti solo per JPA 1 (da JpaTemplate javadoc):

Nota che questa classe non è stata aggiornata a JPA 2.0 e non lo sarà mai.

Di conseguenza, ora è consigliabile utilizzare l'API Java Persistence direttamente invece di JpaTemplate .

2.1. Traduzione di eccezione senza il modello

Una delle responsabilità di JpaTemplate era la traduzione delle eccezioni, traducendo le eccezioni di basso livello in eccezioni Spring generiche di livello superiore.

Senza il modello, la traduzione delle eccezioni è ancora abilitata e completamente funzionante per tutti i DAO annotati con @Repository . Spring lo implementa con un postprocessore bean che avviserà tutti i bean @Repository con tutto il PersistenceExceptionTranslator trovato nel Container.

È anche importante notare che il meccanismo di traduzione delle eccezioni utilizza i proxy : affinché Spring sia in grado di creare proxy attorno alle classi DAO, questi non devono essere dichiarati definitivi .

3. Il DAO

Innanzitutto, implementeremo il livello di base per tutti i DAO, una classe astratta che utilizza generici e progettata per essere estesa:

public abstract class AbstractJpaDAO { private Class clazz; @PersistenceContext EntityManager entityManager; public final void setClazz( Class clazzToSet ){ this.clazz = clazzToSet; } public T findOne( long id ){ return entityManager.find( clazz, id ); } public List findAll(){ return entityManager.createQuery( "from " + clazz.getName() ) .getResultList(); } public void create( T entity ){ entityManager.persist( entity ); } public T update( T entity ){ return entityManager.merge( entity ); } public void delete( T entity ){ entityManager.remove( entity ); } public void deleteById( long entityId ){ T entity = findOne( entityId ); delete( entity ); } }

Il principale aspetto interessante qui è il modo in cui viene iniettato EntityManager , utilizzando l' annotazione @PersistenceContext standard . Dietro le quinte, questo è gestito dal PersistenceAnnotationBeanPostProcessor , che elabora l'annotazione, recupera il gestore entità JPA dal contiene e lo inietta.

Il post processore di persistenza viene creato esplicitamente definendolo nella configurazione o automaticamente, definendo context: annotation-config o context: component-scan nel namespace config.

Inoltre, si noti che l'entità Class viene passata nel costruttore da utilizzare nelle operazioni generiche:

@Repository public class FooDAO extends AbstractJPADAO implements IFooDAO{ public FooDAO(){ setClazz(Foo.class ); } }

4. Conclusione

Questo tutorial ha illustrato come impostare un livello DAO con Spring e JPA , utilizzando la configurazione basata su XML e Java. Abbiamo anche discusso perché non utilizzare JpaTemplate e come sostituirlo con EntityManager . Il risultato finale è un'implementazione DAO leggera e pulita, quasi senza fare affidamento in fase di compilazione su Spring.

L'implementazione di questo semplice progetto può essere trovata nel progetto GitHub: questo è un progetto basato su Maven, quindi dovrebbe essere facile da importare ed eseguire così com'è.