Domanda

Non so molto del modello di repository DDD, ma l'implementazione in primavera mi è confusione.

public interface PersonRepository extends JpaRepository<Person, Long> { … }

Man mano che l'interfaccia estende JParePository (o MongoDbrepository ...), se si cambia da un DB all'altro, devi anche cambiare l'interfaccia.

Per me un'interfaccia è lì per fornire un po 'di astrazione, ma qui non è tanto astratto ...

Sai perché i dati primaverili funzionano così?

È stato utile?

Soluzione

Hai ragione, un'interfaccia è un'astrazione su qualcosa che funziona equivale a tutte le classi di implementazione, da un punto di vista esterno.

Ed è esattamente quello che succede qui:

  • JParePository è una visione comune di tutti i tuoi repository JPA (per tutte le diverse entità), mentre MongoDbrepository è la stessa per tutte le entità MongoDB.
  • Ma JParepository e MongoDbrepository non hanno nulla in comune, tranne le cose che sono definite nelle super interfacce comuni:

    • org.springframework.data.repository.pagingandsortingRepository
    • org.springframework.data.repository.repository

Quindi per me sembra normale.

Se si utilizzano le classi che implementano il tuo repository, utilizzare PagingandSortingRepository o repository se si desidera essere in grado di passare da un'implementazione JPA a un'implementazione basata su documenti (scusa ma non riesco a immaginare un caso d'uso del genere - comunque). E, naturalmente, l'implementazione del repository dovrebbe implementare l'interfaccia corretta (JParePository, MongoDbrepository) a seconda di cosa sia.

Altri suggerimenti

Il ragionamento alla base di questo è chiaramente indicato in questo post sul blog http://blog.springsource.com/2011/02/10/getting-started-with-spring-data-jpa/.

Definizione di questa interfaccia ha due scopi: in primo luogo, estendendo JParePository otteniamo un sacco di metodi CRUD generici nel nostro tipo che consente di salvare gli account, eliminarli e così via. In secondo luogo, ciò consentirà all'infrastruttura del repository JPA dei dati di Spring di scansionare il percorso di classe per questa interfaccia e creare un bean a molla per esso.

Se non ti fidi delle fonti così vicine alla fonte (gioco di parole previsto) potrebbe essere una buona idea leggere anche questo post http://www.brucephillips.name/blog/index.cfm/2011/3/25/using-spring-data-jpa-to-redoced-data-access-coding.

Ciò che non avevo bisogno di codificare è un'implementazione dell'interfaccia di PersonRepository. Spring creerà un'implementazione di questa interfaccia e renderà disponibile un fagiolo di PersonRepository per essere autowired nella mia classe di servizio. Il Bean PersonRepository avrà tutti i metodi CRUD standard (che saranno transazionali) e restituiscono oggetti della persona o raccolta di oggetti persone. Quindi, utilizzando Spring Data JPA, ho salvato scrivendo la mia classe di implementazione.

Fino a M2 dei dati primaverili abbiamo richiesto agli utenti di estendere JpaRepository Per i seguenti motivi:

  1. L'infrastruttura di scansione di ClassPath ha raccolto solo interfacce che estendono quell'interfaccia come si potrebbe utilizzare i dati di primavera JPA e Spring Data Mongo in parallelo e hanno entrambi indicato lo stesso pacchetto in cui non sarebbe chiaro quale archivia per creare il proxy. Tuttavia, dal momento che RC1 lasciamo semplicemente questo onere per lo sviluppatore poiché pensiamo che sia un caso piuttosto esotico e il vantaggio di usare Repository, CrudRepository O gli Outweights simili è lo sforzo che devi intraprendere nel caso angolare appena descritto. Puoi usare exclude e include Elementi nello spazio dei nomi per ottenere un controllo a grana più fine su questo.
  2. Fino a M2 abbiamo avuto la transazionalità applicata ai metodi CRUD ridisegnando i metodi CRUD e annotarli con @Transactional. Questa decisione a sua volta è stata guidata dall'algoritmo AnnotationTransactionAttributeSource Usi per trovare la configurazione delle transazioni. Dato che volevamo fornire all'utente la possibilità di riconfigurare le transazioni semplicemente ridisegnando un metodo CRUD nell'interfaccia del repository in calcestruzzo e applicando @Transactional su di esso. Per RC1 abbiamo deciso di implementare un'usanza TransactionAttributeSource Essere in grado di riportare le annotazioni all'implementazione del repository CRUD.

Per farla breve, ecco cosa si riduce a:

A partire da RC1 non è più necessario estendere l'interfaccia del repository specifico dell'archivio, tranne tu vuoi…

  1. Uso List-Stembled Access a findAll(…) invece di Iterable-basato uno nelle interfacce di repository più core (sebbene tu possa semplicemente ridipingere i metodi pertinenti in un'interfaccia di base comune per restituire Listanche s)
  2. Vuoi utilizzare i metodi specifici per JPA come saveAndFlush(…) e così via.

Generalmente sei molto più flessibile riguardo all'esposizione dei metodi CRUD poiché RC1 come puoi anche estendere il Repository interfaccia marcatore e aggiungi selettivamente i metodi CRUD che si desidera esporre. Poiché l'implementazione di supporto implementerà comunque tutti i metodi di PagingAndSortingRepository Possiamo ancora instradare le chiamate all'istanza:

public interface MyBaseRepository<T, ID extends Serializable> extends Repository<T, ID> {

  List<T> findAll();

  T findOne(ID id);
}

public interface UserRepository extends MyBaseRepository<User, Long> {

  List<T> findByUsername(String username);
}

In questo esempio definiamo MyBaseRepository per esporre solo findAll() e findOne(…) (che verrà instradato nell'istanza che implementa i metodi CRUD) e il repository concreto che aggiunge un metodo Finder ai due CRUD.

Per maggiori dettagli su quell'argomento, consultare il Documentazione di riferimento.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top