Mam WZP @MappedSuperClass
oraz @Entity
rozciągający go:Jak wdrożyć repozytorium Wiosna danych dla @MappedSuperclass
@MappedSuperclass
public class BaseClass {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
@Column
private Boolean active;
//getters & setters
}
@Entity
public class Worker extends BaseClass{
@Column
private String name;
//getters & setters
}
active
pole klasy bazowej jest flaga dla podmiotów dzieci. Tylko te aktywne powinny być załadowane do aplikacji. Wtedy pisałem ogólny Spring Data Proxy interface:
public interface Dao<T extends BaseClass, E extends Serializable> extends
CrudRepository<T, E> {
Iterable<T> findByActive(Boolean active);
}
i ten jest interfejs, który powinien być dla Worker
dostępu do danych, właściwie rozszerzenie poprzedniej:
@Transactional
public interface WorkerDao extends Dao<Worker, Long>{}
Cóż, teraz w moim warstwy logiki Zaimplementowałem klasę abstrakcyjną, która będzie owijała wspólny kod dla operacji CRUD nad moimi elementami. Będę miał usługę dla każdego z nich, ale chcę tylko dziedziczyć po abstract
. Chcę połączyć konkretne repozytorium dla każdej usługi i przekazać ją nadklasie przy użyciu metody abstract
. To jak moja nadklasą jest realizowany:
public abstract class GenericService<E extends BaseClass>{
public abstract Dao<E, Long> getDao();
//Here I've got some common operations for managing
//all my application classes, including Worker
}
Problemem jest to, że metoda getDao()
używa parametru E
klasy, który jest gwarantowany tylko być dzieckiem BaseClass
a nie javax.persistence.Entity
. Gdy próbuję otworzyć DAO z mojego realizacji niestandardowych usług otrzymuję ten błąd:
Caused by: java.lang.IllegalArgumentException: Could not create query metamodel for method public abstract java.lang.Iterable com.mycompany.model.daos.interfaces.Dao.findByActive(java.lang.Boolean)! at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:93)
Caused by: java.lang.IllegalArgumentException: Not an entity: class com.mycompany.model.BaseClass at org.hibernate.jpa.internal.metamodel.MetamodelImpl.entity(MetamodelImpl.java:203)
co ma sens, ponieważ E
jest zdefiniowany jako dziecko BaseClass
. Kompilator pozwala mi napisać to zbyt:
public abstract class GenericService<E extends BaseClass && Entity>
Jednakże pojawia się błąd w Serwisie dziecko, które mówi Worker
klasa nie jest zgodny z podpisem na E
. Czy ktoś wie, jak rozwiązać ten problem?
*, która jest zagwarantowana tylko być klasy bazowej * Nie powinno być typem, który konkretne określa kierownik w tym sprawa "Pracownik". – cy3er
@ cy3er correct. To gwarantuje, że jest dzieckiem "BaseClass". Jednak JPA szuka '@ Entity', a' BaseClass' jest zwykłą '@ MappedSuperclass'. –
[To podobne pytanie] (http: // stackoverflow.com/questions/21415551/generic-spring-data-jpa-repository-implementation-to-load-data-by-class-type) rozwiązało mój problem. Chodziło o opisanie abstrakcyjnego repozytorium jako '@ NoRepositoryBean'. Ten [post] (http://stackoverflow.com/a/11012490/1199132) rozwiązuje to, o co prosiłem, typ o ograniczonej adnotacji nie jest możliwy. –