2016-04-21 8 views
0

Ich habe dao Erbe in Hibernate, hier ist der Code:Hibernate Vererbung hql Typ

public class BaseDaoImpl<T> implements BaseDao<T> { 
    ... 
    protected T findSingle(String hql,Object... params){ 
     List<T> list = find(hql,params); 
     if(list == null || list.isEmpty()){ 
      return null; 
     } 
     if(list.size() > 1){ 
      logger.debug("HQL: {} does not return single element.",hql); 
     } 
     logger.info("find single: "+list.get(0)); 
     return list.get(0); 
    } 
} 

UserDao:

public interface UserDao<T extends User> extends BaseDao<T> { 
    ... 
    public T getUserByUsername(String username); 
} 

ich einen Domain-Klasse User und zwei Unterklassen von Benutzer haben: Kunden und Verkäufe. Ich habe zwei Dao-Klassen für Kunden und Vertrieb entsprechend.

UserDao:

public class UserDaoImpl<T extends User> extends BaseDaoImpl<T> implements UserDao<T>,BaseDao<T> { 
    public T getUserByUsername(String username) { 
    return findSingle("from User user where user.username = ?",username); 
    } 
} 

CustomerDao:

public class CustomerDaoImpl extends UserDaoImpl<Customer> implements CustomerDao { 
    private static Logger logger = LoggerFactory.getLogger(CustomerDaoImpl.class); 
    public Double getDeposit(Integer id) { 
     Customer customer = get(Customer.class,id); 
     if(customer != null){ 
      return customer.getDeposit(); 
     } 
     return 0D; 
    } 
} 

SalesDao:

public class SalesRepDaoImpl extends UserDaoImpl<SalesRep> implements SalesRepDao{ 

} 

Mein Problem ist, dass wenn ich customerDap Methode getUserByUsername() aufzurufen (die von vererbt wird BaseDaoImpl) mit dem Nutzernamen "sales" (der Benutzer mit dem Benutzernamen ist eine Instanz von SalesRep, keine Cust omer), es wirft java.lang.ClassCastException aus, es klagt, dass SalesRep nicht an den Kunden übergeben werden kann. Da ich customerDao zum Abfragen der Datenbank verwende und den generischen Typ verwendet, um sicherzustellen, dass das in CustomerDao verwendete T ein Kunde sein soll, wie würde die Methode findSingle() in BaseDaoImpl in diesem Fall eine Instanz von SalesRep zurückgeben, denke ich Es gibt null zurück, da kein Kunde den Benutzernamen hat.

Antwort

0

Zunächst -> Ich nehme an, Sie verwenden eine Hibernate-Vererbungsstrategie.

Die Abfrage "von Benutzer" lässt Hibernate nicht magisch wissen, dass Ihre einzige Suche nach Kunden. Sie müssen die Abfrage oder Ihren gesamten Mechaniker ändern.

Beispiel Lösung

public class UserDaoImpl<T extends User> extends BaseDaoImpl<T> implements UserDao<T>,BaseDao<T> { 

    protected Class<T> entityClass; 

    public UserDaoImpl(Class<T> entityClass) { 
     this.entityClass = entityClass; 
    } 
    public T getUserByUsername(String username) { 
     return findSingle("from " + getEntityName() + " entity where entity.username = ?",username); 
    } 

    protected String getEntityName() { 
     return entityClass.getSimpleName(); 
    } 
} 

Wenn UserDaoImpl nicht allein verwendet wird, können Sie beispielsweise verwenden können TypeTools den generischen Typ zur Laufzeit zu erben.